Sync winebuild (keeping ReactOS-specific changes).

3 days ago Michael Stefaniuc winebuild: Remove duplicate declaration of variable ...
6 days ago Alexandre Julliard winebuild: Don't set the IMAGE_FILE_DLL flag on native ...
10 days ago Alexandre Julliard winebuild: Also optimize out imports that are only ...
10 days ago Alexandre Julliard winebuild: Improved checks for missing forward entry ...
10 days ago Alexandre Julliard winebuild: Print a warning when failing to import a ...
2007-11-07 Alexandre Julliard winebuild: Add a few nops to stub entry points to make ...
2007-10-26 Alexandre Julliard winebuild: Add a -ordinal flag for entry points that ...
2007-09-10 Dmitry Timoshkov winebuild: Add IMAGE_FILE_32BIT_MACHINE flag for a ...
2007-07-19 Alexandre Julliard ntdll: Move private data to make room in the TEB for ...
2007-05-29 Dmitry Timoshkov winebuild: Mark builtin DLLs as IMAGE_FILE_LARGE_ADDRES ...
2007-05-24 Alexandre Julliard winebuild: Set the IMAGE_FILE_EXECUTABLE_IMAGE flag ...
2007-05-21 Dmitry Timoshkov winebuild: Fix compilation warnings in 64-bit mode.
2007-04-25 Rob Shearman winebuild: Refer to strings used in generated stubs ...
2007-04-09 Dmitry Timoshkov winebuild: Check if a given forward does exist in one ...
2007-03-17 Andrew Talbot winebuild: Replace inline static with static inline.
2007-03-05 Joris Huizer winebuild: sign-compare fixes.
2006-12-27 Alexandre Julliard make_makefiles: Generate the top-level .gitignore file.
2006-12-07 Alexandre Julliard winebuild: Added --nxcompat option, and mark all module ...
2006-12-04 Alexandre Julliard winebuild: Check for illegal characters in entry point ...
2006-10-12 Andrew Talbot winebuild: Cast-qual warning fix.
2006-09-14 Alexandre Julliard makefiles: Generate the dependencies line to avoid ...
2006-08-23 Andrew Talbot winebuild: Cast-qual warnings fix.
2006-08-11 Alexandre Julliard winebuild: Added output() function to properly deal ...
2006-08-07 Alexandre Julliard makefiles: Use make dependencies to create installation ...
2006-07-11 Ge van Geldorp winebuild: Save registers which might contain parameter ...
2006-07-11 Ge van Geldorp winebuild: Reserve enough space for null function pointer.
2006-07-10 Alexandre Julliard Take advantage of the recursive nature of .gitignore ...
2006-06-19 Alexandre Julliard winebuild: Get rid of the data16 prefix, it shouldn't ...
2006-06-13 Alexandre Julliard winebuild: Fix a few printf format warnings by casting ...
2006-05-23 Jonathan Ernst Update the address of the Free Software Foundation.
2006-04-18 Alexandre Julliard winebuild: Disable linking to external symbols by default.
2006-04-18 Alexandre Julliard winebuild: Fixed index in module table for delayed ...
2006-04-05 Alexandre Julliard winebuild: Remove a no longer necessary movzwl instruction.
2006-02-16 Robert Shearman winebuild: Correction for manpage.
2006-02-14 Mike Frysinger Add support for 'make install DESTDIR'.
2006-01-24 Alexandre Julliard winebuild: Get rid of the default ignored symbols list.
2006-01-23 Alexandre Julliard winebuild: Always import atof, the MS version is different.
2006-01-21 Marcus Meissner winebuild: Output a .note.GNU-stack section to allow ...
2006-01-20 Alexandre Julliard winebuild: Moved offset definitions to relay.c since ...
2006-01-20 Alexandre Julliard ntdll: Move the %gs register to the ntdll_thread_regs ... 

svn path=/trunk/; revision=31292
This commit is contained in:
Aleksey Bragin 2007-12-17 20:17:36 +00:00
parent 1e284d22a4
commit 26c115dc6a
14 changed files with 1455 additions and 1477 deletions

View file

@ -24,8 +24,8 @@ The following build tools are shared with Wine.
reactos/tools/unicode # Synced to Wine-0_9_5
reactos/tools/wpp # Synced to Wine-0_9_5
reactos/tools/bin2res # Resource to binary converter
reactos/tools/winebuild # Synced to Wine-0_9_5
reactos/tools/wmc # Synced to Wine-0_9_5
reactos/tools/winebuild # Synced to Wine-20071217
reactos/tools/wmc # Synced to Wine-20071201
reactos/tools/wrc # Synced to Wine-0_9_5
reactos/tools/widl # Synced to Wine-20060729

View file

@ -19,6 +19,8 @@ C_SRCS = \
spec32.c \
utils.c
INSTALLDIRS = $(DESTDIR)$(bindir) $(DESTDIR)$(mandir)/man$(prog_manext)
all: $(PROGRAMS) $(MANPAGES)
@MAKE_RULES@
@ -26,12 +28,11 @@ all: $(PROGRAMS) $(MANPAGES)
winebuild$(EXEEXT): $(OBJS)
$(CC) $(CFLAGS) -o $@ $(OBJS) $(LIBPORT) $(LDFLAGS)
install:: $(PROGRAMS) $(MANPAGES)
$(MKINSTALLDIRS) $(bindir) $(mandir)/man$(prog_manext)
$(INSTALL_PROGRAM) winebuild$(EXEEXT) $(bindir)/winebuild$(EXEEXT)
$(INSTALL_DATA) winebuild.man $(mandir)/man$(prog_manext)/winebuild.$(prog_manext)
install:: $(PROGRAMS) $(MANPAGES) $(INSTALLDIRS)
$(INSTALL_PROGRAM) winebuild$(EXEEXT) $(DESTDIR)$(bindir)/winebuild$(EXEEXT)
$(INSTALL_DATA) winebuild.man $(DESTDIR)$(mandir)/man$(prog_manext)/winebuild.$(prog_manext)
uninstall::
$(RM) $(bindir)/winebuild$(EXEEXT) $(mandir)/man$(prog_manext)/winebuild.$(prog_manext)
$(RM) $(DESTDIR)$(bindir)/winebuild$(EXEEXT) $(DESTDIR)$(mandir)/man$(prog_manext)/winebuild.$(prog_manext)
### Dependencies:
@DEPENDENCIES@ # everything below this line is overwritten by make depend

View file

