diff -ru gcc-3.3.3-vanilla/gcc/builtins.c gcc-3.3.3/gcc/builtins.c --- gcc-3.3.3-vanilla/gcc/builtins.c 2004-01-11 14:13:03.000000000 -0500 +++ gcc-3.3.3/gcc/builtins.c 2005-06-04 21:43:07.000000000 -0400 @@ -3790,6 +3790,13 @@ if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD) return (*targetm.expand_builtin) (exp, target, subtarget, mode, ignore); + if (gem_expand_builtin) { + if (!gem_expand_builtin()) { + /* expand as a standard function */ + return expand_call (exp, target, ignore); + } + } + /* When not optimizing, generate calls to library functions for a certain set of builtins. */ if (!optimize && !CALLED_AS_BUILT_IN (fndecl)) diff -ru gcc-3.3.3-vanilla/gcc/c-common.c gcc-3.3.3/gcc/c-common.c --- gcc-3.3.3-vanilla/gcc/c-common.c 2003-06-07 18:13:24.000000000 -0400 +++ gcc-3.3.3/gcc/c-common.c 2005-06-04 21:38:00.000000000 -0400 @@ -3586,6 +3586,10 @@ (*targetm.init_builtins) (); main_identifier_node = get_identifier ("main"); + + if (gem_c_common_nodes_and_builtins) { + gem_c_common_nodes_and_builtins(); + } } tree diff -ru gcc-3.3.3-vanilla/gcc/c-decl.c gcc-3.3.3/gcc/c-decl.c --- gcc-3.3.3-vanilla/gcc/c-decl.c 2003-09-06 10:44:14.000000000 -0400 +++ gcc-3.3.3/gcc/c-decl.c 2005-06-04 21:41:42.000000000 -0400 @@ -6502,6 +6502,10 @@ /* Tie off the statement tree for this function. */ finish_stmt_tree (&DECL_SAVED_TREE (fndecl)); + if (gem_finish_function) { + gem_finish_function(&fndecl); + } + /* Complain if there's just no return statement. */ if (warn_return_type && TREE_CODE (TREE_TYPE (TREE_TYPE (fndecl))) != VOID_TYPE @@ -6592,6 +6596,10 @@ int saved_lineno; const char *saved_input_filename; + if (gem_expand_body) { + gem_expand_body(&fndecl); + } + /* There's no reason to do any of the work here if we're only doing semantic analysis; this code just generates RTL. */ if (flag_syntax_only) diff -ru gcc-3.3.3-vanilla/gcc/c-opts.c gcc-3.3.3/gcc/c-opts.c --- gcc-3.3.3-vanilla/gcc/c-opts.c 2003-06-12 07:58:31.000000000 -0400 +++ gcc-3.3.3/gcc/c-opts.c 2005-06-08 11:41:34.000000000 -0400 @@ -19,6 +19,8 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ +#include + #include "config.h" #include "system.h" #include "tree.h" @@ -31,6 +33,30 @@ #include "diagnostic.h" #include "intl.h" +/* GCC extension module handle */ +void *gem_handle=NULL; +int gem_result=0; + +void (*gem_init)(void)=NULL; +void (*gem_destroy)(void)=NULL; + +unsigned int (*gem_handle_option)(const char **argv, unsigned int lang_mask)=NULL; +void (*gem_final_start_function)(rtx, FILE *, int)=NULL; +void (*gem_output_asm_insn)(const char*, rtx *)=NULL; +void (*gem_expand_expr_pre)(tree *)=NULL; +void (*gem_expand_expr_post)()=NULL; +void (*gem_genrtl_switch_stmt)(tree)=NULL; +void (*gem_c_common_nodes_and_builtins)()=NULL; +void (*gem_finish_function)(tree*)=NULL; +void (*gem_expand_body)(tree*)=NULL; +void (*gem_genrtl_if_stmt)(tree, tree)=NULL; +void (*gem_genrtl_return_stmt)(tree)=NULL; +void (*gem_genrtl_for_stmt)(tree)=NULL; +void (*gem_finalize_compilation_unit)(void)=NULL; +int (*gem_expand_builtin)(void)=NULL; +void (*gem_macro_name)(cpp_hashnode *)=NULL; +void (*gem_macro_def)(cpp_reader *, cpp_macro *)=NULL; + /* CPP's options. */ static cpp_options *cpp_opts; @@ -207,6 +233,7 @@ OPT("felide-constructors", CL_CXX, OPT_felide_constructors) \ OPT("fenforce-eh-specs", CL_CXX, OPT_fenforce_eh_specs) \ OPT("fenum-int-equiv", CL_CXX, OPT_fenum_int_equiv) \ + OPT("fextension-module=", CL_ALL | CL_JOINED, OPT_fextension_module_) \ OPT("fexternal-templates", CL_CXX, OPT_fexternal_templates) \ OPT("ffixed-form", CL_C, OPT_ffixed_form) \ OPT("ffixed-line-length-", CL_C | CL_JOINED, OPT_ffixed_line_length) \ @@ -399,6 +426,7 @@ while (mx > mn) { + md = (mn + mx) / 2; opt_len = cl_options[md].opt_len; @@ -573,7 +601,9 @@ /* Skip over '-'. */ lang_flag = lang_flags[(c_language << 1) + flag_objc]; + opt_index = find_opt (opt + 1, lang_flag); + if (opt_index == N_OPTS) goto done; @@ -1340,6 +1370,27 @@ case OPT_v: cpp_opts->verbose = 1; break; + + case OPT_fextension_module_: + printf("arg=%s\n", arg); + gem_handle=dlopen(arg, RTLD_LAZY); + + if (!gem_handle) { + printf("Can't open module %s (%s)\n", arg, dlerror()); + break; + } + + gem_init_ptr = dlsym(gem_handle, "gem_init"); + gem_destroy_ptr = dlsym(gem_handle, "gem_destroy"); + + if (!gem_init_ptr || !gem_destroy_ptr) { + printf("Can't find gem_init() or gem_destroy()\n"); + break; + } + + /* init the module */ + gem_init_ptr(); + } done: diff -ru gcc-3.3.3-vanilla/gcc/cpplib.c gcc-3.3.3/gcc/cpplib.c --- gcc-3.3.3-vanilla/gcc/cpplib.c 2003-09-24 19:52:31.000000000 -0400 +++ gcc-3.3.3/gcc/cpplib.c 2005-06-08 17:27:23.000000000 -0400 @@ -26,6 +26,10 @@ #include "cpphash.h" #include "obstack.h" +extern void (*gem_macro_name)(struct cpp_hashnode *); +extern void (*gem_macro_def)(struct cpp_reader *, struct cpp_macro *); + + /* Chained list of answers to an assertion. */ struct answer { @@ -521,6 +525,11 @@ { cpp_hashnode *node = lex_macro_node (pfile); + if (gem_macro_name) { + gem_macro_name(node); + } + + if (node) { /* If we have been requested to expand comments into macros, diff -ru gcc-3.3.3-vanilla/gcc/cpplib.h gcc-3.3.3/gcc/cpplib.h --- gcc-3.3.3-vanilla/gcc/cpplib.h 2003-11-06 18:13:31.000000000 -0500 +++ gcc-3.3.3/gcc/cpplib.h 2005-06-08 17:30:03.000000000 -0400 @@ -729,6 +729,8 @@ /* In cppmain.c */ extern void cpp_preprocess_file PARAMS ((cpp_reader *, const char *, FILE *)); +extern cpp_token *alloc_expansion_token (cpp_reader *, cpp_macro *); + #ifdef __cplusplus } #endif diff -ru gcc-3.3.3-vanilla/gcc/cppmacro.c gcc-3.3.3/gcc/cppmacro.c --- gcc-3.3.3-vanilla/gcc/cppmacro.c 2003-06-19 01:40:29.000000000 -0400 +++ gcc-3.3.3/gcc/cppmacro.c 2005-06-08 17:29:18.000000000 -0400 @@ -28,6 +28,10 @@ #include "cpplib.h" #include "cpphash.h" +extern void (*gem_macro_name)(struct cpp_hashnode *); +extern void (*gem_macro_def)(struct cpp_reader *, struct cpp_macro *); + + typedef struct macro_arg macro_arg; struct macro_arg { @@ -65,7 +69,7 @@ /* #define directive parsing and handling. */ -static cpp_token *alloc_expansion_token PARAMS ((cpp_reader *, cpp_macro *)); +cpp_token *alloc_expansion_token PARAMS ((cpp_reader *, cpp_macro *)); static cpp_token *lex_expansion_token PARAMS ((cpp_reader *, cpp_macro *)); static bool warn_of_redefinition PARAMS ((cpp_reader *, const cpp_hashnode *, const cpp_macro *)); @@ -1408,7 +1412,7 @@ } /* Allocate room for a token from a macro's replacement list. */ -static cpp_token * +cpp_token * alloc_expansion_token (pfile, macro) cpp_reader *pfile; cpp_macro *macro; @@ -1526,6 +1530,10 @@ token = lex_expansion_token (pfile, macro); } + if (gem_macro_def) { + gem_macro_def(pfile, macro); + } + macro->exp.tokens = (cpp_token *) BUFF_FRONT (pfile->a_buff); /* Don't count the CPP_EOF. */ diff -ru gcc-3.3.3-vanilla/gcc/flags.h gcc-3.3.3/gcc/flags.h --- gcc-3.3.3-vanilla/gcc/flags.h 2003-06-20 17:18:41.000000000 -0400 +++ gcc-3.3.3/gcc/flags.h 2005-06-04 21:35:24.000000000 -0400 @@ -690,4 +690,39 @@ #define HONOR_SIGN_DEPENDENT_ROUNDING(MODE) \ (MODE_HAS_SIGN_DEPENDENT_ROUNDING (MODE) && !flag_unsafe_math_optimizations) + +/* GCC extension module hook functions */ + +#define GEM_CONTINUE 0 +#define GEM_RETURN 1 + +extern void *gem_handle; /* module handle */ +extern int gem_result; + +/* hook functions */ +void (*gem_init_ptr)(void); +void (*gem_destroy_ptr)(void); + +extern unsigned int (*gem_handle_option)(const char **argv, unsigned int lang_mask); +extern void (*gem_final_start_function)(rtx, FILE *, int); +extern void (*gem_output_asm_insn)(const char*, rtx *); +extern void (*gem_expand_expr_pre)(tree *); +extern void (*gem_expand_expr_post)(void); +extern void (*gem_genrtl_switch_stmt)(tree); +extern void (*gem_c_common_nodes_and_builtins)(void); +extern void (*gem_finish_function)(tree*); +extern void (*gem_expand_body)(tree*); +extern void (*gem_genrtl_if_stmt)(tree, tree); +extern void (*gem_genrtl_return_stmt)(tree); +extern void (*gem_genrtl_for_stmt)(tree); +extern void (*gem_finalize_compilation_unit)(void); +extern int (*gem_expand_builtin)(void); + +struct cpp_hashnode; +struct cpp_reader; +struct cpp_macro; +extern void (*gem_macro_name)(struct cpp_hashnode *); +extern void (*gem_macro_def)(struct cpp_reader *, struct cpp_macro *); + + #endif /* ! GCC_FLAGS_H */ diff -ru gcc-3.3.3-vanilla/gcc/toplev.c gcc-3.3.3/gcc/toplev.c --- gcc-3.3.3-vanilla/gcc/toplev.c 2003-12-23 01:28:29.000000000 -0500 +++ gcc-3.3.3/gcc/toplev.c 2005-06-08 12:47:04.000000000 -0400 @@ -4961,6 +4961,17 @@ int lang_processed; int indep_processed; + if (gem_handle_option) { + unsigned int res; + + res=gem_handle_option(argv+i, 0); + + if (gem_result==GEM_RETURN) { + i++; + continue; + } + } + /* Give the language a chance to decode the option for itself. */ lang_processed = (*lang_hooks.decode_option) (argc - i, argv + i); @@ -5436,6 +5447,12 @@ if (!exit_after_options) do_compile (); + /* close GEM if it was opened */ + if (gem_handle && gem_destroy_ptr) { + gem_destroy_ptr(); + dlclose(gem_handle); + } + if (errorcount || sorrycount) return (FATAL_EXIT_CODE); --- gcc-3.3.3-vanilla/gcc/Makefile 2005-06-08 19:59:40.000000000 -0400 +++ gcc-3.3.3/gcc/Makefile 2005-06-08 20:07:39.000000000 -0400 @@ -682,7 +682,7 @@ # How to link with both our special library facilities # and the system's installed libraries. -LIBS = $(INTLLIBS) $(LIBIBERTY) +LIBS = $(INTLLIBS) $(LIBIBERTY) -ldl # Any system libraries needed just for GNAT. SYSLIBS = @@ -1054,7 +1054,7 @@ xgcc$(exeext): gcc.o gccspec.o version.o intl.o prefix.o \ version.o $(LIBDEPS) $(EXTRA_GCC_OBJS) $(CC) $(ALL_CFLAGS) $(LDFLAGS) -o $@ gcc.o gccspec.o intl.o \ - prefix.o version.o $(EXTRA_GCC_OBJS) $(LIBS) + prefix.o version.o $(EXTRA_GCC_OBJS) $(LIBS) -export-dynamic # cpp is to cpp0 as gcc is to cc1. # The only difference from xgcc is that it's linked with cppspec.o @@ -1077,7 +1077,7 @@ cc1$(exeext): $(C_OBJS) $(BACKEND) $(LIBDEPS) $(CC) $(ALL_CFLAGS) $(LDFLAGS) -o cc1$(exeext) \ - $(C_OBJS) $(BACKEND) $(LIBS) + $(C_OBJS) $(BACKEND) $(LIBS) -export-dynamic # Build the version of limits.h that we will install. xlimits.h: glimits.h limitx.h limity.h