| This document should help new developers get started. Like all of Wine, it | 
 | is a work in progress. | 
 |  | 
 |  | 
 | SOURCE TREE STRUCTURE | 
 | ===================== | 
 |  | 
 | The Wine source tree is loosely based on the original Windows modules.  | 
 | Most of the source is concerned with implementing the Wine API, although | 
 | there are also various tools, documentation, sample Winelib code, and | 
 | code specific to the binary loader. | 
 |  | 
 | Wine API directories: | 
 | --------------------- | 
 |  | 
 | KERNEL: | 
 |  | 
 | 	files/			- file I/O | 
 | 	loader/			- Win16-, Win32-binary loader | 
 | 	memory/			- memory management | 
 | 	msdos/			- DOS features and BIOS calls (interrupts) | 
 | 	scheduler/		- process and thread management | 
 |  | 
 | GDI: | 
 |  | 
 | 	graphics/		- graphics drivers | 
 | 		x11drv/		- X11 display driver | 
 | 		win16drv/	-> see below  | 
 | 		ttydrv/		- tty display driver | 
 | 		psdrv/		- PostScript graphics driver | 
 | 		metafiledrv/	- metafile driver | 
 | 		enhmetafiledrv/	- enhanced metafile driver | 
 | 	objects/		- logical objects | 
 |  | 
 | USER: | 
 |  | 
 | 	controls/		- built-in widgets | 
 | 	resources/		- built-in menu and message box resources | 
 | 	windows/		- window management | 
 |  | 
 | Other DLLs: | 
 |  | 
 | 	dlls/			- Other system DLLs implemented by Wine | 
 | 		advapi32/	- crypto, systeminfo, security, eventlogging | 
 | 		avifil32/	- COM object to play AVI files | 
 | 		comctl32/	- common controls | 
 | 		commdlg/	- common dialog boxes (both 16 & 32 bit) | 
 | 		dplayx/		- DirectX dplayx | 
 | 		dsound/		- DirectX dsound | 
 | 		imagehlp/	- PE (Portable Executable) Image Helper lib | 
 | 		imm32/ | 
 | 		lzexpand/	- Liv-Zempel compression/decompression | 
 | 		mpr/		- Multi-Protocol Router (interface to various  | 
 |                                   network transport protocols) | 
 | 		msacm/		- audio compression manager (multimedia) (16 bit) | 
 | 		msacm32/	- audio compression manager (multimedia) (32 bit) | 
 | 		msnet/ | 
 | 		msvideo/	- 16 bit video manager | 
 | 		ole32/		- 32 bit OLE 2.0 librairies | 
 | 		oleaut32/	- 32 bit OLE 2.0 automation | 
 | 		olecli/		- 16 bit OLE client | 
 | 		oledlg/		- OLE 2.0 user interface support | 
 | 		olesvr/		- 16 bit OLE server | 
 | 		ntdll/		- NT implementation of kernel calls | 
 | 		psapi/		- process status API | 
 | 		rasapi32/	- remote access server API | 
 | 		shell32/	- COM object implementing shell views | 
 | 		sound/		- Sound on loudspeaker (not sound card) | 
 | 		tapi32/		- telephone API | 
 | 		ver/		- File Installation Library (16 bit) | 
 | 		version/	- File Installation Library (32 bit) | 
 | 		win32s | 
 | 		win87em		- 80387 math-emulation | 
 | 		winaspi/	- 16 bit Advanced SCSI Peripheral Interface | 
 | 		windebug/	- Windows debugger | 
 | 		wing/		- WinG (for games) internface | 
 | 		winmm/		- multimedia (16 & 32 bit) | 
 | 			mciXXX/	- various MCI drivers | 
 | 			wineoss/- MM driver for OSS systems | 
 | 			wavemap/- audio mapper | 
 | 			midimap/- midi mapper | 
 | 		winspool/	- Printing & Print Spooler  | 
 | 		wnaspi32/	- 32 bit ASPI | 
 |  | 
 | Miscellaneous: | 
 |  | 
 | 	misc/			- shell, registry, winsock, etc. | 
 | 	ipc/			- SysV IPC based interprocess communication | 
 | 	win32/			- misc Win32 functions | 
 |         ole/			- OLE code  | 
 | 		nls/		- National Language Support  | 
 | 				  configuration files | 
 |  | 
 | Tools: | 
 | ------ | 
 |  | 
 | 	rc/			- old resource compiler | 
 | 	tools/			- relay code builder, new rc, bugreport | 
 | 				  generator, wineconfigurator, etc. | 
 | 	documentation/		- some documentation | 
 |  | 
 |  | 
 | Binary loader specific directories: | 
 | ----------------------------------- | 
 |  | 
 | 	debugger/		- built-in debugger | 
 | 	if1632/			- relay code | 
 | 	miscemu/		- hardware instruction emulation | 
 | 	graphics/win16drv/	- Win16 printer driver | 
 |         server/			- the main, controlling thread of wine | 
 |         tsx11/			- thread-safe X11 wrappers (auto generated) | 
 |  | 
 | Winelib specific directories: | 
 | ----------------------------- | 
 |  | 
 | 	library/		- Required code for programs using Winelib | 
 | 	libtest/		- Small samples and tests | 
 | 	programs/		- Extended samples / system utilities | 
 |  | 
 |  | 
 | IMPLEMENTING NEW API CALLS | 
 | ========================== | 
 |  | 
 | This is the simple version, and covers only Win32. Win16 is slightly uglier, | 
 | because of the Pascal heritage and the segmented memory model. | 
 |  | 
 | All of the Win32 APIs known to Wine are listed in [relay32/*.spec]. An | 
 | unimplemented call will look like (from gdi32.spec) | 
 |   269 stub PolyBezierTo | 
 | To implement this call, you need to do the following four things. | 
 |  | 
 | 1. Find the appropriate parameters for the call, and add a prototype to | 
 | the correct header file. In this case, that means [include/wingdi.h], | 
 | and it might look like | 
 |   BOOL WINAPI PolyBezierTo(HDC, LPCVOID, DWORD); | 
 | If the function has both an ASCII and a Unicode version, you need to | 
 | define both and add a #define WINELIB_NAME_AW declaration. See below | 
 | for discussion of function naming conventions. | 
 |    | 
 | 2. Modify the .spec file to tell Wine that the function has an | 
 | implementation, what the parameters look like and what Wine function | 
 | to use for the implementation. In Win32, things are simple--everything | 
 | is 32-bits. However, the relay code handles pointers and pointers to | 
 | strings slightly differently, so you should use 'str' and 'wstr' for | 
 | strings, 'ptr' for other pointer types, and 'long' for everything else. | 
 |   269 stdcall PolyBezierTo(long ptr long) PolyBezierTo | 
 | The 'PolyBezierTo' at the end of the line is which Wine function to use | 
 | for the implementation. | 
 |  | 
 | 3. Implement the function as a stub. Once you add the function to the .spec | 
 | file, you must add the function to the Wine source before it will link. | 
 | Add a function called 'PolyBezierTo' somewhere. Good things to put | 
 | into a stub: | 
 |   o a correct prototype, including the WINAPI | 
 |   o header comments, including full documentation for the function and | 
 |     arguments (see documentation/README.documentation) | 
 |   o A FIXME message and an appropriate return value are good things to | 
 |     put in a stub. | 
 |  | 
 |   /************************************************************ | 
 |    *                    PolyBezierTo   (GDI32.269)   | 
 |    *   | 
 |    * Draw many Bezier curves | 
 |    * | 
 |    * RETURNS | 
 |    *   nonzero on success or zero on faillure | 
 |    * | 
 |    * BUGS | 
 |    *   Unimplemented | 
 |    */ | 
 |    BOOL WINAPI PolyBezierTo(HDC hdc,     /* handle to device context */ | 
 |                             LPCVOID p,   /* ptr to array of Point structs */ | 
 |                             DWORD count  /* nr of points in array */ | 
 |    )  | 
 |    { | 
 |       /* tell the user they've got a substandard implementation */ | 
 |       FIXME(gdi, ":(%x,%p,%d): stub\n", hdc, p, count); | 
 |  | 
 |       /* some programs may be able to compensate,  | 
 |        * if they know what happened  | 
 |        */ | 
 |       SetLastError(ERROR_CALL_NOT_IMPLEMENTED);   | 
 |       return FALSE;    /* error value */ | 
 |    } | 
 |  | 
 | 4. Implement and test the rest of the function. | 
 |  | 
 |  | 
 | IMPLEMENTING A NEW DLL | 
 | ====================== | 
 |  | 
 | Generic directions | 
 | ------------------ | 
 |  | 
 | Apart from writing the set of needed .c files, you also need to do the  | 
 | following: | 
 |  | 
 | 1.  Create a directory <MyDll> where to store the implementation of | 
 |     the DLL.  | 
 |  | 
 |     If the DLL exists under Windows as both 16 and 32 bit DLL, you can | 
 |     either create one directory for each, or have a single directory | 
 |     with both implementations.  | 
 |  | 
 |     This (those) directory(ies) have to be put under the dlls/ | 
 |     directory in Wine tree structure. | 
 |  | 
 | 2.  Create the Makefile.in in the ./dlls/<MyDll>/ directory. You can | 
 |     copy an existing Makefile.in from another ./dlls/ subdirectory. | 
 |  | 
 |     You need at least to change the MODULE, SPEC_SRCS, and C_SRCS | 
 |     macros.  | 
 |  | 
 | 3.  Add the directory (and the generated .o file for the module) in:  | 
 |     + ./configure.in (in AC_OUTPUT macro at the end of the file to | 
 |       trigger the Makefile generation), | 
 |     + ./Makefile.in (in LIBSUBDIRS and LIBOBJS macros) | 
 |     + ./dlls/Makefile.in (in SUBDIRS macro) | 
 |  | 
 | 4.  You can now regenerate ./configure file (with 'make configure') | 
 |     and the various Makefiles (with 'configure; make depend') (run | 
 |     from the top of Wine's tree). | 
 |  | 
 |     You shall now have a Makefile file in ./dlls/<MyDll>/ | 
 |  | 
 | 5.  You now need to declare the DLL in the module lists. This is done | 
 |     by adding the corresponding descriptor in ./if1632/builtin.c if | 
 |     your DLL is 16 bit (resp. ./relay32/builtin.c for a 32 bit DLL) | 
 |     (or both if your directory contains the dual 16/32 | 
 |     implementations).  | 
 |  | 
 |     Note: the name of the descriptor is based on the module name, not | 
 |     on the file name (they are the same in most of the case, but for | 
 |     some DLLs it's not the case). | 
 |  | 
 | 6.  You also need to define the loadorder for the created DLL | 
 |     (./wine.ini and ./loader/loadorder.c). Usually, "native,builtin" | 
 |     is ok. If you have written a paired 16/32 bit implementation, don't | 
 |     forget to define it also in those files.  | 
 |  | 
 | 7.  Create the .spec file for the DLL export points in your | 
 |     directory. Refer to 'Implementation of new API calls' earlier in | 
 |     this document for more information on this part. | 
 |  | 
 | 8.  Don't forget the .cvsignore file. The .cvsignore contain (on a per | 
 |     directory basis) all the files generated by the compilation | 
 |     process, why cvs shall ignore when processing the dir.  | 
 |     *.o is in there by default, but in Wine case you will find: | 
 |     - Makefile (generated from Makefile.in) | 
 |     - *.spec.c: those c files are generated by tools/build from the | 
 |       .spec file | 
 |     - when thunking down to 16 bit DLLs, you'll get some others (.glue.c) | 
 |     - result of .y => .c translation (by yacc or bison) | 
 |     - result of .rc compilation | 
 |     - ... | 
 |     For a simple DLL, listing in .cvsignore Makefile and | 
 |     <MyDll>.spec.c will do.  | 
 |  | 
 | 9.  You can now start adding .c files. | 
 |  | 
 | 10. For the .h files, if they are standard Windows one, put them in | 
 |     include/. If they are linked to *your* implementation of the DLL, | 
 |     put them in your newly created directory. | 
 |  | 
 | Debug channels | 
 | -------------- | 
 |  | 
 | If you need to create a new debug channel, just add the | 
 | DECLARE_DEBUG_CHANNEL to your .c file(s) and rerun | 
 | tools/make_debug. When sending out your patch, you don't need to | 
 | provide nor ./configure nor the ./include/debugdefs.h diffs. Just | 
 | indicate that those files need to be regenerated. | 
 |  | 
 | Resources | 
 | --------- | 
 |  | 
 | If you also need to add resources to your DLL, the create the .rc | 
 | file. Since, the .rc file will be translated into a .s file, and then | 
 | compiled as a .o file, its basename must be different from the | 
 | basename of any .c file. | 
 | Add to your ./dlls/<MyDll>/Makefile.in, in the RC_SRCS macro, the list  | 
 | of .rc files to add to the DLL. You may also have to add the following | 
 | directives | 
 | 1/ to tell gnumake to translate .rc into .s files, | 
 | 	$(RC_SRCS:.rc=.s): $(WRC) | 
 | 2/ to give some parameters to wrc for helping the translation. | 
 | 	WRCEXTRA  = -s -p$(MODULE) | 
 |  | 
 | See dlls/comctl32/ for an example of this. | 
 |  | 
 | Thunking | 
 | -------- | 
 |  | 
 | If you're building a 16 & 32 bit DLLs pair, then from the 32 bit code | 
 | you might need to call 16 bit routine. The way to do it to add in the | 
 | code, fragments like: | 
 | /* ### Start build ### */ | 
 | extern WORD CALLBACK <PREFIX>_CallTo16_word_wwlll(FARPROC16,WORD,WORD,LONG,LONG,LONG); | 
 | /* ### stop build ### */ | 
 | Where <PREFIX>_ is an internal prefix for your module. The first | 
 | parameter is always of type FARPROC16. Then, you can get the regular | 
 | list of parameters. The _word_wwlll indicates the type of return (long | 
 | or word) and the size of the parameters (here l=>long, w=>word; which | 
 | maps to WORD,WORD,LONG,LONG,LONG. | 
 | You can put several functions between the Start/Stop build pair. | 
 |  | 
 | You can also read tools/build.txt for more details on this. | 
 |  | 
 | Then, add to ./dlls/<MyDll>/Makefile.in to the macro GLUE the list of | 
 | .c files containing the /* ### Start build ### */ directives. | 
 |  | 
 | See dlls/winmm/ for an example of this. | 
 |  | 
 | MEMORY AND SEGMENTS | 
 | =================== | 
 |  | 
 | NE (Win16) executables consist of multiple segments.  The Wine loader | 
 | loads each segment into a unique location in the Wine processes memory | 
 | and assigns a selector to that segment.  Because of this, it's not | 
 | possible to exchange addresses freely between 16-bit and 32-bit code. | 
 | Addresses used by 16-bit code are segmented addresses (16:16), formed | 
 | by a 16-bit selector and a 16-bit offset.  Those used by the Wine code | 
 | are regular 32-bit linear addresses. | 
 |  | 
 | There are four ways to obtain a segmented pointer: | 
 |   - Use the SEGPTR_* macros in include/heap.h (recommended). | 
 |   - Allocate a block of memory from the global heap and use | 
 |     WIN16_GlobalLock to get its segmented address. | 
 |   - Allocate a block of memory from a local heap, and build the | 
 |     segmented address from the local heap selector (see the | 
 |     USER_HEAP_* macros for an example of this). | 
 |   - Declare the argument as 'segptr' instead of 'ptr' in the spec file | 
 |     for a given API function. | 
 |  | 
 | Once you have a segmented pointer, it must be converted to a linear | 
 | pointer before you can use it from 32-bit code.  This can be done with | 
 | the PTR_SEG_TO_LIN() and PTR_SEG_OFF_TO_LIN() macros.  The linear | 
 | pointer can then be used freely with standard Unix functions like | 
 | memcpy() etc. without worrying about 64k boundaries.  Note: there's no | 
 | easy way to convert back from a linear to a segmented address. | 
 |  | 
 | In most cases, you don't need to worry about segmented address, as the | 
 | conversion is made automatically by the callback code and the API | 
 | functions only see linear addresses. However, in some cases it is | 
 | necessary to manipulate segmented addresses; the most frequent cases | 
 | are: | 
 |   - API functions that return a pointer | 
 |   - lParam of Windows messages that point to a structure | 
 |   - Pointers contained inside structures accessed by 16-bit code. | 
 |  | 
 | It is usually a good practice to used the type 'SEGPTR' for segmented | 
 | pointers, instead of something like 'LPSTR' or 'char *'.  As SEGPTR is | 
 | defined as a DWORD, you'll get a compilation warning if you mistakenly | 
 | use it as a regular 32-bit pointer. | 
 |  | 
 |  | 
 | STRUCTURE PACKING | 
 | ================= | 
 |  | 
 | Under Windows, data structures are tightly packed, i.e. there is no | 
 | padding between structure members. On the other hand, by default gcc | 
 | aligns structure members (e.g. WORDs are on a WORD boundary, etc.). | 
 | This means that a structure like | 
 |  | 
 | struct { BYTE x; WORD y; }; | 
 |  | 
 | will take 3 bytes under Windows, but 4 with gcc, because gcc will add a | 
 | dummy byte between x and y. To have the correct layout for structures | 
 | used by Windows code, you need to embed the struct within two special | 
 | #include's which will take care of the packing for you: | 
 |  | 
 | #include "pshpack1.h" | 
 | struct { BYTE x; WORD y; }; | 
 | #include "poppack1.h" | 
 |  | 
 | For alignment on a 2-byte boundary, there is a "pshpack2.h", etc. | 
 |  | 
 | The use of the WINE_PACKED attribute is obsolete. Please remove these  | 
 | in favour of the above solution.  | 
 | Using WINE_PACKED, you would declare the above structure like this: | 
 |  | 
 | struct { BYTE x; WORD y WINE_PACKED; }; | 
 |  | 
 | You had to do this every time a structure member is not aligned | 
 | correctly under Windows (i.e. a WORD not on an even address, or a | 
 | DWORD on a address that was not a multiple of 4). | 
 |  | 
 |  | 
 | NAMING CONVENTIONS FOR API FUNCTIONS AND TYPES | 
 | ============================================== | 
 |  | 
 | In order to support both Win16 and Win32 APIs within the same source | 
 | code, the following convention must be used in naming all API | 
 | functions and types. If the Windows API uses the name 'xxx', the Wine | 
 | code must use: | 
 |  | 
 |  - 'xxx16' for the Win16 version, | 
 |  - 'xxx'   for the Win32 version when no ASCII/Unicode strings are | 
 |    involved, | 
 |  - 'xxxA'  for the Win32 version with ASCII strings, | 
 |  - 'xxxW'  for the Win32 version with Unicode strings. | 
 |  | 
 | If the function has both ASCII and Unicode version, you should then | 
 | use the macros WINELIB_NAME_AW(xxx) or DECL_WINELIB_TYPE_AW(xxx) | 
 | (defined in include/windef.h) to define the correct 'xxx' function | 
 | or type for Winelib. When compiling Wine itself, 'xxx' is _not_ | 
 | defined, meaning that code inside of Wine must always specify | 
 | explicitly the ASCII or Unicode version. | 
 |  | 
 | If 'xxx' is the same in Win16 and Win32, you can simply use the same | 
 | name as Windows, i.e. just 'xxx'.  If 'xxx' is Win16 only, you could | 
 | use the name as is, but it's preferable to use 'xxx16' to make it | 
 | clear it is a Win16 function. | 
 |  | 
 | Examples: | 
 |  | 
 | typedef struct { /* Win32 ASCII data structure */ } WNDCLASSA; | 
 | typedef struct { /* Win32 Unicode data structure */ } WNDCLASSW; | 
 | typedef struct { /* Win16 data structure */ } WNDCLASS16; | 
 | DECL_WINELIB_TYPE_AW(WNDCLASS); | 
 |  | 
 | ATOM RegisterClass16( WNDCLASS16 * ); | 
 | ATOM RegisterClassA( WNDCLASSA * ); | 
 | ATOM RegisterClassW( WNDCLASSW * ); | 
 | #define RegisterClass WINELIB_NAME_AW(RegisterClass) | 
 |  | 
 | The Winelib user can then say: | 
 |  | 
 |     WNDCLASS wc = { ... }; | 
 |     RegisterClass( &wc ); | 
 |  | 
 | and this will use the correct declaration depending on the definition | 
 | of the UNICODE symbol. | 
 |  | 
 |  | 
 | NAMING CONVENTIONS FOR NON-API FUNCTIONS AND TYPES | 
 | ================================================== | 
 |  | 
 | Functions and data which are internal to your code (or at least shouldn't be | 
 | visible to any WineLib or Windows program) should be preceded by | 
 | an identifier to the module: | 
 |  | 
 | Examples: | 
 |  | 
 | ENUMPRINTERS_GetDWORDFromRegistryA()    (in dlls/winspool/info.c) | 
 | IAVIFile_fnRelease()                    (in dlls/avifil32/avifile.c) | 
 | X11DRV_CreateDC()                       (in graphics/x11drv/init.c) | 
 | TIMER_Init()                            (implemented in windows/timer.c, | 
 |                                          used in loader/main.c ) | 
 |  | 
 | if you need prototypes for these, there are a few possibilities: | 
 | - within same source file only: | 
 |   put the prototypes at the top of your file and mark them as prototypes. | 
 | - within the same module: | 
 |   create a header file within the subdirectory where that module resides, | 
 |   e.g.  graphics/ddraw_private.h | 
 | - from a totally different module, or for use in winelib: | 
 |   put your header file entry in /include/wine/ | 
 |   but be careful not to clutter this directory! | 
 | under no circumstances, you should add non-api calls to the standard | 
 | windoze include files. Unfortunately, this is often the case, e.g. | 
 | the above example of TIMER_Init is defined in include/message.h | 
 |  | 
 |  | 
 | API ENTRY POINTS | 
 | ================ | 
 |  | 
 | Because Win16 programs use a 16-bit stack and because they can only | 
 | call 16:16 addressed functions, all API entry points must be at low | 
 | address offsets and must have the arguments translated and moved to | 
 | Wines 32-bit stack.  This task is handled by the code in the "if1632" | 
 | directory.  To define a new API entry point handler you must place a | 
 | new entry in the appropriate API specification file.  These files are | 
 | named *.spec.  For example, the API specification file for the USER | 
 | DLL is contained in the file user.spec.  These entries are processed | 
 | by the "build" program to create an assembly file containing the entry | 
 | point code for each API call.  The format of the *.spec files is | 
 | documented in the file "tools/build-spec.txt". | 
 |  | 
 |  | 
 | DEBUG MESSAGES | 
 | ============== | 
 |  | 
 | To display a message only during debugging, you normally write something | 
 | like this: | 
 |  | 
 |         TRACE(win,"abc...");  or | 
 |         FIXME(win,"abc...");  or | 
 |         WARN(win,"abc...");   or | 
 |         ERR(win,"abc..."); | 
 |  | 
 | depending on the seriousness of the problem. (documentation/degug-msgs | 
 | explains when it is appropriate to use each of them) | 
 |  | 
 | These macros are defined in include/debug.h. The macro-definitions are | 
 | generated by the shell-script tools/make_debug. It scans the source | 
 | code for symbols of this forms and puts the necessary macro | 
 | definitions in include/debug.h and include/debugdefs.h. These macros | 
 | test whether the debugging "channel" associated with the first | 
 | argument of these macros (win in the above example) is enabled and | 
 | thus decide whether to actually display the text.  In addition you can | 
 | change the types of displayed messages by supplying the "-debugmsg" | 
 | option to Wine.  If your debugging code is more complex than just | 
 | printf, you can use the symbols TRACE_ON(xxx), WARN_ON(xxx), | 
 | ERR_ON(xxx) and FIXME_ON(xxx) as well. These are true when channel xxx | 
 | is enabled, either permanent or in the command line. Thus, you can | 
 | write: | 
 |  | 
 | 	if(TRACE_ON(win))DumpSomeStructure(&str); | 
 |  | 
 | Don't worry about the inefficiency of the test. If it is permanently  | 
 | disabled (that is TRACE_ON(win) is 0 at compile time), the compiler will  | 
 | eliminate the dead code. | 
 |  | 
 | You have to start tools/make_debug only if you introduced a new macro, | 
 | e.g.  TRACE(win32). | 
 |  | 
 | For more info about debugging messages, read: | 
 |  | 
 | documentation/debug-msgs | 
 |  | 
 |  | 
 | MORE INFO | 
 | ========= | 
 |  | 
 | 1. There is a FREE online version of the MSDN library (including | 
 |    documentation for the Win32 API) on http://www.microsoft.com/msdn/ | 
 |  | 
 | 2. http://www.sonic.net/~undoc/bookstore.html | 
 |  | 
 | 3. In 1993 Dr. Dobbs Journal published a column called "Undocumented Corner". | 
 |  | 
 | 4. You might want to check out BYTE from December 1983 as well :-) | 
 |  |