Moved more of the spec initialization code to the winecrt0 library,
and get rid of implicit kernel32 imports.

diff --git a/dlls/winecrt0/Makefile.in b/dlls/winecrt0/Makefile.in
index 72cc517..60a9b0c 100644
--- a/dlls/winecrt0/Makefile.in
+++ b/dlls/winecrt0/Makefile.in
@@ -6,8 +6,11 @@
 
 C_SRCS = \
 	delay_load.c \
+	dll_entry.c \
 	dll_main.c \
+	exe_entry.c \
 	exe_main.c \
+	exe_wentry.c \
 	exe_wmain.c \
 	stub.c
 
diff --git a/dlls/winecrt0/crt0_private.h b/dlls/winecrt0/crt0_private.h
new file mode 100644
index 0000000..d4dbea3
--- /dev/null
+++ b/dlls/winecrt0/crt0_private.h
@@ -0,0 +1,32 @@
+/*
+ * crt0 library private definitions
+ *
+ * Copyright 2005 Alexandre Julliard
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * 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
+ */
+
+#ifndef __WINE_CRT0_PRIVATE_H__
+#define __WINE_CRT0_PRIVATE_H__
+
+#ifdef __APPLE__
+static inline void _init(int argc, char **argv, char **envp ) { /* nothing */ }
+static inline void _fini(void) { /* nothing */ }
+#else
+extern  void _init(int argc, char **argv, char **envp );
+extern void _fini(void);
+#endif
+
+#endif /* __WINE_CRT0_PRIVATE_H__ */
diff --git a/dlls/winecrt0/dll_entry.c b/dlls/winecrt0/dll_entry.c
new file mode 100644
index 0000000..e3be639
--- /dev/null
+++ b/dlls/winecrt0/dll_entry.c
@@ -0,0 +1,41 @@
+/*
+ * Default entry point for a dll
+ *
+ * Copyright 2005 Alexandre Julliard
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * 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
+ */
+
+#include <stdarg.h>
+#include "windef.h"
+#include "winbase.h"
+#include "wine/library.h"
+#include "crt0_private.h"
+
+int __wine_spec_init_state;
+
+extern BOOL WINAPI DllMain( HINSTANCE inst, DWORD reason, LPVOID reserved );
+
+BOOL WINAPI __wine_spec_dll_entry( HINSTANCE inst, DWORD reason, LPVOID reserved )
+{
+    BOOL ret;
+
+    if (reason == DLL_PROCESS_ATTACH && __wine_spec_init_state == 1)
+        _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );
+    ret = DllMain( inst, reason, reserved );
+    if (reason == DLL_PROCESS_DETACH && __wine_spec_init_state == 1)
+        _fini();
+    return ret;
+}
diff --git a/dlls/winecrt0/exe_entry.c b/dlls/winecrt0/exe_entry.c
new file mode 100644
index 0000000..df26bfa
--- /dev/null
+++ b/dlls/winecrt0/exe_entry.c
@@ -0,0 +1,39 @@
+/*
+ * Default entry point for an exe
+ *
+ * Copyright 2005 Alexandre Julliard
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * 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
+ */
+
+#include <stdarg.h>
+#include "windef.h"
+#include "winbase.h"
+#include "winternl.h"
+#include "wine/library.h"
+#include "crt0_private.h"
+
+int __wine_spec_init_state;
+
+extern int main( int argc, char *argv[] );
+
+DWORD WINAPI __wine_spec_exe_entry( PEB *peb )
+{
+    DWORD ret;
+    if (__wine_spec_init_state == 1) _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );
+    ret = main( __wine_main_argc, __wine_main_argv );
+    if (__wine_spec_init_state == 1) _fini();
+    ExitProcess( ret );
+}
diff --git a/dlls/winecrt0/exe_wentry.c b/dlls/winecrt0/exe_wentry.c
new file mode 100644
index 0000000..b79045a
--- /dev/null
+++ b/dlls/winecrt0/exe_wentry.c
@@ -0,0 +1,39 @@
+/*
+ * Default entry point for a Unicode exe
+ *
+ * Copyright 2005 Alexandre Julliard
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * 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
+ */
+
+#include <stdarg.h>
+#include "windef.h"
+#include "winbase.h"
+#include "winternl.h"
+#include "wine/library.h"
+#include "crt0_private.h"
+
+int __wine_spec_init_state;
+
+extern int wmain( int argc, WCHAR *argv[] );
+
+DWORD WINAPI __wine_spec_exe_wentry( PEB *peb )
+{
+    DWORD ret;
+    if (__wine_spec_init_state == 1) _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );
+    ret = wmain( __wine_main_argc, __wine_main_wargv );
+    if (__wine_spec_init_state == 1) _fini();
+    ExitProcess( ret );
+}
diff --git a/tools/winebuild/import.c b/tools/winebuild/import.c
index b482712..989e5bb 100644
--- a/tools/winebuild/import.c
+++ b/tools/winebuild/import.c
@@ -454,31 +454,6 @@
     if (imp->delay) total_delayed++;
 }
 
