|   <chapter id="debugger"> | 
 |     <title>Debugging Wine</title> | 
 |  | 
 |     <sect1 id="dbg-intro"> | 
 |       <title>Introduction</title> | 
 |  | 
 |       <sect2> | 
 |         <title>Processes and threads: in underlying OS and in Windows</title> | 
 |  | 
 |         <para> | 
 |           Before going into the depths of debugging in Wine, here's | 
 |           a small overview of process and thread handling in Wine. | 
 |           It has to be clear that there are two different beasts: | 
 |           processes/threads from the Unix point of view and | 
 |           processes/threads from a Windows point of view. | 
 |         </para> | 
 |         <para> | 
 |           Each Windows' thread is implemented as a Unix thread, meaning | 
 |           that all threads of a same Windows' process share the same | 
 |           (unix) address space. | 
 |         </para> | 
 |         <para> | 
 |           In the following: | 
 |         </para> | 
 |         <itemizedlist> | 
 |           <listitem> | 
 |             <para> | 
 |               <varname>W-process</varname> means a process in Windows' terminology | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               <varname>U-process</varname> means a process in Unix' terminology | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               <varname>W-thread</varname> means a thread in Windows' terminology | 
 |             </para> | 
 |           </listitem> | 
 |         </itemizedlist> | 
 |         <para> | 
 |           A <varname>W-process</varname> is made of one or several | 
 |           <varname>W-threads</varname>. Each | 
 |           <varname>W-thread</varname> is mapped to one and only one | 
 |           <varname>U-process</varname>. All | 
 |           <varname>U-processes</varname> of a same | 
 |           <varname>W-process</varname> share the same address space. | 
 |         </para> | 
 |         <para> | 
 |           Each Unix process can be identified by two values: | 
 |         </para> | 
 |         <itemizedlist> | 
 |           <listitem> | 
 |             <para> | 
 |               the Unix process id (<varname>upid</varname> in the following) | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               the Windows's thread id (<varname>tid</varname>) | 
 |             </para> | 
 |           </listitem> | 
 |         </itemizedlist> | 
 |         <para> | 
 |           Each Windows' process has also a Windows' process id | 
 |           (<varname>wpid</varname> in the following). It must be clear | 
 |           that <varname>upid</varname> and <varname>wpid</varname> are | 
 |           different and shall not be used instead of the other. | 
 |         </para> | 
 |         <para> | 
 |           <varname>Wpid</varname> and <varname>tid</varname> are | 
 |           defined (Windows) system wide. They must not be confused | 
 |           with process or thread handles which, as any handle, is an | 
 |           indirection to a system object (in this case process or | 
 |           thread). A same process can have several different handles | 
 |           on the same kernel object. The handles can be defined as | 
 |           local (the values is only valid in a process), or system | 
 |           wide (the same handle can be used by any | 
 |           <varname>W-process</varname>). | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Wine, debugging and WineDbg</title> | 
 |  | 
 |         <para> | 
 |           When talking of debugging in Wine, there are at least two | 
 |           levels to think of: | 
 |         </para> | 
 |         <itemizedlist> | 
 |           <listitem> | 
 |             <para> | 
 |               the Windows' debugging API. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               the Wine integrated debugger, dubbed <command>winedbg</command>. | 
 |             </para> | 
 |           </listitem> | 
 |         </itemizedlist> | 
 |         <para> | 
 |           Wine implements most of the Windows' debugging API. The | 
 | 	  first part of the debugging APIs (in | 
 | 	  <filename>KERNEL32.DLL</filename>) allows a W-process, called | 
 | 	  the debugger, to control the execution of another W-process, | 
 | 	  the debuggee. To control means stopping/resuming execution, | 
 | 	  enabling/disabling single stepping, setting breakpoints, | 
 | 	  reading/writing debuggee memory... Another part of the | 
 | 	  debugging APIs resides in <filename>DBGHELP.DLL</filename> | 
 | 	  (and its ancestor <filename>IMAGEHLP.DLL</filename>) and lets | 
 | 	  a debugger look into symbols and types from any module (if | 
 | 	  the module has been compiled with the proper options).  | 
 |         </para> | 
 |         <para> | 
 |           <command>winedbg</command> is a Winelib application making | 
 |           use of these APIs (<filename>KERNEL32.DLL</filename>'s | 
 | 	  debugging API and <filename>DBGHELP.DLL</filename>) to allow | 
 | 	  debugging both any Wine or Winelib applications as well as | 
 | 	  Wine itself (kernel and all DLLs). | 
 |         </para> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |  | 
 |     <sect1 id="dbg-modes"> | 
 |       <title>WineDbg's modes of invocation</title> | 
 |  | 
 |       <sect2> | 
 |         <title>Starting a process</title> | 
 |  | 
 |         <para> | 
 |           Any application (either a Windows' native executable, or a | 
 |           Winelib application) can be run through | 
 |           <command>winedbg</command>. Command line options and tricks | 
 |           are the same as for wine: | 
 |         </para> | 
 |         <screen> | 
 | winedbg telnet.exe | 
 | winedbg hl.exe -windowed | 
 |         </screen> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Attaching</title> | 
 |  | 
 |         <para> | 
 |           <command>winedbg</command> can also be launched without any | 
 |           command line argument: <command>winedbg</command> is started | 
 |           without any attached process. You can get a list of running | 
 |           <varname>W-processes</varname> (and their | 
 |           <varname>wpid</varname>'s) using the <command>info | 
 |             process</command> command, and then, with the | 
 |           <command>attach</command> command, pick up the | 
 |           <varname>wpid</varname> of the <varname>W-process</varname> | 
 |           you want to debug. This is a neat feature as it allows you | 
 | 	  to debug an already started application. | 
 | 	 </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2 id="dbg-on-exception"> | 
 |         <title id="dbg-exception-title">On exceptions</title> | 
 |  | 
 |         <para> | 
 |           When something goes wrong, Windows tracks this as an | 
 |           exception. Exceptions exist for segmentation violation, | 
 |           stack overflow, division by zero, etc. | 
 |         </para> | 
 |         <para> | 
 |           When an exception occurs, Wine checks if the | 
 | 	  <varname>W-process</varname> is debugged. If so, the | 
 | 	  exception event is sent to the debugger, which takes care of | 
 | 	  it: end of the story. This mechanism is part of the standard | 
 | 	  Windows' debugging API. | 
 |         </para> | 
 |         <para> | 
 |           If the <varname>W-process</varname> is not debugged, Wine | 
 |           tries to launch a debugger. This debugger (normally | 
 |           <command>winedbg</command>, see III Configuration for more | 
 |           details), at startup, attaches to the | 
 |           <varname>W-process</varname> which generated the exception | 
 |           event. In this case, you are able to look at the causes of | 
 |           the exception, and either fix the causes (and continue | 
 |           further the execution) or dig deeper to understand what went | 
 |           wrong. | 
 |         </para> | 
 |         <para> | 
 |           If <command>winedbg</command> is the standard debugger, the | 
 |           <command>pass</command> and <command>cont</command> commands | 
 |           are the two ways to let the process go further for the | 
 |           handling of the  exception event. | 
 |         </para> | 
 |         <para> | 
 |           To be more precise on the way Wine (and Windows) generates | 
 |           exception events, when a fault occurs (segmentation | 
 |           violation, stack overflow...), the event is first sent to | 
 |           the debugger (this is known as a first chance exception). | 
 |           The debugger can give two answers: | 
 |         </para> | 
 |  | 
 |         <variablelist> | 
 |           <varlistentry> | 
 |             <term>continue</term> | 
 |             <listitem> | 
 |               <para> | 
 |                 the debugger had the ability to correct what's | 
 |                 generated the exception, and is now able to continue | 
 |                 process execution. | 
 |               </para> | 
 |             </listitem> | 
 |           </varlistentry> | 
 |           <varlistentry> | 
 |             <term>pass</term> | 
 |             <listitem> | 
 |               <para> | 
 |                 the debugger couldn't correct the cause of the | 
 |                 first chance exception. Wine will now try to walk | 
 |                 the list of exception handlers to see if one of them | 
 |                 can handle the exception. If no exception handler is | 
 |                 found, the exception is sent once again to the | 
 |                 debugger to indicate the failure of the exception | 
 |                 handling. | 
 |               </para> | 
 |             </listitem> | 
 |           </varlistentry> | 
 |         </variablelist> | 
 |         <note> | 
 |           <para> | 
 |             since some of Wine's code uses exceptions and | 
 |             <function>try/catch</function> blocks to provide some | 
 |             functionality, <command>winedbg</command> can be entered | 
 |             in such cases with segv exceptions. This happens, for | 
 |             example, with <function>IsBadReadPtr</function> function. | 
 |             In that case, the <command>pass</command> command shall be | 
 |             used, to let the handling of the exception to be done by | 
 |             the <function>catch</function> block in | 
 |             <function>IsBadReadPtr</function>. | 
 |           </para> | 
 |         </note> | 
 |       </sect2> | 
 |  | 
 |       <sect2 id="interrupt"> | 
 |         <title>Interrupting</title> | 
 |  | 
 | 	<para> | 
 | 	  You can stop the debugger while it's running by hitting | 
 | 	  Ctrl-C in its window. This will stop the debugged process, | 
 | 	  and let you manipulate the current context. | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Quitting</title> | 
 |  | 
 |         <para> | 
 | 	  Wine supports the new XP APIs, allowing for a debugger to | 
 | 	  detach from a program being debugged (see | 
 | 	  <command>detach</command> command). | 
 |         </para> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |  | 
 |     <sect1 id="wine-debugger"> | 
 |       <title>Using the Wine Debugger</title> | 
 |  | 
 |       <para> | 
 |         This section describes where to start debugging Wine. If at any | 
 |         point you get stuck and want to ask for help, please read the | 
 |         <emphasis>How to Report A Bug</emphasis> section of the  | 
 |         <emphasis>Wine Users Guide</emphasis> for information on how to write | 
 |         useful bug reports. | 
 |       </para> | 
 |  | 
 |       <sect2> | 
 |         <title>Crashes</title> | 
 |  | 
 |         <para> | 
 |           These usually show up like this: | 
 |         </para> | 
 |         <screen> | 
 | |Unexpected Windows program segfault - opcode = 8b | 
 | |Segmentation fault in Windows program 1b7:c41. | 
 | |Loading symbols from ELF file /root/wine/wine... | 
 | |....more Loading symbols from ... | 
 | |In 16 bit mode. | 
 | |Register dump: | 
 | | CS:01b7 SS:016f DS:0287 ES:0000 | 
 | | IP:0c41 SP:878a BP:8796 FLAGS:0246 | 
 | | AX:811e BX:0000 CX:0000 DX:0000 SI:0001 DI:ffff | 
 | |Stack dump: | 
 | |0x016f:0x878a:  0001 016f ffed 0000 0000 0287 890b 1e5b | 
 | |0x016f:0x879a:  01b7 0001 000d 1050 08b7 016f 0001 000d | 
 | |0x016f:0x87aa:  000a 0003 0004 0000 0007 0007 0190 0000 | 
 | |0x016f:0x87ba: | 
 | | | 
 | |0050: sel=0287 base=40211d30 limit=0b93f (bytes) 16-bit rw- | 
 | |Backtrace: | 
 | |0 0x01b7:0x0c41 (PXSRV_FONGETFACENAME+0x7c) | 
 | |1 0x01b7:0x1e5b (PXSRV_FONPUTCATFONT+0x2cd) | 
 | |2 0x01a7:0x05aa | 
 | |3 0x01b7:0x0768 (PXSRV_FONINITFONTS+0x81) | 
 | |4 0x014f:0x03ed (PDOXWIN_@SQLCURCB$Q6CBTYPEULN8CBSCTYPE+0x1b1) | 
 | |5 0x013f:0x00ac | 
 | | | 
 | |0x01b7:0x0c41 (PXSRV_FONGETFACENAME+0x7c):  movw        %es:0x38(%bx),%dx | 
 |         </screen> | 
 |         <para> | 
 |           Steps to debug a crash. You may stop at any step, but please | 
 |           report the bug and provide as much of the information | 
 |           gathered to the bug report as feasible. | 
 |         </para> | 
 |  | 
 |         <orderedlist> | 
 |           <listitem> | 
 |             <para> | 
 |               Get the reason for the crash. This is usually an access to | 
 |               an invalid selector, an access to an out of range address | 
 |               in a valid selector, popping a segment register from the | 
 |               stack or the like. When reporting a crash, report this | 
 |               <emphasis>whole</emphasis> crashdump even if it doesn't | 
 |               make sense to you. | 
 |             </para> | 
 |             <para> | 
 |               (In this case it is access to an invalid selector, for | 
 |               <systemitem>%es</systemitem> is <literal>0000</literal>, as | 
 |               seen in the register dump). | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               Determine the cause of the crash. Since this is usually | 
 |               a primary/secondary reaction to a failed or misbehaving | 
 |               Wine function, rerun Wine with the<parameter>WINEDEBUG=+relay</parameter> | 
 |               environment variable set. This will | 
 |               generate quite a lot of output, but usually the reason is | 
 |               located in the last call(s).  Those lines usually look like | 
 |               this: | 
 |             </para> | 
 |             <screen> | 
 | |Call KERNEL.90: LSTRLEN(0227:0692 "text") ret=01e7:2ce7 ds=0227 | 
 |       ^^^^^^^^^  ^       ^^^^^^^^^ ^^^^^^      ^^^^^^^^^    ^^^^ | 
 |       |          |       |         |           |            |Datasegment | 
 |       |          |       |         |           |Return address | 
 |       |          |       |         |textual parameter | 
 |       |          |       | | 
 |       |          |       |Argument(s). This one is a win16 segmented pointer. | 
 |       |          |Function called. | 
 |       |The module, the function is called in. In this case it is KERNEL. | 
 |  | 
 | |Ret  KERNEL.90: LSTRLEN() retval=0x0004 ret=01e7:2ce7 ds=0227 | 
 |                                   ^^^^^^ | 
 | 				  |Returnvalue is 16 bit and has the value 4. | 
 |             </screen> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               If you have found a misbehaving function, try to find out | 
 |               why it misbehaves. Find the function in the source code. | 
 |               Try to make sense of the arguments passed. Usually there is | 
 |               a <function>WINE_DEFAULT_DEBUG_CHANNEL(<channel>);</function> | 
 |               at the beginning of the file. Rerun wine with the | 
 |               <parameter>WINEDEBUG=+xyz,+relay</parameter> environment variable set. | 
 |             </para> | 
 |             <para> | 
 |               Occasionally there are additional debug channels defined at the  | 
 |               beginning of the file in the form. | 
 |               <function>WINE_DECLARE_DEBUG_CHANNEL(<channel>);</function> | 
 |               If so the offending function may also uses one of these alternate | 
 |               channels. Look through the the function for   | 
 |              <function>TRACE_(<channel>)(" ... /n");</function> and add any | 
 |              additional channels to the commandline. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               Additional information on how to debug using the internal | 
 |               debugger can be  found in | 
 |               <filename>programs/winedbg/README</filename>. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               If this information isn't clear enough or if you want to | 
 |               know more about what's happening in the function itself, | 
 |               try running wine with <parameter>WINEDEBUG=+all</parameter>, | 
 |               which dumps ALL included debug | 
 |               information in wine. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               If even that isn't enough, add more debug output for yourself  | 
 |               into the functions you find relevant. See The section on Debug  | 
 |               Logging in this guide for more information. You might | 
 |               also try to run the program in <command>gdb</command> | 
 |               instead of using the Wine debugger. If you do that, use | 
 |               <parameter>handle SIGSEGV nostop noprint</parameter> to | 
 |               disable the handling of seg faults inside | 
 |               <command>gdb</command> (needed for Win16).  | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               You can also set a breakpoint for that function. Start wine  | 
 |               useing <command>winedbg</command> instead of  | 
 |               <command>wine</command>. Once the debugger is is running enter  | 
 |               <command>break</command> <parameter>KERNEL_LSTRLEN</parameter> | 
 |               (replace by function you want to debug, CASE IS RELEVANT)  | 
 |               to set a breakpoint.  Then | 
 |               use <command>continue</command> to start normal | 
 |               program-execution. Wine will stop if it reaches the | 
 |               breakpoint. If the program isn't yet at the crashing call | 
 |               of that function, use <command>continue</command> again | 
 |               until you are about to enter that function. You may now | 
 |               proceed with single-stepping the function until you reach | 
 |               the point of crash. Use the other debugger commands to | 
 |               print registers and the like. | 
 |             </para> | 
 |           </listitem> | 
 |         </orderedlist> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Program hangs, nothing happens</title> | 
 |  | 
 |         <para> | 
 |           Start the program with <command>winedbg</command> instead of | 
 |           <command>wine</command>. When the program locks up switch to the  | 
 |           winedbg's terminal and press  | 
 |           <keycombo><keycap>Ctrl</keycap><keycap>C</keycap></keycombo>. this | 
 |           will stop the program and let you debug the program as you would for | 
 |           a crash.  | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Program reports an error with a Messagebox</title> | 
 |  | 
 |         <para> | 
 |           Sometimes programs are reporting failure using more or | 
 |           less nondescript messageboxes. We can debug this using the | 
 |           same method as Crashes, but there is one problem... For | 
 |           setting up a message box the program also calls Wine | 
 |           producing huge chunks of debug code. | 
 |         </para> | 
 |         <para> | 
 |           Since the failure happens usually directly before setting up | 
 |           the Messagebox you can start winedbg and set a | 
 |           breakpoint at <function>MessageBoxA</function> (called by win16 | 
 |           and win32 programs) and proceed with | 
 |           <command>continue</command>. With <parameter>WINEDEBUG=+all</parameter> | 
 |           Wine will now stop directly before setting | 
 |           up the Messagebox. Proceed as explained above. | 
 |         </para> | 
 |         <para> | 
 |           You can also run wine using <command>WINEDEBUG=+relay wine | 
 |             program.exe 2>&1 | less -i</command> and in | 
 |           <command>less</command> search for <quote>MessageBox</quote>. | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Disassembling programs</title> | 
 |  | 
 |         <para> | 
 |           You may also try to disassemble the offending program to | 
 |           check for undocumented features and/or use of them. | 
 |         </para> | 
 |         <para> | 
 |           The best, freely available, disassembler for Win16 programs is | 
 |           <application>Windows Codeback</application>, archive name | 
 |           <filename>wcbxxx.zip</> (e.g. <filename>wcb105a.zip</>), which | 
 |           usually can be found in the <filename>Cica-Mirror</filename> | 
 |           subdirectory on the Wine ftp sites. (See <filename>ANNOUNCE</>). | 
 |         </para> | 
 |         <para> | 
 |           Disassembling win32 programs is possible using | 
 |           <application>Windows Disassembler 32</>. Look for | 
 |           a file called <filename>w32dsm87.zip</> (or similar) | 
 |           on <ulink url="http://www.winsite.com/">http://www.winsite.com</> | 
 |           and mirrors.  The shareware version does not allow saving of | 
 |           disassembly listings. You can also use the newer (and in the | 
 |           full version better) <application>Interactive | 
 |             Disassembler</application> (IDA) from the ftp sites mentioned | 
 |           at the end of the document. Understanding disassembled code is | 
 |           mostly a question of exercise. | 
 |         </para> | 
 |         <para> | 
 |           Most code out there uses standard C function entries (for it | 
 |           is usually  written in C). Win16 function entries usually | 
 |           look like that: | 
 |         </para> | 
 |         <programlisting> | 
 | push bp | 
 | mov bp, sp | 
 | ... function code .. | 
 | retf XXXX 	<--------- XXXX is number of bytes of arguments | 
 |         </programlisting> | 
 |         <para> | 
 |           This is a <function>FAR</function> function with no local | 
 |           storage. The arguments usually start at | 
 |           <literal>[bp+6]</literal> with increasing offsets. Note, that | 
 |           <literal>[bp+6]</literal> belongs to the | 
 |           <emphasis>rightmost</emphasis> argument, for exported win16 | 
 |           functions use the PASCAL calling convention. So, if we use | 
 |           <function>strcmp(a,b)</function> with <parameter>a</parameter> | 
 |           and <parameter>b</parameter> both 32 bit variables | 
 |           <parameter>b</parameter> would be at <literal>[bp+6]</literal> | 
 |           and <parameter>a</parameter> at <literal>[bp+10]</literal>. | 
 |         </para> | 
 |         <para> | 
 |           Most functions make also use of local storage in the stackframe: | 
 |         </para> | 
 |         <programlisting> | 
 | enter 0086, 00 | 
 | ... function code ... | 
 | leave | 
 | retf XXXX | 
 |         </programlisting> | 
 |         <para> | 
 |           This does mostly the same as above, but also adds | 
 |           <literal>0x86</literal> bytes of stackstorage, which is | 
 |           accessed using <literal>[bp-xx]</literal>. Before calling a | 
 |           function, arguments are pushed on the stack using something | 
 |           like this: | 
 |         </para> | 
 |         <programlisting> | 
 | push word ptr [bp-02]	<- will be at [bp+8] | 
 | push di			<- will be at [bp+6] | 
 | call KERNEL.LSTRLEN | 
 |         </programlisting> | 
 |         <para> | 
 |           Here first the selector and then the offset to the passed | 
 |           string are pushed. | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Sample debugging session</title> | 
 |  | 
 |         <para> | 
 |           Let's debug the infamous Word <filename>SHARE.EXE</filename> | 
 |           messagebox: | 
 |         </para> | 
 |         <screen> | 
 | |marcus@jet $ wine winword.exe | 
 | |            +---------------------------------------------+ | 
 | |            | !  You must leave Windows and load SHARE.EXE| | 
 | |            |    before starting Word.                    | | 
 | |            +---------------------------------------------+ | 
 |         </screen> | 
 |         <screen> | 
 | |marcus@jet $ WINEDEBUG=+relay,-debug wine winword.exe | 
 | |CallTo32(wndproc=0x40065bc0,hwnd=000001ac,msg=00000081,wp=00000000,lp=00000000) | 
 | |Win16 task 'winword': Breakpoint 1 at 0x01d7:0x001a | 
 | |CallTo16(func=0127:0070,ds=0927) | 
 | |Call WPROCS.24: TASK_RESCHEDULE() ret=00b7:1456 ds=0927 | 
 | |Ret  WPROCS.24: TASK_RESCHEDULE() retval=0x8672 ret=00b7:1456 ds=0927 | 
 | |CallTo16(func=01d7:001a,ds=0927) | 
 | |     AX=0000 BX=3cb4 CX=1f40 DX=0000 SI=0000 DI=0927 BP=0000 ES=11f7 | 
 | |Loading symbols: /home/marcus/wine/wine... | 
 | |Stopped on breakpoint 1 at 0x01d7:0x001a | 
 | |In 16 bit mode. | 
 | |Wine-dbg>break MessageBoxA                          <---- Set Breakpoint | 
 | |Breakpoint 2 at 0x40189100 (MessageBoxA [msgbox.c:190]) | 
 | |Wine-dbg>c                                            <---- Continue | 
 | |Call KERNEL.91: INITTASK() ret=0157:0022 ds=08a7 | 
 | |     AX=0000 BX=3cb4 CX=1f40 DX=0000 SI=0000 DI=08a7 ES=11d7 EFL=00000286 | 
 | |CallTo16(func=090f:085c,ds=0dcf,0x0000,0x0000,0x0000,0x0000,0x0800,0x0000,0x0000,0x0dcf) | 
 | |...                                                   <----- Much debugoutput | 
 | |Call KERNEL.136: GETDRIVETYPE(0x0000) ret=060f:097b ds=0927 | 
 |                                ^^^^^^ Drive 0 (A:) | 
 | |Ret  KERNEL.136: GETDRIVETYPE() retval=0x0002 ret=060f:097b ds=0927 | 
 |                                         ^^^^^^  DRIVE_REMOVEABLE | 
 | 						(It is a floppy diskdrive.) | 
 |  | 
 | |Call KERNEL.136: GETDRIVETYPE(0x0001) ret=060f:097b ds=0927 | 
 |                                ^^^^^^ Drive 1 (B:) | 
 | |Ret  KERNEL.136: GETDRIVETYPE() retval=0x0000 ret=060f:097b ds=0927 | 
 |                                         ^^^^^^  DRIVE_CANNOTDETERMINE | 
 | 						(I don't have drive B: assigned) | 
 |  | 
 | |Call KERNEL.136: GETDRIVETYPE(0x0002) ret=060f:097b ds=0927 | 
 |                                ^^^^^^^ Drive 2 (C:) | 
 | |Ret  KERNEL.136: GETDRIVETYPE() retval=0x0003 ret=060f:097b ds=0927 | 
 |                                         ^^^^^^ DRIVE_FIXED | 
 |                                                (specified as a harddisk) | 
 |  | 
 | |Call KERNEL.97: GETTEMPFILENAME(0x00c3,0x09278364"doc",0x0000,0927:8248) ret=060f:09b1 ds=0927 | 
 |                                  ^^^^^^           ^^^^^        ^^^^^^^^^ | 
 |                                  |                |            |buffer for fname | 
 |                                  |                |temporary name ~docXXXX.tmp | 
 |                                  |Force use of Drive C:. | 
 |  | 
 | |Warning: GetTempFileName returns 'C:~doc9281.tmp', which doesn't seem to be writeable. | 
 | |Please check your configuration file if this generates a failure. | 
 |         </screen> | 
 |         <para> | 
 |           Whoops, it even detects that something is wrong! | 
 |         </para> | 
 |         <screen> | 
 | |Ret  KERNEL.97: GETTEMPFILENAME() retval=0x9281 ret=060f:09b1 ds=0927 | 
 |                                           ^^^^^^ Temporary storage ID | 
 |  | 
 | |Call KERNEL.74: OPENFILE(0x09278248"C:~doc9281.tmp",0927:82da,0x1012) ret=060f:09d8 ds=0927 | 
 |                                     ^^^^^^^^^^^^^^^^ ^^^^^^^^^ ^^^^^^^ | 
 |                                     |filename        |OFSTRUCT |open mode: | 
 |  | 
 |                                        OF_CREATE|OF_SHARE_EXCLUSIVE|OF_READWRITE | 
 |         </screen> | 
 |         <para> | 
 |           This fails, since my <medialabel>C:</medialabel> drive is in | 
 |           this case mounted readonly. | 
 |         </para> | 
 |         <screen> | 
 | |Ret  KERNEL.74: OPENFILE() retval=0xffff ret=060f:09d8 ds=0927 | 
 |                                    ^^^^^^ HFILE_ERROR16, yes, it failed. | 
 |  | 
 | |Call USER.1: MESSAGEBOX(0x0000,0x09278376"You must close Windows and load SHARE.EXE before you start Word.",0x00000000,0x1030) ret=060f:084f ds=0927 | 
 |         </screen> | 
 |         <para> | 
 |           And MessageBox'ed. | 
 |         </para> | 
 |         <screen> | 
 | |Stopped on breakpoint 2 at 0x40189100 (MessageBoxA [msgbox.c:190]) | 
 | |190     {		<- the sourceline | 
 | In 32 bit mode. | 
 | Wine-dbg> | 
 |         </screen> | 
 |         <para> | 
 |           The code seems to find a writeable harddisk and tries to create | 
 |           a file there. To work around this bug, you can define | 
 |           <medialabel>C:</medialabel> as a networkdrive, which is ignored | 
 |           by the code above. | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Debugging Tips</title> | 
 |  | 
 |         <para> | 
 |           Here are some additional debugging tips: | 
 |         </para> | 
 |  | 
 |         <itemizedlist> | 
 |           <listitem> | 
 |             <para> | 
 |               If you have a program crashing at such an early loader phase that you can't | 
 |               use the Wine debugger normally, but Wine already executes the program's | 
 |               start code, then you may use a special trick. You should do a | 
 |               <programlisting> | 
 | WINEDEBUG=+relay wine program | 
 |               </programlisting> | 
 |               to get a listing of the functions the program calls in its start function. | 
 |               Now you do a | 
 |               <programlisting> | 
 | winedbg winfile.exe | 
 |               </programlisting> | 
 |             </para> | 
 |             <para> | 
 |               This way, you get into <command>winedbg</command>. Now you | 
 |               can set a breakpoint on any function the program calls in | 
 |               the start function and just type <userinput>c</userinput> | 
 |               to bypass the eventual calls of Winfile to this function | 
 |               until you are finally at the place where this function gets | 
 |               called by the crashing start function. Now you can proceed | 
 |               with your debugging as usual. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               If you try to run a program and it quits after showing an error messagebox, | 
 |               the problem can usually be identified in the return value of one of the | 
 |               functions executed before <function>MessageBox()</function>. | 
 |               That's why you should re-run the program with e.g. | 
 |               <programlisting> | 
 | WINEDEBUG=+relay wine  <program name> &>relmsg | 
 |               </programlisting> | 
 |               Then do a <command>more relmsg</command> and search for the | 
 |               last occurrence of a call to the string "MESSAGEBOX". This is a line like | 
 |               <programlisting> | 
 | Call USER.1: MESSAGEBOX(0x0000,0x01ff1246 "Runtime error 219 at 0004:1056.",0x00000000,0x1010) ret=01f7:2160 ds=01ff | 
 |               </programlisting> | 
 |               In my example the lines before the call to | 
 |               <function>MessageBox()</function> look like that: | 
 |               <programlisting> | 
 | Call KERNEL.96: FREELIBRARY(0x0347) ret=01cf:1033 ds=01ff | 
 | CallTo16(func=033f:0072,ds=01ff,0x0000) | 
 | Ret  KERNEL.96: FREELIBRARY() retval=0x0001 ret=01cf:1033 ds=01ff | 
 | Call KERNEL.96: FREELIBRARY(0x036f) ret=01cf:1043 ds=01ff | 
 | CallTo16(func=0367:0072,ds=01ff,0x0000) | 
 | Ret  KERNEL.96: FREELIBRARY() retval=0x0001 ret=01cf:1043 ds=01ff | 
 | Call KERNEL.96: FREELIBRARY(0x031f) ret=01cf:105c ds=01ff | 
 | CallTo16(func=0317:0072,ds=01ff,0x0000) | 
 | Ret  KERNEL.96: FREELIBRARY() retval=0x0001 ret=01cf:105c ds=01ff | 
 | Call USER.171: WINHELP(0x02ac,0x01ff05b4 "COMET.HLP",0x0002,0x00000000) ret=01cf:1070 ds=01ff | 
 | CallTo16(func=0117:0080,ds=01ff) | 
 | Call WPROCS.24: TASK_RESCHEDULE() ret=00a7:0a2d ds=002b | 
 | Ret  WPROCS.24: TASK_RESCHEDULE() retval=0x0000 ret=00a7:0a2d ds=002b | 
 | Ret  USER.171: WINHELP() retval=0x0001 ret=01cf:1070 ds=01ff | 
 | Call KERNEL.96: FREELIBRARY(0x01be) ret=01df:3e29 ds=01ff | 
 | Ret  KERNEL.96: FREELIBRARY() retval=0x0000 ret=01df:3e29 ds=01ff | 
 | Call KERNEL.52: FREEPROCINSTANCE(0x02cf00ba) ret=01f7:1460 ds=01ff | 
 | Ret  KERNEL.52: FREEPROCINSTANCE() retval=0x0001 ret=01f7:1460 ds=01ff | 
 | Call USER.1: MESSAGEBOX(0x0000,0x01ff1246 "Runtime error 219 at 0004:1056.",0x00000000,0x1010) ret=01f7:2160 ds=01ff | 
 |               </programlisting> | 
 |             </para> | 
 |             <para> | 
 |               I think that the call to <function>MessageBox()</function> | 
 |               in this example is <emphasis>not</emphasis> caused by a | 
 |               wrong result value of some previously executed function | 
 |               (it's happening quite often like that), but instead the | 
 |               messagebox complains about a runtime error at | 
 |               <literal>0x0004:0x1056</literal>. | 
 |             </para> | 
 |             <para> | 
 |               As the segment value of the address is only | 
 |               <literal>4</literal>, I think that that is only an internal | 
 |               program value. But the offset address reveals something | 
 |               quite interesting: Offset <literal>1056</literal> is | 
 |               <emphasis>very</emphasis> close to the return address of | 
 |               <function>FREELIBRARY()</function>: | 
 |               <programlisting> | 
 | Call KERNEL.96: FREELIBRARY(0x031f) ret=01cf:105c ds=01ff | 
 |                                              ^^^^ | 
 |               </programlisting> | 
 |             </para> | 
 |             <para> | 
 |               Provided that segment <literal>0x0004</literal> is indeed segment | 
 |               <literal>0x1cf</literal>, we now we can use IDA                 (available at | 
 |               <ulink url="http://www.filelibrary.com:8080/cgi-bin/freedownload/DOS/h/72/ida35bx.zip"> | 
 |                http://www.filelibrary.com:8080/cgi-bin/freedownload/DOS/h/72/ida35bx.zip</ulink>) to | 
 |               disassemble the part that caused the error. We just have to find the address of | 
 |               the call to <function>FreeLibrary()</function>. Some lines before that the | 
 |               runtime error occurred. But be careful! In some cases you don't have to | 
 |               disassemble the main program, but instead some DLL called by it in order to find | 
 |               the correct place where the runtime error occurred. That can be determined by | 
 |               finding the origin of the segment value (in this case <literal>0x1cf</literal>). | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               If you have created a relay file of some crashing | 
 |               program and want to set a breakpoint at a certain | 
 |               location which is not yet available as the program loads | 
 |               the breakpoint's segment during execution, you may set a | 
 |               breakpoint to <function>GetVersion16/32</function> as | 
 |               those functions are called very often. | 
 |             </para> | 
 |             <para> | 
 |               Then do a <userinput>c</userinput> until you are able to | 
 |               set this breakpoint without error message. | 
 |             </para> | 
 |           </listitem> | 
 |           <listitem> | 
 |             <para> | 
 |               Some useful programs: | 
 |             </para> | 
 |             <variablelist> | 
 |               <varlistentry> | 
 |                 <term> | 
 |                   <application>IDA</application>: | 
 |                   <filename> | 
 |                     <ulink url="http://www.filelibrary.com:8080/cgi-bin/freedownload/DOS/h/72/ida35bx.zip"> | 
 |                      http://www.filelibrary.com:8080/cgi-bin/freedownload/DOS/h/72/ida35bx.zip</ulink> | 
 |                   </filename> | 
 |                 </term> | 
 |                 <listitem> | 
 |                   <para> | 
 |                     <emphasis>Very</emphasis> good DOS disassembler ! It's badly needed | 
 |                     for debugging Wine sometimes. | 
 |                   </para> | 
 |                 </listitem> | 
 |               </varlistentry> | 
 |               <varlistentry> | 
 |                 <term> | 
 |                   <application>XRAY</application>: | 
 |                   <filename> | 
 |                     <ulink url="http://garbo.uwasa.fi/pub/pc/sysinfo/xray15.zip"> | 
 |                      http://garbo.uwasa.fi/pub/pc/sysinfo/xray15.zip</ulink> | 
 |                   </filename> | 
 |                 </term> | 
 |                 <listitem> | 
 |                   <para> | 
 |                     Traces DOS calls (Int 21h, DPMI, ...). Use it with | 
 |                     Windows to correct file management problems etc. | 
 |                   </para> | 
 |                 </listitem> | 
 |               </varlistentry> | 
 |               <varlistentry> | 
 |                 <term> | 
 |                   <application>pedump</application>: | 
 |                   <filename> | 
 |                     <ulink url="ftp://ftp.simtel.net/pub/simtelnet/win95/prog/pedump.zip"> | 
 |                      ftp://ftp.simtel.net/pub/simtelnet/win95/prog/pedump.zip</ulink> | 
 |                   </filename> | 
 |                 </term> | 
 |                 <listitem> | 
 |                   <para> | 
 |                     Dumps the imports and exports of a PE (Portable | 
 |                     Executable) DLL. | 
 |                   </para> | 
 |                 </listitem> | 
 |               </varlistentry> | 
 |               <varlistentry> | 
 |                 <term> | 
 |                   <application>winedump</application>: | 
 |                 </term> | 
 |                 <listitem> | 
 |                   <para> | 
 |                     Dumps the imports and exports of a PE (Portable | 
 |                     Executable) DLL (included in wine tree). | 
 |                   </para> | 
 |                 </listitem> | 
 |               </varlistentry> | 
 |             </variablelist> | 
 |           </listitem> | 
 |         </itemizedlist> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Some basic debugger usages</title> | 
 |  | 
 |         <para> | 
 |           After starting your program with | 
 |         </para> | 
 |         <screen> | 
 | wine -debug myprog.exe | 
 |         </screen> | 
 |         <para> | 
 |           the program loads and you get a prompt at the program | 
 |           starting point. Then you can set breakpoints: | 
 |         </para> | 
 |         <screen> | 
 |   b RoutineName      (by routine name) OR | 
 |   b *0x812575        (by address) | 
 |         </screen> | 
 |         <para> | 
 |           Then you hit <command>c</command> (continue) to run the | 
 |           program. It stops at the breakpoint. You can type | 
 |         </para> | 
 |         <screen> | 
 |   step               (to step one line) OR | 
 |   stepi              (to step one machine instruction at a time; | 
 |                       here, it helps to know the basic 386 | 
 |                       instruction set) | 
 |   info reg           (to see registers) | 
 |   info stack         (to see hex values in the stack) | 
 |   info local         (to see local variables) | 
 |   list <line number> (to list source code) | 
 |   x <variable name>  (to examine a variable; only works if code | 
 |                       is not compiled with optimization) | 
 |   x 0x4269978        (to examine a memory location) | 
 |   ?                  (help) | 
 |   q                  (quit) | 
 |         </screen> | 
 |         <para> | 
 |           By hitting <keycap>Enter</keycap>, you repeat the last | 
 |           command. | 
 |         </para> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |  | 
 |     <sect1 id="memory-addresses"> | 
 |       <title>Useful memory addresses</title> | 
 |       <para> | 
 |         Wine uses several different kinds of memory addresses. | 
 |       </para> | 
 |       <variablelist> | 
 |         <varlistentry> | 
 |           <term> | 
 |             Win32/"normal" Wine addresses/Linux: linear addresses. | 
 |           </term> | 
 |           <listitem> | 
 |             <para> | 
 |               Linear addresses can be everything from 0x0 up to | 
 |               0xffffffff.  In Wine on Linux they are often around | 
 |               e.g. 0x08000000, 0x00400000 (std. Win32 program load | 
 |               address), 0x40000000.  Every Win32 process has its own | 
 |               private 4GB address space (that is, from 0x0 up to | 
 |               0xffffffff). | 
 |             </para> | 
 |           </listitem> | 
 |         </varlistentry> | 
 |         <varlistentry> | 
 |           <term> | 
 |             Win16 "enhanced mode": segmented addresses. | 
 |           </term> | 
 |           <listitem> | 
 |             <para> | 
 |               These are the "normal" Win16 addresses, called SEGPTR. | 
 |               They have a segment:offset notation, e.g. 0x01d7:0x0012. | 
 |               The segment part usually is a "selector", which | 
 | 	      <emphasis>always</emphasis> | 
 |               has the lowest 3 bits set.  Some sample selectors are | 
 |               0x1f7, 0x16f, 0x8f.  If these bits are set except for | 
 |               the lowest bit, as e.g. with 0x1f6,xi then it might be a | 
 |               handle to global memory. Just set the lowest bit to get | 
 |               the selector in these cases.  A selector kind of | 
 |               "points" to a certain linear (see above) base address. | 
 |               It has more or less three important attributes: segment | 
 |               base address, segment limit, segment access rights. | 
 |             </para> | 
 |             <para> | 
 |               Example: | 
 |             </para> | 
 |             <para> | 
 |               Selector 0x1f7 (0x40320000, 0x0000ffff, r-x) So 0x1f7 | 
 |               has a base address of 0x40320000, the segment's last | 
 |               address is 0x4032ffff (limit 0xffff), and it's readable | 
 |               and executable.  So an address of 0x1f7:0x2300 would be | 
 |               the linear address of 0x40322300. | 
 |             </para> | 
 |           </listitem> | 
 |         </varlistentry> | 
 |         <varlistentry> | 
 |           <term> | 
 |             DOS/Win16 "standard mode" | 
 |           </term> | 
 |           <listitem> | 
 |             <para> | 
 |               They, too, have a segment:offset notation.  But they are | 
 |               completely different from "normal" Win16 addresses, as | 
 |               they just represent at most 1MB of memory: The segment | 
 |               part can be anything from 0 to 0xffff, and it's the same | 
 |               with the offset part. | 
 |             </para> | 
 |             <para> | 
 |               Now the strange thing is the calculation that's behind | 
 |               these addresses: Just calculate segment*16 + offset in | 
 |               order to get a "linear DOS" address.  So | 
 |               e.g. 0x0f04:0x3628 results in 0xf040 + 0x3628 = 0x12668. | 
 |               And the highest address you can get is 0xfffff (1MB), of | 
 |               course.  In Wine, this "linear DOS" address of 0x12668 | 
 |               has to be added to the linear base address of the | 
 |               corresponding DOS memory allocated for dosmod in order | 
 |               to get the true linear address of a DOS seg:offs | 
 |               address.  And make sure that you're doing this in the | 
 |               correct process with the correct linear address space, | 
 |               of course ;-) | 
 |             </para> | 
 |           </listitem> | 
 |         </varlistentry> | 
 |       </variablelist> | 
 |     </sect1> | 
 |  | 
 |     <sect1 id="dbg-config"> | 
 |       <title>Configuration</title> | 
 |  | 
 |       <sect2> | 
 |         <title>Registry configuration</title> | 
 |  | 
 |         <para> | 
 |           The Windows' debugging API uses a registry entry to know | 
 |           which debugger to invoke when an unhandled exception occurs | 
 |           (see <link endterm="dbg-exception-title" | 
 |           linkend="dbg-on-exception"></link> for some details). Two | 
 |           values in key | 
 |         </para> | 
 |         <programlisting> | 
 | "MACHINE\\Software\\Microsoft\\Windows NT\\CurrentVersion\\AeDebug" | 
 |         </programlisting> | 
 |         <para> | 
 |           Determine the behavior: | 
 |         </para> | 
 |         <variablelist> | 
 |           <varlistentry> | 
 |             <term>Debugger</term> | 
 |             <listitem> | 
 |               <para> | 
 |                 this is the command line used to launch the debugger | 
 |                 (it uses two <function>printf</function> formats | 
 |                 (<literal>%ld</literal>) to pass context dependent | 
 |                 information to  the debugger). You should put here a | 
 |                 complete path to your debugger | 
 |                 (<command>winedbg</command> can of course be used, but | 
 |                 any other Windows' debugging API aware debugger will | 
 |                 do). | 
 | 		The path to the debugger you chose to use must be reachable | 
 | 		via a DOS drive in the Wine config file ! | 
 |               </para> | 
 |             </listitem> | 
 |           </varlistentry> | 
 |           <varlistentry> | 
 |             <term>Auto</term> | 
 |             <listitem> | 
 |               <para> | 
 |                 if this value is zero, a message box will ask the | 
 |                 user if he/she wishes to launch the debugger when an | 
 |                 unhandled exception occurs. Otherwise, the debugger | 
 |                 is automatically started. | 
 |               </para> | 
 |             </listitem> | 
 |           </varlistentry> | 
 |         </variablelist> | 
 |  | 
 |         <para> | 
 |           A regular Wine registry looks like: | 
 |         </para> | 
 |         <programlisting> | 
 | [MACHINE\\Software\\Microsoft\\Windows NT\\CurrentVersion\\AeDebug] 957636538 | 
 | "Auto"=dword:00000001 | 
 | "Debugger"="winedbg %ld %ld" | 
 |         </programlisting> | 
 |  | 
 |         <note> | 
 |           <title>Note 1</title> | 
 |           <para> | 
 |             creating this key is mandatory. Not doing so will not | 
 |             fire the debugger when an exception occurs. | 
 |           </para> | 
 |         </note> | 
 |         <note> | 
 |           <title>Note 2</title> | 
 |           <para> | 
 |             <command>wineinstall</command> (available in Wine source) | 
 | 	    sets up this correctly. | 
 |             However, due to some limitation of the registry installed, | 
 |             if a previous Wine installation exists, it's safer to | 
 |             remove the whole | 
 |           </para> | 
 |           <programlisting> | 
 | [MACHINE\\Software\\Microsoft\\Windows NT\\CurrentVersion\\AeDebug] | 
 |           </programlisting> | 
 |           <para> | 
 |             key before running again <command>wineinstall</command> to | 
 |             regenerate this key. | 
 |           </para> | 
 |         </note> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>WineDbg configuration</title> | 
 |  | 
 |         <para> | 
 |           <command>winedbg</command> can be configured through a number | 
 |           of options. Those options are stored in the registry, on a | 
 |           per user basis. The key is (in <emphasis>my</emphasis> registry) | 
 |         </para> | 
 |         <programlisting> | 
 | [HKCU\\Software\\Wine\\WineDbg] | 
 |         </programlisting> | 
 |         <para> | 
 |           Those options can be read/written while inside | 
 |           <command>winedbg</command>, as part of the debugger | 
 |           expressions. To refer to one of these options, its name must | 
 |           be  prefixed by a <literal>$</literal> sign. For example, | 
 |         </para> | 
 |         <programlisting> | 
 | set $BreakAllThreadsStartup = 1 | 
 |         </programlisting> | 
 |         <para> | 
 |           sets the option <varname>BreakAllThreadsStartup</varname> to | 
 |           <literal>TRUE</literal>. | 
 |         </para> | 
 |         <para> | 
 |           All the options are read from the registry when | 
 |           <command>winedbg</command> starts (if no corresponding value | 
 |           is found, a default value is used), and are written back to | 
 |           the registry when <command>winedbg</command> exits (hence, | 
 |           all modifications to those options are automatically saved | 
 |           when <command>winedbg</command> terminates). | 
 |         </para> | 
 |         <para> | 
 |           Here's the list of all options: | 
 |         </para> | 
 |  | 
 | 	<variablelist> | 
 | 	  <varlistentry> | 
 | 	    <term><varname>BreakAllThreadsStartup</varname></term> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Set to <literal>TRUE</literal> if at all threads | 
 | 		start-up the debugger stops  set to | 
 | 		<literal>FALSE</literal> if only at the first thread | 
 | 		startup of a given process the debugger | 
 | 		stops. <literal>FALSE</literal> by default. | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </varlistentry> | 
 | 	  <varlistentry> | 
 | 	    <term><varname>BreakOnCritSectTimeOut</varname></term> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Set to <literal>TRUE</literal> if the debugger stops | 
 | 		when a critical section times out (5 minutes); | 
 | 		<literal>TRUE</literal> by default. | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </varlistentry> | 
 | 	  <varlistentry> | 
 | 	    <term><varname>BreakOnAttach</varname></term> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Set to <literal>TRUE</literal> if when | 
 | 		<command>winedbg</command> attaches to an existing | 
 | 		process after an unhandled exception, | 
 | 		<command>winedbg</command> shall be entered on the | 
 | 		first attach event. Since the attach event is | 
 | 		meaningless in the context of an exception event (the | 
 | 		next event  which is the exception event is of course | 
 | 		relevant), that option is likely to be | 
 | 		<literal>FALSE</literal>. | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </varlistentry> | 
 | 	  <varlistentry> | 
 | 	    <term><varname>BreakOnFirstChance</varname></term> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		An exception can generate two debug events. The first | 
 | 		one is passed to the debugger (known as a first | 
 | 		chance) just after the exception. The debugger can | 
 | 		then decide either to resume execution (see | 
 | 		<command>winedbg</command>'s <command>cont</command> | 
 | 		command) or pass the exception up to the exception | 
 | 		handler chain in the program (if it exists) | 
 | 		(<command>winedbg</command> implements this through | 
 | 		the <command>pass</command> command). If none of the | 
 | 		exception handlers takes care of the exception, the | 
 | 		exception event is sent again to the debugger (known | 
 | 		as last chance exception). You cannot pass on a last | 
 | 		exception. When the | 
 | 		<varname>BreakOnFirstChance</varname> exception is | 
 | 		<literal>TRUE</literal>, then winedbg is entered for | 
 | 		both first and last chance execptions (to | 
 | 		<literal>FALSE</literal>, it's only entered for last | 
 | 		chance exceptions). | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </varlistentry> | 
 | 	  <varlistentry> | 
 | 	    <term><varname>AlwaysShowThunk</varname></term> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Set to <literal>TRUE</literal> if the debugger, when | 
 | 		looking up for a symbol from its name, displays all | 
 | 		the thunks with that name. The default value | 
 | 		(<literal>FALSE</literal>) allows not to have to | 
 | 		choose between a symbol and all the import thunks | 
 | 		from all the DLLs using that symbols. | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </varlistentry> | 
 | 	</variablelist> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |     <sect1 id="dbg-expr"> | 
 |       <title>WineDbg Expressions and Variables</title> | 
 |       <sect2> | 
 | 	<title>Expressions</title> | 
 |  | 
 | 	<para> | 
 | 	  Expressions in Wine Debugger are mostly written in a C | 
 | 	  form. However, there are a few discrepancies: | 
 | 	  <itemizedlist> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Identifiers can take a '!' in their names. This allow | 
 | 		mainly to access symbols from different DLLs like | 
 | 		<function>USER32!CreateWindowExA</function>. | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 	        In cast operation, when specifying a structure or an | 
 | 		union, you must use the <type>struct</type> or | 
 | 		<type>union</type> keyword (even if your program uses a typedef).  | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </itemizedlist> | 
 | 	</para> | 
 | 	<para> | 
 | 	  When specifying an identifier by its name, if several | 
 | 	  symbols with the same name exist, the debugger will prompt | 
 | 	  for the symbol you want to use. Pick up the one you want | 
 | 	  from its number. | 
 | 	</para> | 
 | 	<para> | 
 | 	  In lots of cases, you can also use regular expressions for | 
 | 	  looking for a symbol. | 
 | 	</para> | 
 | 	<para> | 
 | 	  <command>winedbg</command> defines its own set of | 
 | 	  variables. The configuration variables from above are part | 
 | 	  of them. Some others include: | 
 |           <variablelist> | 
 |             <varlistentry> | 
 |               <term><varname>$ThreadId</varname></term> | 
 |               <listitem> | 
 |                 <para> | 
 |                   ID of the <varname>W-thread</varname> currently | 
 |                   examined by the debugger | 
 |                 </para> | 
 |               </listitem> | 
 |             </varlistentry> | 
 |             <varlistentry> | 
 |               <term><varname>$ProcessId</varname></term> | 
 |               <listitem> | 
 |                 <para> | 
 |                   ID of the <varname>W-thread</varname> currently | 
 |                   examined by the debugger | 
 |                 </para> | 
 |               </listitem> | 
 |             </varlistentry> | 
 |             <varlistentry> | 
 |               <term><registers></term> | 
 |               <listitem> | 
 |                 <para> | 
 |                   All CPU registers are also available, using $ as a | 
 | 		  prefix. You can use <command>info regs</command> to | 
 | 		  get a list of avaible CPU registers | 
 |                 </para> | 
 |               </listitem> | 
 |             </varlistentry> | 
 |           </variablelist> | 
 | 	</para> | 
 | 	<para> | 
 | 	  The <varname>$ThreadId</varname> and | 
 | 	  <varname>$ProcessId</varname> variables can be handy to set | 
 | 	  conditional breakpoints on a given thread or process. | 
 | 	</para> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |     <sect1 id="dbg-commands"> | 
 |       <title>WineDbg Command Reference</title> | 
 |  | 
 |       <sect2> | 
 |         <title>Misc</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's misc. commands</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>abort</command></entry> | 
 | 		  <entry>aborts the debugger</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>quit</command></entry> | 
 | 		  <entry>exits the debugger</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>attach N</command></entry> | 
 | 		  <entry> | 
 | 		    attach to a W-process (N is its ID, numeric | 
 | 		    or hexadecimal (0xN)). IDs can be obtained using | 
 | 		    the info process command. Note the info process | 
 | 		    command returns hexadecimal values. | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>detach</command></entry> | 
 | 		  <entry>detach from a W-process.</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>help</command></entry> | 
 | 		  <entry>prints some help on the commands</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>help info</command></entry> | 
 | 		  <entry>prints some help on info commands</entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Flow control</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's flow control commands</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>cont</command></member> | 
 | 			<member><command>c</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry>continue execution until next breakpoint or | 
 | 		    exception.</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>pass</command></entry> | 
 | 		  <entry>pass the exception event up to the filter | 
 | 		    chain.</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>step</command></member> | 
 | 			<member><command>s</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    continue execution until next 'C' line of code | 
 | 		    (enters function call) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>next</command></member> | 
 | 			<member><command>n</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    continue execution until next 'C' line of code | 
 | 		    (doesn't enter function call) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>stepi</command></member> | 
 | 			<member><command>si</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    execute next assembly instruction (enters function | 
 | 		    call) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>nexti</command></member> | 
 | 			<member><command>ni</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    execute next assembly instruction (doesn't enter | 
 | 		    function call) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member><command>finish</command></member> | 
 | 			<member><command>f</command></member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry>execute until current function is exited</entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |         <para> | 
 |           <command>cont</command>, <command>step</command>, | 
 | 	  <command>next</command>, <command>stepi</command>, | 
 | 	  <command>nexti</command> can be postfixed by a number (N), | 
 | 	  meaning that the command must be executed N times.  | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Breakpoints, watch points</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's break & watch points</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>enable N</command></entry> | 
 | 		  <entry>enables (break|watch)point #N</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>disable N</command></entry> | 
 | 		  <entry>disables (break|watch)point #N</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>delete N</command></entry> | 
 | 		  <entry>deletes (break|watch)point #N</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>cond N</command></entry> | 
 | 		  <entry> | 
 | 		    removes any existing condition to | 
 | 		    (break|watch)point N | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>cond N <expr></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    adds condition <expr> to (break|watch)point | 
 | 		    N. <expr> will be evaluated each time the | 
 | 		    breakpoint is hit. If the result is a zero value, | 
 | 		    the breakpoint isn't triggered | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>break * N</command></entry> | 
 | 		  <entry>adds a breakpoint at address N</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>break <id></command></entry> | 
 | 		  <entry> | 
 | 		    adds a breakpoint at the address of symbol | 
 | 		    <id> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>break <id> N</command></entry> | 
 | 		  <entry> | 
 | 		    adds a breakpoint at the address of symbol | 
 | 		    <id> (N ?) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>break N</command></entry> | 
 | 		  <entry> | 
 | 		    adds a breakpoint at line N of current source file | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>break</command></entry> | 
 | 		  <entry> | 
 | 		    adds a breakpoint at current $PC address | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>watch * N</command></entry> | 
 | 		  <entry> | 
 | 		    adds a watch command (on write) at address N (on 4 | 
 | 		    bytes) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>watch <id></command></entry> | 
 | 		  <entry> | 
 | 		    adds a watch command (on write) at the address of | 
 | 		    symbol <id> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info break</command></entry> | 
 | 		  <entry> | 
 | 		    lists all (break|watch)points (with state) | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |         <para> | 
 |           You can use the symbol <emphasis>EntryPoint</emphasis> to stand for | 
 |           the entry point of the Dll. | 
 |         </para> | 
 | 	<para> | 
 |           When setting a break/watch-point by <id>, if the | 
 | 	  symbol cannot be found (for example, the symbol is contained | 
 | 	  in a not yet loaded module), winedbg will recall the name of | 
 | 	  the symbol and will try to set the breakpoint each time a | 
 | 	  new module is loaded (until it succeeds).  | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Stack manipulation</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's stack manipulation</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>bt</command></entry> | 
 | 		  <entry>print calling stack of current thread</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>bt N</command></entry> | 
 | 		  <entry> | 
 | 		    print calling stack of thread of ID N (note: this | 
 | 		    doesn't change the position of the current frame | 
 | 		    as manipulated by the <command>up</command> and | 
 | 		    <command>dn</command> commands) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>up</command></entry> | 
 | 		  <entry> | 
 | 		    goes up one frame in current thread's stack | 
 | 		  </entry>  | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>up N</command></entry> | 
 | 		  <entry> | 
 | 		    goes up N frames in current thread's stack | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>dn</command></entry> | 
 | 		  <entry> | 
 | 		    goes down one frame in current thread's stack | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>dn N</command></entry> | 
 | 		  <entry> | 
 | 		    goes down N frames in current thread's stack | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>frame N</command></entry> | 
 | 		  <entry> | 
 | 		    set N as the current frame for current thread's | 
 | 		    stack | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info local</command></entry> | 
 | 		  <entry> | 
 | 		    prints information on local variables for current | 
 | 		    function frame | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Directory & source file manipulation</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's directory & source file manipulation</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>show dir</command></entry> | 
 | 		  <entry> | 
 | 		    prints the list of dir:s where source files are | 
 | 		    looked for | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>dir <pathname></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    adds <pathname> to the list of dir:s | 
 | 		    where to look for source files | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>dir</command></entry> | 
 | 		  <entry> | 
 | 		    deletes the list of dir:s where to look for source | 
 | 		    files | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      symbolfile <pathname> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry>loads external symbol definition</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      symbolfile <pathname> N | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    loads external symbol definition (applying an | 
 | 		    offset of N to addresses) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list</command></entry> | 
 | 		  <entry> | 
 | 		    lists 10 source lines forwards from current | 
 | 		    position | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list -</command></entry> | 
 | 		  <entry> | 
 | 		    lists 10 source lines backwards from current | 
 | 		    position | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list N</command></entry> | 
 | 		  <entry> | 
 | 		    lists 10 source lines from line N in current file | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>list <path>:N</command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    lists 10 source lines from line N in file | 
 | 		    <path> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list <id></command></entry> | 
 | 		  <entry> | 
 | 		    lists 10 source lines of function <id> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list * N</command></entry> | 
 | 		  <entry>lists 10 source lines from address N</entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |  | 
 |         <para> | 
 |           You can specify the end target (to change the 10 lines | 
 |           value) using the ','. For example: | 
 | 	  <table> | 
 | 	    <title>WineDbg's list command examples</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>list 123, 234</command></entry> | 
 | 		  <entry> | 
 | 		    lists source lines from line 123 up to line 234 in | 
 | 		    current file | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>list foo.c:1, 56</command></entry> | 
 | 		  <entry> | 
 | 		    lists source lines from line 1 up to 56 in file | 
 | 		    foo.c | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Displaying</title> | 
 |  | 
 |         <para> | 
 |           A display is an expression that's evaluated and printed | 
 |           after the execution of any <command>winedbg</command> | 
 |           command. | 
 |         </para> | 
 | 	<para> | 
 | 	  <command>winedbg</command> will automatically detect if the | 
 | 	  expression you entered contains a local variable. If so, | 
 | 	  display will only be shown if the context is still in the | 
 | 	  same function as the one the debugger was in when the | 
 | 	  display expression was entered. | 
 | 	</para> | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's displays</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>info display</command> | 
 | 		  </entry> | 
 | 		  <entry>lists the active displays</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>display</command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    print the active displays' values (as done each | 
 | 		    time the debugger stops) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>display <expr></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    adds a display for expression <expr> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      display /fmt <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    adds a display for expression | 
 | 		    <expr>. Printing evaluated <expr> is | 
 | 		    done using the given format (see | 
 | 		    <command>print</command> command for more on | 
 | 		    formats) | 
 | 		  </entry>  | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <msgtext> | 
 | 		      <simplelist type="inline"> | 
 | 			<member> | 
 | 			  <command>del display N</command> | 
 | 			</member> | 
 | 			<member> | 
 | 			  <command>undisplay N</command> | 
 | 			</member> | 
 | 		      </simplelist> | 
 | 		    </msgtext> | 
 | 		  </entry> | 
 | 		  <entry>deletes display #N</entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Disassembly</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's dissassembly</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>disas</command></entry> | 
 | 		  <entry>disassemble from current position</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>disas <expr></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    disassemble from address <expr> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      disas <expr>,<expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    disassembles code between addresses specified by | 
 | 		    the two <expr> | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Memory (reading, writing, typing)</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's memory management</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>x <expr></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    examines memory at <expr> address | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      x /fmt <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    examines memory at <expr> address using | 
 | 		    format /fmt | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      print <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints the value of <expr> (possibly using | 
 | 		    its type) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      print /fmt <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry>prints the value of <expr> (possibly | 
 | 		    using its type) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      set <lval> = <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    writes the value of <expr> in <lval> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      whatis <expr> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints the C type of expression <expr> | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |         <para> | 
 |           <filename>/fmt</filename> is either <filename>/<letter></filename> or | 
 |           <filename>/<count><letter></filename> letter can be | 
 | 	  <simplelist type="horiz" columns="2"> | 
 | 	    <member>s</member><member>an ASCII string</member> | 
 | 	    <member>u</member><member>an Unicode UTF16 string</member> | 
 | 	    <member>i</member><member>instructions (disassemble)</member> | 
 | 	    <member>x</member><member>32 bit unsigned hexadecimal integer</member> | 
 | 	    <member>d</member><member>32 bit signed decimal integer</member> | 
 | 	    <member>w</member><member>16 bit unsigned hexadecimal integer</member> | 
 | 	    <member>c</member><member>character (only printable 0x20-0x7f are actually printed)</member> | 
 | 	    <member>b</member><member>8 bit unsigned hexadecimal integer</member> | 
 | 	    <member>g</member><member>GUID</member> | 
 | 	  </simplelist> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Information on Wine's internals</title> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's Win32 objects management</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>info class</command></entry> | 
 | 		  <entry> | 
 | 		    lists all Windows' classes registered in Wine | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      info class <id> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints information on Windows's class <id> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info share</command></entry> | 
 | 		  <entry> | 
 | 		    lists all the dynamic libraries loaded in the | 
 | 		    debugged program (including .so files, NE and PE | 
 | 		    DLLs) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command> | 
 | 		      info share <N> | 
 | 		    </command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints information on module at address <N> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info regs</command></entry> | 
 | 		  <entry> | 
 | 		    prints the value of the CPU registers | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>info segment <N></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints information on segment <N> (i386 | 
 | 		    only) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>info segment</command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    lists all allocated segments (i386 only) | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info stack</command></entry> | 
 | 		  <entry> | 
 | 		    prints the values on top of the stack | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info map</command></entry> | 
 | 		  <entry> | 
 | 		    lists all virtual mappings used by the debugged | 
 | 		    program | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>info map <N></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    lists all virtual mappings used by the program of | 
 | 		    pid <N> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>info wnd <N></command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    prints information of Window of handle <N> | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info wnd</command></entry> | 
 | 		  <entry> | 
 | 		    lists all the window hierarchy starting from the | 
 | 		    desktop window | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info process</command></entry> | 
 | 		  <entry> | 
 | 		    lists all w-processes in Wine session | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info thread</command></entry> | 
 | 		  <entry>lists all w-threads in Wine session</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>info exception</command></entry> | 
 | 		  <entry> | 
 | 		    lists the exception frames (starting from current | 
 | 		    stack frame) | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2 id="winedbg-dbg-chan"> | 
 | 	<title>Debug channels</title> | 
 | 	<para> | 
 | 	  It is possible to turn on and off debug messages as you | 
 | 	  are debugging using the set command. | 
 | 	  See <xref linkend="debugging"> for more details on debug | 
 | 	  channels. | 
 | 	</para> | 
 |  | 
 | 	<para> | 
 | 	  <table> | 
 | 	    <title>WineDbg's debug channels' management</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>set + warn win</command> | 
 | 		  </entry> | 
 | 		  <entry>turn on warn on 'win' channel</entry>	 | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>set + win</command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    turn on warn/fixme/err/trace on 'win' channel | 
 | 		  </entry>  | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>set - win</command> | 
 | 		  </entry> | 
 | 		  <entry> | 
 | 		    turn off warn/fixme/err/trace on 'win' channel | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry> | 
 | 		    <command>set - fixme</command> | 
 | 		  </entry> | 
 | 		  <entry>turn off the 'fixme' class</entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |     </sect1> | 
 |  | 
 |     <sect1 id="dbg-others"> | 
 |       <title>Other debuggers</title> | 
 |  | 
 |       <sect2> | 
 |         <title>GDB mode</title> | 
 |  | 
 |         <para> | 
 | 	  WineDbg can act as a remote monitor for GDB. This allows to | 
 | 	  use all the power of GDB, but while debugging wine and/or | 
 | 	  any Win32 application. To enable this mode, just add | 
 | 	  <parameter>--gdb</parameter> to winedbg command line. You'll | 
 | 	  end up on a GDB prompt. You'll have to use the GDB commands | 
 | 	  (not WineDbg's). | 
 | 	</para> | 
 |  | 
 | 	<para> | 
 | 	  However, some limitation in GDB while debugging wine (see | 
 | 	  below) don't appear in this mode: | 
 | 	  <itemizedlist> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		GDB will correctly present Win32 thread | 
 | 		information and breakpoint behavior | 
 | 	      </para>  | 
 | 	    </listitem> | 
 | 	    <listitem> | 
 | 	      <para> | 
 | 		Moreover, it also provides support for the Dwarf II | 
 | 		debug format (which became the default format (instead | 
 | 		of stabs) in gcc 3.1).  | 
 | 	      </para> | 
 | 	    </listitem> | 
 | 	  </itemizedlist> | 
 | 	</para> | 
 |  | 
 | 	<para> | 
 | 	  A few Wine extensions available through the monitor command. | 
 | 	  <table> | 
 | 	    <title>WineDbg's debug channels' management</title> | 
 | 	    <tgroup cols="2" align="left"> | 
 | 	      <tbody> | 
 | 		<row> | 
 | 		  <entry><command>monitor wnd</command></entry> | 
 | 		  <entry>lists all window in the Wine session</entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>monitor proc</command></entry> | 
 | 		  <entry> | 
 | 		    lists all processes in the Wine session | 
 | 		  </entry> | 
 | 		</row> | 
 | 		<row> | 
 | 		  <entry><command>monitor mem</command></entry> | 
 | 		  <entry> | 
 | 		    displays memory mapping of debugged process | 
 | 		  </entry> | 
 | 		</row> | 
 | 	      </tbody> | 
 | 	    </tgroup> | 
 | 	  </table> | 
 | 	</para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 | 	<title>Graphical frontends to gdb</title> | 
 |  | 
 | 	<para> | 
 |           This section will describe how you can debug Wine using the | 
 |           GDB mode of winedbg and some graphical front ends to GDB for | 
 |           those of you who really like graphical debuggers. | 
 |         </para> | 
 |  | 
 | 	<sect3> | 
 | 	  <title>DDD</title> | 
 | 	   | 
 | 	  <para> | 
 |             Use the following steps, in this order: | 
 | 	    <orderedlist> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  Start the Wine debugger with a command line like: | 
 | <screen> | 
 | 	winedbg --gdb --no-start <name_of_exe_to_debug.exe> | 
 | </screen> | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	      <listitem> | 
 | 		<para> | 
 |                   Start ddd | 
 |                 </para> | 
 | 	      </listitem> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  In ddd, use the 'Open File' or 'Open Program' to | 
 |                   point to the Wine executable (which is either | 
 | 		  wine-pthread or wine-kthread depending on your | 
 | 		  settings). | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  In the output of 1/, there's a line like  | 
 | <screen> | 
 | 	target remote localhost:32878 | 
 | </screen> | 
 | 		  copy that line and paste into ddd command pane (the | 
 | 		  one with the (gdb) prompt) | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	    </orderedlist> | 
 | 	    The program should now be loaded and up and running. If | 
 | 	    you want, you can also add in 1/ after the name of the | 
 | 	    exec all the needed parameters | 
 |           </para> | 
 | 	</sect3> | 
 | 	<sect3> | 
 | 	  <title>kdbg</title> | 
 | 	   | 
 | 	  <para> | 
 |             Use the following steps, in this order: | 
 |             <orderedlist> | 
 | 	      <listitem> | 
 | 		<para> | 
 |                   Start the Wine debugger with a command line like: | 
 | <screen> | 
 | 	winedbg --gdb --no-start <name_of_exe_to_debug.exe> | 
 | </screen> | 
 | </para> | 
 | 	      </listitem> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  In the output of 1/, there's a line like  | 
 | <screen> | 
 | 	target remote localhost:32878 | 
 | </screen> | 
 | 		  Start kdbg with | 
 | <screen> | 
 | kdbg -r localhost:32878 wine | 
 | </screen> | 
 | 		  localhost:32878 is not a fixed value, but has been | 
 | 		  printed in step 1/. 'wine' should also be the full | 
 | 		  path to the Wine executable (which is either | 
 | 		  wine-pthread or wine-kthread depending on your settings). | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	    </orderedlist> | 
 | 	    The program should now be loaded and up and running. If | 
 | 	    you want, you can also add in 1/ after the name of the | 
 | 	    exec all the needed parameters | 
 |           </para> | 
 | 	</sect3> | 
 |       </sect2> | 
 | 	 | 
 |       <sect2> | 
 |         <title>Using other Unix debuggers</title> | 
 |  | 
 |         <para> | 
 |           You can also use other debuggers (like | 
 |           <command>gdb</command>), but you must be aware of a few | 
 |           items: | 
 |         </para> | 
 |         <para> | 
 |           You need to attach the unix debugger to the correct unix | 
 |           process (representing the correct windows thread) (you can | 
 |           "guess" it from a <command>ps fax</command> for example: | 
 |           When running the emulator, usually the first two | 
 |           <varname>upids</varname> are for the Windows' application | 
 |           running the desktop, the first thread of the application is | 
 |           generally the third <varname>upid</varname>; when running a | 
 |           Winelib program, the first thread of the application is | 
 |           generally the first <varname>upid</varname>) | 
 |         </para> | 
 |         <note> | 
 |           <para> | 
 | 	    If you plan to used <command>gdb</command> for a | 
 | 	    multi-threaded Wine application (native or Winelib), then | 
 | 	    <command>gdb</command> will be able to handle the multiple | 
 | 	    threads directly only if: | 
 | 	    <itemizedlist> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  Wine is running on the pthread model (it won't work | 
 | 		  in the kthread one). See the Wine architecture | 
 | 		  documentation for further details. | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	      <listitem> | 
 | 		<para> | 
 | 		  <command>gdb</command> supports the multi-threading | 
 | 		  (you need gdb at least 5.0 for that). | 
 | 		</para> | 
 | 	      </listitem> | 
 | 	    </itemizedlist> | 
 | 	    In the unfortunate case (no direct thread support in | 
 | 	    <command>gdb</command> because one of the above conditions | 
 | 	    is false), you'll have to spawn a different | 
 | 	    <command>gdb</command> session for each Windows' thread | 
 | 	    you wish to debug (which means no synchronization for | 
 | 	    debugging purposes between the various threads). | 
 |           </para> | 
 |         </note> | 
 |  | 
 |         <para> | 
 |           Here's how to get info about the current execution status of a | 
 |           certain Wine process: | 
 |         </para> | 
 |         <para> | 
 |           Change into your Wine source dir and enter: | 
 |         </para> | 
 |         <screen> | 
 | $ gdb wine | 
 |         </screen> | 
 |         <para> | 
 |           Switch to another console and enter <command>ps ax | grep | 
 |             wine</command> to find all wine processes. Inside | 
 |           <command>gdb</command>, repeat for all Wine processes: | 
 |         </para> | 
 |         <screen> | 
 | (gdb) attach <userinput>PID</userinput> | 
 |         </screen> | 
 |         <para> | 
 |           with <userinput>PID</userinput> being the process ID of one of | 
 |           the Wine processes.  Use | 
 |         </para> | 
 |         <screen> | 
 | (gdb) bt | 
 |         </screen> | 
 |         <para> | 
 |           to get the backtrace of the current Wine process, i.e. the | 
 |           function call history.  That way you can find out what the | 
 |           current process is doing right now.  And then you can use | 
 |           several times: | 
 |         </para> | 
 |         <screen> | 
 | (gdb) n | 
 |         </screen> | 
 |         <para> | 
 |           or maybe even | 
 |         </para> | 
 |         <screen> | 
 | (gdb) b <userinput>SomeFunction</userinput> | 
 |         </screen> | 
 |         <para> | 
 |           and | 
 |         </para> | 
 |         <screen> | 
 | (gdb) c | 
 |         </screen> | 
 |         <para> | 
 |           to set a breakpoint at a certain function and continue up to | 
 |           that function.  Finally you can enter | 
 |         </para> | 
 |         <screen> | 
 | (gdb) detach | 
 |         </screen> | 
 |         <para> | 
 |           to detach from the Wine process. | 
 |         </para> | 
 |         <!-- *** End of xtra content *** --> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Using other Windows debuggers</title> | 
 |  | 
 |         <para> | 
 |           You can use any Windows' debugging API compliant debugger | 
 |           with Wine. Some reports have been made of success with | 
 |           VisualStudio debugger (in remote mode, only the hub runs | 
 |           in Wine). GoVest fully runs in Wine. | 
 |         </para> | 
 |       </sect2> | 
 |  | 
 |       <sect2> | 
 |         <title>Main differences between winedbg and regular Unix debuggers</title> | 
 | 	<table><title>Debuggers comparison</title> | 
 | 	  <tgroup cols=2 align="left"> | 
 | 	    <tbody> | 
 | 	      <row> | 
 | 		<entry>WineDbg</entry><entry>gdb</entry> | 
 | 	      </row> | 
 | 	      <row> | 
 | 		<entry> | 
 | 		  WineDbg debugs a Windows' process: the various | 
 | 		  threads will be handled by the same WineDbg session, | 
 | 		  and a breakpoint will be triggered for any thread of | 
 | 		  the W-process  | 
 |                 </entry> | 
 | 	        <entry> | 
 | 		  gdb debugs a Windows' thread: a separate gdb session | 
 | 		  is needed for each thread of a Windows' process and | 
 | 		  a breakpoint will be triggered only for the w-thread | 
 | 		  debugged  | 
 |                 </entry> | 
 | 	      </row> | 
 | 	      <row> | 
 | 		<entry> | 
 | 		  WineDbg supports debug information from stabs | 
 | 		  (standard Unix format) and Microsoft's C, CodeView, | 
 | 		  .DBG | 
 |                 </entry> | 
 | 		<entry> | 
 | 		  GDB supports debug information from stabs (standard | 
 | 		  Unix format) and Dwarf II. | 
 |                 </entry> | 
 | 	      </row> | 
 |             </tbody> | 
 |           </tgroup> | 
 |         </table> | 
 |       </sect2> | 
 |     </sect1> | 
 |  | 
 |   </chapter> | 
 |  | 
 | <!-- Keep this comment at the end of the file | 
 | Local variables: | 
 | mode: sgml | 
 | sgml-parent-document:("wine-devel.sgml" "set" "book" "part" "chapter" "") | 
 | End: | 
 | --> |