<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://blogs.technet.com/utility/FeedStylesheets/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/"><channel><title>Supporto Tecnico Enterprise : Performance</title><link>http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx</link><description>Tags: Performance</description><dc:language>en-US</dc:language><generator>CommunityServer 2.1 SP1 (Build: 61025.2)</generator><item><title>Memoria Paged e NonPaged Pool – Come risolvere un memory leak</title><link>http://blogs.technet.com/itasupport/archive/2009/05/18/memoria-paged-e-nonpaged-pool-come-risolvere-un-memory-leak.aspx</link><pubDate>Mon, 18 May 2009 02:00:00 GMT</pubDate><guid isPermaLink="false">d5e57398-b9ef-4490-9955-07cbb4e4a80d:3239803</guid><dc:creator>itentblg</dc:creator><slash:comments>4</slash:comments><comments>http://blogs.technet.com/itasupport/comments/3239803.aspx</comments><wfw:commentRss>http://blogs.technet.com/itasupport/commentrss.aspx?PostID=3239803</wfw:commentRss><description>&lt;P&gt;In questo post vedremo come risolvere un leak di memoria e identificare il driver responsabile. &lt;BR&gt;Vi consiglio di leggere il post &lt;STRONG&gt;&lt;A href="http://blogs.technet.com/itasupport/archive/2009/05/11/memoria-paged-e-nonpaged-pool-come-identificare-un-memory-leak.aspx" target=_blank mce_href="http://blogs.technet.com/itasupport/archive/2009/05/11/memoria-paged-e-nonpaged-pool-come-identificare-un-memory-leak.aspx"&gt;Memoria Paged e NonPaged Pool – Come identificare un memory leak&lt;/A&gt;&lt;/STRONG&gt; per verificare che effettivamente siamo in presenza di un leak di memoria.&lt;/P&gt;
&lt;H3&gt;Utilizzare il PoolMon&lt;/H3&gt;
&lt;P&gt;L’allocazione di una quantità di byte in una delle memorie Pool utilizza un &lt;STRONG&gt;sistema di tagging&lt;/STRONG&gt;. Un TAG è un identificativo di quattro byte associato ad ogni porzione di memoria Pool allocata.&lt;/P&gt;
&lt;P&gt;Il TAG viene specificato da un driver, durante l’allocazione della memoria, attraverso la routine &lt;A href="http://msdn.microsoft.com/en-us/library/ms796989.aspx" mce_href="http://msdn.microsoft.com/en-us/library/ms796989.aspx"&gt;ExAllocatePoolWithTag&lt;/A&gt;. I seguenti tre parametri, devono essere specificati durante la chiamata a questa routine:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;&lt;STRONG&gt;PoolType&lt;/STRONG&gt;: Il tipo di memoria Pool da allocare (Paged o NonPaged) &lt;/LI&gt;
&lt;LI&gt;&lt;STRONG&gt;NumberofBytes&lt;/STRONG&gt;: Il numero di byte da allocare con la richiesta &lt;/LI&gt;
&lt;LI&gt;&lt;STRONG&gt;TAG&lt;/STRONG&gt;: il Pool TAG, rappresentato attraverso quattro caratteri ASCII &lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;L’obiettivo dei Pool TAG è quello di fornire un meccanismo, che attraverso degli identificatore potenzialmente univoci, consenta di stabilire quali driver stanno allocando la memoria. Inoltre, durante la fase di sviluppo di un driver, i TAG sono utili per poter differenziare le diverse tipologie di allocazione, rendendo più selettiva un’eventuale investigazione attraverso il tool &lt;A href="http://support.microsoft.com/kb/244617" mce_href="http://support.microsoft.com/kb/244617"&gt;&lt;STRONG&gt;Driver Verifier&lt;/STRONG&gt;&lt;/A&gt;.&lt;/P&gt;
&lt;H3&gt;Identificare il TAG e byte allocati&lt;/H3&gt;
&lt;P&gt;Per poter verificare quanti byte sono allocati da un determinato TAG occorrerà utilizzare il tool &lt;B&gt;poolmon.exe&lt;/B&gt;, che è possibile recuperare dalla cartella \Support\Tools del CD d’installazione del Sistema Operativo.&lt;/P&gt;
&lt;P&gt;Questo tool consente di ottenere un report di tutti i TAG della Paged e Non Paged Pool con i relativi byte allocati. &lt;BR&gt;In Windows Server 2003 il Pool tagging è già abilitato, mentre in Windows Server 2000 e Windows XP è necessario abilitarlo attraverso il tool Gflags.exe presente sempre nella cartella \Support\Tools del supporto di installazione, o modificando le opportune chiavi di registro.&lt;/P&gt;
&lt;P&gt;Per maggiori informazioni sull'utilizzo di questo tool potete consultare l’articolo &lt;A href="http://support.microsoft.com/kb/177415" target=_blank mce_href="http://support.microsoft.com/kb/177415"&gt;How to use Memory Pool Monitor (Poolmon.exe) to troubleshoot kernel mode memory leaks&lt;/A&gt;&lt;/P&gt;
&lt;P&gt;La seguente immagine illustra un esempio di output relativo al poolmon:&lt;/P&gt;
&lt;P align=center&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/image008_2.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/image008_2.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=image008 border=0 alt=image008 src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/image008_thumb.jpg" width=521 height=392 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/image008_thumb.jpg"&gt;&lt;/A&gt; &lt;/P&gt;
&lt;P align=center&gt;FIG 1 - Output del tool Poolmon.exe&lt;/P&gt;
&lt;P&gt;I campi fondamentali per la nostra analisi sono evidenziati in rosso:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;&lt;STRONG&gt;Tag&lt;/STRONG&gt;&lt;EM&gt;: Rappresenta il TAG che identifica l'allocazione.&lt;/EM&gt; &lt;/LI&gt;
&lt;LI&gt;&lt;STRONG&gt;Type&lt;/STRONG&gt;&lt;EM&gt;: Specifica se la memoria è stata allocata in Paged (Paged) o Nonpaged (Nonp) pool.&lt;/EM&gt; &lt;/LI&gt;
&lt;LI&gt;&lt;STRONG&gt;Bytes&lt;/STRONG&gt;&lt;EM&gt;: Quantità di memoria allocata, in bytes, per il corrispondente TAG&lt;/EM&gt; &lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;Possiamo, dunque, utilizzare i seguenti passi per raccogliere l'output del poolmon in una finestra temporale di nostro interesse:&lt;/P&gt;
&lt;OL&gt;
&lt;LI&gt;Copiare il file "&lt;B&gt;PoolMon.exe&lt;/B&gt;" in "C:\PoolMon", inserendo nella stessa cartella il tool &lt;B&gt;sleep.exe&lt;/B&gt; &lt;/LI&gt;
&lt;LI&gt;Aprire una &lt;B&gt;console dei comandi &lt;/B&gt;da "Start" --&amp;gt; "All programs" --&amp;gt; "Accessories" --&amp;gt; "Command Prompt" &lt;/LI&gt;
&lt;LI&gt;Spostare il prompt in &lt;B&gt;C:\PoolMon&lt;/B&gt; &lt;/LI&gt;
&lt;LI&gt;Per avere una lettura dei dati ogni 15 minuti (per 2 giorni circa), digitare il seguente comando: &lt;BR&gt;&lt;FONT face="Courier New"&gt;&lt;STRONG&gt;for /l %i in (1,1,200) do ( poolmon -n log-%i.txt &amp;amp;&amp;amp; sleep 900000 )&lt;/STRONG&gt;&lt;/FONT&gt;&lt;/LI&gt;
&lt;LI&gt;Nella cartella "&lt;B&gt;C:\PoolMon&lt;/B&gt;" verranno creati i vari file di log. &lt;/LI&gt;&lt;/OL&gt;
&lt;P&gt;Il tool &lt;B&gt;sleep.exe&lt;/B&gt; utilizzato è fornito in allegato al presente post.&lt;/P&gt;
&lt;H3&gt;Determinare la frequenza di campionamento&lt;/H3&gt;
&lt;P&gt;Sleep.exe richiede un parametro che indica il &lt;STRONG&gt;periodo d'attesa in millisecondi&lt;/STRONG&gt; tra due esecuzioni del ciclo for. &lt;BR&gt;Nell’esempio di script riportato sopra, abbiamo il parametro 900’000 che è ottenuto moltiplicando: 15 minuti * 60 secondi * 1000 millisecondi per ottenere una pausa tra una lettura e l’altra di &lt;STRONG&gt;15 minuti&lt;/STRONG&gt;.&lt;/P&gt;
&lt;P&gt;Considerando i 200 cicli impostati ogni 15 minuti, abbiamo un &lt;STRONG&gt;campionamento di circa 2 giorni&lt;/STRONG&gt; calcolato da: 15 minuti/campione * 200 campioni = 3000 minuti totali / 60 = 50 ore totali / 24 = 2,08 giorni.&lt;/P&gt;
&lt;P&gt;Possiamo modificare il numero di cicli e la frequenza di campionamento in base alla rapidità del leak che abbiamo identificato.&lt;/P&gt;
&lt;P&gt;Al termine del periodo di monitoring, avremo dunque &lt;STRONG&gt;200 file di testo&lt;/STRONG&gt;, che iniziano con log1.txt fino a&amp;nbsp; log200.txt nel nostro esempio.&lt;/P&gt;
&lt;P&gt;Copiando questi dati in un foglio Excel ed ordinandoli in base al tipo (Nonp o Paged) e in ordine decrescente rispetto ai byte allocati, saremo in grado di determinare la variazione di allocazione dei TAG in funzione del tempo, identificando quali, in particolare, stanno occupando di più.&lt;/P&gt;
&lt;P&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image006_2.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image006_2.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=clip_image006 border=0 alt=clip_image006 src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image006_thumb.jpg" width=534 height=246 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image006_thumb.jpg"&gt;&lt;/A&gt;&lt;/P&gt;
&lt;P align=center&gt;FIG 2 - Schermata di Excel per l'ordinamento dei TAG.&lt;/P&gt;
&lt;H3&gt;Analizzare i log&lt;/H3&gt;
&lt;P&gt;Avremo risultati di questo tipo:&lt;/P&gt;
&lt;H4&gt;NonPaged Pool&lt;/H4&gt;
&lt;TABLE border=0 cellSpacing=0 cellPadding=2 width=401&gt;
&lt;TBODY&gt;
&lt;TR&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;NonPaged - Log 1&lt;/P&gt;&lt;/TD&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;NonPaged - Log 10&lt;/P&gt;&lt;/TD&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;NonPaged - Log 20&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002_2.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002_2.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002 border=0 alt=clip_image002 src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002_thumb.jpg" width=249 height=250 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B5%5D.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B5%5D.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002[5] border=0 alt=clip_image002[5] src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B5%5D_thumb.jpg" width=255 height=249 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B5%5D_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B7%5D.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B7%5D.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002[7] border=0 alt=clip_image002[7] src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B7%5D_thumb.jpg" width=248 height=251 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B7%5D_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;H4&gt;Paged Pool&lt;/H4&gt;
&lt;TABLE border=0 cellSpacing=0 cellPadding=2 width=401&gt;
&lt;TBODY&gt;
&lt;TR&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;Paged - Log 1&lt;/P&gt;&lt;/TD&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;Paged - Log 10&lt;/P&gt;&lt;/TD&gt;
&lt;TD width=133 align=middle&gt;
&lt;P&gt;Paged - Log 20&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B10%5D.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B10%5D.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002[10] border=0 alt=clip_image002[10] src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B10%5D_thumb.jpg" width=245 height=188 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B10%5D_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B12%5D.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B12%5D.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002[12] border=0 alt=clip_image002[12] src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B12%5D_thumb.jpg" width=251 height=190 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B12%5D_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;
&lt;TD vAlign=top width=133&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B14%5D.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B14%5D.jpg"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=clip_image002[14] border=0 alt=clip_image002[14] src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B14%5D_thumb.jpg" width=241 height=192 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image002%5B14%5D_thumb.jpg"&gt;&lt;/A&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;TABLE cellSpacing=0 cellPadding=0&gt;
&lt;TBODY&gt;
&lt;TR&gt;
&lt;TD width=12&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;
&lt;TD width=17&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;
&lt;TD width=15&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;&lt;/TD&gt;
&lt;TD&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;
&lt;TD&gt;&lt;/TD&gt;
&lt;TD width=274&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;P&gt;Come possiamo notare è evidente un notevole incremento del TAG &lt;B&gt;Pipo&lt;/B&gt; per la Nonpaged pool. &lt;BR&gt;Analizzando anche i restanti log abbiamo infatti il seguente andamento:&lt;/P&gt;
&lt;P&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image020_2.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image020_2.jpg"&gt;&lt;IMG style="BORDER-BOTTOM: 0px; BORDER-LEFT: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-TOP: 0px; MARGIN-RIGHT: auto; BORDER-RIGHT: 0px" title=clip_image020 border=0 alt=clip_image020 src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image020_thumb.jpg" width=521 height=267 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image020_thumb.jpg"&gt;&lt;/A&gt;&lt;/P&gt;
&lt;P align=center&gt;FIG 3 - Andamento della Nonpaged pool allocata dal TAG Pipo.&lt;/P&gt;
&lt;P&gt;Come è possibile notare è presente un leak sul TAG Pipo. Ora che abbiamo identificato il TAG che sta alla base del memory leak, come possiamo identificarne il driver corrispondente?&lt;/P&gt;
&lt;H3&gt;Identificare il driver&lt;/H3&gt;
&lt;P&gt;L’elenco di tutti i TAG utilizzati per le allocazioni nella memoria Pool sono disponibili nel file &lt;I&gt;&lt;STRONG&gt;Pooltag.txt&lt;/STRONG&gt; &lt;BR&gt;&lt;/I&gt;Questo file contiene l’identificativo di tutti i componenti Kernel-mode e driver rilasciati con i Sistemi Operativi Windows.&lt;/P&gt;
&lt;P&gt;E’ disponibile per il download e l’installazione all’interno dei &lt;A href="http://www.microsoft.com/whdc/devtools/debugging/default.mspx" target=_blank mce_href="http://www.microsoft.com/whdc/devtools/debugging/default.mspx"&gt;&lt;STRONG&gt;Debugging Tools for Windows&lt;/STRONG&gt;&lt;/A&gt;:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;&lt;A href="http://www.microsoft.com/whdc/devtools/debugging/installx86.mspx" target=_blank mce_href="http://www.microsoft.com/whdc/devtools/debugging/installx86.mspx"&gt;Debugging Tools for Windows 32-bit Version&lt;/A&gt;&lt;/LI&gt;
&lt;LI&gt;&lt;A href="http://www.microsoft.com/whdc/devtools/debugging/install64bit.mspx" target=_blank&gt;Debugging Tools for Windows 64-bit Version&lt;/A&gt;&lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;Un esempio del contenuto del file Pooltag.txt è riportato di seguito:&lt;/P&gt;
&lt;P mce_keep="true"&gt;&amp;nbsp;&lt;/P&gt;
&lt;BLOCKQUOTE&gt;
&lt;P align=left&gt;&lt;FONT face="Courier New"&gt;8042 - i8042prt.sys - PS/2 kb and mouse &lt;BR&gt;AdSv - vmsrvc.sys&amp;nbsp;&amp;nbsp; - Virtual Machines Additions Service &lt;BR&gt;ARPC - atmarpc.sys&amp;nbsp; - ATM ARP Client &lt;BR&gt;ATMU - atmuni.sys&amp;nbsp;&amp;nbsp; - ATM UNI Call Manager &lt;BR&gt;ACPI - acpi.sys&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; - ACPI &lt;BR&gt;Afd? - afd.sys&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; - AFD objects &lt;BR&gt;AfdA - afd.sys&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; - Afd EA buffer&lt;/FONT&gt;&lt;/P&gt;&lt;/BLOCKQUOTE&gt;
&lt;P&gt;Se il TAG che causa il leak di memoria non è contenuti nell’elenco, vi consiglio di effettuare una ricerca nella nostra &lt;STRONG&gt;Knowledge Base&lt;/STRONG&gt;, in modo da verificare la presenza di eventuali problemi conosciuti e installare la relativa hotfix.&lt;/P&gt;
&lt;P&gt;Se invece, come nel caso del nostro esempio, il TAG non è Microsoft non sarà presente nell'elenco. &lt;BR&gt;In questo caso possiamo utilizzare il comando &lt;B&gt;findstr&lt;/B&gt;, valido per ciascuna versione di Windows, che potrà essere eseguito come indicato di seguito:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;Aprire una &lt;B&gt;console dei comandi &lt;/B&gt;da "Start" --&amp;gt; "All programs" --&amp;gt; "Accessories" --&amp;gt; "Command Prompt"&lt;/LI&gt;
&lt;LI&gt;Spostarsi nella cartella&lt;B&gt; %systemroot%\system32\drivers&lt;/B&gt;&lt;/LI&gt;
&lt;LI&gt;Digitare il comando &lt;BR&gt;&lt;FONT face="Courier New"&gt;&lt;STRONG&gt;findstr /m /l &amp;lt;tag&amp;gt; *.sys&lt;/STRONG&gt;&lt;/FONT&gt;&lt;/LI&gt;
&lt;LI&gt;Verificare l'output restituito dal comando&lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;In questo screenshot è evidenziata la ricerca per il TAG Pipo:&lt;/P&gt;
&lt;P&gt;&lt;A href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image022_2.jpg" mce_href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image022_2.jpg"&gt;&lt;IMG style="BORDER-BOTTOM: 0px; BORDER-LEFT: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-TOP: 0px; MARGIN-RIGHT: auto; BORDER-RIGHT: 0px" title=clip_image022 border=0 alt=clip_image022 src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image022_thumb.jpg" width=443 height=79 mce_src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedeNonPagedPoolComerisolvereun_EE09/clip_image022_thumb.jpg"&gt;&lt;/A&gt;&lt;/P&gt;
&lt;P&gt;Come possiamo notare è restituito il driver corrispondente al TAG specificato “Pipo”.&lt;/P&gt;
&lt;P&gt;In questo caso occorrerà verificare un'eventuale versione aggiornata del driver Pippo.sys, o eventualmente contattare il fornitore del software segnalando la problematica.&lt;/P&gt;
&lt;H3&gt;Conclusione&lt;/H3&gt;
&lt;P&gt;Alla luce di quanto visto fino ad ora, se stiamo evidenziando un leak di memoria sul nostro sistema potremo identificarne la potenziale causa attraverso i seguenti passi:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;Monitorare i byte allocati da ciascun TAG durante una finestra temporale adeguata al nostro leak, attraverso il tool &lt;STRONG&gt;poolmon.exe&lt;/STRONG&gt;&lt;/LI&gt;
&lt;LI&gt;Evidenziare eventuali &lt;STRONG&gt;allocazioni&lt;/STRONG&gt; che variano proporzionalmente al tempo in &lt;STRONG&gt;costante crescita&lt;/STRONG&gt;&lt;/LI&gt;
&lt;LI&gt;Stabilire su che &lt;STRONG&gt;tipo di pool&lt;/STRONG&gt; è presente il leak (Paged o Nonpaged)&lt;/LI&gt;
&lt;LI&gt;Stabilire il &lt;STRONG&gt;driver associato &lt;/STRONG&gt;al TAG che sta causando il leak&lt;/LI&gt;
&lt;LI&gt;Ricercare eventuali &lt;STRONG&gt;problemi noti&lt;/STRONG&gt;, o analizzare la problematica con il &lt;STRONG&gt;fornitore &lt;/STRONG&gt;del driver&lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;&lt;A href="http://blogs.technet.com/itasupport/pages/mattia-tocco.aspx" mce_href="http://blogs.technet.com/itasupport/pages/mattia-tocco.aspx"&gt;Mattia Tocco&lt;/A&gt; &lt;BR&gt;Senior Support Engineer &lt;BR&gt;Microsoft Enterprise Platform Support&lt;/P&gt;&lt;img src="http://blogs.technet.com/aggbug.aspx?PostID=3239803" width="1" height="1"&gt;</description><enclosure url="http://blogs.technet.com/itasupport/attachment/3239803.ashx" length="16896" type="application/octet-stream" /><category domain="http://blogs.technet.com/itasupport/archive/tags/Windows+Team/default.aspx">Windows Team</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Mattia+Tocco/default.aspx">Mattia Tocco</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx">Performance</category><category domain="http://blogs.technet.com/itasupport/archive/tags/NT+Kernel+Architecture/default.aspx">NT Kernel Architecture</category></item><item><title>Memoria Paged e NonPaged Pool – Come identificare un memory leak</title><link>http://blogs.technet.com/itasupport/archive/2009/05/11/memoria-paged-e-nonpaged-pool-come-identificare-un-memory-leak.aspx</link><pubDate>Mon, 11 May 2009 02:00:00 GMT</pubDate><guid isPermaLink="false">d5e57398-b9ef-4490-9955-07cbb4e4a80d:3236896</guid><dc:creator>itentblg</dc:creator><slash:comments>0</slash:comments><comments>http://blogs.technet.com/itasupport/comments/3236896.aspx</comments><wfw:commentRss>http://blogs.technet.com/itasupport/commentrss.aspx?PostID=3236896</wfw:commentRss><description>&lt;p&gt;In questo post vedremo come identificare le problematiche legate ad un esaurimento di due specifiche &lt;a href="http://blogs.technet.com/itasupport/archive/2008/12/15/kernel-memory-overview.aspx" target="_blank"&gt;risorse Kernel&lt;/a&gt;: Paged Pool e NonPaged Pool.     &lt;br /&gt;Vi consiglio di leggere il post di &lt;a href="http://blogs.technet.com/itasupport/pages/fabio-lavatelli.aspx" target="_blank"&gt;Fabio Lavatelli&lt;/a&gt; per una visione esaustiva della memoria: &lt;b&gt;&lt;a href="http://blogs.technet.com/itasupport/archive/2008/12/15/kernel-memory-overview.aspx" target="_blank"&gt;Kernel Memory Overview&lt;/a&gt;.&lt;/b&gt;&lt;/p&gt;  &lt;h3&gt;Memoria Paged e NonPaged Pool&lt;/h3&gt;  &lt;p&gt;All’avvio del computer, il &lt;strong&gt;Memory Manager&lt;/strong&gt; crea dinamicamente due memorie pool di dimensione fissa per tutto il periodo in cui il Sistema Operativo rimane attivo: queste due pool sono conosciute come &lt;b&gt;Paged Pool&lt;/b&gt; e &lt;b&gt;NonPaged Pool&lt;/b&gt;.&lt;/p&gt;  &lt;p&gt;Le dimensioni di queste pool, determinate all'avvio, dipendono da una &lt;strong&gt;serie di fattori&lt;/strong&gt;: alcuni di questi possono essere modificati attraverso specifiche chiavi di registry, mentre altri dipendono dall’hardware specifico del computer, come la quantità di &lt;strong&gt;memoria fisica&lt;/strong&gt;.&lt;/p&gt;  &lt;div&gt;Entrambe le pool possono raggiungere un &lt;strong&gt;valore massimo teorico&lt;/strong&gt; dipendente dall’architettura del sistema operativo:&lt;/div&gt;  &lt;table border="0" cellspacing="0" cellpadding="0" width="577" align="center"&gt;&lt;tbody&gt;     &lt;tr&gt;       &lt;td width="96"&gt;         &lt;p align="center"&gt;&lt;b&gt;Tipo Pool&lt;/b&gt;&lt;/p&gt;       &lt;/td&gt;        &lt;td width="284"&gt;         &lt;p align="center"&gt;&lt;b&gt;Sistemi a 32-Bit (x86)&lt;/b&gt;&lt;/p&gt;       &lt;/td&gt;        &lt;td width="195"&gt;         &lt;p align="center"&gt;&lt;b&gt;Sistemi a 64-Bit (x64)&lt;/b&gt;&lt;/p&gt;       &lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td width="97"&gt;         &lt;p align="center"&gt;NonPaged&lt;/p&gt;       &lt;/td&gt;        &lt;td width="284"&gt;         &lt;p align="left"&gt;256 MB (Windows 2000, XP e 2003)            &lt;br /&gt;128 MB (Con opzione /3GB abilitata al boot)&lt;/p&gt;       &lt;/td&gt;        &lt;td width="195"&gt;         &lt;p align="center"&gt;128 GB&lt;/p&gt;       &lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td width="98"&gt;         &lt;p align="center"&gt;Paged&lt;/p&gt;       &lt;/td&gt;        &lt;td width="284"&gt;         &lt;p align="left"&gt;491,875 MB (Windows 2000 e Windows XP) 650,000 MB (Windows Server 2003)&lt;/p&gt;       &lt;/td&gt;        &lt;td width="195"&gt;         &lt;p align="center"&gt;128GB&lt;/p&gt;       &lt;/td&gt;     &lt;/tr&gt;   &lt;/tbody&gt;&lt;/table&gt;  &lt;p&gt;Nel caso sia abilitata l’&lt;strong&gt;opzione /3GB&lt;/strong&gt; nel file boot.ini la dimensione massima teorica della &lt;strong&gt;NonPaged Pool è dimezzata&lt;/strong&gt;. Questo è dovuto alla gestione nel Sistema Operativo della &lt;a href="http://blogs.technet.com/itasupport/archive/2008/12/15/kernel-memory-overview.aspx" target="_blank"&gt;memoria virtuale&lt;/a&gt;: sono dedicati 3 Gigabyte alla parte applicativa e solo 1 Gigabyte alla parte kernel.&lt;/p&gt;  &lt;p&gt;I Sistemi Operativi a 64 bit (x64) presentano limiti di memoria virtuale superiori di diversi ordini di grandezza rispetto a sistemi a 32 bit (x86), perciò un'eventuale saturazione della memoria disponibile avverrebbe in tempi più elevati.&lt;/p&gt;  &lt;p&gt;La sostanziale differenza tra le due tipologie di pool, come evidenzia il nome, è che la Paged Pool può essere &lt;strong&gt;paginata su disco&lt;/strong&gt;, mentre la NonPaged Pool è sempre &lt;strong&gt;residente in memoria&lt;/strong&gt;.&lt;/p&gt;  &lt;p&gt;I &lt;strong&gt;driver&lt;/strong&gt; utilizzano la NonPaged Pool per tutte quelle operazioni eseguite ad un &lt;strong&gt;Interrupt Request Level&lt;/strong&gt; (IRQL) troppo elevato per ammettere paginazione.     &lt;br /&gt;L'IRQL definisce la priorità a cui il processore sta operando, maggiori informazioni sono disponibili nel seguente articolo: &lt;a href="http://www.microsoft.com/whdc/driver/kernel/IRQL.mspx" target="_blank"&gt;Scheduling, Thread Context, and IRQL&lt;/a&gt;&lt;/p&gt;  &lt;h3&gt;Eventi SRV 2019 e 2020&lt;/h3&gt;  &lt;p&gt;Nel caso in cui un driver abbia un funzionamento anomalo, potrebbe allocare memoria Pool senza mai rilasciarla arrivando alla saturazione di tutto lo spazio a disposizione: questo fenomeno è chiamato &lt;strong&gt;memory leak&lt;/strong&gt;.&lt;/p&gt;  &lt;p&gt;In questo tipo di scenario, generalmente troviamo nel Log degli Eventi di Sistema i seguenti 2 eventi specifici.    &lt;br /&gt;L'&lt;strong&gt;evento 2019&lt;/strong&gt; si riferisce all'esaurimento della &lt;strong&gt;NonPaged pool&lt;/strong&gt;:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;font face="Courier New"&gt;Type: Error        &lt;br /&gt;Date: &amp;lt;date&amp;gt;         &lt;br /&gt;Time: &amp;lt;time&amp;gt;         &lt;br /&gt;Event ID: &lt;strong&gt;&lt;font color="#ff0000"&gt;2019&lt;/font&gt;&lt;/strong&gt;         &lt;br /&gt;Source: Srv         &lt;br /&gt;User: N/A         &lt;br /&gt;Computer: &amp;lt;ComputerName&amp;gt;         &lt;br /&gt;Details: The server was unable to allocate from the &lt;font color="#ff0000"&gt;&lt;strong&gt;system&lt;/strong&gt; &lt;strong&gt;NonPaged pool&lt;/strong&gt;&lt;/font&gt; because the pool was empty. &lt;/font&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;Mentre l'&lt;strong&gt;evento 2020&lt;/strong&gt; riguarda l'esaurimento della &lt;strong&gt;Paged Pool&lt;/strong&gt;:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;font face="Courier New"&gt;Type: Error        &lt;br /&gt;Date: &amp;lt;date&amp;gt;         &lt;br /&gt;Time: &amp;lt;time&amp;gt;         &lt;br /&gt;Event ID: &lt;strong&gt;&lt;font color="#ff0000"&gt;2020&lt;/font&gt;&lt;/strong&gt;         &lt;br /&gt;Source: Srv         &lt;br /&gt;User: N/A         &lt;br /&gt;Computer: &amp;lt;ComputerName&amp;gt;         &lt;br /&gt;Details: The server was unable to allocate from the &lt;strong&gt;&lt;font color="#ff0000"&gt;system Paged pool&lt;/font&gt;&lt;/strong&gt; because the pool was empty&lt;/font&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;In alcuni scenari specifici di memory leak, gli eventi 2019 e 2020 non sono presenti nel Registro Eventi, ma sono loggati molti errori &lt;strong&gt;333 - &lt;/strong&gt;&lt;strong&gt;Application Popup&lt;/strong&gt;:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;font face="Courier New"&gt;Type: Error        &lt;br /&gt;Date: &amp;lt;date&amp;gt;         &lt;br /&gt;Time: &amp;lt;time&amp;gt;         &lt;br /&gt;Event ID: &lt;strong&gt;&lt;font color="#ff0000"&gt;333&lt;/font&gt;&lt;/strong&gt;         &lt;br /&gt;Source: Application Popup         &lt;br /&gt;User: N/A         &lt;br /&gt;Computer: &amp;lt;ComputerName&amp;gt;         &lt;br /&gt;Details: An &lt;strong&gt;&lt;font color="#ff0000"&gt;I/O operation initiated by the Registry failed unrecoverably&lt;/font&gt;&lt;/strong&gt;. The Registry could not read in, or write out, or flush, one of the files that contain the system's image of the Registry&lt;/font&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;Maggiori informazioni riguardo questo scenario sono spiegati nel post &lt;a href="http://blogs.technet.com/itasupport/archive/2008/11/17/analizzare-l-evento-application-popup-333.aspx" target="_blank"&gt;Analizzare l’evento “Application Popup 333”&lt;/a&gt;&lt;/p&gt;  &lt;h3&gt;Analizzare un Memory Leak&lt;/h3&gt;  &lt;p&gt;Il &lt;strong&gt;comportamento&lt;/strong&gt; del Sistema Operativo in presenza di un memory leak è imprevedibile: si possono registrare &lt;strong&gt;hang&lt;/strong&gt;, &lt;strong&gt;crash&lt;/strong&gt; di applicazioni o &lt;strong&gt;BlueScreen&lt;/strong&gt; (bugcheck 0x0000041 MUST_SUCCEED_POOL_EMPTY).&lt;/p&gt;  &lt;div&gt;Il &lt;strong&gt;performance monitor&lt;/strong&gt; permette di verificare lo stato della Memoria Pool con i seguenti &lt;strong&gt;counter&lt;/strong&gt;:&lt;/div&gt;  &lt;div align="center"&gt;   &lt;table border="0" cellspacing="0" cellpadding="0" width="630" align="center"&gt;&lt;tbody&gt;       &lt;tr&gt;         &lt;td valign="bottom" width="209"&gt;           &lt;p align="center"&gt;&lt;b&gt;Counter&lt;/b&gt;&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="bottom" width="419"&gt;           &lt;p align="center"&gt;&lt;b&gt;Description&lt;/b&gt;&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="bottom" width="209"&gt;           &lt;p align="left"&gt;Memory\Paged Pool Bytes&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="bottom" width="419"&gt;           &lt;p align="left"&gt;Indica il numero di byte allocati nella Paged Pool di sistema&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="209"&gt;           &lt;p align="left"&gt;Memory\Non Paged Pool Bytes&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="419"&gt;           &lt;p align="left"&gt;Indica il numero di byte allocati nella NonPaged Pool di sistema&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;     &lt;/tbody&gt;&lt;/table&gt; &lt;/div&gt;  &lt;p&gt;Il grafico seguente illustra un andamento tipo di un &lt;strong&gt;memory leak&lt;/strong&gt; relativo alla NonPaged Pool:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedPooleNonPagedPoolComeidentif_84DF/clip_image002_2.gif"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="clip_image002" border="0" alt="clip_image002" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedPooleNonPagedPoolComeidentif_84DF/clip_image002_thumb.gif" width="563" height="394" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p align="center"&gt;FIG 1 - Andamento tipico di un memory leak relativo alla NonPaged Pool.&lt;/p&gt;  &lt;p&gt;La NonPaged Pool allocata, indicata in MegaByte, è al di sotto del valore massimo teorico di 256 MB, ma presenta un &lt;strong&gt;andamento crescente&lt;/strong&gt; che indica un tipico caso in cui un driver non stia rilasciando la memoria allocata.&lt;/p&gt;  &lt;p&gt;La &lt;strong&gt;crescita&lt;/strong&gt; può essere variabile in funzione del tempo, e per questo la &lt;strong&gt;finestra temporale&lt;/strong&gt; di monitoring dovrà essere modulata proporzionalmente alla rapidità del leak.&lt;/p&gt;  &lt;p&gt;Il grafico seguente illustra un altro andamento tipo di &lt;strong&gt;saturazione di memoria&lt;/strong&gt; relativo alla NonPaged Pool:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedPooleNonPagedPoolComeidentif_84DF/clip_image002%5B5%5D.gif"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="clip_image002[5]" border="0" alt="clip_image002[5]" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/MemoriaPagedPooleNonPagedPoolComeidentif_84DF/clip_image002%5B5%5D_thumb.gif" width="564" height="346" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p align="center"&gt;FIG 2 - Andamento variabile relativo alla NonPaged Pool.&lt;/p&gt;  &lt;p&gt;L’andamento non risulta crescente, ma può indicare ugualmente la presenza di problemi dovuti al raggiungimento del limite massimo di memoria Pool disponibile. In questa situazione non abbiamo un vero e proprio memory leak, ma una saturazione della NonPaged Pool che richiede un &lt;strong&gt;tuning manuale &lt;/strong&gt;di specifiche chiavi di &lt;strong&gt;registry&lt;/strong&gt;.&lt;/p&gt;  &lt;p&gt;I due andamenti riportati valgono per &lt;strong&gt;entrambe le tipologie di memoria Pool&lt;/strong&gt; anche se i limiti più stringenti e che presentano più problemi sono relativi alla memoria NonPaged Pool.&lt;/p&gt;  &lt;p&gt;Nei successivi post vedremo nel dettaglio come approfondire e risolvere:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Problemi di memory leak &lt;/li&gt;    &lt;li&gt;Problemi di saturazione della memoria &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/itasupport/pages/mattia-tocco.aspx"&gt;Mattia Tocco&lt;/a&gt;     &lt;br /&gt;Senior Support Engineer     &lt;br /&gt;Microsoft Enterprise Platform Support&lt;/p&gt;&lt;img src="http://blogs.technet.com/aggbug.aspx?PostID=3236896" width="1" height="1"&gt;</description><category domain="http://blogs.technet.com/itasupport/archive/tags/Mattia+Tocco/default.aspx">Mattia Tocco</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx">Performance</category><category domain="http://blogs.technet.com/itasupport/archive/tags/NT+Kernel+Architecture/default.aspx">NT Kernel Architecture</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Pool+Memory/default.aspx">Pool Memory</category></item><item><title>SQL Server - Facciamo quattro conti con i dischi</title><link>http://blogs.technet.com/itasupport/archive/2009/02/09/sql-server-facciamo-quattro-conti-con-i-dischi.aspx</link><pubDate>Mon, 09 Feb 2009 03:00:00 GMT</pubDate><guid isPermaLink="false">d5e57398-b9ef-4490-9955-07cbb4e4a80d:3199176</guid><dc:creator>itentblg</dc:creator><slash:comments>0</slash:comments><comments>http://blogs.technet.com/itasupport/comments/3199176.aspx</comments><wfw:commentRss>http://blogs.technet.com/itasupport/commentrss.aspx?PostID=3199176</wfw:commentRss><description>&lt;p&gt;Mi capita spesso di incontrare evidenti problemi di performance sui vari volumi utilizzati da SQL Server, sia per un’errata scelta del livello di &lt;a href="http://it.wikipedia.org/wiki/RAID" target="_blank"&gt;RAID&lt;/a&gt; sia per un errato dimensionamento del numero di dischi necessari a soddisfare la quantità di operazioni al secondo richieste dai vari database.&lt;/p&gt;  &lt;p&gt;Le moderne &lt;a href="http://it.wikipedia.org/wiki/Storage_Area_Network" target="_blank"&gt;Storage Area Network&lt;/a&gt; dispongono di sistemi di gestione dei volumi che praticamente in tempo reale possono riallocare su meccaniche completamente differenti,anche come numero, quello che dal sistema operativo viene visto come disco (la lettera dell’unità): inoltre la grande quantità di memoria cache installata garantisce prestazioni teoriche tali da non far sorgere preoccupazioni, tant’è che per volumi dedicati alla “semplice” di repository normalmente si può risparmiare su qualche disco.&amp;#160; &lt;/p&gt;  &lt;p&gt;La tendenza attuale inoltre è quella che porta a vedere la SAN più come una riserva di GigaByte e TeraByte di spazio, piuttosto che come un sistema dal quale si possono estrarre notevoli performance, perché normalmente si chiede “Ho bisogno di&amp;#160; XXX Gb di spazio”&amp;#160; e non “Ho bisogno di&amp;#160; XXX Gb di spazio che sia in grado di garantirmi YYY operazioni di I/O al secondo”.&lt;/p&gt;  &lt;p&gt;E qui si inserisce un aspetto molto importante da considerare: SQL Server ( e anche Exchange ) all’avvio richiede l’apertura dei suoi file di database in modalità WriteThrouh, tramite il flag FILE_FLAG_WRITE_THROUGH e FILE_FLAG_NO_BUFFER della funzione Windows &lt;a href="http://msdn.microsoft.com/en-us/library/aa363858(VS.85).aspx" target="_blank"&gt;CreateFile&lt;/a&gt;, ignorando quindi qualsiasi tipo di cache, da quella del sistema operativo a quella che può essere presente sul disco. Solo alcuni sistemi molto avanzati possono essere configurati per ignorare questi due flag e fare in modo che SQL Server “veda” la cache come “stable media” (praticamente un disco) garantendo così elevate performance, ma la maggior parte delle installazioni oggi presenti non è in grado: e qui iniziano i problemi perché dobbiamo fare i conti, nel vero senso del termine, con le pure caratteristiche fisiche dei dischi che compongono gli array (spesso uno solo) dove risiedono i file di dati di SQL Server.&lt;/p&gt;  &lt;p&gt;Vediamo quindi un generico disco SCSI di ultima generazione cosa può garantirci come numero di operazioni di I/O prima di iniziare ad accodare le richieste e allungare i tempi di risposta: il riferimento dei nostri calcoli è un &lt;a href="http://www.seagate.com/www/en-us/products/servers/cheetah/cheetah_15k.5/" target="_blank"&gt;Seagate Cheetah 15.5K&lt;/a&gt;, disponibile nei tagli 74Gb, 146Gb e 300Gb, i più comuni (purtroppo … come dimensione del singolo) usati oggi all’interno delle SAN.&lt;/p&gt;  &lt;p&gt;Il disco in questione presenta per i tre formati le seguenti caratteristiche:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;latenza media di 2ms (considerata come la metà del tempo necessario per compiere un intera rotazione dei piatti) &lt;/li&gt;    &lt;li&gt;Scrittura Random 4.0ms &lt;/li&gt;    &lt;li&gt;Lettura Random 3.5ms &lt;/li&gt;    &lt;li&gt;Scrittura Sequenziale 0.4ms &lt;/li&gt;    &lt;li&gt;Lettura Sequenziale 0.2ms &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Tenendo presente che un disco inizia a dare evidenti segni di accodamento quando viene usato in modo continuativo oltre l’ 85% delle sue capacità (Cap. 8 di “Microsoft SQL Server 2000 Performance Tuning Technical Reference”), possiamo passare a valutare quanto rende il nostro Cheetah in termini di operazioni al secondo.&lt;/p&gt;  &lt;p&gt;&lt;a name="IMG_13"&gt;&lt;/a&gt;&lt;img title="clip_image001" style="border-top-width: 0px; display: block; border-left-width: 0px; float: none; border-bottom-width: 0px; margin-left: auto; margin-right: auto; border-right-width: 0px" height="207" alt="clip_image001" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/Facciamoquattroconticonidischi_B75E/clip_image001_f6fcb021-7528-4965-a681-12a2fc4b93ee.jpg" width="373" border="0" /&gt;&lt;/p&gt;  &lt;p align="center"&gt;&lt;em&gt;Relazione tra tempi di risposta e percentuale di utilizzo del disco&lt;/em&gt;&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Abbiamo che in modalità sequenziale una lettura richiede una latenza totale di 2.2ms mentre per una scrittura servono 2.4ms, per un totale rispettivamente di 455 e 417 operazioni/sec (= 1000m / latenza ). In modalità random i valori salgono 5.5ms e 6.0ms ottenendo così 182 e 167 operazioni/sec.&lt;/p&gt;  &lt;p&gt;A questi risultati dobbiamo sottrarre l’overhead della catena driver+controller+logica di gestione del disco, in sostanza tutto quello che si trova tra la richiesta di scrittura da parte del sistema operativo e la testina del disco, valutato intorno al 20% per le operazioni random e 10% per quelle sequenziali. I valori calcolati prima diventano così 364 e 333 per l’accesso sequenziale mentre per l’accesso random si scende a 164 e 150: abbiamo così il massimo ammissibile per ogni disco nel caso di uso non continuativo. I valori medi diventano quindi 348 nel caso di accesso sequenziale e 157 per l’accesso random.&lt;/p&gt;  &lt;p&gt;Prendendo ora come riferimento l’85% dell’utilizzo onde evitare evidenti accodamenti, i nostri valori diventano 309 e 283 nel primo caso e 139 e 128 nel secondo, con una media rispettivamente di 296 per l’accesso sequenziale e 133 per l’accesso random.&lt;/p&gt;  &lt;p&gt;Di seguito la tabella riassuntiva dei dati appena trovati:&lt;/p&gt;  &lt;div align="center"&gt;   &lt;table cellspacing="0" cellpadding="2" width="772" align="center" border="1"&gt;&lt;tbody&gt;       &lt;tr&gt;         &lt;td align="center" width="125"&gt;           &lt;h5&gt;Latenza di rotazione              &lt;br /&gt;(1/2 giro) = 2ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="59"&gt;&lt;font size="2"&gt;&lt;/font&gt;&lt;/td&gt;          &lt;td align="center" width="72"&gt;           &lt;h5&gt;Latenza totale&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="121"&gt;Operazioni/Sec&lt;/td&gt;          &lt;td align="center" width="116"&gt;Overhead:20% random, 10% sequenziale&lt;/td&gt;          &lt;td align="center" width="118"&gt;Media per uso non continuativo&lt;/td&gt;          &lt;td align="center" width="86"&gt;85% per evitare code&lt;/td&gt;          &lt;td align="center" width="73"&gt;Media&lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="124"&gt;           &lt;h5&gt;Lettura Sequenziale&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="61"&gt;           &lt;h5&gt;0.2ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" align="center" width="73"&gt;           &lt;h5&gt;2.2ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="122"&gt;455&lt;/td&gt;          &lt;td align="center" width="116"&gt;364&lt;/td&gt;          &lt;td align="center" width="118"&gt;348&lt;/td&gt;          &lt;td align="center" width="86"&gt;309&lt;/td&gt;          &lt;td align="center" width="73"&gt;&lt;strong&gt;296&lt;/strong&gt;&lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="122"&gt;           &lt;h5&gt;Scrittura Sequenziale&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="62"&gt;           &lt;h5&gt;0.4ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" align="center" width="73"&gt;           &lt;h5&gt;2.4ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="123"&gt;417&lt;/td&gt;          &lt;td align="center" width="116"&gt;333&lt;/td&gt;          &lt;td valign="top" width="118"&gt;&amp;#160;&lt;/td&gt;          &lt;td align="center" width="86"&gt;283&lt;/td&gt;          &lt;td valign="top" width="72"&gt;&amp;#160;&lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="121"&gt;           &lt;h5&gt;Lettura Random&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="63"&gt;           &lt;h5&gt;3.5ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" align="center" width="73"&gt;           &lt;h5&gt;5.5ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="123"&gt;182&lt;/td&gt;          &lt;td align="center" width="116"&gt;164&lt;/td&gt;          &lt;td align="center" width="118"&gt;157&lt;/td&gt;          &lt;td align="center" width="85"&gt;139&lt;/td&gt;          &lt;td align="center" width="72"&gt;&lt;strong&gt;133&lt;/strong&gt;&lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="123"&gt;           &lt;h5&gt;Scrittura Random&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="64"&gt;           &lt;h5&gt;4.0ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" align="center" width="73"&gt;           &lt;h5&gt;6.0ms&lt;/h5&gt;         &lt;/td&gt;          &lt;td align="center" width="124"&gt;167&lt;/td&gt;          &lt;td align="center" width="116"&gt;150&lt;/td&gt;          &lt;td valign="top" width="118"&gt;&amp;#160;&lt;/td&gt;          &lt;td align="center" width="86"&gt;128&lt;/td&gt;          &lt;td valign="top" width="73"&gt;&amp;#160;&lt;/td&gt;       &lt;/tr&gt;     &lt;/tbody&gt;&lt;/table&gt; &lt;/div&gt;  &lt;p&gt;Vediamo ora i vari livelli di RAID come si comportano dal punto di vista delle operazioni di I/O richieste ad ogni disco che compone un Array.&lt;/p&gt;  &lt;h3&gt;RAID0&lt;/h3&gt;  &lt;p&gt;Alla base di tutti i livelli abbiamo il RAID0, un semplice striping che non offre caratteristiche di fault tolerance e naturalmente non è raccomandato per fornire storage a SQL Server, anche se rappresenta il massimo livello di performance. Il numero di operazioni gestite da ogni disco componente l’array è dato da:&lt;/p&gt;  &lt;p&gt;I/O per Disco = (Letture + Scritture) / Numero di dischi&lt;/p&gt;  &lt;h4&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/h4&gt;  &lt;h3&gt;RAID1&lt;/h3&gt;  &lt;p&gt;Rappresenta il “classico” mirroring in cui i il meccanismo di “fault tolerance” viene implementato replicando i dati un secondo disco. dal punto di vista del calcolo abbiamo:&lt;/p&gt;  &lt;p&gt;I/O per Disco = [Letture + (2 * Scritture)] / 2&lt;/p&gt;  &lt;p&gt;Si nota quindi come in questo caso le operazioni di scrittura siano più onerose, mentre nel caso delle letture grazie al supporto “Split seeks”, che permette di distribuire equamente il carico sui due dischi, si comporta come un RAID0&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;  &lt;h3&gt;RAID5&lt;/h3&gt;  &lt;p&gt;E’ probabilmente il livello più utilizzato perché fornisce un buon livello “fault tolerance” unitamente ad un elevato rapporto numero di dischi/spazio disponibile, e in determinate condizione anche buone performance. Il RAID5 introduce il concetto di “parità” per potere ricostruire il dato nel caso in cui uno dei dischi componenti un array dovesse rompersi: il calcolo della parità risulta essere anche il “tallone d’Achille” per le performance di questa implementazione. Al momento della creazione di un volume di questo tipo la parte riservata ai dati viene inizializzata a 0 ed il bit di parità resettato: per questo motivo sono necessarie quattro operazioni, la prima per leggere il dato esistente, la seconda lo stato della parità, la terza per riscrivere il nuovo dato&amp;#160; e la quarta per la nuova parità&amp;#160; dopo che il processore del controller ne ha calcolato il valore. Abbiamo quindi:&lt;/p&gt;  &lt;p&gt;I/O per Disco = [Letture + (4 * Scritture)] / Numero di dischi&lt;/p&gt;  &lt;p&gt;dal momento che come abbiamo visto sopra per ogni operazione di scrittura ne occorrono 4&lt;/p&gt;  &lt;h3&gt;RAID10&lt;/h3&gt;  &lt;p&gt;E' l'unica vera alternativa al RAID5 nel momento in cui si vuole il massimo delle performance unitamente al migliore livello di “fault tolerance” ed è in sostanza un mirroring al quale viene aggiunta la funzionalità di stripe.&lt;/p&gt;  &lt;p&gt;Il calcolo presenta la stessa formula del RAID0 ma con il denominatore che diventa uguale al numero di dischi (sempre multiplo di 2) &lt;/p&gt;  &lt;p&gt;I/O per Disco = [Letture + (2 * Scritture)] / Numero di dischi&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Sono previsti anche altri livelli di RAID: 3,4, 6 (un 5 con doppia parità) e 7 ( 3 o 4 con caching), ma il loro impiego è limitato a casi sporadici.&lt;/p&gt;  &lt;h3&gt;LA DOMANDA FATIDICA: &lt;strong&gt;RAID5&lt;/strong&gt; o &lt;strong&gt;RAID10&lt;/strong&gt;?&lt;/h3&gt;  &lt;p&gt;Purtroppo molto spesso le esigenze di spazio dominano nei confronti delle performance ed il RAID5, a parità di dischi fornisce sempre una capacità di memorizzazione superiore, ma una volta che questo problema passa in secondo piano sarebbe opportuno scegliere praticamente sempre il RAID10 dal punto di vista delle performance. Il RAID5 nel momento in cui la percentuale delle scritture supera il 10% del totale inizia a imporre un maggior carico ai singoli dischi dell’array.&lt;/p&gt;  &lt;p&gt;Prendiamo ad esempio il nostro disco visto sopra, da 188 operazioni random al secondo prima di iniziare ad accodare, e vediamo cosa succede una volta inserito in un array composto da 6 unità (configurazione molto diffusa), che si trova a gestire 500 operazioni al secondo.&lt;/p&gt;  &lt;p align="center"&gt;&lt;em&gt;Confronto sul carico dei dischi&lt;/em&gt;&lt;/p&gt;  &lt;div align="center"&gt;   &lt;table cellspacing="0" cellpadding="2" width="498" align="center" border="1"&gt;&lt;tbody&gt;       &lt;tr&gt;         &lt;td valign="top" width="239"&gt;           &lt;p&gt;&lt;b&gt;Rapporto Lettura/Scrittura&lt;/b&gt;&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;&lt;b&gt;RAID 5 I/Os&lt;/b&gt; &lt;/p&gt;            &lt;p&gt;&lt;b&gt;&lt;sup&gt;[a]&lt;/sup&gt;&lt;/b&gt;&lt;b&gt;&lt;/b&gt;&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="125"&gt;           &lt;p&gt;&lt;b&gt;RAID 10 I/Os&lt;/b&gt; &lt;/p&gt;            &lt;p&gt;&lt;b&gt;&lt;sup&gt;[b]&lt;/sup&gt;&lt;/b&gt;&lt;b&gt;&lt;/b&gt;&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;100% letture; 0% scritture&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;(500 + 0) / 6              &lt;br /&gt;83 I/Os per disco&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="126"&gt;           &lt;p&gt;(500 + 0) / 6              &lt;br /&gt;83 I/Os per disco&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;90% letture; 10% scritture&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;(450 + 200) / 6              &lt;br /&gt;108 I/Os per disco&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="126"&gt;           &lt;p&gt;(450 + 100) / 6              &lt;br /&gt;91 I/Os per disco&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;75% letture; 25% scritture&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;(375 + 500) / 6              &lt;br /&gt;145 I/Os per disco&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="126"&gt;           &lt;p&gt;(375 + 250) / 6              &lt;br /&gt;104 I/Os per disco&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;50% letture; 50% scritture&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;(250 + 1000) / 10              &lt;br /&gt;208 I/Os per disco&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="126"&gt;           &lt;p&gt;(250 + 500) / 6              &lt;br /&gt;125 I/Os per disco&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;0% letture; 100% scritture&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;           &lt;p&gt;(0 + 2000) / 6              &lt;br /&gt;333 I/Os per disco&lt;/p&gt;         &lt;/td&gt;          &lt;td valign="top" width="126"&gt;           &lt;p&gt;(0 + 1000) / 6              &lt;br /&gt;166 I/Os per disco&lt;/p&gt;         &lt;/td&gt;       &lt;/tr&gt;        &lt;tr&gt;         &lt;td valign="top" width="238"&gt;           &lt;h5&gt;&lt;a name="156"&gt;&lt;/a&gt;&lt;sup&gt;[&lt;/sup&gt;&lt;sup&gt;a&lt;/sup&gt;&lt;sup&gt;]&lt;/sup&gt; [Letture+ (4 * Scritture)] / N°Dischi &lt;/h5&gt;            &lt;h5&gt;&lt;a name="157"&gt;&lt;/a&gt;&lt;sup&gt;[&lt;/sup&gt;&lt;sup&gt;b&lt;/sup&gt;&lt;sup&gt;]&lt;/sup&gt; [Letture+ (2 * Scritture)] /N°Dischi&lt;/h5&gt;         &lt;/td&gt;          &lt;td valign="top" width="132"&gt;&amp;#160;&lt;/td&gt;          &lt;td valign="top" width="127"&gt;&amp;#160;&lt;/td&gt;       &lt;/tr&gt;     &lt;/tbody&gt;&lt;/table&gt; &lt;/div&gt;  &lt;p&gt;Come si vede già con il 10% di scritture il RAID5 impone più del 15% in più di carico su ogni disco, al 25% il confronto inizia a diventare molto sconveniente, e già prima del 50% supera il limite oltre il quale inizia l’accodamento. infine al 100% di scritture il RAID5 risulta evidentemente in difficoltà mentre il RAID10 si mantiene ancora entro le capacità del singolo disco. &lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/itasupport/pages/mauro-munzi.aspx"&gt;Mauro Munzi&lt;/a&gt;     &lt;br /&gt;Senior Support Engineer     &lt;br /&gt;Microsoft Enterprise SQL Support&lt;/p&gt;&lt;img src="http://blogs.technet.com/aggbug.aspx?PostID=3199176" width="1" height="1"&gt;</description><category domain="http://blogs.technet.com/itasupport/archive/tags/SQL+Team/default.aspx">SQL Team</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Mauro+Munzi/default.aspx">Mauro Munzi</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx">Performance</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Disk+Management/default.aspx">Disk Management</category><category domain="http://blogs.technet.com/itasupport/archive/tags/SQL+Server/default.aspx">SQL Server</category></item><item><title>SQL Server - Analizzare un problema di timeout utilizzando Sqlnexus</title><link>http://blogs.technet.com/itasupport/archive/2009/01/05/sql-server-analizzare-un-problema-di-timeout-utilizzando-sqlnexus.aspx</link><pubDate>Mon, 05 Jan 2009 03:00:00 GMT</pubDate><guid isPermaLink="false">d5e57398-b9ef-4490-9955-07cbb4e4a80d:3174718</guid><dc:creator>itentblg</dc:creator><slash:comments>0</slash:comments><comments>http://blogs.technet.com/itasupport/comments/3174718.aspx</comments><wfw:commentRss>http://blogs.technet.com/itasupport/commentrss.aspx?PostID=3174718</wfw:commentRss><description>&lt;p&gt;Una delle richieste più frequenti che riceviamo nel team di supporto di Sql Server è quella di capire la causa determinante timeout applicativi durante l’esecuzione di query.&lt;/p&gt;  &lt;p&gt;In questo post spiegherò come utilizzare &lt;a href="http://www.codeplex.com/sqlnexus"&gt;Sqlnexus&lt;/a&gt; per effettuare velocemente l'analisi di un problema relativo alla lentezza di una query e determinante un timeout applicativo.&lt;/p&gt;  &lt;h3&gt;Problema &lt;/h3&gt;  &lt;p&gt;Errori di timeout, che si verificano in modalità casuale, durante una complessa attività applicativa.&lt;/p&gt;  &lt;h3&gt;Dati da raccogliere&lt;/h3&gt;  &lt;p&gt;Per capire la causa di problemi di timeout è necessario individuare l'attività su cui il timeout si verifica e se tale attività è stata affetta da blocchi o da problemi di performance sul server.&lt;/p&gt;  &lt;p&gt;Dal punto di vista di Sql server, l’analisi di un timeout verificatosi durante l’esecuzione di una query, può essere inizialmente affrontata come un generico problema di performance volto ad identificare la causa per cui una determinata query viene eseguita in un tempo superiore a quello impostato dal timeout applicativo. &lt;/p&gt;  &lt;p&gt;A tale scopo, durante il riprodursi del problema, si chiede generalmente di raccogliere dati di performance quali trace di &lt;a href="http://msdn.microsoft.com/en-us/library/ms173757(SQL.90).aspx"&gt;Sql server profiler&lt;/a&gt;, &lt;a href="http://msdn.microsoft.com/en-us/library/ms191246(SQL.90).aspx"&gt;System monitor counters &lt;/a&gt;e trace di &lt;a href="http://support.microsoft.com/kb/271509/en-us"&gt;Blocker script&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;Il tool in grado di raccogliere contemporaneamente tali informazioni è Pssdiag:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Sql server 2000 è disponibile pubblicamente con interfaccia grafica al seguente indirizzo &lt;a href="http://support.microsoft.com/kb/830232"&gt;http://support.microsoft.com/kb/830232&lt;/a&gt; &lt;/li&gt;    &lt;li&gt;Sql server 2005 è possibile utilizzare il tool &lt;a href="http://msdn.microsoft.com/en-us/library/ms162833(SQL.90).aspx"&gt;Sqldiag&lt;/a&gt; compreso nell'installazione e non avente interfaccia grafica &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Per avere un esempio degli eventi e counters da catturare è possibile far riferimento al seguente articolo &lt;a href="http://support.microsoft.com/kb/224587/en-us"&gt;HOW TO: Troubleshoot Application Performance with SQL Server&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;In questa situazione specifica sono stati raccolti i seguenti eventi:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Database: tutti gli eventi &lt;/li&gt;    &lt;li&gt;Errors and warning: tutti gli eventi &lt;/li&gt;    &lt;li&gt;Locks: Lock:Deadlock, Lock:Escalation, Lock:Timeout &lt;/li&gt;    &lt;li&gt;Objects: Auto Update Stats &lt;/li&gt;    &lt;li&gt;Performance: Show Plan Statistics &lt;/li&gt;    &lt;li&gt;Security Audit: Login, Login Failed, Logout &lt;/li&gt;    &lt;li&gt;Sessions: ExistingConnestion &lt;/li&gt;    &lt;li&gt;StoredProcedure: RPC:Completed, RPC:Starting, SP:CacheInsert, SP:CacheRemove, SP:Recompile, SP:StmtCompleted, SP:StmtStarting &lt;/li&gt;    &lt;li&gt;Tsql:SQL:BatchCompleted, SQL:BatchStarting, SQL:StmtCompleted, SQL:StmtStarting &lt;/li&gt; &lt;/ul&gt;  &lt;h3&gt;Analisi dei dati&lt;/h3&gt;  &lt;p&gt;In questa sezione vedremo come Sqlnexus possa essere utilizzato per analizzare i dati raccolti tramite le trace di Sql server profiler.&lt;/p&gt;  &lt;h4&gt;Installazione di Sqlnexus&lt;/h4&gt;  &lt;p&gt;&lt;a href="http://www.codeplex.com/sqlnexus" target="_blank"&gt;Scaricare il tool Sqlnexus&lt;/a&gt; e verificare le informazioni sul suo utilizzo&lt;/p&gt;  &lt;p&gt;Installare RML utilities &lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyId=7EDFA95A-A32F-440F-A3A8-5160C8DBE926&amp;amp;displaylang=en" target="_blank"&gt;RML Utilities for SQL Server – Versione a 32 bit (x86)&lt;/a&gt; &lt;/li&gt;    &lt;li&gt;&lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyId=B60CDFA3-732E-4347-9C06-2D1F1F84C342&amp;amp;displaylang=en" target="_blank"&gt;RML Utilities for SQL Server – Versione a 64 bit (x64)&lt;/a&gt; &lt;/li&gt; &lt;/ul&gt;  &lt;h4&gt;Caricamento dati in Sqlnexus&lt;/h4&gt;  &lt;p&gt;Avviare Sqlnexus.exe e connettersi a un Sql server in ambiente di test per effettuare l’analisi dei dati.    &lt;br /&gt;Una volta aperta l’interfaccia di Sqlnexus, cliccando su import, verrà visualizzata la finestra in cui impostare la cartella contenente i file di Sql server profiler raccolti con Pssdiag:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb1_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb1" border="0" alt="image_thumb1" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb1_thumb.png" width="546" height="238" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;h4&gt;Visualizzazione dei dati di performance &lt;/h4&gt;  &lt;p&gt;Terminato l'import dei dati , potremo selezionare &lt;b&gt;Readtrace_main&lt;/b&gt;, nella sezione &lt;b&gt;Reports&lt;/b&gt;, per visualizzare l'analisi:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb3_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb3" border="0" alt="image_thumb3" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb3_thumb.png" width="547" height="198" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Selezionando i link presenti nella schermata di &lt;b&gt;Performance Overview&lt;/b&gt;, potremo visualizzare i report indicanti le query eseguite durante l’intervallo di tempo di cattura dei dati e il rispettivo consumo di risorse. Tali report costituiscono un aiuto essenziale nell’individuare le query aventi maggiore impatto in termini di tempo di esecuzione , letture , scritture o consumo di CPU.&lt;/p&gt;  &lt;h4&gt;Individuazione dei timeout &lt;/h4&gt;  &lt;p&gt;Siccome l’obiettivo di questo blog e quello di analizzare le query su cui è avvenuto un timeout applicativo, dovremo individuare gli eventi di &lt;a href="http://msdn.microsoft.com/en-us/library/ms190979(SQL.90).aspx"&gt;Attention&lt;/a&gt; avvenuti durante la cattura dei dati.     &lt;br /&gt;Per visualizzare tali eventi, selezioniamo &lt;b&gt;Interesting events&lt;/b&gt; e sarà visualizzato un grafico simile a quello sotto riportato:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb5_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb5" border="0" alt="image_thumb5" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb5_thumb.png" width="614" height="449" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Come è possibile verificare dalla schermata sopra riportata, supponendo di aver impostato gli eventi necessari in Sql server profiler, potremo visualizzare tramite un grafico facilmente leggibile, altri tipi di eventi quali la crescita dei datafile o i sort warning e associare o meno tali eventi al verificarsi del problema.    &lt;br /&gt;Selezionando il link &lt;b&gt;Attention&lt;/b&gt;, potremo visualizzare la query su cui è avvenuto il timeout e lo spid che stava eseguendo in quel momento la query.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb7_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb7" border="0" alt="image_thumb7" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb7_thumb.png" width="654" height="264" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Selezionando la query, potremo visualizzare tutti i dettagli sul tempo di esecuzione, le letture eseguite, il consumo di CPU e il nome del file di Sql server profiler contenente l’esecuzione della query durante l’avvenuto timeout.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb9_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb9" border="0" alt="image_thumb9" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb9_thumb.png" width="654" height="159" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Dalla schermata sopra riportata è evidente che il tempo di esecuzione della query ha superato i 30 sec di timeout impostato dall’applicazione.&lt;/p&gt;  &lt;p&gt;Una volta individuata la query su cui si manifesta il problema, lo spid avente in esecuzione la query e l’intervallo di tempo in cui è avvenuto il timeout, potremo aprire la trace di Sql server profiler, filtrare per lo spid indicato da Sqlnexus, cercare la query affetta dal problema e analizzare in dettaglio i vari passi di esecuzione.&lt;/p&gt;  &lt;p&gt;Nell’esempio qui riportato, analizzando la trace di Sql server profiler in corrispondenza della query e dell’intervallo di tempo in cui si è verificato il problema è stato possibile verificare che il timeout applicativo era dovuto ad un tempo di esecuzione superiori ai 30 sec e che la maggior parte del tempo di esecuzione, circa 25 sec, era utilizzato nella ricompilazione e inserimento in cache.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb11_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb11" border="0" alt="image_thumb11" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/SQLServerAnalizzareunproblemaditimeoutut_9F72/image_thumb11_thumb.png" width="627" height="170" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Se la trace di Sql server profiler non dovesse bastare ad individuare la causa del problema, sarà necessario effettuare altre verifiche quali l’analisi del Blocker script e dei Performance counters in corrispondenza dell’intervallo di tempo in cui si è verificato il problema oppure la verifica dettagliata del piano di esecuzione della query per effettuare un adeguato tuning.&lt;/p&gt;  &lt;p&gt;Anche per analisi più approfondite Sqlnexus potrà aiutare, dandoci velocemente una panoramica delle attività presenti sul server durante il verificarsi del problema.&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/itasupport/pages/raffaella-canobbio.aspx" target="_blank"&gt;Raffaella Canobbio&lt;/a&gt;     &lt;br /&gt;Support Escalation Engineer     &lt;br /&gt;Microsoft Enterprise SQL Support&lt;/p&gt;&lt;img src="http://blogs.technet.com/aggbug.aspx?PostID=3174718" width="1" height="1"&gt;</description><category domain="http://blogs.technet.com/itasupport/archive/tags/SQL+Team/default.aspx">SQL Team</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Raffaella+Canobbio/default.aspx">Raffaella Canobbio</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx">Performance</category><category domain="http://blogs.technet.com/itasupport/archive/tags/SQL+Server/default.aspx">SQL Server</category></item><item><title>Analizzare l’evento “Application Popup 333”</title><link>http://blogs.technet.com/itasupport/archive/2008/11/17/analizzare-l-evento-application-popup-333.aspx</link><pubDate>Mon, 17 Nov 2008 03:00:00 GMT</pubDate><guid isPermaLink="false">d5e57398-b9ef-4490-9955-07cbb4e4a80d:3150310</guid><dc:creator>itentblg</dc:creator><slash:comments>2</slash:comments><comments>http://blogs.technet.com/itasupport/comments/3150310.aspx</comments><wfw:commentRss>http://blogs.technet.com/itasupport/commentrss.aspx?PostID=3150310</wfw:commentRss><description>&lt;p&gt;In questo mio primo post vorrei parlarvi di un evento, che sotto determinate condizioni, è possibile riscontrare nel Registro Eventi del proprio server: l’&lt;b&gt;Application Popup 333&lt;/b&gt;.&lt;/p&gt;  &lt;p&gt;Come prima cosa cerchiamo di capire a cosa si riferisce questo evento. &lt;/p&gt;  &lt;p&gt;Partiamo con l’indicare che il relativo source è l’Application Popup, che ci notifica negli eventi di sistema che un’operazione di I/O iniziata dal registro è fallita. In particolare questo componente non è stato capace di leggere, scrivere o fare il flush su disco di determinate informazioni, che andranno dunque perse. Negli eventi di sistema vedremo una serie di segnalazioni come queste:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image%5B1%5D.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image_thumb[1][1]" border="0" alt="image_thumb[1][1]" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image_thumb%5B1%5D%5B1%5D_d37bc840-cab3-4516-b82c-b3481c3e16f2.png" width="371" height="409" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Sottolineo una serie perché in seguito al presentarsi del primo di questi eventi, circa ogni 5 secondi il sistema memorizzerà una nuova notifica, fino a quando non verrà effettuato un reboot della macchina.&lt;/p&gt;  &lt;p&gt;In generale non possiamo determinare gli effetti della mancata scrittura o lettura del registro, ma questi saranno sicuramente circoscritti al componente che ha richiesto l’operazione. I sintomi che accompagnano questo evento, se presenti, sono differenti a seconda della causa che lo genera. &lt;/p&gt;  &lt;p&gt;Tipici scenari possono riguardare hangs del sistema, risorse insufficienti per il completamento di un servizio richiesto, database SQL che si stoppano o che eseguono le query lentamente, o più in generale eventi legati alle performance del sistema operativo. &lt;/p&gt;  &lt;p&gt;Questo evento è stato introdotto con Windows Server 2003 Service Pack 1 ed è possibile trovarlo sia su sistemi x86 che x64.&lt;/p&gt;  &lt;p&gt;Terminata questa breve introduzione, passiamo all’analisi di quelle che possono essere le cause che portano a questo evento. &lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;b&gt;Il disco&lt;/b&gt; che sta ospitando il sistema operativo ha un carico di lavoro molto elevato, o ha dei problemi hardware, evidenziando una lunga coda di operazioni che attendono per essere eseguite. Possiamo avere questa circostanza sia su sistemi x86 che x64. &lt;/li&gt;    &lt;li&gt;Esaurimento delle &lt;b&gt;risorse lato Kernel&lt;/b&gt;: Non Paged Pool Memory (Evento SRV 2020 nel registro di sistema), Paged Pool Memory (Evento SRV 2019 nel registro di sistema) o Page Table Entries (PTE). Questa problematica riguarda, salvo eventi particolari, sistemi x86, a causa delle limitazioni dettate dall’architettura a 32 bit. &lt;/li&gt;    &lt;li&gt;Un &lt;b&gt;filter driver&lt;/b&gt; sta impedendo flush su disco del registri. Questo può accadere sia in sistemi x86, che x64. &lt;/li&gt;    &lt;li&gt;E’ stato concesso il privilegio “&lt;b&gt;Lock system pages in memory&lt;/b&gt;” ad un account user. Questo può succedere sia in sistemi x86, che x64. &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Abbiamo elencato le ipotetiche cause del nostro evento 333, ma come facciamo a rimuoverlo?!&lt;/p&gt;  &lt;p&gt;Dipende dal particolare scenario alla base del problema, analizziamo singolarmente le varie casistiche:&lt;/p&gt;  &lt;h4&gt;&lt;strong&gt;Problemi legati al disco&lt;/strong&gt;&lt;/h4&gt;  &lt;p&gt;Per identificare questo tipo di problematica possiamo configurare i performance monitor forniti dal sistema operativo per l’analisi del nostro disco fisico. La prima grandezza che ci fornisce un’idea di come il nostro disco sta rispondendo alle operazioni richieste è la &lt;b&gt;Current Disk Queue Length&lt;/b&gt;. Questo valore dovrebbe essere tipicamente non superiore a 1 per un disco, o più in generale non superiore a n per sistemi di memorizzazione costituiti da n dischi, come le varie tipologie di RAID. Occorre sollevare un’eccezione per le SAN, dove questo valore può essere falsato dalla metodologia di archiviazione utilizzata dall’hardware a disposizione e dunque eventuali anomalie riscontrate vanno sempre discusse con l’OEM.&lt;/p&gt;  &lt;p align="center"&gt;&amp;#160;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image3_thumb_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image3_thumb" border="0" alt="image3_thumb" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image3_thumb_thumb.png" width="636" height="398" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p align="center"&gt; FIG. 1 – Disco con valori della Current Queue Length anomali&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image6_thumb%5B4%5D.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image6_thumb[4]" border="0" alt="image6_thumb[4]" src="http://blogs.technet.com/blogfiles/itasupport/WindowsLiveWriter/AnalizzareleventoApplicationPopup333_A2C0/image6_thumb%5B4%5D_thumb.png" width="636" height="398" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p align="center"&gt; FIG. 2 – Disco con valori della Current Queue Length normali&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;La figura 2 ci mostra un esempio un disco che sta eseguendo senza problemi le richieste di I/O derivanti dall’attività del sistema operativo. Dalla figura 2, invece, è possibile osservare un disco che sta accodando le richieste di I/O, introducendo dunque delle potenziali problematiche. E’ possibile suddividere le cause che possono portare ad una situazione come quella illustrata nella figura 1, in due sottogruppi:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Problemi strettamente legati all’hardware (Controller o unità disco) &lt;/li&gt;    &lt;li&gt;Sovraccarico delle operazioni su disco &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Consideriamo la prima casistica, il disco sta accodando delle richieste a causa di problemi hardware. L’accodamento è dunque causato da una lentezza da parte del sistema si storage nell’eseguire le richieste. Un altro counter, che affiancato alla Current Disk Queue Length, ci può evidenziare questa tipologia di problema è il &lt;b&gt;Disk Response Time&lt;/b&gt;. Il tempo di risposta può variare a seconda delle specifiche del disco, ma in generale un tempo superiore ai 30ms dovrebbe essere investigato. Se i contatori esposti sembrano evidenziare un problema legato al sistema di storage, occorrerà aggiornare firmware e driver del controller ed eventualmente controllare i dischi attraverso i tool di hardware monitoring.&lt;/p&gt;  &lt;p&gt;La seconda casistica riguarda un’eccessiva attività su disco. Un altro counter, che associato al Disk Queue Length, ci può evidenziare questo tipo di situazione è il I/O Data bytes/sec dell’oggetto Process. Occorrerà per prima cosa evidenziare eventuali processi che stanno eseguendo un’elevata attività di I/O e verificare se questo risulta in linea con i ruoli e le attività quotidiane del server. Se non si riscontrassero anomalie legate al binomio ruoli/attività disco, occorrerà effettuare un bilanciamento del carico su più dischi o server, ed eventualmente spostare il file di paging su un disco differente da quello di sistema.&lt;/p&gt;  &lt;h4&gt;&lt;strong&gt;Esaurimento delle risorse kernel&lt;/strong&gt;&lt;/h4&gt;  &lt;p&gt;Tratteremo nel dettaglio la gestione di questa problematica nei prossimi post, partiamo comunque col dire che le tre grandezze che entrano in gioco in questo tipo e sono la Non Paged Pool Memory, la Paged Pool Memory e le Free Page Table Entries. Possiamo verificare questi valori attraverso i relativi contatori dell’oggetto memory. In particolare le soglie che dobbiamo tenere come riferimento, per sistemi Windows Server 2000 e 2003, sono le seguenti:&lt;/p&gt;  &lt;table border="1" cellspacing="0" cellpadding="5" align="center"&gt;&lt;tbody&gt;     &lt;tr&gt;       &lt;td valign="top"&gt;&lt;b&gt;Non Paged Pool Memory (NPP)&lt;/b&gt;&lt;/td&gt;        &lt;td valign="top"&gt;&lt;b&gt;&amp;lt;&lt;/b&gt; &lt;b&gt;256&lt;/b&gt; MB ( &lt;b&gt;128&lt;/b&gt; MB in sistemi con lo switch &lt;b&gt;/3GB&lt;/b&gt; abilitato )&lt;b&gt;&amp;#160;&lt;/b&gt;&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td valign="top"&gt;&lt;b&gt;Paged Pool Memory (PP)&lt;/b&gt;&lt;/td&gt;        &lt;td valign="top"&gt;&lt;b&gt;&amp;lt;&lt;/b&gt; &lt;b&gt;650&lt;/b&gt; MB (&lt;b&gt;491.875&lt;/b&gt; per Windows 2000 e Windows XP)&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td valign="top"&gt;&lt;b&gt;Free Page Table Entries (PTE)&lt;/b&gt;&lt;/td&gt;        &lt;td valign="top"&gt;&lt;b&gt;&amp;gt; 5.000&lt;/b&gt; (Sotto questo valore il comportamento del sistema è imprevedibile)&lt;/td&gt;     &lt;/tr&gt;   &lt;/tbody&gt;&lt;/table&gt;  &lt;p&gt;L’esaurimento della Non Paged Pool Memory e Non Paged Pool Memory, è solitamente accompagnato dagli eventi d’errore 2019 e 2020 nei system events.&lt;/p&gt;  &lt;p&gt;Se riscontriamo che la PP,o la NPP, si stanno avvicinando alle soglie indicate, occorrerà effettuare una specifica analisi per capire quale driver sta causando l’esaurimento della risorsa. Come anticipato tratteremo questo tipo di analisi in un articolo separato. In generale possiamo comunque investigare su problemi conosciuti di esaurimento della memoria, riguardanti i driver di terze parti attualmente installati sul nostro server. E’ buona norma mantenere sempre i driver dei vari prodotti, aggiornati all’ultima versione disponibile.&lt;/p&gt;  &lt;p&gt;Per quanto riguarda le PTEs, occorrerà effettuare la seguente distinzione:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;strong&gt;Switch /3GB abilitato nel boot.ini        &lt;br /&gt;&lt;/strong&gt;In questo caso la memoria virtuale dedicata al sistema operativo si riduce da 2 a 1 GBytes, riducendo così anche lo spazio libero per le PTE. In questo particolare caso possiamo intervenire con lo switch /USERVA, come indicato nel seguente articolo:       &lt;br /&gt;KB 316739       &lt;br /&gt;How to use the /userva switch with the /3GB switch to tune the User-mode space to a value between 2 GB and 3 GB       &lt;br /&gt;&lt;a href="http://support.microsoft.com/default.aspx?scid=kb;EN-US;316739"&gt;http://support.microsoft.com/default.aspx?scid=kb;EN-US;316739&lt;/a&gt;       &lt;br /&gt;      &lt;br /&gt;In questo modo possiamo modificare la soglia tra i 3Gbyte della memoria virtuale user e il Gbyte della memoria virtuale dedicata al kernel.       &lt;br /&gt;&lt;/li&gt;    &lt;li&gt;&lt;strong&gt;Switch /3GB disabilitato nel boot.ini        &lt;br /&gt;&lt;/strong&gt;In questo caso potremmo avere un leak di PTE, che possiamo analizzare attraverso l’impostazione del Track PTE ed un tool di debugging. Anche questa specifica problematica, verra trattata nell’articolo dedicato alle risorse kernel. &lt;/li&gt; &lt;/ul&gt;  &lt;h4&gt;&lt;strong&gt;Filter driver&lt;/strong&gt;&lt;/h4&gt;  &lt;p&gt;E’ doveroso premettere che rimuovendo o disabilitando un filter driver senza capire l’impatto sul sistema, potremmo riscontrare comportamenti inaspettati, come hang o blue screen. Esempi di applicativi che possono utilizzare dei filter driver includono: Anti-virus software, Backup Software, software di gestione volumi, software di criptazione/decriptazione dati etc.&lt;/p&gt;  &lt;p&gt;Il metodo più semplice per determinare i filter driver, di terze parti, installati sulla nostra macchina è utilizzare la nostra utility MPS Report, che consente di raccogliere queste informazioni. Possiamo seguire dunque i seguenti passi:&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;Download del tool MPSRPT_SETUPPerf.exe dal link &lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyID=cebf3c7c-7ca5-408f-88b7-f9c79b7306c0&amp;amp;DisplayLang=en"&gt;Microsoft Product Support Reporting Tools page&lt;/a&gt;. &lt;/li&gt;    &lt;li&gt;Eseguire il file MPSRPT_SETUPPerf.EXE scaricato. &lt;/li&gt;    &lt;li&gt;Terminata l’esecuzione, la durata media è di circa 15min, è possibile analizzare il file PStat.txt, estraendolo dal file .CAB creato dal tool. Tramite questo file possiamo verificare tutti i filter / kernel drivers con le relative date. Verificare eventuali versioni non aggiornata, o eventuali versioni che hanno già problemi riconosciuti dal vendor. &lt;/li&gt; &lt;/ol&gt;  &lt;p&gt;E’ importante che, prima di effettuare qualsiasi operazione di disabilitazione o rimozione, venga effettuato il controllo sulla disponibilità da parte del vendor di eventuali versioni aggiornate.&lt;/p&gt;  &lt;h4&gt;&lt;strong&gt;Lock system pages in memory&lt;/strong&gt;&lt;/h4&gt;  &lt;p&gt;In sistemi a 64bit, come descritto precedentemente, la probabilità di avere valori preoccupanti per le PTEs è assai inferiore rispetto a sistemi x86. Tuttavia, abbiamo visto nella nostra attività quotidiana, eventi 333 capitare ugualmente anche in sistemi x64, dovuti a questo motivo.&lt;/p&gt;  &lt;p&gt;Un workaround per questo comportamento in sistemi x64 con 4GB, o meno, di memoria RAM è costituito dai seguenti passi:&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;Cliccare su Start --&amp;gt; Run &lt;/li&gt;    &lt;li&gt;Digitare Secpol.msc e premere OK &lt;/li&gt;    &lt;li&gt;Espandere &amp;quot;Local Policies&amp;quot; e cliccare su &amp;quot;User Rights Assignment&amp;quot; &lt;/li&gt;    &lt;li&gt;Doppio click su &amp;quot;Lock pages in memory&amp;quot; &lt;/li&gt;    &lt;li&gt;Evidenziare eventuali user accounts elencati e cliccare su &amp;quot;Remove&amp;quot; &lt;/li&gt;    &lt;li&gt;Premere su OK, una volta rimossi tutti gli user account &lt;/li&gt;    &lt;li&gt;Riavviare il sistema &lt;/li&gt; &lt;/ol&gt;  &lt;p&gt;Di default il sistema operative non fornisce questo diritto a nessun account. Il privilegio “Lock pages in memory” è fornito all’account utilizzato per i servizi SQL in SQL 2005 RTM/SP1 Enterprise Edition installato su sistemi a 32bit. Se state utilizzando SQL Enterprise in un servers x86, con più di 4GB di RAM, questo privilegio è necessario. Per cercare di ridurre l’occorrenza degli eventi 333 nel sistema, occorrerà verificare che l’account che si sta utilizzando per I servizi SQL, sia utilizzato solo per SQL. Per sistemi x64 possiamo rimuovere tutti gli utenti elencati.&lt;/p&gt;  &lt;p&gt;Bene questo è tutto per questo post. Come potete vedere le cause per l’evento 333 sono svariate e spesso correlate a problemi con alcuni driver o configurazioni: vi consiglio dunque di visitare regolarmente la nostra &lt;a href="http://support.microsoft.com/" target="_blank"&gt;Microsoft Knowledge base&lt;/a&gt; per verificare le nuove pubblicazioni e gli ultimi aggiornamenti disponibili.&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.technet.com/itasupport/pages/mattia-tocco.aspx" target="_blank"&gt;Mattia Tocco&lt;/a&gt;     &lt;br /&gt;Senior Support Engineer     &lt;br /&gt;Microsoft Enterprise Platforms Support&lt;/p&gt;&lt;img src="http://blogs.technet.com/aggbug.aspx?PostID=3150310" width="1" height="1"&gt;</description><category domain="http://blogs.technet.com/itasupport/archive/tags/Windows+Team/default.aspx">Windows Team</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Mattia+Tocco/default.aspx">Mattia Tocco</category><category domain="http://blogs.technet.com/itasupport/archive/tags/Performance/default.aspx">Performance</category></item></channel></rss>