-/* add a symbol to the extra list, but only if needed */
-static int add_extra_symbol( const char **extras, int *count, const char *name, const DLLSPEC *spec )
-{
-    int i;
-
-    if (!find_name( name, &undef_symbols ))
-    {
-        /* check if the symbol is being exported by this dll */
-        for (i = 0; i < spec->nb_entry_points; i++)
-        {
-            ORDDEF *odp = &spec->entry_points[i];
-            if (odp->type == TYPE_STDCALL ||
-                odp->type == TYPE_CDECL ||
-                odp->type == TYPE_VARARGS ||
-                odp->type == TYPE_EXTERN)
-            {
-                if (odp->name && !strcmp( odp->name, name )) return 0;
-            }
-        }
-        extras[*count] = name;
-        (*count)++;
-    }
-    return 1;
-}
-
 /* check if the spec file exports any stubs */
 static int has_stubs( const DLLSPEC *spec )
 {
@@ -491,35 +466,21 @@
     return 0;
 }
 
-/* add the extra undefined symbols that will be contained in the generated spec file itself */
-static void add_extra_undef_symbols( const DLLSPEC *spec )
+/* get the default entry point for a given spec file */
+static const char *get_default_entry_point( const DLLSPEC *spec )
 {
-    const char *extras[10];
-    int i, count = 0;
-    int kernel_imports = 0;
+    if (spec->characteristics & IMAGE_FILE_DLL) return "__wine_spec_dll_entry";
+    if (spec->subsystem == IMAGE_SUBSYSTEM_NATIVE) return "DriverEntry";
+    return "__wine_spec_exe_entry";
+}
 
-    sort_names( &undef_symbols );
-
-    /* add symbols that will be contained in the spec file itself */
-    if (!(spec->characteristics & IMAGE_FILE_DLL))
-    {
-        switch (spec->subsystem)
-        {
-        case IMAGE_SUBSYSTEM_WINDOWS_GUI:
-        case IMAGE_SUBSYSTEM_WINDOWS_CUI:
-            kernel_imports += add_extra_symbol( extras, &count, "ExitProcess", spec );
-            break;
-        }
-    }
-
-    /* make sure we import the dlls that contain these functions */
-    if (kernel_imports) add_import_dll( "kernel32", NULL );
-
-    if (count)
-    {
-        for (i = 0; i < count; i++) add_name( &undef_symbols, extras[i] );
-        sort_names( &undef_symbols );
-    }
+/* add the extra undefined symbols that will be contained in the generated spec file itself */
+static void add_extra_undef_symbols( DLLSPEC *spec )
+{
+    if (!spec->init_func) spec->init_func = xstrdup( get_default_entry_point(spec) );
+    add_extra_ld_symbol( spec->init_func );
+    if (has_stubs( spec )) add_extra_ld_symbol( "__wine_spec_unimplemented_stub" );
+    if (nb_delayed) add_extra_ld_symbol( "__wine_spec_delay_load" );
 }
 
 /* check if a given imported dll is not needed, taking forwards into account */
@@ -588,13 +549,7 @@
 
     if (!argv[0]) return;
 
-    if (spec->init_func) add_extra_ld_symbol( spec->init_func );
-    else if (spec->characteristics & IMAGE_FILE_DLL) add_extra_ld_symbol( "DllMain" );
-    else if (spec->subsystem == IMAGE_SUBSYSTEM_NATIVE) add_extra_ld_symbol( "DriverEntry ");
-    else add_extra_ld_symbol( "main" );
-
-    if (has_stubs( spec )) add_extra_ld_symbol( "__wine_spec_unimplemented_stub" );
-    if (nb_delayed) add_extra_ld_symbol( "__wine_spec_delay_load" );
+    add_extra_undef_symbols( spec );
 
     strcpy( name_prefix, asm_name("") );
     prefix_len = strlen( name_prefix );
