<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="https://www.w3.org/2005/Atom" xmlns:sy="https://purl.org/rss/1.0/modules/syndication/" xmlns:dc="https://purl.org/dc/elements/1.1/" xmlns:content="https://purl.org/rss/1.0/modules/content/" xmlns:wfw="https://wellformedweb.org/CommentAPI/" xmlns:slash="https://purl.org/rss/1.0/modules/slash/"
  version="2.0">
  <channel>
    <title>Srini Gajjela's</title>
    <atom:link
      href="https://docs.microsoft.com/archive/blogs/sgajjela/feed.xml"
      rel="self"
      type="application/rss+xml" />
    <link>https://docs.microsoft.com/archive/blogs/sgajjela/feed.xml</link>
    <description />
    <lastBuildDate>Wed, 17 Apr 2019 03:50:20 GMT</lastBuildDate>
    <language>en-US</language>
    <sy:updatePeriod>hourly</sy:updatePeriod>
    <sy:updateFrequency>1</sy:updateFrequency>
    <item>
      <title>Package stored in MSDB runs slower while executing in DEBUG from SSDT</title>
      <link>https://docs.microsoft.com/archive/blogs/sgajjela/package-stored-in-msdb-runs-slower-while-executing-in-debug-from-ssdt</link>
      <pubDate>Sat, 10 May 2014 08:18:00 GMT</pubDate>
      <dc:creator><![CDATA[Srini Gajjela]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/sgajjela/2014/05/10/package-stored-in-msdb-runs-slower-while-executing-in-debug-from-ssdt/</guid>
      <description><![CDATA[Customer had opened a case&nbsp;with Microsoft Customer Service and Support (CSS) SQL Support to...]]></description>
      <content:encoded><![CDATA[<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">Customer had opened a case&nbsp;with Microsoft Customer Service and Support (CSS) SQL Support to find why Package stored in MSDB runs slower&nbsp;&nbsp;while executing in <strong>DEBUG</strong> mode from <strong>SSDT</strong> comparatively to the package stored on the file system.&nbsp;&nbsp;</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">For a specific customer scenario, package imports about one million rows. If the package is stored on the file system, Package execution from SSDT in DEBUG mode finishes importing all million rows in about 2 minutes. if the package is stored in MSDB, package execution from SSDT in <strong>DEBUG</strong> takes about 20-30 minutes to import same amount of the source data .</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">I enabled package log for all the tasks and events and collected&nbsp;one memory dumps for every 1-2 minutes for the processes :</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">DEVENV.EXE </span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">DTSDEBUGHOST.EXE - 64 bit</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">DTSDEBUGHOST.EXE - 32 bit</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">Package logs showed a pattern that "OnPipelineRowSent" is always 5 seconds apart indicating delay in processing the buffers of the data . </span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">As per the package log below , 4748 rows per each buffer,</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">User:BufferSizeTuning,SGAJJE010430VM,SGAJJE010430VM\Administrator,Data Flow Task 1,{F2030480-53DF-409F-81A9-0BE8B26E9FE7},{DA5A9C54-F935-4821-B9BB-F0ACD107AD40},2/21/2014 9:58:59 AM,2/21/2014 9:58:59 AM,0,0x,Rows in buffer type 0 would cause a buffer size greater than the configured maximum. <strong>There will be only 4748 rows in buffers of this type</strong>.</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">So, for 1 million rows about 210 data flow pipeline buffers and 5 seconds delay between processing each buffer. </span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">Hence total delayed time for importing all the 210 buffers that has 1 million rows is 5 *210 = 1053 seconds = 17.5 seconds</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">The total delay time (17.5 seconds) + Time for importing the 1 million rows ( about 2-3 minutes) = ~20 minutes, which the total time to finish the package execution.&nbsp;</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">The memory dumps showed that DTSDEBUGHOST.EXE raised an RPC event to send to the debugger window over RPC</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">The RPC listener thread which is handling the custom event in DtsDebuggerHOST.exe window waiting for with for predefined time 5 seconds. This is the 5 seconds delay that was logged in the package log</span><span style="font-family: arial,helvetica,sans-serif; font-size: small;">.</span></p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">SSIS Product team confirmed the slowness is due to a bug and a fix will be released in the future versions of the SSDT that can be downloaded from public facing portal and the version that ships with SQL 2012 Product .</span></p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">Until a hot fix is released, The alternate solution is to store the package on the file system to resolve the performance problem while executing in DEBUG MODE from SSDT. </span></p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p><span style="font-family: arial,helvetica,sans-serif; font-size: small;">&nbsp;</span></p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>&nbsp;</p>]]></content:encoded>
    </item>
    <item>
      <title>How to develop WinDbg extension DLL</title>
      <link>https://docs.microsoft.com/archive/blogs/sgajjela/how-to-develop-windbg-extension-dll</link>
      <pubDate>Sat, 02 Mar 2013 08:33:00 GMT</pubDate>
      <dc:creator><![CDATA[Srini Gajjela]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/sgajjela/2013/03/02/how-to-develop-windbg-extension-dll/</guid>
      <description><![CDATA[How to develop WinDbg extension DLL?

A WinDbg extension DLL is set of exported callback functions...]]></description>
      <content:encoded><![CDATA[<p><span style="font-size: medium;"><strong><span style="font-family: tahoma,arial,helvetica,sans-serif;">How to develop WinDbg extension DLL?</span></strong></span></p>
<p><span style="font-size: medium;"><strong><span style="font-family: tahoma,arial,helvetica,sans-serif;"></span></strong></span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">A WinDbg extension DLL is set of exported callback functions for implementing user defined commands to extract specific customized&nbsp; information from the memory dump(s).&nbsp; Extension DLLs are loaded by debugger engine and can provide extra functionality of automation tasks while performing user-mode or kenrel-mode debugging.&nbsp; An extension DLL may export any number of functions that are used to execute extension commands.&nbsp; Each function is explicitly declared as an export in the&nbsp; DLL's definition file or .def file and function names must be in lowercase letters</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">WinDbg (DbgEng ) extension DLL must export <strong>DebugExtensionInitialize</strong>. This will be called when the DLL is loaded, to initialize the DLL. It may be used by the DLL to initialize global variables.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">An extension DLL may export an optional function <strong>DebugExtensionUninitialize</strong>. If this is exported, it will be called just before the extension DLL is unloaded.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">An extension DLL may export a <strong>DebugExtensionNotify</strong>. If this is exported, it will be called when a session begins or ends, and when a target starts or stops executing. These notifications are also provided to <strong>IDebugEventCallbacks</strong> objects registered with a client.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">An extension DLL may export <strong>KnownStructOutput</strong>. If this is exported, it will be called when the DLL is loaded. This function returns a list of structures that the DLL knows how to print on a single line. It may be called later to format instances of these structures for printing.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">So, how to develop&nbsp;&nbsp; your own Windbg Extension DLL? Lets follow these steps:</span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">1. Download &amp; Install debugging tools for windows from <a href="https://www.microsoft.com/whdc/devtools/debugging/installx86.Mspx">https://www.microsoft.com/whdc/devtools/debugging/installx86.Mspx</a></span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">2. Create "Win32 Console Application" using VS 2008</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">3. Select Application type as "DLL" and click "Finish" .</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><img src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%203_2.jpg" original-url="https://blogs.msdn.com/blogfiles/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%203_2.jpg" alt="" /></span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">4. Add a "Module-Definition File (.def)" called "wdbrowser" to the project. One way to export your extension function is by specifying the function names in the EXPORTS section of the .def file. You may you use other ways of exporting functions, such as __dllexport</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><img src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%204_4.jpg" original-url="https://blogs.msdn.com/blogfiles/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%204_4.jpg" alt="" /></span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">5. Configure the project "Additional include Directories" to point to header files that comes with Windbg. Default folder for x86 is "C:\Program Files\Debugging Tools for Windows (x86)\sdk\inc"</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">6. Configure the project "Additional Library Directories" to point to library files that comes with Windbg. Default folder&nbsp; for x86 libraries&nbsp; is&nbsp; ""C:\Program Files\Debugging Tools for Windows (x86)\sdk\lib\i386""</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">7. The library, "dbgeng.lib " &amp; "dbgeng.dll" has the implementation of the Debug engine exported functions. So, add "dbgeng.lib" in "Additional Dependencies".</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">8. Add name of the module definition file created at the above Step #3</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><img src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%208_2.jpg" original-url="https://blogs.msdn.com/blogfiles/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step%208_2.jpg" alt="" /></span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">9. Now Include the following required headers files in "stdafx.h"</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;windows.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;imagehlp.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;wdbgexts.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;dbgeng.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;extsfns.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">10. Declare following two global variables in your extension project main implementation file.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//Version.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">EXT_API_VERSION g_ExtApiVersion = {1,1,EXT_API_VERSION_NUMBER,0} ;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">WINDBG_EXTENSION_APIS ExtensionApis = {0};</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">11. Declare following debug engine COM interface pointers.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugAdvanced2*&nbsp; gAdvancedDebug2=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugControl4*&nbsp;&nbsp; gDebugControl4=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugControl*&nbsp;&nbsp;&nbsp; gExecuteCmd=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugClient*&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; gDebugClient=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">12. Next step is to declare and implement <strong><em>WinDbgExtensionDllInit </em></strong>function in your DLL main implementation source file. In this example that is "wdbrowser.cpp" . The WinDbgExntensionDllInit is the first function that will be called by windbg . So, this function is the idle for implementing any extension specific initialization or related functionality. Please refer <a href="https://msdn.microsoft.com/en-us/library/cc267872.aspx">https://msdn.microsoft.com/en-us/library/cc267872.aspx</a> for more details about this function.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">VOID WDBGAPI WinDbgExtensionDllInit (PWINDBG_EXTENSION_APIS lpExtensionApis, USHORT usMajorVersion, USHORT usMinorVersion)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ExtensionApis = *lpExtensionApis;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; HRESULT hResult = S_FALSE;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (hResult = DebugCreate(__uuidof(IDebugClient), (void**) &amp;gDebugClient) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; dprintf("Acuqiring IDebugClient* Failled\n\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (hResult = gDebugClient-&gt;QueryInterface(__uuidof(IDebugControl), (void**) &amp;gExecuteCmd) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; dprintf("Acuqiring IDebugControl* Failled\n\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (hResult = gDebugClient-&gt;QueryInterface(__uuidof(IDebugAdvanced2), (void**) &amp;gAdvancedDebug2) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; dprintf("Acuqiring IDebugAdvanced2* Failled\n\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (hResult = gDebugClient-&gt;QueryInterface(__uuidof(IDebugControl4), (void**) &amp;gDebugControl4) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; dprintf("Acuqiring IDebugControl4* Failled\n\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">13. Declare another exported function <strong><em>ExtensionApiVersion</em></strong> to report the version of your extension to windbg. Please refer to <a href="https://msdn.microsoft.com/en-us/library/cc267873.aspx">https://msdn.microsoft.com/en-us/library/cc267873.aspx</a> for detailed information about this function.</span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">LPEXT_API_VERSION WDBGAPI ExtensionApiVersion (void)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; return &amp;g_ExtApiVersion;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p>&nbsp;</p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">14. Define Debug engine's interface pointers, so that your extension module can interact with debug engine. For more information please refer</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><a href="https://msdn.microsoft.com/en-us/library/cc265976.aspx">https://msdn.microsoft.com/en-us/library/cc265976.aspx</a>&nbsp; - IDebugClient, <a href="https://msdn.microsoft.com/en-us/library/cc266102.aspx">https://msdn.microsoft.com/en-us/library/cc266102.aspx</a> - IDebugControl</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><a href="https://msdn.microsoft.com/en-us/library/cc265957.aspx">https://msdn.microsoft.com/en-us/library/cc265957.aspx</a> - IDebugAdvanced</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugAdvanced2* gAdvancedDebug2=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugControl4* gDebugControl4=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugControl* gExecuteCmd=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">IDebugClient*&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; gDebugClient=NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">15. Next step is to - implement debug engine's callback interface <strong><em>IDebugOutputCallbacks</em></strong> . Debug engine callbacks your implementation of IDebugOutCallbacks::Output() with output as a result of the commands that are executed by your extension function.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">Refer to <a href="https://msdn.microsoft.com/en-us/library/cc265716.aspx">https://msdn.microsoft.com/en-us/library/cc265716.aspx</a>&nbsp;&nbsp; for detailed information about IDebugOutputCallbacks::Output()</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">16. Add the following new class in a header file that inherits the <strong><em>IDebugOutputCallbacks</em></strong> interface .</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#ifndef __OUT_HPP__</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#define __OUT_HPP__</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;string&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;sstream&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">class StdioOutputCallbacks : public IDebugOutputCallbacks</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">private:</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; std::string m_OutputBuffer;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //This buffer holds the output from the command execution.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; CHAR m_OutPutBuffer[4096];</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">public:</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; void InitOutPutBuffer();</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; std::string GetOutputBuffer()</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return m_OutputBuffer;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; };</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; void ClearOutPutBuffer()&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; m_OutputBuffer = "";</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; };</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; STDMETHOD(QueryInterface)(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; THIS_</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; IN REFIID InterfaceId,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; OUT PVOID* Interface</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; );</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; STDMETHOD_(ULONG, AddRef)(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; THIS</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; );</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; STDMETHOD_(ULONG, Release)(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; THIS</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; );</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; // IDebugOutputCallbacks.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; STDMETHOD(Output)(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; THIS_</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; IN ULONG Mask,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; IN PCSTR Text</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; );</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">};</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">extern StdioOutputCallbacks g_OutputCb;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#endif // #ifndef __OUT_HPP__</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">17. Add the following code that implements the <strong><em>IDebugOutputCallbacks </em></strong>interface methods, especially Output()</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include "stdafx.h"</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;stdio.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;windows.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include &lt;dbgeng.h&gt;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">#include "OutputCallBack.h"</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">StdioOutputCallbacks g_OutputCb;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">STDMETHODIMP</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">StdioOutputCallbacks::QueryInterface(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; THIS_</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; IN REFIID InterfaceId,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; OUT PVOID* Interface</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; )</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; *Interface = NULL;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; if (IsEqualIID(InterfaceId, __uuidof(IUnknown)) ||</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; IsEqualIID(InterfaceId, __uuidof(IDebugOutputCallbacks)))</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; *Interface = (IDebugOutputCallbacks *)this;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; AddRef();</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return S_OK;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; else</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; {</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return E_NOINTERFACE;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; }</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">STDMETHODIMP_(ULONG)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">StdioOutputCallbacks::AddRef(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; THIS</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; )</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; // This class is designed to be static so</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; // there's no true refcount.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; return 1;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">STDMETHODIMP_(ULONG)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">StdioOutputCallbacks::Release(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; THIS</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; )</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; // This class is designed to be static so</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; // there's no true refcount.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; return 0;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">STDMETHODIMP</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">StdioOutputCallbacks::Output(</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; THIS_</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; IN ULONG Mask,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; IN PCSTR Text</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; )</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; UNREFERENCED_PARAMETER(Mask);</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; m_OutputBuffer += Text;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp; return S_OK;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">void StdioOutputCallbacks::InitOutPutBuffer()</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; m_OutputBuffer.erase();</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">18. Add implementation of your extension function. In this example, we choose to implement an extension that displays the variable names, types in the frame 2 of the current thread. The implementation is:</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DECLARE_API (dvf3)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">// Install output callbacks.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">if ((gDebugClient-&gt;SetOutputCallbacks((PDEBUG_OUTPUT_CALLBACKS) &amp;g_OutputCb))!= S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">dprintf("*****Error while installing Outputcallback.*****\n\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">// Since frame count starts from 0 index, we have to pass 2 as parameter for .frame command for the frame# 2</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//Execute command to extrac 2nd frame.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">if (gExecuteCmd-&gt;Execute(DEBUG_OUTCTL_THIS_CLIENT | //Send output to only outputcallbacks</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_OUTCTL_OVERRIDE_MASK |</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_OUTCTL_NOT_LOGGED,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">".frame 2",</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_EXECUTE_DEFAULT ) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">dprintf("Executing .frame 2 failled\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">//Execute command to extrac 2nd frame.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">if (gExecuteCmd-&gt;Execute(DEBUG_OUTCTL_THIS_CLIENT | //Send output to only outputcallbacks</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_OUTCTL_OVERRIDE_MASK |</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_OUTCTL_NOT_LOGGED,</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">"dv /i /t /v",</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">DEBUG_EXECUTE_DEFAULT ) != S_OK)</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">{</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">dprintf("Executing dv /i /t /v failled\n");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">return;</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">dprintf("***** Extracting locals &amp; formal params from frame 2 *****");</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">dprintf("\n%s\n", g_OutputCb.GetOutputBuffer().c_str());</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">}</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">19. Re-build the project. Copy the .DLL from release folder to a folder where Windbg looks for extension DLLs.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">On x86 machine default location is&nbsp; "&lt;Drive letter&gt;\Program Files\Debugging Tools for Windows (x86)\winext"</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">20. The extension is ready for the use or test.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">21. Start windbg and open a full user mode dump. Type .load myextension and hit enter to load the extension DLL into Windbg process space</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><img src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step21_2.jpg" original-url="https://blogs.msdn.com/blogfiles/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step21_2.jpg" alt="" /></span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">22. Run .chain command to verify if your extension is loaded by WinDbg . you will see output similar to below output, if your extension is loaded.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">23. Type !dvf3 to run the extension function for extracting and displaying variable names, types from the frame 2 .</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><img src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step23_2.jpg" original-url="https://blogs.msdn.com/blogfiles/sqlblog/WindowsLiveWriter/ToolsoftheTradePartIVDevelopingWinDbgExt_AA0D/Step23_2.jpg" alt="" /></span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">Additional references:</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><a href="https://msdn.microsoft.com/en-us/library/cc265826.aspx">https://msdn.microsoft.com/en-us/library/cc265826.aspx</a> - describes about how to Interact with debug engine, I/O operations with debug engine, Memory access, Using symbols, source files.</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;"><a href="https://www.codeplex.com/ODbgExt">https://www.codeplex.com/ODbgExt</a>&nbsp; - Microsoft Open Debugger Extension for Windbg</span></p>
<p><span style="font-family: tahoma,arial,helvetica,sans-serif; font-size: small;">Happy developing debug engine extensions!</span></p>]]></content:encoded>
    </item>
    <item>
      <title>Max. Number of servers a transaction can be propagated using DTC</title>
      <link>https://docs.microsoft.com/archive/blogs/sgajjela/max-number-of-servers-a-transaction-can-be-propagated-using-dtc</link>
      <pubDate>Thu, 23 Feb 2012 09:00:44 GMT</pubDate>
      <dc:creator><![CDATA[Srini Gajjela]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/sgajjela/2012/02/23/max-number-of-servers-a-transaction-can-be-propagated-using-dtc/</guid>
      <description><![CDATA[The Issue:
We recently worked on a customer issue, where a distributed SQL query was executed in a...]]></description>
      <content:encoded><![CDATA[<p><b>The Issue:</b></p>
<p><span style="font-size: small;">We recently worked on a customer issue, where a distributed SQL query was executed in a single transaction using&nbsp; SQL &nbsp;&ndash; SQL&nbsp; &nbsp;as linked server. The 2<sup>nd</sup> SQL Server has about 80 linked servers defined to 80 different remote SQL Servers.&nbsp; The distributed query updates a table, which has update trigger defined.&nbsp; The update trigger was implemented to execute distributed queries to more than 65 different SQL linked servers.</span></p>
<p><span style="font-size: small;">&nbsp;The distributed query that was executed in transaction scope was failing with following error</span></p>
<p>&nbsp;</p>
<p><strong><span style="color: #ff0000; font-size: small;">The OLE DB provider "SQLNCLI10" for linked server "&lt;Name of the linked Server&gt;" reported an error. The provider reported an unexpected catastrophic failure.</span></strong></p>
<p><strong><span style="color: #ff0000; font-size: small;">&nbsp;Error: 7391, Severity: 16, State: 2</span></strong></p>
<p><strong><span style="color: #ff0000; font-size: small;">&nbsp;The operation could not be performed because OLE DB provider "SQLNCLI10" for linked server "&lt;Name of the Linked Server&gt;" was unable to begin a distributed transaction.</span></strong></p>
<p>&nbsp;</p>
<p><span style="font-size: small;">Since the error indicates some challenges in starting the distributed transaction, we collected MS DTC ETW traces and analyzed.</span></p>
<p>&nbsp;</p>
<p><span style="font-size: small;">As per the traces, the query execution was successful when the table update trigger executed distributed queries in &nbsp;less than or equal&nbsp; to&nbsp; 64 number of linked servers:</span></p>
<p><span style="font-size: small;">'&ldquo;;"transaction propagated to &lt; Name of the linked Serve &gt; as transaction child node #1"</span></p>
<p><span style="font-size: small;">&hellip;.</span></p>
<p><span style="font-size: small;">'&ldquo;;"transaction propagated to &lt; Name of the linked Serve &gt; as transaction child node #64"</span></p>
<p>&nbsp;</p>
<p><span style="font-size: small;">But failed when trigger executed distributed queries on the 65<sup>th </sup>linked servers and logged following error</span></p>
<p>&nbsp;</p>
<p><strong><span style="color: #ff0000; font-size: small;"><i>'" ;"failed to propagate transaction to child node &lt; Name of the linked Serve &gt;&nbsp; because the limit on the number of children has been reached at the local transaction manager"</i></span></strong></p>
<p>&nbsp;</p>
<p><span style="font-size: small;"><b>The Cause:</b></span></p>
<p><span style="font-size: small;">We found the issue is by design as the MSDTC is designed to communicate, maximum up to only 64 DTC transaction managers &nbsp;&nbsp;in a single transaction. The solution is to make sure a single transaction is not propagated for more than 64 servers/ DTC transaction managers.</span></p>
<p><span style="font-size: small;"></span>&nbsp;</p>
<p><span style="font-size: small;">Reviewed by: </span><strong><span style="font-size: small;">David Qiu - Escalation Engineer at Microsoft.</span></strong></p>]]></content:encoded>
    </item>
    <item>
      <title>Accessing rowset after committing a transaction</title>
      <link>https://docs.microsoft.com/archive/blogs/sgajjela/accessing-rowset-after-committing-a-transaction</link>
      <pubDate>Sun, 12 Feb 2012 15:56:25 GMT</pubDate>
      <dc:creator><![CDATA[Srini Gajjela]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/sgajjela/2012/02/12/accessing-rowset-after-committing-a-transaction/</guid>
      <description><![CDATA[The rowset full functionality is either preserved or rowset enters into zombie state, after...]]></description>
      <content:encoded><![CDATA[<p>The rowset full functionality is either preserved or rowset enters into zombie state, after completing a transaction.</p>
<p>If the rowset needs to be preserved after committing a transaction, to add or fetch new rows, delete or update existing, the cursor type must be explicitly set to use server side cursor in conjunction with preserve rowset after commit (DBPROP_COMMITPRESERVE) setting.</p>
<p>&nbsp;While accessing the rows in the rowset after commit generates following error, If the rowset was created with preserve after commit property, but not using server side cursor,</p>
<p>&nbsp;<i>HRESULT&nbsp; = -2147418113</i></p>
<p><i>Error Source:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Microsoft SQL Server Native Client 10.0</i></p>
<p><i>Error Description: The object is in a zombie state. An object may enter a zombie state when either ITransaction::Commit or ITransaction::Abort is called, or when a storage object was created and not yet released. SQLSTATE and SQLCODE not supplied</i></p>
<p>&nbsp;</p>
<p>The reason is &ndash;</p>
<p>Either default cursor type or client side cursor does not preserve cursor, even with preserve rowset after commit setting.&nbsp; Hence, use the server side cursor in conjunction with preserve rowset after commit to add or fetch new rows and delete or update existing rows after committing a transaction.</p>
<p>&nbsp;</p>
<p style="padding-left: 30px;"><strong>-&nbsp;Configuration to preserve the cursor after committing a transaction&nbsp;</strong></p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].dwPropertyID&nbsp;&nbsp; = DBPROP_COMMITPRESERVE;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].dwOptions&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; = DBPROPOPTIONS_REQUIRED;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].colid&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; = DB_NULLID;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].vValue.vt &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;= VT_BOOL;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].vValue.boolVal = VARIANT_TRUE;</p>
<p>&nbsp;&nbsp;</p>
<p style="padding-left: 30px;"><strong>-&nbsp; Configuration to use the Server side cursor</strong></p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].dwPropertyID&nbsp;&nbsp; = DBPROP_SERVERCURSOR;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].dwOptions&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; = DBPROPOPTIONS_REQUIRED;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].colid&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; = DB_NULLID;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].vValue.vt&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; = VT_BOOL;</p>
<p style="padding-left: 30px;">&nbsp;&nbsp; rgProperties[DBPropInddex].vValue.boolVal = VARIANT_TRUE;</p>
<p style="padding-left: 30px;">&nbsp;</p>]]></content:encoded>
    </item>
  </channel>
</rss>