@ -17,7 +17,7 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef __WINE_BUILD_H
@ -31,6 +31,8 @@
#include <stdlib.h>
#include <string.h>
#include "winglue.h"
typedef enum
{
TYPE_VARIABLE, /* variable */
@ -85,6 +87,7 @@ typedef struct
typedef struct
{
char *src_name; /* file name of the source spec file */
char *file_name; /* file name of the dll */
char *dll_name; /* internal name of the dll */
char *init_func; /* initialization routine */
@ -98,6 +101,7 @@ typedef struct
int nb_names; /* number of entry points with names */
unsigned int nb_resources; /* number of resources */
int characteristics; /* characteristics for the PE header */
int dll_characteristics;/* DLL characteristics for the PE header */
int subsystem; /* subsystem id */
int subsystem_major; /* subsystem version major number */
int subsystem_minor; /* subsystem version minor number */
@ -114,7 +118,7 @@ enum target_cpu
enum target_platform
{
PLATFORM_UNSPECIFIED, PLATFORM_APPLE, PLATFORM_SVR4, PLATFORM_WINDOWS
PLATFORM_UNSPECIFIED, PLATFORM_APPLE, PLATFORM_WINDOWS
};
extern enum target_cpu target_cpu;
@ -122,31 +126,16 @@ extern enum target_platform target_platform;
/* entry point flags */
#define FLAG_NORELAY 0x01 /* don't use relay debugging for this function */
#define FLAG_NONAME 0x02 /* don't import function by name */
#define FLAG_NONAME 0x02 /* don't export function by name */
#define FLAG_RET16 0x04 /* function returns a 16-bit value */
#define FLAG_RET64 0x08 /* function returns a 64-bit value */
#define FLAG_I386 0x10 /* function is i386 only */
#define FLAG_REGISTER 0x20 /* use register calling convention */
#define FLAG_PRIVATE 0x40 /* function is private (cannot be imported) */
#define FLAG_ORDINAL 0x80 /* function should be imported by ordinal */
#define FLAG_FORWARD 0x80 /* function is a forwarded name */
#define FLAG_EXT_LINK 0x100 /* function links to an external symbol */
/* Offset of a structure field relative to the start of the struct */
#define STRUCTOFFSET(type,field) ((int)&((type *)0)->field)
/* Offset of register relative to the start of the CONTEXT struct */
#define CONTEXTOFFSET(reg) STRUCTOFFSET(CONTEXT86,reg)
/* Offset of register relative to the start of the STACK16FRAME struct */
#define STACK16OFFSET(reg) STRUCTOFFSET(STACK16FRAME,reg)
/* Offset of register relative to the start of the STACK32FRAME struct */
#define STACK32OFFSET(reg) STRUCTOFFSET(STACK32FRAME,reg)
/* Offset of the stack pointer relative to %fs:(0) */
#define STACKOFFSET (STRUCTOFFSET(TEB,WOW32Reserved))
#define FLAG_FORWARD 0x100 /* function is a forwarded name */
#define FLAG_EXT_LINK 0x200 /* function links to an external symbol */
#define MAX_ORDINALS 65535
@ -169,11 +158,13 @@ extern void error( const char *msg, ... )
__attribute__ ((__format__ (__printf__, 1, 2)));
extern void warning( const char *msg, ... )
__attribute__ ((__format__ (__printf__, 1, 2)));
extern int output( const char *format, ... )
__attribute__ ((__format__ (__printf__, 1, 2)));
extern char *get_temp_file_name( const char *prefix, const char *suffix );
extern void output_standard_file_header( FILE *outfile );
extern void output_standard_file_header(void);
extern FILE *open_input_file( const char *srcdir, const char *name );
extern void close_input_file( FILE *file );
extern void dump_bytes( FILE *outfile, const void *buffer, unsigned int size );
extern void dump_bytes( const void *buffer, unsigned int size );
extern int remove_stdcall_decoration( char *name );
extern void assemble_file( const char *src_file, const char *obj_file );
extern DLLSPEC *alloc_dll_spec(void);
@ -191,7 +182,8 @@ extern const char *get_asm_string_keyword(void);
extern const char *get_asm_short_keyword(void);
extern const char *get_asm_rodata_section(void);
extern const char *get_asm_string_section(void);
extern void output_function_size( FILE *outfile, const char *name );
extern void output_function_size( const char *name );
extern void output_gnu_stack_note(void);
extern void add_import_dll( const char *name, const char *filename );
extern void add_delayed_import( const char *name );
@ -201,27 +193,25 @@ extern void read_undef_symbols( DLLSPEC *spec, char **argv );
extern int resolve_imports( DLLSPEC *spec );
extern int has_imports(void);
extern int has_relays( DLLSPEC *spec );
extern void output_get_pc_thunk( FILE *outfile );
extern void output_stubs( FILE *outfile, DLLSPEC *spec );
extern void output_imports( FILE *outfile, DLLSPEC *spec );
extern void output_get_pc_thunk(void);
extern void output_stubs( DLLSPEC *spec );
extern void output_imports( DLLSPEC *spec );
extern int load_res32_file( const char *name, DLLSPEC *spec );
extern void output_resources( FILE *outfile, DLLSPEC *spec );
extern void output_resources( DLLSPEC *spec );
extern void load_res16_file( const char *name, DLLSPEC *spec );
extern void output_res16_data( FILE *outfile, DLLSPEC *spec );
extern void output_res16_directory( FILE *outfile, DLLSPEC *spec, const char *header_name );
extern void output_res16_data( DLLSPEC *spec );
extern void output_res16_directory( DLLSPEC *spec, const char *header_name );
extern void BuildRelays16( FILE *outfile );
extern void BuildRelays32( FILE *outfile );
extern void BuildSpec16File( FILE *outfile, DLLSPEC *spec );
extern void BuildSpec32File( FILE *outfile, DLLSPEC *spec );
extern void BuildDef32File( FILE *outfile, DLLSPEC *spec );
extern void BuildPedllFile( FILE *outfile, DLLSPEC *spec );
extern void BuildRelays16(void);
extern void BuildRelays32(void);
extern void BuildSpec16File( DLLSPEC *spec );
extern void BuildSpec32File( DLLSPEC *spec );
extern void BuildDef32File( DLLSPEC *spec );
extern void BuildPedllFile( DLLSPEC *spec );
extern int parse_spec_file( FILE *file, DLLSPEC *spec );
extern int parse_def_file( FILE *file, DLLSPEC *spec );
extern int mkstemps(char *template, int suffix_len);
/* global variables */
extern int current_line;
@ -232,9 +222,11 @@ extern int display_warnings;
extern int kill_at;
extern int verbose;
extern int save_temps;
extern int link_ext_symbols;
extern char *input_file_name;
extern char *spec_file_name;
extern FILE *output_file;
extern const char *output_file_name;
extern char **lib_path;

File diff suppressed because it is too large Load diff

View file

@ -19,16 +19,14 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <assert.h>
#include <stdio.h>
#ifdef WIN32
#include <io.h> /* unlink() */
#endif//WIN32
#include <signal.h>
#include <errno.h>
#include <string.h>
@ -38,7 +36,8 @@
# include <getopt.h>
#endif
#include "winglue.h"
#include "windef.h"
#include "winbase.h"
#include "build.h"
int UsePIC = 0;
@ -48,8 +47,9 @@ int display_warnings = 0;
int kill_at = 0;
int verbose = 0;
int save_temps = 0;
int link_ext_symbols = 0;
#if defined(__i386__) || defined(__x86_64__)
#ifdef __i386__
enum target_cpu target_cpu = CPU_x86;
#elif defined(__x86_64__)
enum target_cpu target_cpu = CPU_x86_64;
@ -65,8 +65,6 @@ enum target_cpu target_cpu = CPU_POWERPC;
#ifdef __APPLE__
enum target_platform target_platform = PLATFORM_APPLE;
#elif defined(__svr4__)
enum target_platform target_platform = PLATFORM_SVR4;
#elif defined(_WINDOWS)
enum target_platform target_platform = PLATFORM_WINDOWS;
#else
@ -77,6 +75,7 @@ char **lib_path = NULL;
char *input_file_name = NULL;
char *spec_file_name = NULL;
FILE *output_file = NULL;
const char *output_file_name = NULL;
static const char *output_file_source_name;
@ -84,7 +83,6 @@ char *as_command = NULL;
char *ld_command = NULL;
char *nm_command = NULL;
static FILE *output_file;
static int nb_res_files;
static char **res_files;
@ -127,7 +125,6 @@ static const struct
{
{ "macos", PLATFORM_APPLE },
{ "darwin", PLATFORM_APPLE },
{ "sunos", PLATFORM_SVR4 },
{ "windows", PLATFORM_WINDOWS },
{ "winnt", PLATFORM_WINDOWS }
};
@ -248,8 +245,9 @@ static const char usage_str[] =
" --as-cmd=AS Command to use for assembling (default: as)\n"
" -d, --delay-lib=LIB Import the specified library in delayed mode\n"
" -D SYM Ignored for C flags compatibility\n"
" -E, --export=FILE Export the symbols defined in the .spec or .def file\n"
" -e, --entry=FUNC Set the DLL entry point function (default: DllMain)\n"
" -E, --export=FILE Export the symbols defined in the .spec or .def file\n"
" --external-symbols Allow linking to external symbols\n"
" -f FLAGS Compiler flags (only -fPIC is supported)\n"
" -F, --filename=DLLFILE Set the DLL filename (default: from input file name)\n"
" -h, --help Display this help message\n"
@ -263,6 +261,7 @@ static const char usage_str[] =
" -L, --library-path=DIR Look for imports libraries in DIR\n"
" -M, --main-module=MODULE Set the name of the main module for a Win16 dll\n"
" --nm-cmd=NM Command to use to get undefined symbols (default: nm)\n"
" --nxcompat=y|n Set the NX compatibility flag (default: yes)\n"
" -N, --dll-name=DLLNAME Set the DLL name (default: from input file name)\n"
" -o, --output=NAME Set the output file name (default: stdout)\n"
" -r, --res=RSRC.RES Load resources from RSRC.RES\n"
@ -278,7 +277,7 @@ static const char usage_str[] =
" --def Build a .def file from a .spec file\n"
" --exe Build a .c file for an executable\n"
" --relay16 Build the 16-bit relay assembly routines\n"
" --relay32 Build the 32-bit relay assembly routines\n"
" --relay32 Build the 32-bit relay assembly routines\n\n"
" --pedll Build a .c file for PE dll\n\n"
"The mode options are mutually exclusive; you must specify one and only one.\n\n";
@ -288,14 +287,16 @@ enum long_options_values
LONG_OPT_DEF,
LONG_OPT_EXE,
LONG_OPT_ASCMD,
LONG_OPT_EXTERNAL_SYMS,
LONG_OPT_LDCMD,
LONG_OPT_NMCMD,
LONG_OPT_NXCOMPAT,
LONG_OPT_RELAY16,
LONG_OPT_RELAY32,
LONG_OPT_SAVE_TEMPS,
LONG_OPT_SUBSYSTEM,
LONG_OPT_VERSION,
LONG_OPT_TARGET,
LONG_OPT_VERSION,
LONG_OPT_PEDLL
};
@ -303,19 +304,21 @@ static const char short_options[] = "C:D:E:F:H:I:K:L:M:N:d:e:f:hi:kl:m:o:r:u:vw"
static const struct option long_options[] =
{
{ "dll", 0, 0, LONG_OPT_DLL },
{ "def", 0, 0, LONG_OPT_DEF },
{ "exe", 0, 0, LONG_OPT_EXE },
{ "as-cmd", 1, 0, LONG_OPT_ASCMD },
{ "ld-cmd", 1, 0, LONG_OPT_LDCMD },
{ "nm-cmd", 1, 0, LONG_OPT_NMCMD },
{ "relay16", 0, 0, LONG_OPT_RELAY16 },
{ "relay32", 0, 0, LONG_OPT_RELAY32 },
{ "save-temps",0, 0, LONG_OPT_SAVE_TEMPS },
{ "subsystem",1, 0, LONG_OPT_SUBSYSTEM },
{ "target", 1, 0, LONG_OPT_TARGET },
{ "version", 0, 0, LONG_OPT_VERSION },
{ "pedll", 1, 0, LONG_OPT_PEDLL },
{ "dll", 0, 0, LONG_OPT_DLL },
{ "def", 0, 0, LONG_OPT_DEF },
{ "exe", 0, 0, LONG_OPT_EXE },
{ "as-cmd", 1, 0, LONG_OPT_ASCMD },
{ "external-symbols", 0, 0, LONG_OPT_EXTERNAL_SYMS },
{ "ld-cmd", 1, 0, LONG_OPT_LDCMD },
{ "nm-cmd", 1, 0, LONG_OPT_NMCMD },
{ "nxcompat", 1, 0, LONG_OPT_NXCOMPAT },
{ "relay16", 0, 0, LONG_OPT_RELAY16 },
{ "relay32", 0, 0, LONG_OPT_RELAY32 },
{ "save-temps", 0, 0, LONG_OPT_SAVE_TEMPS },
{ "subsystem", 1, 0, LONG_OPT_SUBSYSTEM },
{ "target", 1, 0, LONG_OPT_TARGET },
{ "version", 0, 0, LONG_OPT_VERSION },
{ "pedll", 1, 0, LONG_OPT_PEDLL },
/* aliases for short options */
{ "delay-lib", 1, 0, 'd' },
{ "export", 1, 0, 'E' },
@ -471,12 +474,19 @@ static char **parse_options( int argc, char **argv, DLLSPEC *spec )
case LONG_OPT_ASCMD:
as_command = xstrdup( optarg );
break;
case LONG_OPT_EXTERNAL_SYMS:
link_ext_symbols = 1;
break;
case LONG_OPT_LDCMD:
ld_command = xstrdup( optarg );
break;
case LONG_OPT_NMCMD:
nm_command = xstrdup( optarg );
break;
case LONG_OPT_NXCOMPAT:
if (optarg[0] == 'n' || optarg[0] == 'N')
spec->dll_characteristics &= ~IMAGE_DLLCHARACTERISTICS_NX_COMPAT;
break;
case LONG_OPT_RELAY16:
set_exec_mode( MODE_RELAY16 );
break;
@ -564,6 +574,7 @@ static int parse_input_file( DLLSPEC *spec )
char *extension = strrchr( spec_file_name, '.' );
int result;
spec->src_name = xstrdup( input_file_name );
if (extension && !strcmp( extension, ".def" ))
result = parse_def_file( input_file, spec );
else
@ -592,7 +603,8 @@ int main(int argc, char **argv)
switch(exec_mode)
{
case MODE_DLL:
spec->characteristics |= IMAGE_FILE_DLL;
if (spec->subsystem != IMAGE_SUBSYSTEM_NATIVE)
spec->characteristics |= IMAGE_FILE_DLL;
load_resources( argv, spec );
load_import_libs( argv );
if (!spec_file_name) fatal_error( "missing .spec file\n" );
@ -604,7 +616,7 @@ int main(int argc, char **argv)
break;
case SPEC_WIN32:
read_undef_symbols( spec, argv );
BuildSpec32File( output_file, spec );
BuildSpec32File( spec );
break;
default: assert(0);
}
@ -616,14 +628,14 @@ int main(int argc, char **argv)
load_import_libs( argv );
if (spec_file_name && !parse_input_file( spec )) break;
read_undef_symbols( spec, argv );
BuildSpec32File( output_file, spec );
BuildSpec32File( spec );
break;
case MODE_DEF:
if (argv[0]) fatal_error( "file argument '%s' not allowed in this mode\n", argv[0] );
if (spec->type == SPEC_WIN16) fatal_error( "Cannot yet build .def file for 16-bit dlls\n" );
if (!spec_file_name) fatal_error( "missing .spec file\n" );
if (!parse_input_file( spec )) break;
BuildDef32File( output_file, spec );
BuildDef32File( spec );
break;
case MODE_RELAY16:
fatal_error( "Win16 relays are not supported in ReactOS version of winebuild\n" );
@ -634,7 +646,7 @@ int main(int argc, char **argv)
case MODE_PEDLL:
if (argv[0]) fatal_error( "file argument '%s' not allowed in this mode\n", argv[0] );
if (!parse_input_file( spec )) break;
BuildPedllFile( output_file, spec );
BuildPedllFile( spec );
break;
default:
usage(1);
@ -643,7 +655,7 @@ int main(int argc, char **argv)
if (nb_errors) exit(1);
if (output_file_name)
{
fclose( output_file );
if (fclose( output_file ) < 0) fatal_perror( "fclose" );
if (output_file_source_name) assemble_file( output_file_source_name, output_file_name );
output_file_name = NULL;
}

View file

@ -19,10 +19,11 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <assert.h>
#include <ctype.h>
@ -31,7 +32,8 @@
#include <stdlib.h>
#include <string.h>
#include "winglue.h"
#include "windef.h"
#include "winbase.h"
#include "build.h"
int current_line = 0;
@ -44,6 +46,9 @@ static FILE *input_file;
static const char *separator_chars;
static const char *comment_chars;
/* valid characters in ordinal names */
static const char valid_ordname_chars[] = "/$:-_@?abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
static const char * const TypeNames[TYPE_NBTYPES] =
{
"variable", /* TYPE_VARIABLE */
@ -65,6 +70,7 @@ static const char * const FlagNames[] =
"i386", /* FLAG_I386 */
"register", /* FLAG_REGISTER */
"private", /* FLAG_PRIVATE */
"ordinal", /* FLAG_ORDINAL */
NULL
};
@ -74,12 +80,12 @@ static int IsNumberString(const char *s)
return 1;
}
inline static int is_token_separator( char ch )
static inline int is_token_separator( char ch )
{
return strchr( separator_chars, ch ) != NULL;
}
inline static int is_token_comment( char ch )
static inline int is_token_comment( char ch )
{
return strchr( comment_chars, ch ) != NULL;
}
@ -445,6 +451,7 @@ static const char *parse_spec_flags( ORDDEF *odp )
static int parse_spec_ordinal( int ordinal, DLLSPEC *spec )
{
const char *token;
size_t len;
ORDDEF *odp = add_entry_point( spec );
memset( odp, 0, sizeof(*odp) );
@ -468,6 +475,13 @@ static int parse_spec_ordinal( int ordinal, DLLSPEC *spec )
odp->lineno = current_line;
odp->ordinal = ordinal;
len = strspn( odp->name, valid_ordname_chars );
if (len < strlen( odp->name ))
{
error( "Character '%c' is not allowed in exported name '%s'\n", odp->name[len], odp->name );
goto error;
}
switch(odp->type)
{
case TYPE_VARIABLE:
@ -532,11 +546,14 @@ static int parse_spec_ordinal( int ordinal, DLLSPEC *spec )
}
}
if (!strcmp( odp->name, "@" ) || odp->flags & FLAG_NONAME)
if (!strcmp( odp->name, "@" ) || odp->flags & (FLAG_NONAME | FLAG_ORDINAL))
{
if (ordinal == -1)
{
error( "Nameless function needs an explicit ordinal number\n" );
if (!strcmp( odp->name, "@" ))
error( "Nameless function needs an explicit ordinal number\n" );
else
error( "Function imported by ordinal needs an explicit ordinal number\n" );
goto error;
}
if (spec->type != SPEC_WIN32)
@ -544,9 +561,16 @@ static int parse_spec_ordinal( int ordinal, DLLSPEC *spec )
error( "Nameless functions not supported for Win16\n" );
goto error;
}
if (!strcmp( odp->name, "@" )) free( odp->name );
else odp->export_name = odp->name;
odp->name = NULL;
if (!strcmp( odp->name, "@" ))
{
free( odp->name );
odp->name = NULL;
}
else if (!(odp->flags & FLAG_ORDINAL)) /* -ordinal only affects the import library */
{
odp->export_name = odp->name;
odp->name = NULL;
}
}
return 1;

File diff suppressed because it is too large Load diff

View file

@ -15,10 +15,11 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <assert.h>
#include <ctype.h>
@ -37,7 +38,8 @@
#include <sys/mman.h>
#endif
#include "winglue.h"
#include "windef.h"
#include "winbase.h"
#include "build.h"
/* Unicode string or integer id */
@ -77,7 +79,7 @@ static const unsigned char *file_end; /* end of resource file */
static const char *file_name; /* current resource file name */
inline static struct resource *add_resource( DLLSPEC *spec )
static inline struct resource *add_resource( DLLSPEC *spec )
{
spec->resources = xrealloc( spec->resources, (spec->nb_resources + 1) * sizeof(*spec->resources) );
return &spec->resources[spec->nb_resources++];
@ -140,7 +142,7 @@ static void get_string( struct string_id *str )
}
else
{
char *p = xmalloc( (strlen((char*)file_pos) + 1) );
char *p = xmalloc(strlen((const char *)file_pos) + 1);
str->str = p;
str->id = 0;
while ((*p++ = get_byte()));
@ -240,16 +242,16 @@ static void free_resource_tree( struct res_tree *tree )
}
/* output a string preceded by its length */
static void output_string( FILE *outfile, const char *str )
static void output_string( const char *str )
{
unsigned int i, len = strlen(str);
fprintf( outfile, "\t.byte 0x%02x", len );
for (i = 0; i < len; i++) fprintf( outfile, ",0x%02x", (unsigned char)str[i] );
fprintf( outfile, " /* %s */\n", str );
output( "\t.byte 0x%02x", len );
for (i = 0; i < len; i++) output( ",0x%02x", (unsigned char)str[i] );
output( " /* %s */\n", str );
}
/* output the resource data */
void output_res16_data( FILE *outfile, DLLSPEC *spec )
void output_res16_data( DLLSPEC *spec )
{
const struct resource *res;
unsigned int i;
@ -258,14 +260,14 @@ void output_res16_data( FILE *outfile, DLLSPEC *spec )
for (i = 0, res = spec->resources; i < spec->nb_resources; i++, res++)
{
fprintf( outfile, ".L__wine_spec_resource_%u:\n", i );
dump_bytes( outfile, res->data, res->data_size );
fprintf( outfile, ".L__wine_spec_resource_%u_end:\n", i );
output( ".L__wine_spec_resource_%u:\n", i );
dump_bytes( res->data, res->data_size );
output( ".L__wine_spec_resource_%u_end:\n", i );
}
}
/* output the resource definitions */
void output_res16_directory( FILE *outfile, DLLSPEC *spec, const char *header_name )
void output_res16_directory( DLLSPEC *spec, const char *header_name )
{
unsigned int i, j;
struct res_tree *tree;
@ -274,38 +276,39 @@ void output_res16_directory( FILE *outfile, DLLSPEC *spec, const char *header_na
tree = build_resource_tree( spec );
fprintf( outfile, "\n.L__wine_spec_ne_rsrctab:\n" );
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* alignment */
output( "\n.L__wine_spec_ne_rsrctab:\n" );
output( "\t%s 0\n", get_asm_short_keyword() ); /* alignment */
/* type and name structures */
for (i = 0, type = tree->types; i < tree->nb_types; i++, type++)
{
if (type->type->str)
fprintf( outfile, "\t%s .L__wine_spec_restype_%u-.L__wine_spec_ne_rsrctab\n",
output( "\t%s .L__wine_spec_restype_%u-.L__wine_spec_ne_rsrctab\n",
get_asm_short_keyword(), i );
else
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), type->type->id | 0x8000 );
output( "\t%s 0x%04x\n", get_asm_short_keyword(), type->type->id | 0x8000 );
fprintf( outfile, "\t%s %u,0,0\n", get_asm_short_keyword(), type->nb_names );
output( "\t%s %u,0,0\n", get_asm_short_keyword(), type->nb_names );
for (j = 0, res = type->res; j < type->nb_names; j++, res++)
{
fprintf( outfile, "\t%s .L__wine_spec_resource_%u-%s\n",
get_asm_short_keyword(), res - spec->resources, header_name );
fprintf( outfile, "\t%s .L__wine_spec_resource_%u_end-.L__wine_spec_resource_%u\n",
get_asm_short_keyword(), res - spec->resources, res - spec->resources );
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), res->memopt );
output( "\t%s .L__wine_spec_resource_%lu-%s\n",
get_asm_short_keyword(), (unsigned long)(res - spec->resources), header_name );
output( "\t%s .L__wine_spec_resource_%lu_end-.L__wine_spec_resource_%lu\n",
get_asm_short_keyword(), (unsigned long)(res - spec->resources),
(unsigned long)(res - spec->resources) );
output( "\t%s 0x%04x\n", get_asm_short_keyword(), res->memopt );
if (res->name.str)
fprintf( outfile, "\t%s .L__wine_spec_resname_%u_%u-.L__wine_spec_ne_rsrctab\n",
output( "\t%s .L__wine_spec_resname_%u_%u-.L__wine_spec_ne_rsrctab\n",
get_asm_short_keyword(), i, j );
else
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), res->name.id | 0x8000 );
output( "\t%s 0x%04x\n", get_asm_short_keyword(), res->name.id | 0x8000 );
fprintf( outfile, "\t%s 0,0\n", get_asm_short_keyword() );
output( "\t%s 0,0\n", get_asm_short_keyword() );
}
}
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* terminator */
output( "\t%s 0\n", get_asm_short_keyword() ); /* terminator */
/* name strings */
@ -313,19 +316,19 @@ void output_res16_directory( FILE *outfile, DLLSPEC *spec, const char *header_na
{
if (type->type->str)
{
fprintf( outfile, ".L__wine_spec_restype_%u:\n", i );
output_string( outfile, type->type->str );
output( ".L__wine_spec_restype_%u:\n", i );
output_string( type->type->str );
}
for (j = 0, res = type->res; j < type->nb_names; j++, res++)
{
if (res->name.str)
{
fprintf( outfile, ".L__wine_spec_resname_%u_%u:\n", i, j );
output_string( outfile, res->name.str );
output( ".L__wine_spec_resname_%u_%u:\n", i, j );
output_string( res->name.str );
}
}
}
fprintf( outfile, "\t.byte 0\n" ); /* names terminator */
output( "\t.byte 0\n" ); /* names terminator */
free_resource_tree( tree );
}

