PR rtl-optimization/88470
[official-gcc.git] / gcc / d / d-lang.cc
blob42fefaf640912cd6a282f42958a96b1099c85cf2
1 /* d-lang.cc -- Language-dependent hooks for D.
2 Copyright (C) 2006-2018 Free Software Foundation, Inc.
4 GCC is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 3, or (at your option)
7 any later version.
9 GCC is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with GCC; see the file COPYING3. If not see
16 <http://www.gnu.org/licenses/>. */
18 #include "config.h"
19 #include "system.h"
20 #include "coretypes.h"
22 #include "dmd/aggregate.h"
23 #include "dmd/cond.h"
24 #include "dmd/declaration.h"
25 #include "dmd/doc.h"
26 #include "dmd/errors.h"
27 #include "dmd/expression.h"
28 #include "dmd/hdrgen.h"
29 #include "dmd/identifier.h"
30 #include "dmd/json.h"
31 #include "dmd/mangle.h"
32 #include "dmd/mars.h"
33 #include "dmd/module.h"
34 #include "dmd/mtype.h"
35 #include "dmd/target.h"
37 #include "opts.h"
38 #include "alias.h"
39 #include "tree.h"
40 #include "diagnostic.h"
41 #include "fold-const.h"
42 #include "toplev.h"
43 #include "langhooks.h"
44 #include "langhooks-def.h"
45 #include "target.h"
46 #include "stringpool.h"
47 #include "stor-layout.h"
48 #include "varasm.h"
49 #include "output.h"
50 #include "print-tree.h"
51 #include "gimple-expr.h"
52 #include "gimplify.h"
53 #include "debug.h"
55 #include "d-tree.h"
56 #include "id.h"
59 /* Array of D frontend type/decl nodes. */
60 tree d_global_trees[DTI_MAX];
62 /* True if compilation is currently inside the D frontend semantic passes. */
63 bool doing_semantic_analysis_p = false;
65 /* Options handled by the compiler that are separate from the frontend. */
66 struct d_option_data
68 const char *fonly; /* -fonly=<arg> */
69 const char *multilib; /* -imultilib <dir> */
70 const char *prefix; /* -iprefix <dir> */
72 bool deps; /* -M */
73 bool deps_skip_system; /* -MM */
74 const char *deps_filename; /* -M[M]D */
75 const char *deps_filename_user; /* -MF <arg> */
76 OutBuffer *deps_target; /* -M[QT] <arg> */
77 bool deps_phony; /* -MP */
79 bool stdinc; /* -nostdinc */
81 d_option;
83 /* List of modules being compiled. */
84 static Modules builtin_modules;
86 /* Module where `C main' is defined, compiled in if needed. */
87 static Module *entrypoint_module = NULL;
88 static Module *entrypoint_root_module = NULL;
90 /* The current and global binding level in effect. */
91 struct binding_level *current_binding_level;
92 struct binding_level *global_binding_level;
94 /* The context to be used for global declarations. */
95 static GTY(()) tree global_context;
97 /* Array of all global declarations to pass back to the middle-end. */
98 static GTY(()) vec<tree, va_gc> *global_declarations;
100 /* Support for GCC-style command-line make dependency generation.
101 Adds TARGET to the make dependencies target buffer.
102 QUOTED is true if the string should be quoted. */
104 static void
105 deps_add_target (const char *target, bool quoted)
107 if (!d_option.deps_target)
108 d_option.deps_target = new OutBuffer ();
109 else
110 d_option.deps_target->writeByte (' ');
112 d_option.deps_target->reserve (strlen (target));
114 if (!quoted)
116 d_option.deps_target->writestring (target);
117 return;
120 /* Quote characters in target which are significant to Make. */
121 for (const char *p = target; *p != '\0'; p++)
123 switch (*p)
125 case ' ':
126 case '\t':
127 for (const char *q = p - 1; target <= q && *q == '\\'; q--)
128 d_option.deps_target->writeByte ('\\');
129 d_option.deps_target->writeByte ('\\');
130 break;
132 case '$':
133 d_option.deps_target->writeByte ('$');
134 break;
136 case '#':
137 d_option.deps_target->writeByte ('\\');
138 break;
140 default:
141 break;
144 d_option.deps_target->writeByte (*p);
148 /* Write out all dependencies of a given MODULE to the specified BUFFER.
149 COLMAX is the number of columns to word-wrap at (0 means don't wrap). */
151 static void
152 deps_write (Module *module, OutBuffer *buffer, unsigned colmax = 72)
154 hash_set <const char *> dependencies;
156 Modules modlist;
157 modlist.push (module);
159 Modules phonylist;
161 const char *str;
162 unsigned size;
163 unsigned column = 0;
165 /* Write out make target module name. */
166 if (d_option.deps_target)
168 size = d_option.deps_target->offset;
169 str = d_option.deps_target->extractString ();
171 else
173 str = module->objfile->name->str;
174 size = strlen (str);
177 buffer->writestring (str);
178 column = size;
179 buffer->writestring (":");
180 column++;
182 /* Write out all make dependencies. */
183 while (modlist.dim > 0)
185 Module *depmod = modlist.pop ();
187 str = depmod->srcfile->name->str;
188 size = strlen (str);
190 /* Skip dependencies that have already been written. */
191 if (dependencies.add (str))
192 continue;
194 column += size;
196 if (colmax && column > colmax)
198 buffer->writestring (" \\\n ");
199 column = size + 1;
201 else
203 buffer->writestring (" ");
204 column++;
207 buffer->writestring (str);
209 /* Add to list of phony targets if is not being compile. */
210 if (d_option.deps_phony && !depmod->isRoot ())
211 phonylist.push (depmod);
213 /* Search all imports of the written dependency. */
214 for (size_t i = 0; i < depmod->aimports.dim; i++)
216 Module *m = depmod->aimports[i];
218 /* Ignore compiler-generated modules. */
219 if ((m->ident == Identifier::idPool ("__entrypoint")
220 || m->ident == Identifier::idPool ("__main"))
221 && m->parent == NULL)
222 continue;
224 /* Don't search system installed modules, this includes
225 object, core.*, std.*, and gcc.* packages. */
226 if (d_option.deps_skip_system)
228 if (m->ident == Identifier::idPool ("object")
229 && m->parent == NULL)
230 continue;
232 if (m->md && m->md->packages)
234 Identifier *package = (*m->md->packages)[0];
236 if (package == Identifier::idPool ("core")
237 || package == Identifier::idPool ("std")
238 || package == Identifier::idPool ("gcc"))
239 continue;
243 modlist.push (m);
247 buffer->writenl ();
249 /* Write out all phony targets. */
250 for (size_t i = 0; i < phonylist.dim; i++)
252 Module *m = phonylist[i];
254 buffer->writenl ();
255 buffer->writestring (m->srcfile->name->str);
256 buffer->writestring (":\n");
260 /* Implements the lang_hooks.init_options routine for language D.
261 This initializes the global state for the D frontend before calling
262 the option handlers. */
264 static void
265 d_init_options (unsigned int, cl_decoded_option *decoded_options)
267 /* Set default values. */
268 global._init ();
270 global.vendor = lang_hooks.name;
271 global.params.argv0 = xstrdup (decoded_options[0].arg);
272 global.params.link = true;
273 global.params.useAssert = true;
274 global.params.useInvariants = true;
275 global.params.useIn = true;
276 global.params.useOut = true;
277 global.params.useArrayBounds = BOUNDSCHECKdefault;
278 global.params.useSwitchError = true;
279 global.params.useInline = false;
280 global.params.obj = true;
281 global.params.hdrStripPlainFunctions = true;
282 global.params.betterC = false;
283 global.params.allInst = false;
285 global.params.linkswitches = new Strings ();
286 global.params.libfiles = new Strings ();
287 global.params.objfiles = new Strings ();
288 global.params.ddocfiles = new Strings ();
290 /* Warnings and deprecations are disabled by default. */
291 global.params.useDeprecated = DIAGNOSTICoff;
292 global.params.warnings = DIAGNOSTICoff;
294 global.params.imppath = new Strings ();
295 global.params.fileImppath = new Strings ();
296 global.params.modFileAliasStrings = new Strings ();
298 /* Extra GDC-specific options. */
299 d_option.fonly = NULL;
300 d_option.multilib = NULL;
301 d_option.prefix = NULL;
302 d_option.deps = false;
303 d_option.deps_skip_system = false;
304 d_option.deps_filename = NULL;
305 d_option.deps_filename_user = NULL;
306 d_option.deps_target = NULL;
307 d_option.deps_phony = false;
308 d_option.stdinc = true;
311 /* Implements the lang_hooks.init_options_struct routine for language D.
312 Initializes the options structure OPTS. */
314 static void
315 d_init_options_struct (gcc_options *opts)
317 /* GCC options. */
318 opts->x_flag_exceptions = 1;
320 /* Avoid range issues for complex multiply and divide. */
321 opts->x_flag_complex_method = 2;
323 /* Unlike C, there is no global 'errno' variable. */
324 opts->x_flag_errno_math = 0;
325 opts->frontend_set_flag_errno_math = true;
327 /* Keep in sync with existing -fbounds-check flag. */
328 opts->x_flag_bounds_check = global.params.useArrayBounds;
330 /* D says that signed overflow is precisely defined. */
331 opts->x_flag_wrapv = 1;
334 /* Implements the lang_hooks.lang_mask routine for language D.
335 Returns language mask for option parsing. */
337 static unsigned int
338 d_option_lang_mask (void)
340 return CL_D;
343 /* Implements the lang_hooks.init routine for language D. */
345 static bool
346 d_init (void)
348 Type::_init ();
349 Id::initialize ();
350 Module::_init ();
351 Expression::_init ();
352 Objc::_init ();
354 /* Back-end init. */
355 global_binding_level = ggc_cleared_alloc<binding_level> ();
356 current_binding_level = global_binding_level;
358 /* This allows the code in d-builtins.cc to not have to worry about
359 converting (C signed char *) to (D char *) for string arguments of
360 built-in functions. The parameter (signed_char = false) specifies
361 whether char is signed. */
362 build_common_tree_nodes (false);
364 d_init_builtins ();
366 if (flag_exceptions)
367 using_eh_for_cleanups ();
369 if (!supports_one_only ())
370 flag_weak = 0;
372 /* This is the C main, not the D main. */
373 main_identifier_node = get_identifier ("main");
375 Target::_init ();
376 d_init_versions ();
378 /* Insert all library-configured identifiers and import paths. */
379 add_import_paths (d_option.prefix, d_option.multilib, d_option.stdinc);
381 return 1;
384 /* Implements the lang_hooks.init_ts routine for language D. */
386 static void
387 d_init_ts (void)
389 MARK_TS_TYPED (FLOAT_MOD_EXPR);
390 MARK_TS_TYPED (UNSIGNED_RSHIFT_EXPR);
393 /* Implements the lang_hooks.handle_option routine for language D.
394 Handles D specific options. Return false if we didn't do anything. */
396 static bool
397 d_handle_option (size_t scode, const char *arg, HOST_WIDE_INT value,
398 int kind ATTRIBUTE_UNUSED,
399 location_t loc ATTRIBUTE_UNUSED,
400 const cl_option_handlers *handlers ATTRIBUTE_UNUSED)
402 opt_code code = (opt_code) scode;
403 bool result = true;
405 switch (code)
407 case OPT_fall_instantiations:
408 global.params.allInst = value;
409 break;
411 case OPT_fassert:
412 global.params.useAssert = value;
413 break;
415 case OPT_fbounds_check:
416 global.params.useArrayBounds = value
417 ? BOUNDSCHECKon : BOUNDSCHECKoff;
418 break;
420 case OPT_fbounds_check_:
421 global.params.useArrayBounds = (value == 2) ? BOUNDSCHECKon
422 : (value == 1) ? BOUNDSCHECKsafeonly : BOUNDSCHECKoff;
423 break;
425 case OPT_fdebug:
426 global.params.debuglevel = value ? 1 : 0;
427 break;
429 case OPT_fdebug_:
430 if (ISDIGIT (arg[0]))
432 int level = integral_argument (arg);
433 if (level != -1)
435 DebugCondition::setGlobalLevel (level);
436 break;
440 if (Identifier::isValidIdentifier (CONST_CAST (char *, arg)))
442 DebugCondition::addGlobalIdent (arg);
443 break;
446 error ("bad argument for -fdebug %qs", arg);
447 break;
449 case OPT_fdoc:
450 global.params.doDocComments = value;
451 break;
453 case OPT_fdoc_dir_:
454 global.params.doDocComments = true;
455 global.params.docdir = arg;
456 break;
458 case OPT_fdoc_file_:
459 global.params.doDocComments = true;
460 global.params.docname = arg;
461 break;
463 case OPT_fdoc_inc_:
464 global.params.ddocfiles->push (arg);
465 break;
467 case OPT_fdump_d_original:
468 global.params.vcg_ast = value;
469 break;
471 case OPT_fignore_unknown_pragmas:
472 global.params.ignoreUnsupportedPragmas = value;
473 break;
475 case OPT_finvariants:
476 global.params.useInvariants = value;
477 break;
479 case OPT_fmain:
480 global.params.addMain = value;
481 break;
483 case OPT_fmodule_file_:
484 global.params.modFileAliasStrings->push (arg);
485 if (!strchr (arg, '='))
486 error ("bad argument for -fmodule-file %qs", arg);
487 break;
489 case OPT_fmoduleinfo:
490 global.params.betterC = !value;
491 break;
493 case OPT_fonly_:
494 d_option.fonly = arg;
495 break;
497 case OPT_fpostconditions:
498 global.params.useOut = value;
499 break;
501 case OPT_fpreconditions:
502 global.params.useIn = value;
503 break;
505 case OPT_frelease:
506 global.params.release = value;
507 break;
509 case OPT_fswitch_errors:
510 global.params.useSwitchError = value;
511 break;
513 case OPT_ftransition_all:
514 global.params.vtls = value;
515 global.params.vfield = value;
516 global.params.vcomplex = value;
517 break;
519 case OPT_ftransition_checkimports:
520 global.params.check10378 = value;
521 break;
523 case OPT_ftransition_complex:
524 global.params.vcomplex = value;
525 break;
527 case OPT_ftransition_dip1000:
528 global.params.vsafe = value;
529 global.params.useDIP25 = value;
530 break;
532 case OPT_ftransition_dip25:
533 global.params.useDIP25 = value;
534 break;
536 case OPT_ftransition_field:
537 global.params.vfield = value;
538 break;
540 case OPT_ftransition_import:
541 global.params.bug10378 = value;
542 break;
544 case OPT_ftransition_nogc:
545 global.params.vgc = value;
546 break;
548 case OPT_ftransition_tls:
549 global.params.vtls = value;
550 break;
552 case OPT_funittest:
553 global.params.useUnitTests = value;
554 break;
556 case OPT_fversion_:
557 if (ISDIGIT (arg[0]))
559 int level = integral_argument (arg);
560 if (level != -1)
562 VersionCondition::setGlobalLevel (level);
563 break;
567 if (Identifier::isValidIdentifier (CONST_CAST (char *, arg)))
569 VersionCondition::addGlobalIdent (arg);
570 break;
573 error ("bad argument for -fversion %qs", arg);
574 break;
576 case OPT_H:
577 global.params.doHdrGeneration = true;
578 break;
580 case OPT_Hd:
581 global.params.doHdrGeneration = true;
582 global.params.hdrdir = arg;
583 break;
585 case OPT_Hf:
586 global.params.doHdrGeneration = true;
587 global.params.hdrname = arg;
588 break;
590 case OPT_imultilib:
591 d_option.multilib = arg;
592 break;
594 case OPT_iprefix:
595 d_option.prefix = arg;
596 break;
598 case OPT_I:
599 global.params.imppath->push (arg);
600 break;
602 case OPT_J:
603 global.params.fileImppath->push (arg);
604 break;
606 case OPT_MM:
607 d_option.deps_skip_system = true;
608 /* Fall through. */
610 case OPT_M:
611 d_option.deps = true;
612 break;
614 case OPT_MMD:
615 d_option.deps_skip_system = true;
616 /* Fall through. */
618 case OPT_MD:
619 d_option.deps = true;
620 d_option.deps_filename = arg;
621 break;
623 case OPT_MF:
624 /* If specified multiple times, last one wins. */
625 d_option.deps_filename_user = arg;
626 break;
628 case OPT_MP:
629 d_option.deps_phony = true;
630 break;
632 case OPT_MQ:
633 deps_add_target (arg, true);
634 break;
636 case OPT_MT:
637 deps_add_target (arg, false);
638 break;
640 case OPT_nostdinc:
641 d_option.stdinc = false;
642 break;
644 case OPT_v:
645 global.params.verbose = value;
646 break;
648 case OPT_Wall:
649 if (value)
650 global.params.warnings = DIAGNOSTICinform;
651 break;
653 case OPT_Wdeprecated:
654 global.params.useDeprecated = value ? DIAGNOSTICinform : DIAGNOSTICoff;
655 break;
657 case OPT_Werror:
658 if (value)
659 global.params.warnings = DIAGNOSTICerror;
660 break;
662 case OPT_Wspeculative:
663 if (value)
664 global.params.showGaggedErrors = 1;
665 break;
667 case OPT_Xf:
668 global.params.jsonfilename = arg;
669 /* Fall through. */
671 case OPT_X:
672 global.params.doJsonGeneration = true;
673 break;
675 default:
676 break;
679 D_handle_option_auto (&global_options, &global_options_set,
680 scode, arg, value,
681 d_option_lang_mask (), kind,
682 loc, handlers, global_dc);
684 return result;
687 /* Implements the lang_hooks.post_options routine for language D.
688 Deal with any options that imply the turning on/off of features.
689 FN is the main input filename passed on the command line. */
691 static bool
692 d_post_options (const char ** fn)
694 /* Verify the input file name. */
695 const char *filename = *fn;
696 if (!filename || strcmp (filename, "-") == 0)
697 filename = "";
699 /* The front end considers the first input file to be the main one. */
700 *fn = filename;
702 /* Release mode doesn't turn off bounds checking for safe functions. */
703 if (global.params.useArrayBounds == BOUNDSCHECKdefault)
705 global.params.useArrayBounds = global.params.release
706 ? BOUNDSCHECKsafeonly : BOUNDSCHECKon;
707 flag_bounds_check = !global.params.release;
710 if (global.params.release)
712 if (!global_options_set.x_flag_invariants)
713 global.params.useInvariants = false;
715 if (!global_options_set.x_flag_preconditions)
716 global.params.useIn = false;
718 if (!global_options_set.x_flag_postconditions)
719 global.params.useOut = false;
721 if (!global_options_set.x_flag_assert)
722 global.params.useAssert = false;
724 if (!global_options_set.x_flag_switch_errors)
725 global.params.useSwitchError = false;
728 /* Error about use of deprecated features. */
729 if (global.params.useDeprecated == DIAGNOSTICinform
730 && global.params.warnings == DIAGNOSTICerror)
731 global.params.useDeprecated = DIAGNOSTICerror;
733 /* Make -fmax-errors visible to frontend's diagnostic machinery. */
734 if (global_options_set.x_flag_max_errors)
735 global.errorLimit = flag_max_errors;
737 if (flag_excess_precision_cmdline == EXCESS_PRECISION_DEFAULT)
738 flag_excess_precision_cmdline = EXCESS_PRECISION_STANDARD;
740 if (global.params.useUnitTests)
741 global.params.useAssert = true;
743 global.params.symdebug = write_symbols != NO_DEBUG;
744 global.params.useInline = flag_inline_functions;
745 global.params.showColumns = flag_show_column;
747 if (global.params.useInline)
748 global.params.hdrStripPlainFunctions = false;
750 global.params.obj = !flag_syntax_only;
752 /* Has no effect yet. */
753 global.params.pic = flag_pic != 0;
755 if (warn_return_type == -1)
756 warn_return_type = 0;
758 return false;
761 /* Return TRUE if an operand OP of a given TYPE being copied has no data.
762 The middle-end does a similar check with zero sized types. */
764 static bool
765 empty_modify_p (tree type, tree op)
767 tree_code code = TREE_CODE (op);
768 switch (code)
770 case COMPOUND_EXPR:
771 return empty_modify_p (type, TREE_OPERAND (op, 1));
773 case CONSTRUCTOR:
774 /* Non-empty construcors are valid. */
775 if (CONSTRUCTOR_NELTS (op) != 0 || TREE_CLOBBER_P (op))
776 return false;
777 break;
779 case CALL_EXPR:
780 /* Leave nrvo alone because it isn't a copy. */
781 if (CALL_EXPR_RETURN_SLOT_OPT (op))
782 return false;
783 break;
785 default:
786 /* If the operand doesn't have a simple form. */
787 if (!is_gimple_lvalue (op) && !INDIRECT_REF_P (op))
788 return false;
789 break;
792 return empty_aggregate_p (type);
795 /* Implements the lang_hooks.gimplify_expr routine for language D.
796 Do gimplification of D specific expression trees in EXPR_P. */
799 d_gimplify_expr (tree *expr_p, gimple_seq *pre_p,
800 gimple_seq *post_p ATTRIBUTE_UNUSED)
802 tree_code code = TREE_CODE (*expr_p);
803 enum gimplify_status ret = GS_UNHANDLED;
804 tree op0, op1;
805 tree type;
807 switch (code)
809 case INIT_EXPR:
810 case MODIFY_EXPR:
811 op0 = TREE_OPERAND (*expr_p, 0);
812 op1 = TREE_OPERAND (*expr_p, 1);
814 if (!error_operand_p (op0) && !error_operand_p (op1)
815 && (AGGREGATE_TYPE_P (TREE_TYPE (op0))
816 || AGGREGATE_TYPE_P (TREE_TYPE (op1)))
817 && !useless_type_conversion_p (TREE_TYPE (op1), TREE_TYPE (op0)))
819 /* If the back end isn't clever enough to know that the lhs and rhs
820 types are the same, add an explicit conversion. */
821 TREE_OPERAND (*expr_p, 1) = build1 (VIEW_CONVERT_EXPR,
822 TREE_TYPE (op0), op1);
823 ret = GS_OK;
825 else if (empty_modify_p (TREE_TYPE (op0), op1))
827 /* Remove any copies of empty aggregates. */
828 gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
829 is_gimple_lvalue, fb_lvalue);
831 if (TREE_SIDE_EFFECTS (op1))
832 gimplify_and_add (op1, pre_p);
834 *expr_p = TREE_OPERAND (*expr_p, 0);
835 ret = GS_OK;
837 break;
839 case ADDR_EXPR:
840 op0 = TREE_OPERAND (*expr_p, 0);
841 /* Constructors are not lvalues, so make them one. */
842 if (TREE_CODE (op0) == CONSTRUCTOR)
844 TREE_OPERAND (*expr_p, 0) = force_target_expr (op0);
845 ret = GS_OK;
847 break;
849 case CALL_EXPR:
850 if (CALL_EXPR_ARGS_ORDERED (*expr_p))
852 /* Strictly evaluate all arguments from left to right. */
853 int nargs = call_expr_nargs (*expr_p);
854 location_t loc = EXPR_LOC_OR_LOC (*expr_p, input_location);
856 /* No need to enforce evaluation order if only one argument. */
857 if (nargs < 2)
858 break;
860 /* Or if all arguments are already free of side-effects. */
861 bool has_side_effects = false;
862 for (int i = 0; i < nargs; i++)
864 if (TREE_SIDE_EFFECTS (CALL_EXPR_ARG (*expr_p, i)))
866 has_side_effects = true;
867 break;
871 if (!has_side_effects)
872 break;
874 /* Leave the last argument for gimplify_call_expr. */
875 for (int i = 0; i < nargs - 1; i++)
877 tree new_arg = CALL_EXPR_ARG (*expr_p, i);
879 /* If argument has a side-effect, gimplify_arg will handle it. */
880 if (gimplify_arg (&new_arg, pre_p, loc) == GS_ERROR)
881 ret = GS_ERROR;
883 /* Even if an argument itself doesn't have any side-effects, it
884 might be altered by another argument in the list. */
885 if (new_arg == CALL_EXPR_ARG (*expr_p, i)
886 && !really_constant_p (new_arg))
887 new_arg = get_formal_tmp_var (new_arg, pre_p);
889 CALL_EXPR_ARG (*expr_p, i) = new_arg;
892 if (ret != GS_ERROR)
893 ret = GS_OK;
895 break;
897 case UNSIGNED_RSHIFT_EXPR:
898 /* Convert op0 to an unsigned type. */
899 op0 = TREE_OPERAND (*expr_p, 0);
900 op1 = TREE_OPERAND (*expr_p, 1);
902 type = d_unsigned_type (TREE_TYPE (op0));
904 *expr_p = convert (TREE_TYPE (*expr_p),
905 build2 (RSHIFT_EXPR, type, convert (type, op0), op1));
906 ret = GS_OK;
907 break;
909 case FLOAT_MOD_EXPR:
910 gcc_unreachable ();
912 default:
913 break;
916 return ret;
919 /* Add the module M to the list of modules that may declare GCC builtins.
920 These are scanned after first semantic and before codegen passes.
921 See d_maybe_set_builtin() for the implementation. */
923 void
924 d_add_builtin_module (Module *m)
926 builtin_modules.push (m);
929 /* Record the entrypoint module ENTRY which will be compiled in the current
930 compilation. ROOT is the module scope where this was requested from. */
932 void
933 d_add_entrypoint_module (Module *entry, Module *root)
935 /* We are emitting this straight to object file. */
936 entrypoint_module = entry;
937 entrypoint_root_module = root;
940 /* Implements the lang_hooks.parse_file routine for language D. */
942 void
943 d_parse_file (void)
945 if (global.params.verbose)
947 message ("binary %s", global.params.argv0);
948 message ("version %s", global.version);
950 if (global.params.versionids)
952 OutBuffer buf;
953 buf.writestring ("predefs ");
954 for (size_t i = 0; i < global.params.versionids->dim; i++)
956 const char *s = (*global.params.versionids)[i];
957 buf.writestring (" ");
958 buf.writestring (s);
961 message ("%.*s", (int) buf.offset, (char *) buf.data);
965 /* Start the main input file, if the debug writer wants it. */
966 if (debug_hooks->start_end_main_source_file)
967 debug_hooks->start_source_file (0, main_input_filename);
969 /* Create Module's for all sources we will load. */
970 Modules modules;
971 modules.reserve (num_in_fnames);
973 /* In this mode, the first file name is supposed to be a duplicate
974 of one of the input files. */
975 if (d_option.fonly && strcmp (d_option.fonly, main_input_filename) != 0)
976 error ("-fonly= argument is different from first input file name");
978 for (size_t i = 0; i < num_in_fnames; i++)
980 if (strcmp (in_fnames[i], "-") == 0)
982 /* Handling stdin, generate a unique name for the module. */
983 obstack buffer;
984 gcc_obstack_init (&buffer);
985 int c;
987 Module *m = Module::create (in_fnames[i],
988 Identifier::generateId ("__stdin"),
989 global.params.doDocComments,
990 global.params.doHdrGeneration);
991 modules.push (m);
993 /* Load the entire contents of stdin into memory. */
994 while ((c = getc (stdin)) != EOF)
995 obstack_1grow (&buffer, c);
997 if (!obstack_object_size (&buffer))
998 obstack_1grow (&buffer, '\0');
1000 /* Overwrite the source file for the module, the one created by
1001 Module::create would have a forced a `.d' suffix. */
1002 m->srcfile = File::create ("<stdin>");
1003 m->srcfile->len = obstack_object_size (&buffer);
1004 m->srcfile->buffer = (unsigned char *) obstack_finish (&buffer);
1006 /* Tell the front-end not to free the buffer after parsing. */
1007 m->srcfile->ref = 1;
1009 else
1011 /* Handling a D source file, strip off the path and extension. */
1012 const char *basename = FileName::name (in_fnames[i]);
1013 const char *name = FileName::removeExt (basename);
1015 Module *m = Module::create (in_fnames[i], Identifier::idPool (name),
1016 global.params.doDocComments,
1017 global.params.doHdrGeneration);
1018 modules.push (m);
1019 FileName::free (name);
1023 /* Read all D source files. */
1024 for (size_t i = 0; i < modules.dim; i++)
1026 Module *m = modules[i];
1027 m->read (Loc ());
1030 /* Parse all D source files. */
1031 for (size_t i = 0; i < modules.dim; i++)
1033 Module *m = modules[i];
1035 if (global.params.verbose)
1036 message ("parse %s", m->toChars ());
1038 if (!Module::rootModule)
1039 Module::rootModule = m;
1041 m->importedFrom = m;
1042 m->parse ();
1043 Compiler::loadModule (m);
1045 if (m->isDocFile)
1047 gendocfile (m);
1048 /* Remove M from list of modules. */
1049 modules.remove (i);
1050 i--;
1054 /* Load the module containing D main. */
1055 if (global.params.addMain)
1057 unsigned errors = global.startGagging ();
1058 Module *m = Module::load (Loc (), NULL, Identifier::idPool ("__main"));
1060 if (! global.endGagging (errors))
1062 m->importedFrom = m;
1063 modules.push (m);
1067 if (global.errors)
1068 goto had_errors;
1070 if (global.params.doHdrGeneration)
1072 /* Generate 'header' import files. Since 'header' import files must be
1073 independent of command line switches and what else is imported, they
1074 are generated before any semantic analysis. */
1075 for (size_t i = 0; i < modules.dim; i++)
1077 Module *m = modules[i];
1078 if (d_option.fonly && m != Module::rootModule)
1079 continue;
1081 if (global.params.verbose)
1082 message ("import %s", m->toChars ());
1084 genhdrfile (m);
1088 if (global.errors)
1089 goto had_errors;
1091 /* Load all unconditional imports for better symbol resolving. */
1092 for (size_t i = 0; i < modules.dim; i++)
1094 Module *m = modules[i];
1096 if (global.params.verbose)
1097 message ("importall %s", m->toChars ());
1099 m->importAll (NULL);
1102 if (global.errors)
1103 goto had_errors;
1105 /* Do semantic analysis. */
1106 doing_semantic_analysis_p = true;
1108 for (size_t i = 0; i < modules.dim; i++)
1110 Module *m = modules[i];
1112 if (global.params.verbose)
1113 message ("semantic %s", m->toChars ());
1115 m->semantic (NULL);
1118 /* Do deferred semantic analysis. */
1119 Module::dprogress = 1;
1120 Module::runDeferredSemantic ();
1122 if (Module::deferred.dim)
1124 for (size_t i = 0; i < Module::deferred.dim; i++)
1126 Dsymbol *sd = Module::deferred[i];
1127 error_at (make_location_t (sd->loc),
1128 "unable to resolve forward reference in definition");
1132 /* Process all built-in modules or functions now for CTFE. */
1133 while (builtin_modules.dim != 0)
1135 Module *m = builtin_modules.pop ();
1136 d_maybe_set_builtin (m);
1139 /* Do pass 2 semantic analysis. */
1140 for (size_t i = 0; i < modules.dim; i++)
1142 Module *m = modules[i];
1144 if (global.params.verbose)
1145 message ("semantic2 %s", m->toChars ());
1147 m->semantic2 (NULL);
1150 Module::runDeferredSemantic2 ();
1152 if (global.errors)
1153 goto had_errors;
1155 /* Do pass 3 semantic analysis. */
1156 for (size_t i = 0; i < modules.dim; i++)
1158 Module *m = modules[i];
1160 if (global.params.verbose)
1161 message ("semantic3 %s", m->toChars ());
1163 m->semantic3 (NULL);
1166 Module::runDeferredSemantic3 ();
1168 /* Check again, incase semantic3 pass loaded any more modules. */
1169 while (builtin_modules.dim != 0)
1171 Module *m = builtin_modules.pop ();
1172 d_maybe_set_builtin (m);
1175 /* Do not attempt to generate output files if errors or warnings occurred. */
1176 if (global.errors || global.warnings)
1177 goto had_errors;
1179 /* Generate output files. */
1180 doing_semantic_analysis_p = false;
1182 if (Module::rootModule)
1184 /* Declare the name of the root module as the first global name in order
1185 to make the middle-end fully deterministic. */
1186 OutBuffer buf;
1187 mangleToBuffer (Module::rootModule, &buf);
1188 first_global_object_name = buf.extractString ();
1191 /* Make dependencies. */
1192 if (d_option.deps)
1194 OutBuffer buf;
1196 for (size_t i = 0; i < modules.dim; i++)
1197 deps_write (modules[i], &buf);
1199 /* -MF <arg> overrides -M[M]D. */
1200 if (d_option.deps_filename_user)
1201 d_option.deps_filename = d_option.deps_filename_user;
1203 if (d_option.deps_filename)
1205 File *fdeps = File::create (d_option.deps_filename);
1206 fdeps->setbuffer ((void *) buf.data, buf.offset);
1207 fdeps->ref = 1;
1208 writeFile (Loc (), fdeps);
1210 else
1211 message ("%.*s", (int) buf.offset, (char *) buf.data);
1214 /* Generate JSON files. */
1215 if (global.params.doJsonGeneration)
1217 OutBuffer buf;
1218 json_generate (&buf, &modules);
1220 const char *name = global.params.jsonfilename;
1222 if (name && (name[0] != '-' || name[1] != '\0'))
1224 const char *nameext = FileName::defaultExt (name, global.json_ext);
1225 File *fjson = File::create (nameext);
1226 fjson->setbuffer ((void *) buf.data, buf.offset);
1227 fjson->ref = 1;
1228 writeFile (Loc (), fjson);
1230 else
1231 message ("%.*s", (int) buf.offset, (char *) buf.data);
1234 /* Generate Ddoc files. */
1235 if (global.params.doDocComments && !global.errors && !errorcount)
1237 for (size_t i = 0; i < modules.dim; i++)
1239 Module *m = modules[i];
1240 gendocfile (m);
1244 /* Handle -fdump-d-original. */
1245 if (global.params.vcg_ast)
1247 for (size_t i = 0; i < modules.dim; i++)
1249 Module *m = modules[i];
1250 OutBuffer buf;
1251 buf.doindent = 1;
1253 moduleToBuffer (&buf, m);
1254 message ("%.*s", (int) buf.offset, (char *) buf.data);
1258 for (size_t i = 0; i < modules.dim; i++)
1260 Module *m = modules[i];
1261 if (d_option.fonly && m != Module::rootModule)
1262 continue;
1264 if (global.params.verbose)
1265 message ("code %s", m->toChars ());
1267 if (!flag_syntax_only)
1269 if ((entrypoint_module != NULL) && (m == entrypoint_root_module))
1270 build_decl_tree (entrypoint_module);
1272 build_decl_tree (m);
1276 /* And end the main input file, if the debug writer wants it. */
1277 if (debug_hooks->start_end_main_source_file)
1278 debug_hooks->end_source_file (0);
1280 had_errors:
1281 /* Add the D frontend error count to the GCC error count to correctly
1282 exit with an error status. */
1283 errorcount += (global.errors + global.warnings);
1285 /* Write out globals. */
1286 d_finish_compilation (vec_safe_address (global_declarations),
1287 vec_safe_length (global_declarations));
1290 /* Implements the lang_hooks.types.type_for_mode routine for language D. */
1292 static tree
1293 d_type_for_mode (machine_mode mode, int unsignedp)
1295 if (mode == QImode)
1296 return unsignedp ? d_ubyte_type : d_byte_type;
1298 if (mode == HImode)
1299 return unsignedp ? d_ushort_type : d_short_type;
1301 if (mode == SImode)
1302 return unsignedp ? d_uint_type : d_int_type;
1304 if (mode == DImode)
1305 return unsignedp ? d_ulong_type : d_long_type;
1307 if (mode == TYPE_MODE (d_cent_type))
1308 return unsignedp ? d_ucent_type : d_cent_type;
1310 if (mode == TYPE_MODE (float_type_node))
1311 return float_type_node;
1313 if (mode == TYPE_MODE (double_type_node))
1314 return double_type_node;
1316 if (mode == TYPE_MODE (long_double_type_node))
1317 return long_double_type_node;
1319 if (mode == TYPE_MODE (build_pointer_type (char8_type_node)))
1320 return build_pointer_type (char8_type_node);
1322 if (mode == TYPE_MODE (build_pointer_type (d_int_type)))
1323 return build_pointer_type (d_int_type);
1325 if (COMPLEX_MODE_P (mode))
1327 machine_mode inner_mode;
1328 tree inner_type;
1330 if (mode == TYPE_MODE (complex_float_type_node))
1331 return complex_float_type_node;
1332 if (mode == TYPE_MODE (complex_double_type_node))
1333 return complex_double_type_node;
1334 if (mode == TYPE_MODE (complex_long_double_type_node))
1335 return complex_long_double_type_node;
1337 inner_mode = (machine_mode) GET_MODE_INNER (mode);
1338 inner_type = d_type_for_mode (inner_mode, unsignedp);
1339 if (inner_type != NULL_TREE)
1340 return build_complex_type (inner_type);
1342 else if (VECTOR_MODE_P (mode))
1344 machine_mode inner_mode = (machine_mode) GET_MODE_INNER (mode);
1345 tree inner_type = d_type_for_mode (inner_mode, unsignedp);
1346 if (inner_type != NULL_TREE)
1347 return build_vector_type_for_mode (inner_type, mode);
1350 return 0;
1353 /* Implements the lang_hooks.types.type_for_size routine for language D. */
1355 static tree
1356 d_type_for_size (unsigned bits, int unsignedp)
1358 if (bits <= TYPE_PRECISION (d_byte_type))
1359 return unsignedp ? d_ubyte_type : d_byte_type;
1361 if (bits <= TYPE_PRECISION (d_short_type))
1362 return unsignedp ? d_ushort_type : d_short_type;
1364 if (bits <= TYPE_PRECISION (d_int_type))
1365 return unsignedp ? d_uint_type : d_int_type;
1367 if (bits <= TYPE_PRECISION (d_long_type))
1368 return unsignedp ? d_ulong_type : d_long_type;
1370 if (bits <= TYPE_PRECISION (d_cent_type))
1371 return unsignedp ? d_ucent_type : d_cent_type;
1373 return 0;
1376 /* Return the signed or unsigned version of TYPE, an integral type, the
1377 signedness being specified by UNSIGNEDP. */
1379 static tree
1380 d_signed_or_unsigned_type (int unsignedp, tree type)
1382 if (TYPE_UNSIGNED (type) == (unsigned) unsignedp)
1383 return type;
1385 if (TYPE_PRECISION (type) == TYPE_PRECISION (d_cent_type))
1386 return unsignedp ? d_ucent_type : d_cent_type;
1388 if (TYPE_PRECISION (type) == TYPE_PRECISION (d_long_type))
1389 return unsignedp ? d_ulong_type : d_long_type;
1391 if (TYPE_PRECISION (type) == TYPE_PRECISION (d_int_type))
1392 return unsignedp ? d_uint_type : d_int_type;
1394 if (TYPE_PRECISION (type) == TYPE_PRECISION (d_short_type))
1395 return unsignedp ? d_ushort_type : d_short_type;
1397 if (TYPE_PRECISION (type) == TYPE_PRECISION (d_byte_type))
1398 return unsignedp ? d_ubyte_type : d_byte_type;
1400 return signed_or_unsigned_type_for (unsignedp, type);
1403 /* Return the unsigned version of TYPE, an integral type. */
1405 tree
1406 d_unsigned_type (tree type)
1408 return d_signed_or_unsigned_type (1, type);
1411 /* Return the signed version of TYPE, an integral type. */
1413 tree
1414 d_signed_type (tree type)
1416 return d_signed_or_unsigned_type (0, type);
1419 /* Implements the lang_hooks.types.type_promotes_to routine for language D.
1420 All promotions for variable arguments are handled by the D frontend. */
1422 static tree
1423 d_type_promotes_to (tree type)
1425 return type;
1428 /* Implements the lang_hooks.decls.global_bindings_p routine for language D.
1429 Return true if we are in the global binding level. */
1431 static bool
1432 d_global_bindings_p (void)
1434 return (current_binding_level == global_binding_level);
1437 /* Return global_context, but create it first if need be. */
1439 static tree
1440 get_global_context (void)
1442 if (!global_context)
1444 global_context = build_translation_unit_decl (NULL_TREE);
1445 debug_hooks->register_main_translation_unit (global_context);
1448 return global_context;
1451 /* Implements the lang_hooks.decls.pushdecl routine for language D.
1452 Record DECL as belonging to the current lexical scope. */
1454 tree
1455 d_pushdecl (tree decl)
1457 /* Set the context of the decl. If current_function_decl did not help in
1458 determining the context, use global scope. */
1459 if (!DECL_CONTEXT (decl))
1461 if (current_function_decl)
1462 DECL_CONTEXT (decl) = current_function_decl;
1463 else
1464 DECL_CONTEXT (decl) = get_global_context ();
1467 /* Put decls on list in reverse order. */
1468 if (TREE_STATIC (decl) || d_global_bindings_p ())
1469 vec_safe_push (global_declarations, decl);
1470 else
1472 TREE_CHAIN (decl) = current_binding_level->names;
1473 current_binding_level->names = decl;
1476 return decl;
1479 /* Implements the lang_hooks.decls.getdecls routine for language D.
1480 Return the list of declarations of the current level. */
1482 static tree
1483 d_getdecls (void)
1485 if (current_binding_level)
1486 return current_binding_level->names;
1488 return NULL_TREE;
1492 /* Implements the lang_hooks.get_alias_set routine for language D.
1493 Get the alias set corresponding to type or expression T.
1494 Return -1 if we don't do anything special. */
1496 static alias_set_type
1497 d_get_alias_set (tree)
1499 /* For now in D, assume everything aliases everything else, until we define
1500 some solid rules backed by a specification. There are also some parts
1501 of code generation routines that don't adhere to C alias rules, such as
1502 build_vconvert. In any case, a lot of user code already assumes there
1503 is no strict aliasing and will break if we were to change that. */
1504 return 0;
1507 /* Implements the lang_hooks.types_compatible_p routine for language D.
1508 Compares two types for equivalence in the D programming language.
1509 This routine should only return 1 if it is sure, even though the frontend
1510 should have already ensured that all types are compatible before handing
1511 over the parsed ASTs to the code generator. */
1513 static int
1514 d_types_compatible_p (tree x, tree y)
1516 Type *tx = TYPE_LANG_FRONTEND (x);
1517 Type *ty = TYPE_LANG_FRONTEND (y);
1519 /* Try validating the types in the frontend. */
1520 if (tx != NULL && ty != NULL)
1522 /* Types are equivalent. */
1523 if (same_type_p (tx, ty))
1524 return true;
1526 /* Type system allows implicit conversion between. */
1527 if (tx->implicitConvTo (ty) || ty->implicitConvTo (tx))
1528 return true;
1531 /* Fallback on using type flags for comparison. E.g: all dynamic arrays
1532 are distinct types in D, but are VIEW_CONVERT compatible. */
1533 if (TREE_CODE (x) == RECORD_TYPE && TREE_CODE (y) == RECORD_TYPE)
1535 if (TYPE_DYNAMIC_ARRAY (x) && TYPE_DYNAMIC_ARRAY (y))
1536 return true;
1538 if (TYPE_DELEGATE (x) && TYPE_DELEGATE (y))
1539 return true;
1541 if (TYPE_ASSOCIATIVE_ARRAY (x) && TYPE_ASSOCIATIVE_ARRAY (y))
1542 return true;
1545 return false;
1548 /* Implements the lang_hooks.finish_incomplete_decl routine for language D. */
1550 static void
1551 d_finish_incomplete_decl (tree decl)
1553 if (VAR_P (decl))
1555 /* D allows zero-length declarations. Such a declaration ends up with
1556 DECL_SIZE (t) == NULL_TREE which is what the back-end function
1557 assembler_variable checks. This could change in later versions, or
1558 maybe all of these variables should be aliased to one symbol. */
1559 if (DECL_SIZE (decl) == 0)
1561 DECL_SIZE (decl) = bitsize_zero_node;
1562 DECL_SIZE_UNIT (decl) = size_zero_node;
1567 /* Implements the lang_hooks.types.classify_record routine for language D.
1568 Return the true debug type for TYPE. */
1570 static classify_record
1571 d_classify_record (tree type)
1573 Type *t = TYPE_LANG_FRONTEND (type);
1575 if (t && t->ty == Tclass)
1577 TypeClass *tc = (TypeClass *) t;
1579 /* extern(C++) interfaces get emitted as classes. */
1580 if (tc->sym->isInterfaceDeclaration ()
1581 && !tc->sym->isCPPinterface ())
1582 return RECORD_IS_INTERFACE;
1584 return RECORD_IS_CLASS;
1587 return RECORD_IS_STRUCT;
1590 /* Implements the lang_hooks.tree_size routine for language D.
1591 Determine the size of our tcc_constant or tcc_exceptional nodes. */
1593 static size_t
1594 d_tree_size (tree_code code)
1596 switch (code)
1598 case FUNCFRAME_INFO:
1599 return sizeof (tree_frame_info);
1601 default:
1602 gcc_unreachable ();
1606 /* Implements the lang_hooks.print_xnode routine for language D. */
1608 static void
1609 d_print_xnode (FILE *file, tree node, int indent)
1611 switch (TREE_CODE (node))
1613 case FUNCFRAME_INFO:
1614 print_node (file, "frame_type", FRAMEINFO_TYPE (node), indent + 4);
1615 break;
1617 default:
1618 break;
1622 /* Return which tree structure is used by NODE, or TS_D_GENERIC if NODE
1623 is one of the language-independent trees. */
1625 d_tree_node_structure_enum
1626 d_tree_node_structure (lang_tree_node *t)
1628 switch (TREE_CODE (&t->generic))
1630 case IDENTIFIER_NODE:
1631 return TS_D_IDENTIFIER;
1633 case FUNCFRAME_INFO:
1634 return TS_D_FRAMEINFO;
1636 default:
1637 return TS_D_GENERIC;
1641 /* Allocate and return a lang specific structure for the frontend type. */
1643 struct lang_type *
1644 build_lang_type (Type *t)
1646 struct lang_type *lt = ggc_cleared_alloc<struct lang_type> ();
1647 lt->type = t;
1648 return lt;
1651 /* Allocate and return a lang specific structure for the frontend decl. */
1653 struct lang_decl *
1654 build_lang_decl (Declaration *d)
1656 /* For compiler generated run-time typeinfo, a lang_decl is allocated even if
1657 there's no associated frontend symbol to refer to (yet). If the symbol
1658 appears later in the compilation, then the slot will be re-used. */
1659 if (d == NULL)
1660 return ggc_cleared_alloc<struct lang_decl> ();
1662 struct lang_decl *ld = (d->csym) ? DECL_LANG_SPECIFIC (d->csym) : NULL;
1663 if (ld == NULL)
1664 ld = ggc_cleared_alloc<struct lang_decl> ();
1666 if (ld->decl == NULL)
1667 ld->decl = d;
1669 return ld;
1672 /* Implements the lang_hooks.dup_lang_specific_decl routine for language D.
1673 Replace the DECL_LANG_SPECIFIC field of NODE with a copy. */
1675 static void
1676 d_dup_lang_specific_decl (tree node)
1678 if (! DECL_LANG_SPECIFIC (node))
1679 return;
1681 struct lang_decl *ld = ggc_alloc<struct lang_decl> ();
1682 memcpy (ld, DECL_LANG_SPECIFIC (node), sizeof (struct lang_decl));
1683 DECL_LANG_SPECIFIC (node) = ld;
1686 /* This preserves trees we create from the garbage collector. */
1688 static GTY(()) tree d_keep_list = NULL_TREE;
1690 void
1691 d_keep (tree t)
1693 d_keep_list = tree_cons (NULL_TREE, t, d_keep_list);
1696 /* Implements the lang_hooks.eh_personality routine for language D.
1697 Return the GDC personality function decl. */
1699 static GTY(()) tree d_eh_personality_decl;
1701 static tree
1702 d_eh_personality (void)
1704 if (!d_eh_personality_decl)
1705 d_eh_personality_decl = build_personality_function ("gdc");
1707 return d_eh_personality_decl;
1710 /* Implements the lang_hooks.eh_runtime_type routine for language D. */
1712 static tree
1713 d_build_eh_runtime_type (tree type)
1715 Type *t = TYPE_LANG_FRONTEND (type);
1717 if (t != NULL)
1718 t = t->toBasetype ();
1720 gcc_assert (t != NULL && t->ty == Tclass);
1721 ClassDeclaration *cd = ((TypeClass *) t)->sym;
1722 tree decl;
1724 if (cd->isCPPclass ())
1725 decl = get_cpp_typeinfo_decl (cd);
1726 else
1727 decl = get_classinfo_decl (cd);
1729 return convert (ptr_type_node, build_address (decl));
1732 /* Definitions for our language-specific hooks. */
1734 #undef LANG_HOOKS_NAME
1735 #undef LANG_HOOKS_INIT
1736 #undef LANG_HOOKS_INIT_TS
1737 #undef LANG_HOOKS_INIT_OPTIONS
1738 #undef LANG_HOOKS_INIT_OPTIONS_STRUCT
1739 #undef LANG_HOOKS_OPTION_LANG_MASK
1740 #undef LANG_HOOKS_HANDLE_OPTION
1741 #undef LANG_HOOKS_POST_OPTIONS
1742 #undef LANG_HOOKS_PARSE_FILE
1743 #undef LANG_HOOKS_COMMON_ATTRIBUTE_TABLE
1744 #undef LANG_HOOKS_ATTRIBUTE_TABLE
1745 #undef LANG_HOOKS_GET_ALIAS_SET
1746 #undef LANG_HOOKS_TYPES_COMPATIBLE_P
1747 #undef LANG_HOOKS_BUILTIN_FUNCTION
1748 #undef LANG_HOOKS_REGISTER_BUILTIN_TYPE
1749 #undef LANG_HOOKS_FINISH_INCOMPLETE_DECL
1750 #undef LANG_HOOKS_GIMPLIFY_EXPR
1751 #undef LANG_HOOKS_CLASSIFY_RECORD
1752 #undef LANG_HOOKS_TREE_SIZE
1753 #undef LANG_HOOKS_PRINT_XNODE
1754 #undef LANG_HOOKS_DUP_LANG_SPECIFIC_DECL
1755 #undef LANG_HOOKS_EH_PERSONALITY
1756 #undef LANG_HOOKS_EH_RUNTIME_TYPE
1757 #undef LANG_HOOKS_PUSHDECL
1758 #undef LANG_HOOKS_GETDECLS
1759 #undef LANG_HOOKS_GLOBAL_BINDINGS_P
1760 #undef LANG_HOOKS_TYPE_FOR_MODE
1761 #undef LANG_HOOKS_TYPE_FOR_SIZE
1762 #undef LANG_HOOKS_TYPE_PROMOTES_TO
1764 #define LANG_HOOKS_NAME "GNU D"
1765 #define LANG_HOOKS_INIT d_init
1766 #define LANG_HOOKS_INIT_TS d_init_ts
1767 #define LANG_HOOKS_INIT_OPTIONS d_init_options
1768 #define LANG_HOOKS_INIT_OPTIONS_STRUCT d_init_options_struct
1769 #define LANG_HOOKS_OPTION_LANG_MASK d_option_lang_mask
1770 #define LANG_HOOKS_HANDLE_OPTION d_handle_option
1771 #define LANG_HOOKS_POST_OPTIONS d_post_options
1772 #define LANG_HOOKS_PARSE_FILE d_parse_file
1773 #define LANG_HOOKS_COMMON_ATTRIBUTE_TABLE d_langhook_common_attribute_table
1774 #define LANG_HOOKS_ATTRIBUTE_TABLE d_langhook_attribute_table
1775 #define LANG_HOOKS_GET_ALIAS_SET d_get_alias_set
1776 #define LANG_HOOKS_TYPES_COMPATIBLE_P d_types_compatible_p
1777 #define LANG_HOOKS_BUILTIN_FUNCTION d_builtin_function
1778 #define LANG_HOOKS_REGISTER_BUILTIN_TYPE d_register_builtin_type
1779 #define LANG_HOOKS_FINISH_INCOMPLETE_DECL d_finish_incomplete_decl
1780 #define LANG_HOOKS_GIMPLIFY_EXPR d_gimplify_expr
1781 #define LANG_HOOKS_CLASSIFY_RECORD d_classify_record
1782 #define LANG_HOOKS_TREE_SIZE d_tree_size
1783 #define LANG_HOOKS_PRINT_XNODE d_print_xnode
1784 #define LANG_HOOKS_DUP_LANG_SPECIFIC_DECL d_dup_lang_specific_decl
1785 #define LANG_HOOKS_EH_PERSONALITY d_eh_personality
1786 #define LANG_HOOKS_EH_RUNTIME_TYPE d_build_eh_runtime_type
1787 #define LANG_HOOKS_PUSHDECL d_pushdecl
1788 #define LANG_HOOKS_GETDECLS d_getdecls
1789 #define LANG_HOOKS_GLOBAL_BINDINGS_P d_global_bindings_p
1790 #define LANG_HOOKS_TYPE_FOR_MODE d_type_for_mode
1791 #define LANG_HOOKS_TYPE_FOR_SIZE d_type_for_size
1792 #define LANG_HOOKS_TYPE_PROMOTES_TO d_type_promotes_to
1794 struct lang_hooks lang_hooks = LANG_HOOKS_INITIALIZER;
1796 #include "gt-d-d-lang.h"
1797 #include "gtype-d.h"