@@ -640,7 +595,6 @@
 {
     unsigned int i, j, removed;
 
-    add_extra_undef_symbols( spec );
     remove_ignored_symbols();
 
     for (i = 0; i < nb_imports; i++)
diff --git a/tools/winebuild/spec32.c b/tools/winebuild/spec32.c
index 966165a..56f9883 100644
--- a/tools/winebuild/spec32.c
+++ b/tools/winebuild/spec32.c
@@ -443,7 +443,6 @@
     int exports_size = 0;
     int nr_exports, nr_imports, nr_delayed;
     unsigned int page_size = get_page_size();
-    const char *init_func = spec->init_func;
 
     nr_exports = spec->base <= spec->limit ? spec->limit - spec->base + 1 : 0;
     resolve_imports( spec );
@@ -478,11 +477,6 @@
     fprintf( outfile, "static const char __wine_spec_file_name[] = \"%s\";\n", spec->file_name );
     fprintf( outfile, "extern int __wine_spec_data_start[], __wine_spec_exports[];\n\n" );
 
-    if (target_cpu == CPU_x86)
-        fprintf( outfile, "#define __stdcall __attribute__((__stdcall__))\n\n" );
-    else
-        fprintf( outfile, "#define __stdcall\n\n" );
-
     output_stub_funcs( outfile, spec );
 
     /* Output the DLL imports */
@@ -495,105 +489,8 @@
 
     /* Output the entry point function */
 
-    fprintf( outfile, "static int __wine_spec_init_state;\n" );
-    fprintf( outfile, "extern int __wine_main_argc;\n" );
-    fprintf( outfile, "extern char **__wine_main_argv;\n" );
-    fprintf( outfile, "extern char **__wine_main_environ;\n" );
-    if (target_platform == PLATFORM_APPLE)
-    {
-        fprintf( outfile, "extern _dyld_func_lookup(char *, void *);" );
-        fprintf( outfile, "static void __wine_spec_hidden_init(int argc, char** argv, char** envp)\n" );
-        fprintf( outfile, "{\n" );
-        fprintf( outfile, "    void (*init)(void);\n" );
-        fprintf( outfile, "    _dyld_func_lookup(\"__dyld_make_delayed_module_initializer_calls\", (unsigned long *)&init);\n" );
-        fprintf( outfile, "    init();\n" );
-        fprintf( outfile, "}\n" );
-        fprintf( outfile, "static void __wine_spec_hidden_fini()\n" );
-        fprintf( outfile, "{\n" );
-        fprintf( outfile, "    void (*fini)(void);\n" );
-        fprintf( outfile, "    _dyld_func_lookup(\"__dyld_mod_term_funcs\", (unsigned long *)&fini);\n" );
-        fprintf( outfile, "    fini();\n" );
-        fprintf( outfile, "}\n" );
-        fprintf( outfile, "#define _init __wine_spec_hidden_init\n" );
-        fprintf( outfile, "#define _fini __wine_spec_hidden_fini\n" );
-    }
-    else
-    {
-        fprintf( outfile, "extern void _init(int, char**, char**);\n" );
-        fprintf( outfile, "extern void _fini();\n" );
-    }
-
-    if (spec->characteristics & IMAGE_FILE_DLL)
-    {
-        if (!init_func) init_func = "DllMain";
-        fprintf( outfile, "extern int __stdcall %s( void*, unsigned int, void* );\n\n", init_func );
-        fprintf( outfile,
-                 "static int __stdcall __wine_dll_main( void *inst, unsigned int reason, void *reserved )\n"
-                 "{\n"
-                 "    int ret;\n"
-                 "    if (reason == %d && __wine_spec_init_state == 1)\n"
-                 "        _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );\n"
-                 "    ret = %s( inst, reason, reserved );\n"
-                 "    if (reason == %d && __wine_spec_init_state == 1)\n"
-                 "        _fini();\n"
-                 "    return ret;\n}\n",
-                 DLL_PROCESS_ATTACH, init_func, DLL_PROCESS_DETACH );
-        init_func = "__wine_dll_main";
-    }
-    else switch(spec->subsystem)
-    {
-    case IMAGE_SUBSYSTEM_NATIVE:
-        if (!init_func) init_func = "DriverEntry";
-        fprintf( outfile, "extern int __stdcall %s( void*, void* );\n\n", init_func );
-        fprintf( outfile,
-                 "static int __stdcall __wine_driver_entry( void *obj, void *path )\n"
-                 "{\n"
-                 "    int ret;\n"
-                 "    if (__wine_spec_init_state == 1)\n"
-                 "        _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );\n"
-                 "    ret = %s( obj, path );\n"
-                 "    if (__wine_spec_init_state == 1) _fini();\n"
-                 "    return ret;\n"
-                 "}\n",
-                 init_func );
-        init_func = "__wine_driver_entry";
-        break;
-    case IMAGE_SUBSYSTEM_WINDOWS_GUI:
-    case IMAGE_SUBSYSTEM_WINDOWS_CUI:
-        if (!init_func) init_func = "main";
-        else if (!strcmp( init_func, "wmain" ))  /* FIXME: temp hack for crt0 support */
-        {
-            fprintf( outfile, "extern int wmain( int argc, unsigned short *argv[] );\n" );
-            fprintf( outfile, "extern unsigned short **__wine_main_wargv;\n" );
-            fprintf( outfile,
-                     "\nextern void __stdcall ExitProcess(unsigned int);\n"
-                     "static void __wine_exe_wmain(void)\n"
-                     "{\n"
-                     "    int ret;\n"
-                     "    if (__wine_spec_init_state == 1)\n"
-                     "        _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );\n"
-                     "    ret = wmain( __wine_main_argc, __wine_main_wargv );\n"
-                     "    if (__wine_spec_init_state == 1) _fini();\n"
-                     "    ExitProcess( ret );\n"
-                     "}\n\n" );
-            init_func = "__wine_exe_wmain";
-            break;
-        }
-        fprintf( outfile, "extern int %s( int argc, char *argv[] );\n", init_func );
-        fprintf( outfile,
-                 "\nextern void __stdcall ExitProcess(unsigned int);\n"
-                 "static void __wine_exe_main(void)\n"
-                 "{\n"
-                 "    int ret;\n"
-                 "    if (__wine_spec_init_state == 1)\n"
-                 "        _init( __wine_main_argc, __wine_main_argv, __wine_main_environ );\n"
-                 "    ret = %s( __wine_main_argc, __wine_main_argv );\n"
-                 "    if (__wine_spec_init_state == 1) _fini();\n"
-                 "    ExitProcess( ret );\n"
-                 "}\n\n", init_func );
-        init_func = "__wine_exe_main";
-        break;
-    }
+    fprintf( outfile, "int __wine_spec_init_state;\n" );
+    fprintf( outfile, "extern void %s();\n\n", spec->init_func );
 
     /* Output the NT header */
 
@@ -666,7 +563,7 @@
     fprintf( outfile, "  { 0x%04x,\n", IMAGE_NT_OPTIONAL_HDR_MAGIC );  /* Magic */
     fprintf( outfile, "    0, 0,\n" );                   /* Major/MinorLinkerVersion */
     fprintf( outfile, "    0, 0, 0,\n" );                /* SizeOfCode/Data */
-    fprintf( outfile, "    %s,\n", init_func );          /* AddressOfEntryPoint */
+    fprintf( outfile, "    %s,\n", spec->init_func );    /* AddressOfEntryPoint */
     fprintf( outfile, "    0, __wine_spec_data_start,\n" );              /* BaseOfCode/Data */
     fprintf( outfile, "    __wine_spec_pe_header,\n" );  /* ImageBase */
     fprintf( outfile, "    %u,\n", page_size );          /* SectionAlignment */
diff --git a/tools/winegcc/winegcc.c b/tools/winegcc/winegcc.c
index 30bcb33..502f860 100644
--- a/tools/winegcc/winegcc.c
+++ b/tools/winegcc/winegcc.c
@@ -563,7 +563,7 @@
         if (opts->unicode_app)
         {
             strarray_add(spec_args, "--entry");
-            strarray_add(spec_args, "wmain");
+            strarray_add(spec_args, "__wine_spec_exe_wentry");
         }
     }