View file

@ -15,10 +15,11 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <ctype.h>
#include <stdlib.h>
@ -36,7 +37,8 @@
#include <sys/mman.h>
#endif
#include "winglue.h"
#include "windef.h"
#include "winbase.h"
#include "build.h"
/* Unicode string or integer id */
@ -91,7 +93,7 @@ static const char *file_name; /* current resource file name */
#define RESDIR_SIZE(n) (sizeof(IMAGE_RESOURCE_DIRECTORY) + (n) * sizeof(IMAGE_RESOURCE_DIRECTORY_ENTRY))
inline static struct resource *add_resource( DLLSPEC *spec )
static inline struct resource *add_resource( DLLSPEC *spec )
{
spec->resources = xrealloc( spec->resources, (spec->nb_resources + 1) * sizeof(spec->resources[0]) );
return &spec->resources[spec->nb_resources++];
@ -314,29 +316,29 @@ static void free_resource_tree( struct res_tree *tree )
}
/* output a Unicode string */
static void output_string( FILE *outfile, const WCHAR *name )
static void output_string( const WCHAR *name )
{
int i, len = strlenW(name);
fprintf( outfile, "\t%s 0x%04x", get_asm_short_keyword(), len );
for (i = 0; i < len; i++) fprintf( outfile, ",0x%04x", name[i] );
fprintf( outfile, " /* " );
for (i = 0; i < len; i++) fprintf( outfile, "%c", isprint((char)name[i]) ? (char)name[i] : '?' );
fprintf( outfile, " */\n" );
output( "\t%s 0x%04x", get_asm_short_keyword(), len );
for (i = 0; i < len; i++) output( ",0x%04x", name[i] );
output( " /* " );
for (i = 0; i < len; i++) output( "%c", isprint((char)name[i]) ? (char)name[i] : '?' );
output( " */\n" );
}
/* output a resource directory */
static inline void output_res_dir( FILE *outfile, unsigned int nb_names, unsigned int nb_ids )
static inline void output_res_dir( unsigned int nb_names, unsigned int nb_ids )
{
fprintf( outfile, "\t.long 0\n" ); /* Characteristics */
fprintf( outfile, "\t.long 0\n" ); /* TimeDateStamp */
fprintf( outfile, "\t%s 0,0\n", /* Major/MinorVersion */
output( "\t.long 0\n" ); /* Characteristics */
output( "\t.long 0\n" ); /* TimeDateStamp */
output( "\t%s 0,0\n", /* Major/MinorVersion */
get_asm_short_keyword() );
fprintf( outfile, "\t%s %u,%u\n", /* NumberOfNamed/IdEntries */
output( "\t%s %u,%u\n", /* NumberOfNamed/IdEntries */
get_asm_short_keyword(), nb_names, nb_ids );
}
/* output the resource definitions */
void output_resources( FILE *outfile, DLLSPEC *spec )
void output_resources( DLLSPEC *spec )
{
int k, nb_id_types;
unsigned int i, n, offset, data_offset;
@ -386,19 +388,19 @@ void output_resources( FILE *outfile, DLLSPEC *spec )
/* output the resource directories */
fprintf( outfile, "\n/* resources */\n\n" );
fprintf( outfile, "\t.data\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(get_ptr_size()) );
fprintf( outfile, ".L__wine_spec_resources:\n" );
output( "\n/* resources */\n\n" );
output( "\t.data\n" );
output( "\t.align %d\n", get_alignment(get_ptr_size()) );
output( ".L__wine_spec_resources:\n" );
output_res_dir( outfile, tree->nb_types - nb_id_types, nb_id_types );
output_res_dir( tree->nb_types - nb_id_types, nb_id_types );
/* dump the type directory */
offset = RESDIR_SIZE( tree->nb_types );
for (i = 0, type = tree->types; i < tree->nb_types; i++, type++)
{
fprintf( outfile, "\t.long 0x%08x,0x%08x\n",
output( "\t.long 0x%08x,0x%08x\n",
type->name_offset, offset | 0x80000000 );
offset += RESDIR_SIZE( type->nb_names );
for (n = 0, name = type->names; n < type->nb_names; n++, name++)
@ -412,22 +414,22 @@ void output_resources( FILE *outfile, DLLSPEC *spec )
for (i = 0, type = tree->types; i < tree->nb_types; i++, type++)
{
output_res_dir( outfile, type->nb_names - type->nb_id_names, type->nb_id_names );
output_res_dir( type->nb_names - type->nb_id_names, type->nb_id_names );
offset += RESDIR_SIZE( type->nb_names );
for (n = 0, name = type->names; n < type->nb_names; n++, name++)
{
fprintf( outfile, "\t.long 0x%08x,0x%08x\n",
output( "\t.long 0x%08x,0x%08x\n",
name->name_offset, offset | 0x80000000 );
offset += RESDIR_SIZE( name->nb_languages );
}
for (n = 0, name = type->names; n < type->nb_names; n++, name++)
{
output_res_dir( outfile, 0, name->nb_languages );
output_res_dir( 0, name->nb_languages );
for (k = 0, res = name->res; k < name->nb_languages; k++, res++)
{
fprintf( outfile, "\t.long 0x%08x,0x%08x\n", res->lang,
data_offset + (res - spec->resources) * sizeof(IMAGE_RESOURCE_DATA_ENTRY) );
unsigned int entry_offset = (res - spec->resources) * sizeof(IMAGE_RESOURCE_DATA_ENTRY);
output( "\t.long 0x%08x,0x%08x\n", res->lang, data_offset + entry_offset );
}
}
}
@ -435,28 +437,28 @@ void output_resources( FILE *outfile, DLLSPEC *spec )
/* dump the resource data entries */
for (i = 0, res = spec->resources; i < spec->nb_resources; i++, res++)
fprintf( outfile, "\t.long .L__wine_spec_res_%d-.L__wine_spec_rva_base,%u,0,0\n",
output( "\t.long .L__wine_spec_res_%d-.L__wine_spec_rva_base,%u,0,0\n",
i, res->data_size );
/* dump the name strings */
for (i = 0, type = tree->types; i < tree->nb_types; i++, type++)
{
if (type->type->str) output_string( outfile, type->type->str );
if (type->type->str) output_string( type->type->str );
for (n = 0, name = type->names; n < type->nb_names; n++, name++)
if (name->name->str) output_string( outfile, name->name->str );
if (name->name->str) output_string( name->name->str );
}
/* resource data */
for (i = 0, res = spec->resources; i < spec->nb_resources; i++, res++)
{
fprintf( outfile, "\n\t.align %d\n", get_alignment(get_ptr_size()) );
fprintf( outfile, ".L__wine_spec_res_%d:\n", i );
dump_bytes( outfile, res->data, res->data_size );
output( "\n\t.align %d\n", get_alignment(get_ptr_size()) );
output( ".L__wine_spec_res_%d:\n", i );
dump_bytes( res->data, res->data_size );
}
fprintf( outfile, ".L__wine_spec_resources_end:\n" );
fprintf( outfile, "\t.byte 0\n" );
output( ".L__wine_spec_resources_end:\n" );
output( "\t.byte 0\n" );
free_resource_tree( tree );
}

View file

@ -19,10 +19,11 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <assert.h>
#include <ctype.h>
@ -53,31 +54,31 @@ static inline int is_function( const ORDDEF *odp )
*
* Output entries for individual symbols in the entry table.
*/
static void output_entries( FILE *outfile, DLLSPEC *spec, int first, int count )
static void output_entries( DLLSPEC *spec, int first, int count )
{
int i;
for (i = 0; i < count; i++)
{
ORDDEF *odp = spec->ordinals[first + i];
fprintf( outfile, "\t.byte 0x03\n" ); /* flags: exported & public data */
output( "\t.byte 0x03\n" ); /* flags: exported & public data */
switch (odp->type)
{
case TYPE_CDECL:
case TYPE_PASCAL:
case TYPE_VARARGS:
case TYPE_STUB:
fprintf( outfile, "\t%s .L__wine_%s_%u-.L__wine_spec_code_segment\n",
output( "\t%s .L__wine_%s_%u-.L__wine_spec_code_segment\n",
get_asm_short_keyword(),
make_c_identifier(spec->dll_name), first + i );
break;
case TYPE_VARIABLE:
fprintf( outfile, "\t%s .L__wine_%s_%u-.L__wine_spec_data_segment\n",
output( "\t%s .L__wine_%s_%u-.L__wine_spec_data_segment\n",
get_asm_short_keyword(),
make_c_identifier(spec->dll_name), first + i );
break;
case TYPE_ABS:
fprintf( outfile, "\t%s 0x%04x /* %s */\n",
output( "\t%s 0x%04x /* %s */\n",
get_asm_short_keyword(), odp->u.abs.value, odp->name );
break;
default:
@ -90,7 +91,7 @@ static void output_entries( FILE *outfile, DLLSPEC *spec, int first, int count )
/*******************************************************************
* output_entry_table
*/
static void output_entry_table( FILE *outfile, DLLSPEC *spec )
static void output_entry_table( DLLSPEC *spec )
{
int i, prev = 0, prev_sel = -1, bundle_count = 0;
@ -125,10 +126,10 @@ static void output_entry_table( FILE *outfile, DLLSPEC *spec )
/* flush previous bundle */
if (bundle_count)
{
fprintf( outfile, "\t/* %s.%d - %s.%d */\n",
output( "\t/* %s.%d - %s.%d */\n",
spec->dll_name, prev - bundle_count + 1, spec->dll_name, prev );
fprintf( outfile, "\t.byte 0x%02x,0x%02x\n", bundle_count, prev_sel );
output_entries( outfile, spec, prev - bundle_count + 1, bundle_count );
output( "\t.byte 0x%02x,0x%02x\n", bundle_count, prev_sel );
output_entries( spec, prev - bundle_count + 1, bundle_count );
}
if (prev + 1 != i)
@ -136,10 +137,10 @@ static void output_entry_table( FILE *outfile, DLLSPEC *spec )
int skip = i - (prev + 1);
while (skip > 255)
{
fprintf( outfile, "\t.byte 0xff,0x00\n" );
output( "\t.byte 0xff,0x00\n" );
skip -= 255;
}
fprintf( outfile, "\t.byte 0x%02x,0x00\n", skip );
output( "\t.byte 0x%02x,0x00\n", skip );
}
bundle_count = 0;
@ -152,24 +153,24 @@ static void output_entry_table( FILE *outfile, DLLSPEC *spec )
/* flush last bundle */
if (bundle_count)
{
fprintf( outfile, "\t.byte 0x%02x,0x%02x\n", bundle_count, prev_sel );
output_entries( outfile, spec, prev - bundle_count + 1, bundle_count );
output( "\t.byte 0x%02x,0x%02x\n", bundle_count, prev_sel );
output_entries( spec, prev - bundle_count + 1, bundle_count );
}
fprintf( outfile, "\t.byte 0x00\n" );
output( "\t.byte 0x00\n" );
}
/*******************************************************************
* output_resident_name
*/
static void output_resident_name( FILE *outfile, const char *string, int ordinal )
static void output_resident_name( const char *string, int ordinal )
{
unsigned int i, len = strlen(string);
fprintf( outfile, "\t.byte 0x%02x", len );
for (i = 0; i < len; i++) fprintf( outfile, ",0x%02x", (unsigned char)toupper(string[i]) );
fprintf( outfile, " /* %s */\n", string );
fprintf( outfile, "\t%s %u\n", get_asm_short_keyword(), ordinal );
output( "\t.byte 0x%02x", len );
for (i = 0; i < len; i++) output( ",0x%02x", (unsigned char)toupper(string[i]) );
output( " /* %s */\n", string );
output( "\t%s %u\n", get_asm_short_keyword(), ordinal );
}
@ -282,7 +283,7 @@ static int get_function_argsize( const ORDDEF *odp )
* the same as for normal functions, but in addition the CONTEXT86 pointer
* filled with the current register values is passed to the 32-bit routine.
*/
static void output_call16_function( FILE *outfile, ORDDEF *odp )
static void output_call16_function( ORDDEF *odp )
{
char name[256];
int i, pos, stack_words;
@ -292,41 +293,41 @@ static void output_call16_function( FILE *outfile, ORDDEF *odp )
sprintf( name, ".L__wine_spec_call16_%s", get_relay_name(odp) );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t%s\n", func_declaration(name) );
fprintf( outfile, "%s:\n", name );
fprintf( outfile, "\tpushl %%ebp\n" );
fprintf( outfile, "\tmovl %%esp,%%ebp\n" );
output( "\t.align %d\n", get_alignment(4) );
output( "\t%s\n", func_declaration(name) );
output( "%s:\n", name );
output( "\tpushl %%ebp\n" );
output( "\tmovl %%esp,%%ebp\n" );
stack_words = 2;
if (needs_ldt)
{
fprintf( outfile, "\tpushl %%esi\n" );
output( "\tpushl %%esi\n" );
stack_words++;
if (UsePIC)
{
fprintf( outfile, "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
fprintf( outfile, "1:\tmovl wine_ldt_copy_ptr-1b(%%eax),%%esi\n" );
output( "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
output( "1:\tmovl wine_ldt_copy_ptr-1b(%%eax),%%esi\n" );
}
else
fprintf( outfile, "\tmovl $%s,%%esi\n", asm_name("wine_ldt_copy") );
output( "\tmovl $%s,%%esi\n", asm_name("wine_ldt_copy") );
}
/* preserve 16-byte stack alignment */
stack_words += strlen(args);
if ((odp->flags & FLAG_REGISTER) || (odp->type == TYPE_VARARGS)) stack_words++;
if (stack_words % 4) fprintf( outfile, "\tsubl $%d,%%esp\n", 16 - 4 * (stack_words % 4) );
if (stack_words % 4) output( "\tsubl $%d,%%esp\n", 16 - 4 * (stack_words % 4) );
if (args[0] || odp->type == TYPE_VARARGS)
fprintf( outfile, "\tmovl 12(%%ebp),%%ecx\n" ); /* args */
output( "\tmovl 12(%%ebp),%%ecx\n" ); /* args */
if (odp->flags & FLAG_REGISTER)
{
fprintf( outfile, "\tpushl 16(%%ebp)\n" ); /* context */
output( "\tpushl 16(%%ebp)\n" ); /* context */
}
else if (odp->type == TYPE_VARARGS)
{
fprintf( outfile, "\tleal %d(%%ecx),%%eax\n", argsize );
fprintf( outfile, "\tpushl %%eax\n" ); /* va_list16 */
output( "\tleal %d(%%ecx),%%eax\n", argsize );
output( "\tpushl %%eax\n" ); /* va_list16 */
}
pos = (odp->type == TYPE_PASCAL) ? 0 : argsize;
@ -336,33 +337,33 @@ static void output_call16_function( FILE *outfile, ORDDEF *odp )
{
case 'w': /* word */
if (odp->type != TYPE_PASCAL) pos -= 2;
fprintf( outfile, "\tmovzwl %d(%%ecx),%%eax\n", pos );
fprintf( outfile, "\tpushl %%eax\n" );
output( "\tmovzwl %d(%%ecx),%%eax\n", pos );
output( "\tpushl %%eax\n" );
if (odp->type == TYPE_PASCAL) pos += 2;
break;
case 's': /* s_word */
if (odp->type != TYPE_PASCAL) pos -= 2;
fprintf( outfile, "\tmovswl %d(%%ecx),%%eax\n", pos );
fprintf( outfile, "\tpushl %%eax\n" );
output( "\tmovswl %d(%%ecx),%%eax\n", pos );
output( "\tpushl %%eax\n" );
if (odp->type == TYPE_PASCAL) pos += 2;
break;
case 'l': /* long or segmented pointer */
case 'T': /* segmented pointer to null-terminated string */
if (odp->type != TYPE_PASCAL) pos -= 4;
fprintf( outfile, "\tpushl %d(%%ecx)\n", pos );
output( "\tpushl %d(%%ecx)\n", pos );
if (odp->type == TYPE_PASCAL) pos += 4;
break;
case 'p': /* linear pointer */
case 't': /* linear pointer to null-terminated string */
if (odp->type != TYPE_PASCAL) pos -= 4;
fprintf( outfile, "\tmovzwl %d(%%ecx),%%edx\n", pos + 2 ); /* sel */
fprintf( outfile, "\tshr $3,%%edx\n" );
fprintf( outfile, "\tmovzwl %d(%%ecx),%%eax\n", pos ); /* offset */
fprintf( outfile, "\taddl (%%esi,%%edx,4),%%eax\n" );
fprintf( outfile, "\tpushl %%eax\n" );
output( "\tmovzwl %d(%%ecx),%%edx\n", pos + 2 ); /* sel */
output( "\tshr $3,%%edx\n" );
output( "\tmovzwl %d(%%ecx),%%eax\n", pos ); /* offset */
output( "\taddl (%%esi,%%edx,4),%%eax\n" );
output( "\tpushl %%eax\n" );
if (odp->type == TYPE_PASCAL) pos += 4;
break;
@ -371,14 +372,13 @@ static void output_call16_function( FILE *outfile, ORDDEF *odp )
}
}
fprintf( outfile, "\tcall *8(%%ebp)\n" );
output( "\tcall *8(%%ebp)\n" );
if (needs_ldt) fprintf( outfile, "\tmovl -4(%%ebp),%%esi\n" );
if (odp->flags & FLAG_RET16) fprintf( outfile, "\tmovzwl %%ax,%%eax\n" );
if (needs_ldt) output( "\tmovl -4(%%ebp),%%esi\n" );
fprintf( outfile, "\tleave\n" );
fprintf( outfile, "\tret\n" );
output_function_size( outfile, name );
output( "\tleave\n" );
output( "\tret\n" );
output_function_size( name );
}
@ -450,72 +450,72 @@ static int sort_func_list( ORDDEF **list, int count,
*
* Output the dll initialization code.
*/
static void output_init_code( FILE *outfile, const DLLSPEC *spec, const char *header_name )
static void output_init_code( const DLLSPEC *spec, const char *header_name )
{
char name[80];
sprintf( name, ".L__wine_spec_%s_init", make_c_identifier(spec->dll_name) );
fprintf( outfile, "\n/* dll initialization code */\n\n" );
fprintf( outfile, "\t.text\n" );
fprintf( outfile, "\t.align 4\n" );
fprintf( outfile, "\t%s\n", func_declaration(name) );
fprintf( outfile, "%s:\n", name );
fprintf( outfile, "subl $4,%%esp\n" );
output( "\n/* dll initialization code */\n\n" );
output( "\t.text\n" );
output( "\t.align 4\n" );
output( "\t%s\n", func_declaration(name) );
output( "%s:\n", name );
output( "subl $4,%%esp\n" );
if (UsePIC)
{
fprintf( outfile, "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
fprintf( outfile, "1:\tleal .L__wine_spec_file_name-1b(%%eax),%%ecx\n" );
fprintf( outfile, "\tpushl %%ecx\n" );
fprintf( outfile, "\tleal %s-1b(%%eax),%%ecx\n", header_name );
fprintf( outfile, "\tpushl %%ecx\n" );
output( "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
output( "1:\tleal .L__wine_spec_file_name-1b(%%eax),%%ecx\n" );
output( "\tpushl %%ecx\n" );
output( "\tleal %s-1b(%%eax),%%ecx\n", header_name );
output( "\tpushl %%ecx\n" );
}
else
{
fprintf( outfile, "\tpushl $.L__wine_spec_file_name\n" );
fprintf( outfile, "\tpushl $%s\n", header_name );
output( "\tpushl $.L__wine_spec_file_name\n" );
output( "\tpushl $%s\n", header_name );
}
fprintf( outfile, "\tcall %s\n", asm_name("__wine_dll_register_16") );
fprintf( outfile, "\taddl $12,%%esp\n" );
fprintf( outfile, "\tret\n" );
output_function_size( outfile, name );
output( "\tcall %s\n", asm_name("__wine_dll_register_16") );
output( "\taddl $12,%%esp\n" );
output( "\tret\n" );
output_function_size( name );
sprintf( name, ".L__wine_spec_%s_fini", make_c_identifier(spec->dll_name) );
fprintf( outfile, "\t.align 4\n" );
fprintf( outfile, "\t%s\n", func_declaration(name) );
fprintf( outfile, "%s:\n", name );
fprintf( outfile, "subl $8,%%esp\n" );
output( "\t.align 4\n" );
output( "\t%s\n", func_declaration(name) );
output( "%s:\n", name );
output( "subl $8,%%esp\n" );
if (UsePIC)
{
fprintf( outfile, "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
fprintf( outfile, "1:\tleal %s-1b(%%eax),%%ecx\n", header_name );
fprintf( outfile, "\tpushl %%ecx\n" );
output( "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
output( "1:\tleal %s-1b(%%eax),%%ecx\n", header_name );
output( "\tpushl %%ecx\n" );
}
else
{
fprintf( outfile, "\tpushl $%s\n", header_name );
output( "\tpushl $%s\n", header_name );
}
fprintf( outfile, "\tcall %s\n", asm_name("__wine_dll_unregister_16") );
fprintf( outfile, "\taddl $12,%%esp\n" );
fprintf( outfile, "\tret\n" );
output_function_size( outfile, name );
output( "\tcall %s\n", asm_name("__wine_dll_unregister_16") );
output( "\taddl $12,%%esp\n" );
output( "\tret\n" );
output_function_size( name );
if (target_platform == PLATFORM_APPLE)
{
fprintf( outfile, "\t.mod_init_func\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.long .L__wine_spec_%s_init\n", make_c_identifier(spec->dll_name) );
fprintf( outfile, "\t.mod_term_func\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.long .L__wine_spec_%s_fini\n", make_c_identifier(spec->dll_name) );
output( "\t.mod_init_func\n" );
output( "\t.align %d\n", get_alignment(4) );
output( "\t.long .L__wine_spec_%s_init\n", make_c_identifier(spec->dll_name) );
output( "\t.mod_term_func\n" );
output( "\t.align %d\n", get_alignment(4) );
output( "\t.long .L__wine_spec_%s_fini\n", make_c_identifier(spec->dll_name) );
}
else
{
fprintf( outfile, "\t.section \".init\",\"ax\"\n" );
fprintf( outfile, "\tcall .L__wine_spec_%s_init\n", make_c_identifier(spec->dll_name) );
fprintf( outfile, "\t.section \".fini\",\"ax\"\n" );
fprintf( outfile, "\tcall .L__wine_spec_%s_fini\n", make_c_identifier(spec->dll_name) );
output( "\t.section \".init\",\"ax\"\n" );
output( "\tcall .L__wine_spec_%s_init\n", make_c_identifier(spec->dll_name) );
output( "\t.section \".fini\",\"ax\"\n" );
output( "\tcall .L__wine_spec_%s_fini\n", make_c_identifier(spec->dll_name) );
}
}
@ -525,7 +525,7 @@ static void output_init_code( FILE *outfile, const DLLSPEC *spec, const char *he
*
* Build a Win16 assembly file from a spec file.
*/
void BuildSpec16File( FILE *outfile, DLLSPEC *spec )
void BuildSpec16File( DLLSPEC *spec )
{
ORDDEF **typelist;
int i, j, nb_funcs;
@ -533,7 +533,7 @@ void BuildSpec16File( FILE *outfile, DLLSPEC *spec )
/* File header */
output_standard_file_header( outfile );
output_standard_file_header();
if (!spec->dll_name) /* set default name from file name */
{
@ -558,135 +558,135 @@ void BuildSpec16File( FILE *outfile, DLLSPEC *spec )
/* Output the module structure */
sprintf( header_name, "__wine_spec_%s_dos_header", make_c_identifier(spec->dll_name) );
fprintf( outfile, "\n/* module data */\n\n" );
fprintf( outfile, "\t.data\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, "%s:\n", header_name );
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), /* e_magic */
output( "\n/* module data */\n\n" );
output( "\t.data\n" );
output( "\t.align %d\n", get_alignment(4) );
output( "%s:\n", header_name );
output( "\t%s 0x%04x\n", get_asm_short_keyword(), /* e_magic */
IMAGE_DOS_SIGNATURE );
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_cblp */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_cp */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_crlc */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_cparhdr */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_minalloc */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_maxalloc */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_ss */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_sp */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_csum */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_ip */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_cs */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_lfarlc */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_ovno */
fprintf( outfile, "\t%s 0,0,0,0\n", get_asm_short_keyword() ); /* e_res */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_oemid */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* e_oeminfo */
fprintf( outfile, "\t%s 0,0,0,0,0,0,0,0,0,0\n", get_asm_short_keyword() ); /* e_res2 */
fprintf( outfile, "\t.long .L__wine_spec_ne_header-%s\n", header_name ); /* e_lfanew */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_cblp */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_cp */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_crlc */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_cparhdr */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_minalloc */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_maxalloc */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_ss */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_sp */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_csum */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_ip */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_cs */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_lfarlc */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_ovno */
output( "\t%s 0,0,0,0\n", get_asm_short_keyword() ); /* e_res */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_oemid */
output( "\t%s 0\n", get_asm_short_keyword() ); /* e_oeminfo */
output( "\t%s 0,0,0,0,0,0,0,0,0,0\n", get_asm_short_keyword() ); /* e_res2 */
output( "\t.long .L__wine_spec_ne_header-%s\n", header_name ); /* e_lfanew */
fprintf( outfile, ".L__wine_spec_ne_header:\n" );
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), /* ne_magic */
output( ".L__wine_spec_ne_header:\n" );
output( "\t%s 0x%04x\n", get_asm_short_keyword(), /* ne_magic */
IMAGE_OS2_SIGNATURE );
fprintf( outfile, "\t.byte 0\n" ); /* ne_ver */
fprintf( outfile, "\t.byte 0\n" ); /* ne_rev */
fprintf( outfile, "\t%s .L__wine_spec_ne_enttab-.L__wine_spec_ne_header\n", /* ne_enttab */
output( "\t.byte 0\n" ); /* ne_ver */
output( "\t.byte 0\n" ); /* ne_rev */
output( "\t%s .L__wine_spec_ne_enttab-.L__wine_spec_ne_header\n", /* ne_enttab */
get_asm_short_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_ne_enttab_end-.L__wine_spec_ne_enttab\n", /* ne_cbenttab */
output( "\t%s .L__wine_spec_ne_enttab_end-.L__wine_spec_ne_enttab\n", /* ne_cbenttab */
get_asm_short_keyword() );
fprintf( outfile, "\t.long 0\n" ); /* ne_crc */
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), /* ne_flags */
output( "\t.long 0\n" ); /* ne_crc */
output( "\t%s 0x%04x\n", get_asm_short_keyword(), /* ne_flags */
NE_FFLAGS_SINGLEDATA | NE_FFLAGS_LIBMODULE );
fprintf( outfile, "\t%s 2\n", get_asm_short_keyword() ); /* ne_autodata */
fprintf( outfile, "\t%s %u\n", get_asm_short_keyword(), spec->heap_size ); /* ne_heap */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_stack */
fprintf( outfile, "\t.long 0\n" ); /* ne_csip */
fprintf( outfile, "\t.long 0\n" ); /* ne_sssp */
fprintf( outfile, "\t%s 2\n", get_asm_short_keyword() ); /* ne_cseg */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_cmod */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_cbnrestab */
fprintf( outfile, "\t%s .L__wine_spec_ne_segtab-.L__wine_spec_ne_header\n", /* ne_segtab */
output( "\t%s 2\n", get_asm_short_keyword() ); /* ne_autodata */
output( "\t%s %u\n", get_asm_short_keyword(), spec->heap_size ); /* ne_heap */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_stack */
output( "\t.long 0\n" ); /* ne_csip */
output( "\t.long 0\n" ); /* ne_sssp */
output( "\t%s 2\n", get_asm_short_keyword() ); /* ne_cseg */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_cmod */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_cbnrestab */
output( "\t%s .L__wine_spec_ne_segtab-.L__wine_spec_ne_header\n", /* ne_segtab */
get_asm_short_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_ne_rsrctab-.L__wine_spec_ne_header\n", /* ne_rsrctab */
output( "\t%s .L__wine_spec_ne_rsrctab-.L__wine_spec_ne_header\n", /* ne_rsrctab */
get_asm_short_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_ne_restab-.L__wine_spec_ne_header\n", /* ne_restab */
output( "\t%s .L__wine_spec_ne_restab-.L__wine_spec_ne_header\n", /* ne_restab */
get_asm_short_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_ne_modtab-.L__wine_spec_ne_header\n", /* ne_modtab */
output( "\t%s .L__wine_spec_ne_modtab-.L__wine_spec_ne_header\n", /* ne_modtab */
get_asm_short_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_ne_imptab-.L__wine_spec_ne_header\n", /* ne_imptab */
output( "\t%s .L__wine_spec_ne_imptab-.L__wine_spec_ne_header\n", /* ne_imptab */
get_asm_short_keyword() );
fprintf( outfile, "\t.long 0\n" ); /* ne_nrestab */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_cmovent */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_align */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_cres */
fprintf( outfile, "\t.byte 0x%02x\n", NE_OSFLAGS_WINDOWS ); /* ne_exetyp */
fprintf( outfile, "\t.byte 0x%02x\n", NE_AFLAGS_FASTLOAD ); /* ne_flagsothers */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_pretthunks */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_psegrefbytes */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_swaparea */
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() ); /* ne_expver */
output( "\t.long 0\n" ); /* ne_nrestab */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_cmovent */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_align */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_cres */
output( "\t.byte 0x%02x\n", NE_OSFLAGS_WINDOWS ); /* ne_exetyp */
output( "\t.byte 0x%02x\n", NE_AFLAGS_FASTLOAD ); /* ne_flagsothers */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_pretthunks */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_psegrefbytes */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_swaparea */
output( "\t%s 0\n", get_asm_short_keyword() ); /* ne_expver */
/* segment table */
fprintf( outfile, "\n.L__wine_spec_ne_segtab:\n" );
output( "\n.L__wine_spec_ne_segtab:\n" );
/* code segment entry */
fprintf( outfile, "\t%s .L__wine_spec_code_segment-%s\n", /* filepos */
output( "\t%s .L__wine_spec_code_segment-%s\n", /* filepos */
get_asm_short_keyword(), header_name );
fprintf( outfile, "\t%s .L__wine_spec_code_segment_end-.L__wine_spec_code_segment\n", /* size */
output( "\t%s .L__wine_spec_code_segment_end-.L__wine_spec_code_segment\n", /* size */
get_asm_short_keyword() );
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), NE_SEGFLAGS_32BIT ); /* flags */
fprintf( outfile, "\t%s .L__wine_spec_code_segment_end-.L__wine_spec_code_segment\n", /* minsize */
output( "\t%s 0x%04x\n", get_asm_short_keyword(), NE_SEGFLAGS_32BIT ); /* flags */
output( "\t%s .L__wine_spec_code_segment_end-.L__wine_spec_code_segment\n", /* minsize */
get_asm_short_keyword() );
/* data segment entry */
fprintf( outfile, "\t%s .L__wine_spec_data_segment-%s\n", /* filepos */
output( "\t%s .L__wine_spec_data_segment-%s\n", /* filepos */
get_asm_short_keyword(), header_name );
fprintf( outfile, "\t%s .L__wine_spec_data_segment_end-.L__wine_spec_data_segment\n", /* size */
output( "\t%s .L__wine_spec_data_segment_end-.L__wine_spec_data_segment\n", /* size */
get_asm_short_keyword() );
fprintf( outfile, "\t%s 0x%04x\n", get_asm_short_keyword(), NE_SEGFLAGS_DATA ); /* flags */
fprintf( outfile, "\t%s .L__wine_spec_data_segment_end-.L__wine_spec_data_segment\n", /* minsize */
output( "\t%s 0x%04x\n", get_asm_short_keyword(), NE_SEGFLAGS_DATA ); /* flags */
output( "\t%s .L__wine_spec_data_segment_end-.L__wine_spec_data_segment\n", /* minsize */
get_asm_short_keyword() );
/* resource directory */
output_res16_directory( outfile, spec, header_name );
output_res16_directory( spec, header_name );
/* resident names table */
fprintf( outfile, "\n\t.align %d\n", get_alignment(2) );
fprintf( outfile, ".L__wine_spec_ne_restab:\n" );
output_resident_name( outfile, spec->dll_name, 0 );
output( "\n\t.align %d\n", get_alignment(2) );
output( ".L__wine_spec_ne_restab:\n" );
output_resident_name( spec->dll_name, 0 );
for (i = 1; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (!odp || !odp->name[0]) continue;
output_resident_name( outfile, odp->name, i );
output_resident_name( odp->name, i );
}
fprintf( outfile, "\t.byte 0\n" );
output( "\t.byte 0\n" );
/* imported names table */
fprintf( outfile, "\n\t.align %d\n", get_alignment(2) );
fprintf( outfile, ".L__wine_spec_ne_modtab:\n" );
fprintf( outfile, ".L__wine_spec_ne_imptab:\n" );
fprintf( outfile, "\t.byte 0,0\n" );
output( "\n\t.align %d\n", get_alignment(2) );
output( ".L__wine_spec_ne_modtab:\n" );
output( ".L__wine_spec_ne_imptab:\n" );
output( "\t.byte 0,0\n" );
/* entry table */
fprintf( outfile, "\n.L__wine_spec_ne_enttab:\n" );
output_entry_table( outfile, spec );
fprintf( outfile, ".L__wine_spec_ne_enttab_end:\n" );
output( "\n.L__wine_spec_ne_enttab:\n" );
output_entry_table( spec );
output( ".L__wine_spec_ne_enttab_end:\n" );
/* code segment */
fprintf( outfile, "\n\t.align %d\n", get_alignment(2) );
fprintf( outfile, ".L__wine_spec_code_segment:\n" );
output( "\n\t.align %d\n", get_alignment(2) );
output( ".L__wine_spec_code_segment:\n" );
for ( i = 0; i < nb_funcs; i++ )
{
unsigned int arg_types[2];
int j, nop_words, argsize = 0;
int nop_words, argsize = 0;
if ( typelist[i]->type == TYPE_PASCAL )
argsize = get_function_argsize( typelist[i] );
@ -709,9 +709,9 @@ void BuildSpec16File( FILE *outfile, DLLSPEC *spec )
}
if (typelist[i]->type == TYPE_VARARGS) arg_types[j / 10] |= ARG_VARARG << (3 * (j % 10));
fprintf( outfile, ".L__wine_spec_callfrom16_%s:\n", get_callfrom16_name(typelist[i]) );
fprintf( outfile, "\tpushl $.L__wine_spec_call16_%s\n", get_relay_name(typelist[i]) );
fprintf( outfile, "\tlcall $0,$0\n" );
output( ".L__wine_spec_callfrom16_%s:\n", get_callfrom16_name(typelist[i]) );
output( "\tpushl $.L__wine_spec_call16_%s\n", get_relay_name(typelist[i]) );
output( "\tlcall $0,$0\n" );
if (typelist[i]->flags & FLAG_REGISTER)
{
@ -719,90 +719,91 @@ void BuildSpec16File( FILE *outfile, DLLSPEC *spec )
}
else if (typelist[i]->flags & FLAG_RET16)
{
fprintf( outfile, "\torw %%ax,%%ax\n" );
fprintf( outfile, "\tnop\n" ); /* so that the lretw is aligned */
output( "\torw %%ax,%%ax\n" );
output( "\tnop\n" ); /* so that the lretw is aligned */
nop_words = 2;
}
else
{
fprintf( outfile, "shld $16,%%eax,%%edx\n" );
fprintf( outfile, "orl %%eax,%%eax\n" );
output( "\tshld $16,%%eax,%%edx\n" );
output( "\torl %%eax,%%eax\n" );
nop_words = 1;
}
if (argsize)
{
fprintf( outfile, "lretw $%u\n", argsize );
output( "\tlretw $%u\n", argsize );
nop_words--;
}
else fprintf( outfile, "lretw\n" );
else output( "\tlretw\n" );
if (nop_words) fprintf( outfile, "\t%s\n", nop_sequence[nop_words-1] );
if (nop_words) output( "\t%s\n", nop_sequence[nop_words-1] );
/* the movl is here so that the code contains only valid instructions, */
/* it's never actually executed, we only care about the arg_types[] values */
fprintf( outfile, "\t%s 0x86c7\n", get_asm_short_keyword() );
fprintf( outfile, "\t.long 0x%08x,0x%08x\n", arg_types[0], arg_types[1] );
output( "\t%s 0x86c7\n", get_asm_short_keyword() );
output( "\t.long 0x%08x,0x%08x\n", arg_types[0], arg_types[1] );
}
for (i = 0; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (!odp || !is_function( odp )) continue;
fprintf( outfile, ".L__wine_%s_%u:\n", make_c_identifier(spec->dll_name), i );
fprintf( outfile, "\tpushw %%bp\n" );
fprintf( outfile, "\tpushl $%s\n",
output( ".L__wine_%s_%u:\n", make_c_identifier(spec->dll_name), i );
output( "\tpushw %%bp\n" );
output( "\tpushl $%s\n",
asm_name( odp->type == TYPE_STUB ? get_stub_name( odp, spec ) : odp->link_name ));
fprintf( outfile, "\tcallw .L__wine_spec_callfrom16_%s\n", get_callfrom16_name( odp ) );
output( "\tcallw .L__wine_spec_callfrom16_%s\n", get_callfrom16_name( odp ) );
}
fprintf( outfile, ".L__wine_spec_code_segment_end:\n" );
output( ".L__wine_spec_code_segment_end:\n" );
/* data segment */
fprintf( outfile, "\n.L__wine_spec_data_segment:\n" );
fprintf( outfile, "\t.byte 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0\n" ); /* instance data */
output( "\n.L__wine_spec_data_segment:\n" );
output( "\t.byte 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0\n" ); /* instance data */
for (i = 0; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (!odp || odp->type != TYPE_VARIABLE) continue;
fprintf( outfile, ".L__wine_%s_%u:\n", make_c_identifier(spec->dll_name), i );
fprintf( outfile, "\t.long " );
output( ".L__wine_%s_%u:\n", make_c_identifier(spec->dll_name), i );
output( "\t.long " );
for (j = 0; j < odp->u.var.n_values-1; j++)
fprintf( outfile, "0x%08x,", odp->u.var.values[j] );
fprintf( outfile, "0x%08x\n", odp->u.var.values[j] );
output( "0x%08x,", odp->u.var.values[j] );
output( "0x%08x\n", odp->u.var.values[j] );
}
fprintf( outfile, ".L__wine_spec_data_segment_end:\n" );
output( ".L__wine_spec_data_segment_end:\n" );
/* resource data */
if (spec->nb_resources)
{
fprintf( outfile, "\n.L__wine_spec_resource_data:\n" );
output_res16_data( outfile, spec );
output( "\n.L__wine_spec_resource_data:\n" );
output_res16_data( spec );
}
fprintf( outfile, "\t.byte 0\n" ); /* make sure the last symbol points to something */
output( "\t.byte 0\n" ); /* make sure the last symbol points to something */
/* relay functions */
nb_funcs = sort_func_list( typelist, nb_funcs, relay_type_compare );
if (nb_funcs)
{
fprintf( outfile, "\n/* relay functions */\n\n" );
fprintf( outfile, "\t.text\n" );
for ( i = 0; i < nb_funcs; i++ ) output_call16_function( outfile, typelist[i] );
fprintf( outfile, "\t.data\n" );
fprintf( outfile, "wine_ldt_copy_ptr:\n" );
fprintf( outfile, "\t.long %s\n", asm_name("wine_ldt_copy") );
output( "\n/* relay functions */\n\n" );
output( "\t.text\n" );
for ( i = 0; i < nb_funcs; i++ ) output_call16_function( typelist[i] );
output( "\t.data\n" );
output( "wine_ldt_copy_ptr:\n" );
output( "\t.long %s\n", asm_name("wine_ldt_copy") );
}
fprintf( outfile, "\n\t%s\n", get_asm_string_section() );
fprintf( outfile, ".L__wine_spec_file_name:\n" );
fprintf( outfile, "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
output( "\n\t%s\n", get_asm_string_section() );
output( ".L__wine_spec_file_name:\n" );
output( "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
output_stubs( outfile, spec );
output_get_pc_thunk( outfile );
output_init_code( outfile, spec, header_name );
output_stubs( spec );
output_get_pc_thunk();
output_init_code( spec, header_name );
output_gnu_stack_note();
free( typelist );
}

View file

@ -19,21 +19,20 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#include "wine/port.h"
#include <assert.h>
#include <ctype.h>
#include <stdarg.h>
#include <string.h>
#include "winglue.h"
#define EXCEPTION_WINE_STUB 0x80000100 /* stub entry point called */
#define EH_NONCONTINUABLE 0x01
#include "windef.h"
#include "winbase.h"
//#include "wine/exception.h"
#include "build.h"
@ -52,7 +51,7 @@ static inline int needs_relay( const ORDDEF *odp )
/* check if dll will output relay thunks */
int has_relays( DLLSPEC *spec )
{
unsigned int i;
int i;
if (target_cpu != CPU_x86) return 0;
@ -91,30 +90,31 @@ static const char *make_internal_name( const ORDDEF *odp, DLLSPEC *spec, const c
*
* Output entry points for relay debugging
*/
static void output_relay_debug( FILE *outfile, DLLSPEC *spec )
static void output_relay_debug( DLLSPEC *spec )
{
unsigned int i, j, args, flags;
int i;
unsigned int j, args, flags;
/* first the table of entry point offsets */
fprintf( outfile, "\t%s\n", get_asm_rodata_section() );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, ".L__wine_spec_relay_entry_point_offsets:\n" );
output( "\t%s\n", get_asm_rodata_section() );
output( "\t.align %d\n", get_alignment(4) );
output( ".L__wine_spec_relay_entry_point_offsets:\n" );
for (i = spec->base; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (needs_relay( odp ))
fprintf( outfile, "\t.long .L__wine_spec_relay_entry_point_%d-__wine_spec_relay_entry_points\n", i );
output( "\t.long .L__wine_spec_relay_entry_point_%d-__wine_spec_relay_entry_points\n", i );
else
fprintf( outfile, "\t.long 0\n" );
output( "\t.long 0\n" );
}
/* then the table of argument types */
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, ".L__wine_spec_relay_arg_types:\n" );
output( "\t.align %d\n", get_alignment(4) );
output( ".L__wine_spec_relay_arg_types:\n" );
for (i = spec->base; i <= spec->limit; i++)
{
@ -129,14 +129,14 @@ static void output_relay_debug( FILE *outfile, DLLSPEC *spec )
if (odp->u.func.arg_types[j] == 'W') mask |= 2<< (j*2);
}
}
fprintf( outfile, "\t.long 0x%08x\n", mask );
output( "\t.long 0x%08x\n", mask );
}
/* then the relay thunks */
fprintf( outfile, "\t.text\n" );
fprintf( outfile, "__wine_spec_relay_entry_points:\n" );
fprintf( outfile, "\tnop\n" ); /* to avoid 0 offset */
output( "\t.text\n" );
output( "__wine_spec_relay_entry_points:\n" );
output( "\tnop\n" ); /* to avoid 0 offset */
for (i = spec->base; i <= spec->limit; i++)
{
@ -144,39 +144,39 @@ static void output_relay_debug( FILE *outfile, DLLSPEC *spec )
if (!needs_relay( odp )) continue;
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, ".L__wine_spec_relay_entry_point_%d:\n", i );
output( "\t.align %d\n", get_alignment(4) );
output( ".L__wine_spec_relay_entry_point_%d:\n", i );
if (odp->flags & FLAG_REGISTER)
fprintf( outfile, "\tpushl %%eax\n" );
output( "\tpushl %%eax\n" );
else
fprintf( outfile, "\tpushl %%esp\n" );
output( "\tpushl %%esp\n" );
args = strlen(odp->u.func.arg_types);
flags = 0;
if (odp->flags & FLAG_RET64) flags |= 1;
if (odp->type == TYPE_STDCALL) flags |= 2;
fprintf( outfile, "\tpushl $%u\n", (flags << 24) | (args << 16) | (i - spec->base) );
output( "\tpushl $%u\n", (flags << 24) | (args << 16) | (i - spec->base) );
if (UsePIC)
{
fprintf( outfile, "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
fprintf( outfile, "1:\tleal .L__wine_spec_relay_descr-1b(%%eax),%%eax\n" );
output( "\tcall %s\n", asm_name("__wine_spec_get_pc_thunk_eax") );
output( "1:\tleal .L__wine_spec_relay_descr-1b(%%eax),%%eax\n" );
}
else fprintf( outfile, "\tmovl $.L__wine_spec_relay_descr,%%eax\n" );
fprintf( outfile, "\tpushl %%eax\n" );
else output( "\tmovl $.L__wine_spec_relay_descr,%%eax\n" );
output( "\tpushl %%eax\n" );
if (odp->flags & FLAG_REGISTER)
{
fprintf( outfile, "\tcall *8(%%eax)\n" );
output( "\tcall *8(%%eax)\n" );
}
else
{
fprintf( outfile, "\tcall *4(%%eax)\n" );
output( "\tcall *4(%%eax)\n" );
if (odp->type == TYPE_STDCALL)
fprintf( outfile, "\tret $%u\n", args * get_ptr_size() );
output( "\tret $%u\n", args * get_ptr_size() );
else
fprintf( outfile, "\tret\n" );
output( "\tret\n" );
}
}
}
@ -186,46 +186,46 @@ static void output_relay_debug( FILE *outfile, DLLSPEC *spec )
*
* Output the export table for a Win32 module.
*/
static void output_exports( FILE *outfile, DLLSPEC *spec )
static void output_exports( DLLSPEC *spec )
{
int i, fwd_size = 0;
int nr_exports = spec->base <= spec->limit ? spec->limit - spec->base + 1 : 0;
if (!nr_exports) return;
fprintf( outfile, "\n/* export table */\n\n" );
fprintf( outfile, "\t.data\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, ".L__wine_spec_exports:\n" );
output( "\n/* export table */\n\n" );
output( "\t.data\n" );
output( "\t.align %d\n", get_alignment(4) );
output( ".L__wine_spec_exports:\n" );
/* export directory header */
fprintf( outfile, "\t.long 0\n" ); /* Characteristics */
fprintf( outfile, "\t.long 0\n" ); /* TimeDateStamp */
fprintf( outfile, "\t.long 0\n" ); /* MajorVersion/MinorVersion */
fprintf( outfile, "\t.long .L__wine_spec_exp_names-.L__wine_spec_rva_base\n" ); /* Name */
fprintf( outfile, "\t.long %u\n", spec->base ); /* Base */
fprintf( outfile, "\t.long %u\n", nr_exports ); /* NumberOfFunctions */
fprintf( outfile, "\t.long %u\n", spec->nb_names ); /* NumberOfNames */
fprintf( outfile, "\t.long .L__wine_spec_exports_funcs-.L__wine_spec_rva_base\n" ); /* AddressOfFunctions */
output( "\t.long 0\n" ); /* Characteristics */
output( "\t.long 0\n" ); /* TimeDateStamp */
output( "\t.long 0\n" ); /* MajorVersion/MinorVersion */
output( "\t.long .L__wine_spec_exp_names-.L__wine_spec_rva_base\n" ); /* Name */
output( "\t.long %u\n", spec->base ); /* Base */
output( "\t.long %u\n", nr_exports ); /* NumberOfFunctions */
output( "\t.long %u\n", spec->nb_names ); /* NumberOfNames */
output( "\t.long .L__wine_spec_exports_funcs-.L__wine_spec_rva_base\n" ); /* AddressOfFunctions */
if (spec->nb_names)
{
fprintf( outfile, "\t.long .L__wine_spec_exp_name_ptrs-.L__wine_spec_rva_base\n" ); /* AddressOfNames */
fprintf( outfile, "\t.long .L__wine_spec_exp_ordinals-.L__wine_spec_rva_base\n" ); /* AddressOfNameOrdinals */
output( "\t.long .L__wine_spec_exp_name_ptrs-.L__wine_spec_rva_base\n" ); /* AddressOfNames */
output( "\t.long .L__wine_spec_exp_ordinals-.L__wine_spec_rva_base\n" ); /* AddressOfNameOrdinals */
}
else
{
fprintf( outfile, "\t.long 0\n" ); /* AddressOfNames */
fprintf( outfile, "\t.long 0\n" ); /* AddressOfNameOrdinals */
output( "\t.long 0\n" ); /* AddressOfNames */
output( "\t.long 0\n" ); /* AddressOfNameOrdinals */
}
/* output the function pointers */
fprintf( outfile, "\n.L__wine_spec_exports_funcs:\n" );
output( "\n.L__wine_spec_exports_funcs:\n" );
for (i = spec->base; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (!odp) fprintf( outfile, "\t.long 0\n" );
if (!odp) output( "\t%s 0\n", get_asm_ptr_keyword() );
else switch(odp->type)
{
case TYPE_EXTERN:
@ -234,21 +234,21 @@ static void output_exports( FILE *outfile, DLLSPEC *spec )
case TYPE_CDECL:
if (odp->flags & FLAG_FORWARD)
{
fprintf( outfile, "\t%s .L__wine_spec_forwards+%u\n", get_asm_ptr_keyword(), fwd_size );
output( "\t%s .L__wine_spec_forwards+%u\n", get_asm_ptr_keyword(), fwd_size );
fwd_size += strlen(odp->link_name) + 1;
}
else if (odp->flags & FLAG_EXT_LINK)
{
fprintf( outfile, "\t%s %s_%s\n",
output( "\t%s %s_%s\n",
get_asm_ptr_keyword(), asm_name("__wine_spec_ext_link"), odp->link_name );
}
else
{
fprintf( outfile, "\t%s %s\n", get_asm_ptr_keyword(), asm_name(odp->link_name) );
output( "\t%s %s\n", get_asm_ptr_keyword(), asm_name(odp->link_name) );
}
break;
case TYPE_STUB:
fprintf( outfile, "\t%s %s\n", get_asm_ptr_keyword(),
output( "\t%s %s\n", get_asm_ptr_keyword(),
asm_name( get_stub_name( odp, spec )) );
break;
default:
@ -262,68 +262,68 @@ static void output_exports( FILE *outfile, DLLSPEC *spec )
int namepos = strlen(spec->file_name) + 1;
fprintf( outfile, "\n.L__wine_spec_exp_name_ptrs:\n" );
output( "\n.L__wine_spec_exp_name_ptrs:\n" );
for (i = 0; i < spec->nb_names; i++)
{
fprintf( outfile, "\t.long .L__wine_spec_exp_names+%u-.L__wine_spec_rva_base\n", namepos );
output( "\t.long .L__wine_spec_exp_names+%u-.L__wine_spec_rva_base\n", namepos );
namepos += strlen(spec->names[i]->name) + 1;
}
/* output the function ordinals */
fprintf( outfile, "\n.L__wine_spec_exp_ordinals:\n" );
output( "\n.L__wine_spec_exp_ordinals:\n" );
for (i = 0; i < spec->nb_names; i++)
{
fprintf( outfile, "\t%s %d\n",
output( "\t%s %d\n",
get_asm_short_keyword(), spec->names[i]->ordinal - spec->base );
}
if (spec->nb_names % 2)
{
fprintf( outfile, "\t%s 0\n", get_asm_short_keyword() );
output( "\t%s 0\n", get_asm_short_keyword() );
}
}
/* output the export name strings */
fprintf( outfile, "\n.L__wine_spec_exp_names:\n" );
fprintf( outfile, "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
output( "\n.L__wine_spec_exp_names:\n" );
output( "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
for (i = 0; i < spec->nb_names; i++)
fprintf( outfile, "\t%s \"%s\"\n",
output( "\t%s \"%s\"\n",
get_asm_string_keyword(), spec->names[i]->name );
/* output forward strings */
if (fwd_size)
{
fprintf( outfile, "\n.L__wine_spec_forwards:\n" );
output( "\n.L__wine_spec_forwards:\n" );
for (i = spec->base; i <= spec->limit; i++)
{
ORDDEF *odp = spec->ordinals[i];
if (odp && (odp->flags & FLAG_FORWARD))
fprintf( outfile, "\t%s \"%s\"\n", get_asm_string_keyword(), odp->link_name );
output( "\t%s \"%s\"\n", get_asm_string_keyword(), odp->link_name );
}
}
fprintf( outfile, "\t.align %d\n", get_alignment(get_ptr_size()) );
fprintf( outfile, ".L__wine_spec_exports_end:\n" );
output( "\t.align %d\n", get_alignment(get_ptr_size()) );
output( ".L__wine_spec_exports_end:\n" );
/* output relays */
/* we only support relay debugging on i386 */
if (target_cpu != CPU_x86)
{
fprintf( outfile, "\t%s 0\n", get_asm_ptr_keyword() );
output( "\t%s 0\n", get_asm_ptr_keyword() );
return;
}
fprintf( outfile, ".L__wine_spec_relay_descr:\n" );
fprintf( outfile, "\t%s 0xdeb90001\n", get_asm_ptr_keyword() ); /* magic */
fprintf( outfile, "\t%s 0,0\n", get_asm_ptr_keyword() ); /* relay funcs */
fprintf( outfile, "\t%s 0\n", get_asm_ptr_keyword() ); /* private data */
fprintf( outfile, "\t%s __wine_spec_relay_entry_points\n", get_asm_ptr_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_relay_entry_point_offsets\n", get_asm_ptr_keyword() );
fprintf( outfile, "\t%s .L__wine_spec_relay_arg_types\n", get_asm_ptr_keyword() );
output( ".L__wine_spec_relay_descr:\n" );
output( "\t%s 0xdeb90001\n", get_asm_ptr_keyword() ); /* magic */
output( "\t%s 0,0\n", get_asm_ptr_keyword() ); /* relay funcs */
output( "\t%s 0\n", get_asm_ptr_keyword() ); /* private data */
output( "\t%s __wine_spec_relay_entry_points\n", get_asm_ptr_keyword() );
output( "\t%s .L__wine_spec_relay_entry_point_offsets\n", get_asm_ptr_keyword() );
output( "\t%s .L__wine_spec_relay_arg_types\n", get_asm_ptr_keyword() );
output_relay_debug( outfile, spec );
output_relay_debug( spec );
}
@ -332,7 +332,7 @@ static void output_exports( FILE *outfile, DLLSPEC *spec )
*
* Output the functions for stub entry points
*/
static void output_stub_funcs( FILE *outfile, DLLSPEC *spec )
static void output_stub_funcs( DLLSPEC *spec )
{
int i;
@ -354,13 +354,13 @@ static void output_stub_funcs( FILE *outfile, DLLSPEC *spec )
{
const ORDDEF *odp = &spec->entry_points[i];
if (odp->type != TYPE_STUB) continue;
fprintf( outfile, "void %s(void) ", make_internal_name( odp, spec, "stub" ) );
output( "void %s(void) ", make_internal_name( odp, spec, "stub" ) );
if (odp->name)
fprintf( outfile, "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%s\"); }\n", odp->name );
output( "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%s\"); }\n", odp->name );
else if (odp->export_name)
fprintf( outfile, "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%s\"); }\n", odp->export_name );
output( "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%s\"); }\n", odp->export_name );
else
fprintf( outfile, "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%d\"); }\n", odp->ordinal );
output( "{ __wine_spec_unimplemented_stub(__wine_spec_file_name, \"%d\"); }\n", odp->ordinal );
}
}
@ -370,33 +370,33 @@ static void output_stub_funcs( FILE *outfile, DLLSPEC *spec )
*
* Output code for calling a dll constructor.
*/
static void output_asm_constructor( FILE *outfile, const char *constructor )
static void output_asm_constructor( const char *constructor )
{
if (target_platform == PLATFORM_APPLE)
{
/* Mach-O doesn't have an init section */
fprintf( outfile, "\n\t.mod_init_func\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.long %s\n", asm_name(constructor) );
output( "\n\t.mod_init_func\n" );
output( "\t.align %d\n", get_alignment(4) );
output( "\t.long %s\n", asm_name(constructor) );
}
else
{
fprintf( outfile, "\n\t.section \".init\",\"ax\"\n" );
output( "\n\t.section \".init\",\"ax\"\n" );
switch(target_cpu)
{
case CPU_x86:
case CPU_x86_64:
fprintf( outfile, "\tcall %s\n", asm_name(constructor) );
output( "\tcall %s\n", asm_name(constructor) );
break;
case CPU_SPARC:
fprintf( outfile, "\tcall %s\n", asm_name(constructor) );
fprintf( outfile, "\tnop\n" );
output( "\tcall %s\n", asm_name(constructor) );
output( "\tnop\n" );
break;
case CPU_ALPHA:
fprintf( outfile, "\tjsr $26,%s\n", asm_name(constructor) );
output( "\tjsr $26,%s\n", asm_name(constructor) );
break;
case CPU_POWERPC:
fprintf( outfile, "\tbl %s\n", asm_name(constructor) );
output( "\tbl %s\n", asm_name(constructor) );
break;
}
}
@ -408,32 +408,32 @@ static void output_asm_constructor( FILE *outfile, const char *constructor )
*
* Build a Win32 C file from a spec file.
*/
void BuildSpec32File( FILE *outfile, DLLSPEC *spec )
void BuildSpec32File( DLLSPEC *spec )
{
int machine = 0;
unsigned int page_size = get_page_size();
resolve_imports( spec );
output_standard_file_header( outfile );
output_standard_file_header();
/* Reserve some space for the PE header */
fprintf( outfile, "\t.text\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(page_size) );
fprintf( outfile, "__wine_spec_pe_header:\n" );
output( "\t.text\n" );
output( "\t.align %d\n", get_alignment(page_size) );
output( "__wine_spec_pe_header:\n" );
if (target_platform == PLATFORM_APPLE)
fprintf( outfile, "\t.space 65536\n" );
output( "\t.space 65536\n" );
else
fprintf( outfile, "\t.skip 65536\n" );
output( "\t.skip 65536\n" );
/* Output the NT header */
fprintf( outfile, "\n\t.data\n" );
fprintf( outfile, "\t.align %d\n", get_alignment(get_ptr_size()) );
fprintf( outfile, "%s\n", asm_globl("__wine_spec_nt_header") );
fprintf( outfile, ".L__wine_spec_rva_base:\n" );
output( "\n\t.data\n" );
output( "\t.align %d\n", get_alignment(get_ptr_size()) );
output( "%s\n", asm_globl("__wine_spec_nt_header") );
output( ".L__wine_spec_rva_base:\n" );
fprintf( outfile, "\t.long 0x%04x\n", IMAGE_NT_SIGNATURE ); /* Signature */
output( "\t.long 0x%04x\n", IMAGE_NT_SIGNATURE ); /* Signature */
switch(target_cpu)
{
case CPU_x86: machine = IMAGE_FILE_MACHINE_I386; break;
@ -442,104 +442,105 @@ void BuildSpec32File( FILE *outfile, DLLSPEC *spec )
case CPU_ALPHA: machine = IMAGE_FILE_MACHINE_ALPHA; break;
case CPU_SPARC: machine = IMAGE_FILE_MACHINE_UNKNOWN; break;
}
fprintf( outfile, "\t%s 0x%04x\n", /* Machine */
output( "\t%s 0x%04x\n", /* Machine */
get_asm_short_keyword(), machine );
fprintf( outfile, "\t%s 0\n", /* NumberOfSections */
output( "\t%s 0\n", /* NumberOfSections */
get_asm_short_keyword() );
fprintf( outfile, "\t.long 0\n" ); /* TimeDateStamp */
fprintf( outfile, "\t.long 0\n" ); /* PointerToSymbolTable */
fprintf( outfile, "\t.long 0\n" ); /* NumberOfSymbols */
fprintf( outfile, "\t%s %d\n", /* SizeOfOptionalHeader */
output( "\t.long 0\n" ); /* TimeDateStamp */
output( "\t.long 0\n" ); /* PointerToSymbolTable */
output( "\t.long 0\n" ); /* NumberOfSymbols */
output( "\t%s %d\n", /* SizeOfOptionalHeader */
get_asm_short_keyword(),
get_ptr_size() == 8 ? IMAGE_SIZEOF_NT_OPTIONAL64_HEADER : IMAGE_SIZEOF_NT_OPTIONAL32_HEADER );
fprintf( outfile, "\t%s 0x%04x\n", /* Characteristics */
output( "\t%s 0x%04x\n", /* Characteristics */
get_asm_short_keyword(), spec->characteristics );
fprintf( outfile, "\t%s 0x%04x\n", /* Magic */
output( "\t%s 0x%04x\n", /* Magic */
get_asm_short_keyword(),
get_ptr_size() == 8 ? IMAGE_NT_OPTIONAL_HDR64_MAGIC : IMAGE_NT_OPTIONAL_HDR32_MAGIC );
fprintf( outfile, "\t.byte 0\n" ); /* MajorLinkerVersion */
fprintf( outfile, "\t.byte 0\n" ); /* MinorLinkerVersion */
fprintf( outfile, "\t.long 0\n" ); /* SizeOfCode */
fprintf( outfile, "\t.long 0\n" ); /* SizeOfInitializedData */
fprintf( outfile, "\t.long 0\n" ); /* SizeOfUninitializedData */
output( "\t.byte 0\n" ); /* MajorLinkerVersion */
output( "\t.byte 0\n" ); /* MinorLinkerVersion */
output( "\t.long 0\n" ); /* SizeOfCode */
output( "\t.long 0\n" ); /* SizeOfInitializedData */
output( "\t.long 0\n" ); /* SizeOfUninitializedData */
/* note: we expand the AddressOfEntryPoint field on 64-bit by overwriting the BaseOfCode field */
fprintf( outfile, "\t%s %s\n", /* AddressOfEntryPoint */
output( "\t%s %s\n", /* AddressOfEntryPoint */
get_asm_ptr_keyword(), asm_name(spec->init_func) );
if (get_ptr_size() == 4)
{
fprintf( outfile, "\t.long 0\n" ); /* BaseOfCode */
fprintf( outfile, "\t.long 0\n" ); /* BaseOfData */
output( "\t.long 0\n" ); /* BaseOfCode */
output( "\t.long 0\n" ); /* BaseOfData */
}
fprintf( outfile, "\t%s __wine_spec_pe_header\n", /* ImageBase */
output( "\t%s __wine_spec_pe_header\n", /* ImageBase */
get_asm_ptr_keyword() );
fprintf( outfile, "\t.long %u\n", page_size ); /* SectionAlignment */
fprintf( outfile, "\t.long %u\n", page_size ); /* FileAlignment */
fprintf( outfile, "\t%s 1,0\n", /* Major/MinorOperatingSystemVersion */
output( "\t.long %u\n", page_size ); /* SectionAlignment */
output( "\t.long %u\n", page_size ); /* FileAlignment */
output( "\t%s 1,0\n", /* Major/MinorOperatingSystemVersion */
get_asm_short_keyword() );
fprintf( outfile, "\t%s 0,0\n", /* Major/MinorImageVersion */
output( "\t%s 0,0\n", /* Major/MinorImageVersion */
get_asm_short_keyword() );
fprintf( outfile, "\t%s %u,%u\n", /* Major/MinorSubsystemVersion */
output( "\t%s %u,%u\n", /* Major/MinorSubsystemVersion */
get_asm_short_keyword(), spec->subsystem_major, spec->subsystem_minor );
fprintf( outfile, "\t.long 0\n" ); /* Win32VersionValue */
fprintf( outfile, "\t.long %s-.L__wine_spec_rva_base\n", /* SizeOfImage */
output( "\t.long 0\n" ); /* Win32VersionValue */
output( "\t.long %s-.L__wine_spec_rva_base\n", /* SizeOfImage */
asm_name("_end") );
fprintf( outfile, "\t.long %u\n", page_size ); /* SizeOfHeaders */
fprintf( outfile, "\t.long 0\n" ); /* CheckSum */
fprintf( outfile, "\t%s 0x%04x\n", /* Subsystem */
output( "\t.long %u\n", page_size ); /* SizeOfHeaders */
output( "\t.long 0\n" ); /* CheckSum */
output( "\t%s 0x%04x\n", /* Subsystem */
get_asm_short_keyword(), spec->subsystem );
fprintf( outfile, "\t%s 0\n", /* DllCharacteristics */
get_asm_short_keyword() );
fprintf( outfile, "\t%s %u,%u\n", /* SizeOfStackReserve/Commit */
output( "\t%s 0x%04x\n", /* DllCharacteristics */
get_asm_short_keyword(), spec->dll_characteristics );
output( "\t%s %u,%u\n", /* SizeOfStackReserve/Commit */
get_asm_ptr_keyword(), (spec->stack_size ? spec->stack_size : 1024) * 1024, page_size );
fprintf( outfile, "\t%s %u,%u\n", /* SizeOfHeapReserve/Commit */
output( "\t%s %u,%u\n", /* SizeOfHeapReserve/Commit */
get_asm_ptr_keyword(), (spec->heap_size ? spec->heap_size : 1024) * 1024, page_size );
fprintf( outfile, "\t.long 0\n" ); /* LoaderFlags */
fprintf( outfile, "\t.long 16\n" ); /* NumberOfRvaAndSizes */
output( "\t.long 0\n" ); /* LoaderFlags */
output( "\t.long 16\n" ); /* NumberOfRvaAndSizes */
if (spec->base <= spec->limit) /* DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT] */
fprintf( outfile, "\t.long .L__wine_spec_exports-.L__wine_spec_rva_base,"
output( "\t.long .L__wine_spec_exports-.L__wine_spec_rva_base,"
".L__wine_spec_exports_end-.L__wine_spec_exports\n" );
else
fprintf( outfile, "\t.long 0,0\n" );
output( "\t.long 0,0\n" );
if (has_imports()) /* DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT] */
fprintf( outfile, "\t.long .L__wine_spec_imports-.L__wine_spec_rva_base,"
output( "\t.long .L__wine_spec_imports-.L__wine_spec_rva_base,"
".L__wine_spec_imports_end-.L__wine_spec_imports\n" );
else
fprintf( outfile, "\t.long 0,0\n" );
output( "\t.long 0,0\n" );
if (spec->nb_resources) /* DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE] */
fprintf( outfile, "\t.long .L__wine_spec_resources-.L__wine_spec_rva_base,"
output( "\t.long .L__wine_spec_resources-.L__wine_spec_rva_base,"
".L__wine_spec_resources_end-.L__wine_spec_resources\n" );
else
fprintf( outfile, "\t.long 0,0\n" );
output( "\t.long 0,0\n" );
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[3] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[4] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[5] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[6] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[7] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[8] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[9] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[10] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[11] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[12] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[13] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[14] */
fprintf( outfile, "\t.long 0,0\n" ); /* DataDirectory[15] */
output( "\t.long 0,0\n" ); /* DataDirectory[3] */
output( "\t.long 0,0\n" ); /* DataDirectory[4] */
output( "\t.long 0,0\n" ); /* DataDirectory[5] */
output( "\t.long 0,0\n" ); /* DataDirectory[6] */
output( "\t.long 0,0\n" ); /* DataDirectory[7] */
output( "\t.long 0,0\n" ); /* DataDirectory[8] */
output( "\t.long 0,0\n" ); /* DataDirectory[9] */
output( "\t.long 0,0\n" ); /* DataDirectory[10] */
output( "\t.long 0,0\n" ); /* DataDirectory[11] */
output( "\t.long 0,0\n" ); /* DataDirectory[12] */
output( "\t.long 0,0\n" ); /* DataDirectory[13] */
output( "\t.long 0,0\n" ); /* DataDirectory[14] */
output( "\t.long 0,0\n" ); /* DataDirectory[15] */
fprintf( outfile, "\n\t%s\n", get_asm_string_section() );
fprintf( outfile, "%s\n", asm_globl("__wine_spec_file_name") );
fprintf( outfile, ".L__wine_spec_file_name:\n" );
fprintf( outfile, "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
output( "\n\t%s\n", get_asm_string_section() );
output( "%s\n", asm_globl("__wine_spec_file_name") );
output( ".L__wine_spec_file_name:\n" );
output( "\t%s \"%s\"\n", get_asm_string_keyword(), spec->file_name );
if (target_platform == PLATFORM_APPLE)
fprintf( outfile, "\t.lcomm %s,4\n", asm_name("_end") );
output( "\t.lcomm %s,4\n", asm_name("_end") );
output_stubs( outfile, spec );
output_exports( outfile, spec );
output_imports( outfile, spec );
output_resources( outfile, spec );
output_asm_constructor( outfile, "__wine_spec_init_ctor" );
output_stubs( spec );
output_exports( spec );
output_imports( spec );
output_resources( spec );
output_asm_constructor( "__wine_spec_init_ctor" );
output_gnu_stack_note();
}
@ -548,20 +549,19 @@ void BuildSpec32File( FILE *outfile, DLLSPEC *spec )
*
* Build a Win32 def file from a spec file.
*/
void BuildDef32File( FILE *outfile, DLLSPEC *spec )
void BuildDef32File( DLLSPEC *spec )
{
const char *name;
int i, total;
if (spec_file_name)
fprintf( outfile, "; File generated automatically from %s; do not edit!\n\n",
output( "; File generated automatically from %s; do not edit!\n\n",
spec_file_name );
else
fprintf( outfile, "; File generated automatically; do not edit!\n\n" );
output( "; File generated automatically; do not edit!\n\n" );
fprintf(outfile, "LIBRARY %s\n\n", spec->file_name);
fprintf(outfile, "EXPORTS\n");
output( "LIBRARY %s\n\n", spec->file_name);
output( "EXPORTS\n");
/* Output the exports and relay entry points */
@ -573,13 +573,13 @@ void BuildDef32File( FILE *outfile, DLLSPEC *spec )
if (!odp) continue;
if (odp->name) name = odp->name;
else if (odp->type == TYPE_STUB) name = make_internal_name( odp, spec, "stub" );
else if (odp->export_name) name = odp->export_name;
else name = make_internal_name( odp, spec, "noname_export" );
else continue;
if (!(odp->flags & FLAG_PRIVATE)) total++;
fprintf(outfile, " %s", name);
output( " %s", name );
switch(odp->type)
{
@ -590,20 +590,20 @@ void BuildDef32File( FILE *outfile, DLLSPEC *spec )
case TYPE_CDECL:
/* try to reduce output */
if(strcmp(name, odp->link_name) || (odp->flags & FLAG_FORWARD))
fprintf(outfile, "=%s", odp->link_name);
output( "=%s", odp->link_name );
break;
case TYPE_STDCALL:
{
int at_param = strlen(odp->u.func.arg_types) * get_ptr_size();
if (!kill_at) fprintf(outfile, "@%d", at_param);
if (!kill_at) output( "@%d", at_param );
if (odp->flags & FLAG_FORWARD)
{
fprintf(outfile, "=%s", odp->link_name);
output( "=%s", odp->link_name );
}
else if (strcmp(name, odp->link_name)) /* try to reduce output */
{
fprintf(outfile, "=%s", odp->link_name);
if (!kill_at) fprintf(outfile, "@%d", at_param);
output( "=%s", odp->link_name );
if (!kill_at) output( "@%d", at_param );
}
break;
}
@ -620,30 +620,23 @@ void BuildDef32File( FILE *outfile, DLLSPEC *spec )
if (name != check && check != name + strlen(name) &&
'@' == check[-1])
{
fprintf(outfile, "%s", check - 1);
output("%s", check - 1);
}
}
if (NULL != odp->name)
{
fprintf(outfile, "=%s", make_internal_name( odp, spec, "stub" ));
output("=%s", make_internal_name( odp, spec, "stub" ));
}
break;
}
default:
assert(0);
}
fprintf( outfile, " @%d", odp->ordinal );
#if 0 /* MinGW binutils cannot handle this correctly */
if (!odp->name) fprintf( outfile, " NONAME" );
#else
if (!odp->name && (odp->type == TYPE_STUB || odp->export_name)) fprintf( outfile, " NONAME" );
#endif
if (is_data) fprintf( outfile, " DATA" );
#if 0
/* MinGW binutils cannot handle this correctly */
if (odp->flags & FLAG_PRIVATE) fprintf( outfile, " PRIVATE" );
#endif
fprintf( outfile, "\n" );
output( " @%d", odp->ordinal );
if (!odp->name || (odp->flags & FLAG_ORDINAL)) output( " NONAME" );
if (is_data) output( " DATA" );
if (odp->flags & FLAG_PRIVATE) output( " PRIVATE" );
output( "\n" );
}
if (!total) warning( "%s: Import library doesn't export anything\n", spec->file_name );
}
@ -654,34 +647,34 @@ void BuildDef32File( FILE *outfile, DLLSPEC *spec )
*
* Build a PE DLL C file from a spec file.
*/
void BuildPedllFile( FILE *outfile, DLLSPEC *spec )
void BuildPedllFile( DLLSPEC *spec )
{
int nr_exports;
nr_exports = spec->base <= spec->limit ? spec->limit - spec->base + 1 : 0;
output_standard_file_header( outfile );
output_standard_file_header();
fprintf( outfile, "#include <stdarg.h>\n");
fprintf( outfile, "#include \"windef.h\"\n");
fprintf( outfile, "#include \"winbase.h\"\n");
fprintf( outfile, "#include \"wine/config.h\"\n");
fprintf( outfile, "#include \"wine/exception.h\"\n\n");
output( "#include <stdarg.h>\n");
output( "#include \"windef.h\"\n");
output( "#include \"winbase.h\"\n");
output( "#include \"wine/config.h\"\n");
output( "#include \"wine/exception.h\"\n\n");
fprintf( outfile, "void __wine_spec_unimplemented_stub( const char *module, const char *function )\n");
fprintf( outfile, "{\n");
fprintf( outfile, " ULONG_PTR args[2];\n");
fprintf( outfile, "\n");
fprintf( outfile, " args[0] = (ULONG_PTR)module;\n");
fprintf( outfile, " args[1] = (ULONG_PTR)function;\n");
fprintf( outfile, " RaiseException( EXCEPTION_WINE_STUB, EH_NONCONTINUABLE, 2, args );\n");
fprintf( outfile, "}\n\n");
output( "void __wine_spec_unimplemented_stub( const char *module, const char *function )\n");
output( "{\n");
output( " ULONG_PTR args[2];\n");
output( "\n");
output( " args[0] = (ULONG_PTR)module;\n");
output( " args[1] = (ULONG_PTR)function;\n");
output( " RaiseException( EXCEPTION_WINE_STUB, EH_NONCONTINUABLE, 2, args );\n");
output( "}\n\n");
fprintf( outfile, "static const char __wine_spec_file_name[] = \"%s\";\n\n", spec->file_name );
output( "static const char __wine_spec_file_name[] = \"%s\";\n\n", spec->file_name );
if (nr_exports)
{
/* Output the stub functions */
output_stub_funcs( outfile, spec );
output_stub_funcs( spec );
}
}

View file

@ -15,14 +15,11 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "config.h"
#if !defined(WIN32)
#undef strdup
#endif
#include "wine/port.h"
#include <assert.h>
#include <ctype.h>
@ -34,6 +31,8 @@
# include <unistd.h>
#endif
#include "windef.h"
#include "winnt.h"
#include "build.h"
#define MAX_TMP_FILES 8
@ -165,6 +164,18 @@ void warning( const char *msg, ... )
va_end( valist );
}
int output( const char *format, ... )
{
int ret;
va_list valist;
va_start( valist, format );
ret = vfprintf( output_file, format, valist );
va_end( valist );
if (ret < 0) fatal_perror( "Output error" );
return ret;
}
/* get a name for a temp file, automatically cleaned up on exit */
char *get_temp_file_name( const char *prefix, const char *suffix )
{
@ -196,31 +207,29 @@ char *get_temp_file_name( const char *prefix, const char *suffix )
}
/* output a standard header for generated files */
void output_standard_file_header( FILE *outfile )
void output_standard_file_header(void)
{
if (spec_file_name)
fprintf( outfile, "/* File generated automatically from %s; do not edit! */\n",
spec_file_name );
output( "/* File generated automatically from %s; do not edit! */\n", spec_file_name );
else
fprintf( outfile, "/* File generated automatically; do not edit! */\n" );
fprintf( outfile,
"/* This file can be copied, modified and distributed without restriction. */\n\n" );
output( "/* File generated automatically; do not edit! */\n" );
output( "/* This file can be copied, modified and distributed without restriction. */\n\n" );
}
/* dump a byte stream into the assembly code */
void dump_bytes( FILE *outfile, const void *buffer, unsigned int size )
void dump_bytes( const void *buffer, unsigned int size )
{
unsigned int i;
const unsigned char *ptr = buffer;
if (!size) return;
fprintf( outfile, "\t.byte " );
output( "\t.byte " );
for (i = 0; i < size - 1; i++, ptr++)
{
if ((i % 16) == 15) fprintf( outfile, "0x%02x\n\t.byte ", *ptr );
else fprintf( outfile, "0x%02x,", *ptr );
if ((i % 16) == 15) output( "0x%02x\n\t.byte ", *ptr );
else output( "0x%02x,", *ptr );
}
fprintf( outfile, "0x%02x\n", *ptr );
output( "0x%02x\n", *ptr );
}
@ -324,7 +333,12 @@ DLLSPEC *alloc_dll_spec(void)
spec->alloc_entry_points = 0;
spec->nb_names = 0;
spec->nb_resources = 0;
spec->characteristics = 0;
spec->characteristics = IMAGE_FILE_EXECUTABLE_IMAGE;
if (get_ptr_size() > 4)
spec->characteristics |= IMAGE_FILE_LARGE_ADDRESS_AWARE;
else
spec->characteristics |= IMAGE_FILE_32BIT_MACHINE;
spec->dll_characteristics = IMAGE_DLLCHARACTERISTICS_NX_COMPAT;
spec->subsystem = 0;
spec->subsystem_major = 4;
spec->subsystem_minor = 0;
@ -444,7 +458,7 @@ unsigned int get_alignment(unsigned int align)
case CPU_POWERPC:
case CPU_ALPHA:
n = 0;
while ((1 << n) != align) n++;
while ((1u << n) != align) n++;
return n;
}
/* unreached */
@ -523,7 +537,7 @@ const char *func_declaration( const char *func )
}
/* output a size declaration for an assembly function */
void output_function_size( FILE *outfile, const char *name )
void output_function_size( const char *name )
{
switch (target_platform)
{
@ -531,7 +545,21 @@ void output_function_size( FILE *outfile, const char *name )
case PLATFORM_WINDOWS:
break;
default:
fprintf( outfile, "\t.size %s, .-%s\n", name, name );
output( "\t.size %s, .-%s\n", name, name );
break;
}
}
/* output the GNU note for non-exec stack */
void output_gnu_stack_note(void)
{
switch (target_platform)
{
case PLATFORM_WINDOWS:
case PLATFORM_APPLE:
break;
default:
output( "\t.section .note.GNU-stack,\"\",@progbits\n" );
break;
}
}

View file

@ -73,11 +73,11 @@ Specify the module entry point function; if not specified, the default
is
.B DllMain
for dlls, and
.B WinMain
for executables (if
.B WinMain
is not defined, the standard C
.B main
for executables (if the standard C
.B main
is not defined,
.B WinMain
is used instead). This is only valid for Win32 modules.
.TP
.BI \-E,\ --export= filename
@ -85,6 +85,14 @@ Specify a .spec file (see \fBSPEC FILE SYNTAX\fR for details),
or a standard Windows .def file that defines the exports
of the DLL or executable that is being built.
.TP
.B \--external-symbols
Allow linking to external symbols directly from the spec
file. Normally symbols exported by a dll have to be defined in the dll
itself; this option makes it possible to use symbols defined in
another Unix library (for symbols defined in another dll, a
.I forward
specification must be used instead).
.TP
.BI \-f\ flags
Ignored for compatibility with the C compiler.
.TP
@ -145,6 +153,10 @@ KRNL386.EXE. It shouldn't be needed otherwise.
Specify the command to use to get the list of undefined symbols; the
default is \fBnm\fR.
.TP
.BI --nxcompat= yes|no
Specify whether the module is compatible with no-exec support. The
default is yes.
.TP
.BI \-o,\ --output= file
Set the name of the output file (default is standard output). If the
output file name end in \fB.o\fR, the text output is sent to a
@ -248,7 +260,8 @@ The entry point is not displayed in relay debugging traces (Win32
only).
.TP
.B -noname
The entry point will be imported by ordinal instead of by name.
The entry point will be exported by ordinal instead of by name. The
name is still available for importing.
.TP
.B -ret16
The function returns a 16-bit value (Win16 only).
@ -265,6 +278,10 @@ The function uses CPU register to pass arguments.
.B -private
The function cannot be imported from other dlls, it can only be
accessed through GetProcAddress.
.TP
.B -ordinal
The entry point will be imported by ordinal instead of by name. The
name is still exported.
.SS "Function ordinals"
Syntax:
.br

View file

@ -1,132 +1,10 @@
#ifndef _WINGLUE_H
#define _WINGLUE_H
typedef unsigned char BYTE;
typedef unsigned short WORD;
typedef unsigned long DWORD;
typedef unsigned short WCHAR;
#if defined(_WIN64)
typedef unsigned __int64 UINT_PTR;
#else
typedef unsigned int UINT_PTR;
#endif
#define LOBYTE(w) ((BYTE)(w))
#define HIBYTE(w) ((BYTE)(((WORD)(w)>>8)&0xFF))
#define DLL_PROCESS_ATTACH 1
#define DLL_PROCESS_DETACH 0
#define IMAGE_FILE_DLL 8192
#define IMAGE_SUBSYSTEM_NATIVE 1
#define IMAGE_SUBSYSTEM_WINDOWS_GUI 2
#define IMAGE_SUBSYSTEM_WINDOWS_CUI 3
#define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16
#define IMAGE_FILE_MACHINE_UNKNOWN 0
#define IMAGE_FILE_MACHINE_I386 0x014c
/* Stuff missing in the host's PSDK */
#define IMAGE_DLLCHARACTERISTICS_NX_COMPAT 0x0100
#define IMAGE_FILE_MACHINE_ALPHA 0x0184
#define IMAGE_FILE_MACHINE_POWERPC 0x01f0
#define IMAGE_FILE_MACHINE_AMD64 0x8664
#define IMAGE_NT_SIGNATURE 0x00004550
#define IMAGE_SIZEOF_NT_OPTIONAL32_HEADER 224
#define IMAGE_SIZEOF_NT_OPTIONAL64_HEADER 240
#define IMAGE_NT_OPTIONAL_HDR32_MAGIC 0x10b
#define IMAGE_NT_OPTIONAL_HDR64_MAGIC 0x20b
#if defined(_WIN64)
#define IMAGE_SIZEOF_NT_OPTIONAL_HEADER IMAGE_SIZEOF_NT_OPTIONAL64_HEADER
#define IMAGE_NT_OPTIONAL_HDR_MAGIC IMAGE_NT_OPTIONAL_HDR64_MAGIC
#else
#define IMAGE_SIZEOF_NT_OPTIONAL_HEADER IMAGE_SIZEOF_NT_OPTIONAL32_HEADER
#define IMAGE_NT_OPTIONAL_HDR_MAGIC IMAGE_NT_OPTIONAL_HDR32_MAGIC
#endif
#ifdef __GNUC__
#ifndef NONAMELESSUNION
#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95)
#define _ANONYMOUS_UNION __extension__
#define _ANONYMOUS_STRUCT __extension__
#else
#if defined(__cplusplus)
#define _ANONYMOUS_UNION __extension__
#endif /* __cplusplus */
#endif /* __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95) */
#endif /* NONAMELESSUNION */
#elif defined(__WATCOMC__) || defined(_MSC_VER)
#define _ANONYMOUS_UNION
#define _ANONYMOUS_STRUCT
#endif /* __GNUC__/__WATCOMC__ */
#ifndef _ANONYMOUS_UNION
#define _ANONYMOUS_UNION
#define _UNION_NAME(x) x
#define DUMMYUNIONNAME u
#define DUMMYUNIONNAME2 u2
#define DUMMYUNIONNAME3 u3
#define DUMMYUNIONNAME4 u4
#define DUMMYUNIONNAME5 u5
#define DUMMYUNIONNAME6 u6
#define DUMMYUNIONNAME7 u7
#define DUMMYUNIONNAME8 u8
#else
#define _UNION_NAME(x)
#define DUMMYUNIONNAME
#define DUMMYUNIONNAME2
#define DUMMYUNIONNAME3
#define DUMMYUNIONNAME4
#define DUMMYUNIONNAME5
#define DUMMYUNIONNAME6
#define DUMMYUNIONNAME7
#define DUMMYUNIONNAME8
#endif
#ifndef _ANONYMOUS_STRUCT
#define _ANONYMOUS_STRUCT
#define _STRUCT_NAME(x) x
#define DUMMYSTRUCTNAME s
#define DUMMYSTRUCTNAME2 s2
#define DUMMYSTRUCTNAME3 s3
#else
#define _STRUCT_NAME(x)
#define DUMMYSTRUCTNAME
#define DUMMYSTRUCTNAME2
#define DUMMYSTRUCTNAME3
#endif
typedef struct _IMAGE_RESOURCE_DIRECTORY {
DWORD Characteristics;
DWORD TimeDateStamp;
WORD MajorVersion;
WORD MinorVersion;
WORD NumberOfNamedEntries;
WORD NumberOfIdEntries;
} IMAGE_RESOURCE_DIRECTORY,*PIMAGE_RESOURCE_DIRECTORY;
_ANONYMOUS_STRUCT typedef struct _IMAGE_RESOURCE_DIRECTORY_ENTRY {
_ANONYMOUS_UNION union {
_ANONYMOUS_STRUCT struct {
DWORD NameOffset:31;
DWORD NameIsString:1;
}DUMMYSTRUCTNAME;
DWORD Name;
WORD Id;
} DUMMYUNIONNAME;
_ANONYMOUS_UNION union {
DWORD OffsetToData;
_ANONYMOUS_STRUCT struct {
DWORD OffsetToDirectory:31;
DWORD DataIsDirectory:1;
} DUMMYSTRUCTNAME2;
} DUMMYUNIONNAME2;
} IMAGE_RESOURCE_DIRECTORY_ENTRY,*PIMAGE_RESOURCE_DIRECTORY_ENTRY;
typedef struct _IMAGE_RESOURCE_DATA_ENTRY {
DWORD OffsetToData;
DWORD Size;
DWORD CodePage;
DWORD Reserved;
} IMAGE_RESOURCE_DATA_ENTRY,*PIMAGE_RESOURCE_DATA_ENTRY;
#ifndef max
#define max(a,b) ((a)>(b)?(a):(b))
#endif
#ifndef min
#define min(a,b) ((a)<(b)?(a):(b))
#endif
#endif /* _WINGLUE_H */