OSDN Git Service

* go-gcc.cc (set_placeholder_pointer_type): Arrange for the type
[pf3gnuchains/gcc-fork.git] / gcc / go / go-gcc.cc
1 // go-gcc.cc -- Go frontend to gcc IR.
2 // Copyright (C) 2011 Free Software Foundation, Inc.
3 // Contributed by Ian Lance Taylor, Google.
4
5 // This file is part of GCC.
6
7 // GCC is free software; you can redistribute it and/or modify it under
8 // the terms of the GNU General Public License as published by the Free
9 // Software Foundation; either version 3, or (at your option) any later
10 // version.
11
12 // GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 // WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15 // for more details.
16
17 // You should have received a copy of the GNU General Public License
18 // along with GCC; see the file COPYING3.  If not see
19 // <http://www.gnu.org/licenses/>.
20
21 #include "go-system.h"
22
23 // This has to be included outside of extern "C", so we have to
24 // include it here before tree.h includes it later.
25 #include <gmp.h>
26
27 #ifndef ENABLE_BUILD_WITH_CXX
28 extern "C"
29 {
30 #endif
31
32 #include "tree.h"
33 #include "tree-iterator.h"
34 #include "gimple.h"
35 #include "toplev.h"
36
37 #ifndef ENABLE_BUILD_WITH_CXX
38 }
39 #endif
40
41 #include "go-c.h"
42
43 #include "gogo.h"
44 #include "backend.h"
45
46 // A class wrapping a tree.
47
48 class Gcc_tree
49 {
50  public:
51   Gcc_tree(tree t)
52     : t_(t)
53   { }
54
55   tree
56   get_tree() const
57   { return this->t_; }
58
59  private:
60   tree t_;
61 };
62
63 // In gcc, types, expressions, and statements are all trees.
64 class Btype : public Gcc_tree
65 {
66  public:
67   Btype(tree t)
68     : Gcc_tree(t)
69   { }
70 };
71
72 class Bexpression : public Gcc_tree
73 {
74  public:
75   Bexpression(tree t)
76     : Gcc_tree(t)
77   { }
78 };
79
80 class Bstatement : public Gcc_tree
81 {
82  public:
83   Bstatement(tree t)
84     : Gcc_tree(t)
85   { }
86 };
87
88 class Bfunction : public Gcc_tree
89 {
90  public:
91   Bfunction(tree t)
92     : Gcc_tree(t)
93   { }
94 };
95
96 class Bblock : public Gcc_tree
97 {
98  public:
99   Bblock(tree t)
100     : Gcc_tree(t)
101   { }
102 };
103
104 class Bvariable : public Gcc_tree
105 {
106  public:
107   Bvariable(tree t)
108     : Gcc_tree(t)
109   { }
110 };
111
112 class Blabel : public Gcc_tree
113 {
114  public:
115   Blabel(tree t)
116     : Gcc_tree(t)
117   { }
118 };
119
120 // This file implements the interface between the Go frontend proper
121 // and the gcc IR.  This implements specific instantiations of
122 // abstract classes defined by the Go frontend proper.  The Go
123 // frontend proper class methods of these classes to generate the
124 // backend representation.
125
126 class Gcc_backend : public Backend
127 {
128  public:
129   // Types.
130
131   Btype*
132   error_type()
133   { return this->make_type(error_mark_node); }
134
135   Btype*
136   void_type()
137   { return this->make_type(void_type_node); }
138
139   Btype*
140   bool_type()
141   { return this->make_type(boolean_type_node); }
142
143   Btype*
144   integer_type(bool, int);
145
146   Btype*
147   float_type(int);
148
149   Btype*
150   complex_type(int);
151
152   Btype*
153   pointer_type(Btype*);
154
155   Btype*
156   function_type(const Btyped_identifier&,
157                 const std::vector<Btyped_identifier>&,
158                 const std::vector<Btyped_identifier>&,
159                 const Location);
160
161   Btype*
162   struct_type(const std::vector<Btyped_identifier>&);
163
164   Btype*
165   array_type(Btype*, Bexpression*);
166
167   Btype*
168   placeholder_pointer_type(const std::string&, Location, bool);
169
170   bool
171   set_placeholder_pointer_type(Btype*, Btype*);
172
173   bool
174   set_placeholder_function_type(Btype*, Btype*);
175
176   Btype*
177   placeholder_struct_type(const std::string&, Location);
178
179   bool
180   set_placeholder_struct_type(Btype* placeholder,
181                               const std::vector<Btyped_identifier>&);
182
183   Btype*
184   placeholder_array_type(const std::string&, Location);
185
186   bool
187   set_placeholder_array_type(Btype*, Btype*, Bexpression*);
188
189   Btype*
190   named_type(const std::string&, Btype*, Location);
191
192   Btype*
193   circular_pointer_type(Btype*, bool);
194
195   bool
196   is_circular_pointer_type(Btype*);
197
198   // Expressions.
199
200   Bexpression*
201   zero_expression(Btype*);
202
203   // Statements.
204
205   Bstatement*
206   error_statement()
207   { return this->make_statement(error_mark_node); }
208
209   Bstatement*
210   expression_statement(Bexpression*);
211
212   Bstatement*
213   init_statement(Bvariable* var, Bexpression* init);
214
215   Bstatement*
216   assignment_statement(Bexpression* lhs, Bexpression* rhs, Location);
217
218   Bstatement*
219   return_statement(Bfunction*, const std::vector<Bexpression*>&,
220                    Location);
221
222   Bstatement*
223   if_statement(Bexpression* condition, Bblock* then_block, Bblock* else_block,
224                Location);
225
226   Bstatement*
227   switch_statement(Bexpression* value,
228                    const std::vector<std::vector<Bexpression*> >& cases,
229                    const std::vector<Bstatement*>& statements,
230                    Location);
231
232   Bstatement*
233   compound_statement(Bstatement*, Bstatement*);
234
235   Bstatement*
236   statement_list(const std::vector<Bstatement*>&);
237
238   // Blocks.
239
240   Bblock*
241   block(Bfunction*, Bblock*, const std::vector<Bvariable*>&,
242         Location, Location);
243
244   void
245   block_add_statements(Bblock*, const std::vector<Bstatement*>&);
246
247   Bstatement*
248   block_statement(Bblock*);
249
250   // Variables.
251
252   Bvariable*
253   error_variable()
254   { return new Bvariable(error_mark_node); }
255
256   Bvariable*
257   global_variable(const std::string& package_name,
258                   const std::string& unique_prefix,
259                   const std::string& name,
260                   Btype* btype,
261                   bool is_external,
262                   bool is_hidden,
263                   Location location);
264
265   void
266   global_variable_set_init(Bvariable*, Bexpression*);
267
268   Bvariable*
269   local_variable(Bfunction*, const std::string&, Btype*, bool,
270                  Location);
271
272   Bvariable*
273   parameter_variable(Bfunction*, const std::string&, Btype*, bool,
274                      Location);
275
276   Bvariable*
277   temporary_variable(Bfunction*, Bblock*, Btype*, Bexpression*, bool,
278                      Location, Bstatement**);
279
280   Bvariable*
281   immutable_struct(const std::string&, bool, Btype*, Location);
282
283   void
284   immutable_struct_set_init(Bvariable*, const std::string&, bool, Btype*,
285                             Location, Bexpression*);
286
287   Bvariable*
288   immutable_struct_reference(const std::string&, Btype*, Location);
289
290   // Labels.
291
292   Blabel*
293   label(Bfunction*, const std::string& name, Location);
294
295   Bstatement*
296   label_definition_statement(Blabel*);
297
298   Bstatement*
299   goto_statement(Blabel*, Location);
300
301   Bexpression*
302   label_address(Blabel*, Location);
303
304  private:
305   // Make a Bexpression from a tree.
306   Bexpression*
307   make_expression(tree t)
308   { return new Bexpression(t); }
309
310   // Make a Bstatement from a tree.
311   Bstatement*
312   make_statement(tree t)
313   { return new Bstatement(t); }
314
315   // Make a Btype from a tree.
316   Btype*
317   make_type(tree t)
318   { return new Btype(t); }
319
320   Btype*
321   fill_in_struct(Btype*, const std::vector<Btyped_identifier>&);
322
323   Btype*
324   fill_in_array(Btype*, Btype*, Bexpression*);
325 };
326
327 // A helper function.
328
329 static inline tree
330 get_identifier_from_string(const std::string& str)
331 {
332   return get_identifier_with_length(str.data(), str.length());
333 }
334
335 // Get an unnamed integer type.
336
337 Btype*
338 Gcc_backend::integer_type(bool is_unsigned, int bits)
339 {
340   tree type;
341   if (is_unsigned)
342     {
343       if (bits == INT_TYPE_SIZE)
344         type = unsigned_type_node;
345       else if (bits == CHAR_TYPE_SIZE)
346         type = unsigned_char_type_node;
347       else if (bits == SHORT_TYPE_SIZE)
348         type = short_unsigned_type_node;
349       else if (bits == LONG_TYPE_SIZE)
350         type = long_unsigned_type_node;
351       else if (bits == LONG_LONG_TYPE_SIZE)
352         type = long_long_unsigned_type_node;
353       else
354         type = make_unsigned_type(bits);
355     }
356   else
357     {
358       if (bits == INT_TYPE_SIZE)
359         type = integer_type_node;
360       else if (bits == CHAR_TYPE_SIZE)
361         type = signed_char_type_node;
362       else if (bits == SHORT_TYPE_SIZE)
363         type = short_integer_type_node;
364       else if (bits == LONG_TYPE_SIZE)
365         type = long_integer_type_node;
366       else if (bits == LONG_LONG_TYPE_SIZE)
367         type = long_long_integer_type_node;
368       else
369         type = make_signed_type(bits);
370     }
371   return this->make_type(type);
372 }
373
374 // Get an unnamed float type.
375
376 Btype*
377 Gcc_backend::float_type(int bits)
378 {
379   tree type;
380   if (bits == FLOAT_TYPE_SIZE)
381     type = float_type_node;
382   else if (bits == DOUBLE_TYPE_SIZE)
383     type = double_type_node;
384   else if (bits == LONG_DOUBLE_TYPE_SIZE)
385     type = long_double_type_node;
386   else
387     {
388       type = make_node(REAL_TYPE);
389       TYPE_PRECISION(type) = bits;
390       layout_type(type);
391     }
392   return this->make_type(type);
393 }
394
395 // Get an unnamed complex type.
396
397 Btype*
398 Gcc_backend::complex_type(int bits)
399 {
400   tree type;
401   if (bits == FLOAT_TYPE_SIZE * 2)
402     type = complex_float_type_node;
403   else if (bits == DOUBLE_TYPE_SIZE * 2)
404     type = complex_double_type_node;
405   else if (bits == LONG_DOUBLE_TYPE_SIZE * 2)
406     type = complex_long_double_type_node;
407   else
408     {
409       type = make_node(REAL_TYPE);
410       TYPE_PRECISION(type) = bits / 2;
411       layout_type(type);
412       type = build_complex_type(type);
413     }
414   return this->make_type(type);
415 }
416
417 // Get a pointer type.
418
419 Btype*
420 Gcc_backend::pointer_type(Btype* to_type)
421 {
422   tree to_type_tree = to_type->get_tree();
423   if (to_type_tree == error_mark_node)
424     return this->error_type();
425   tree type = build_pointer_type(to_type_tree);
426   return this->make_type(type);
427 }
428
429 // Make a function type.
430
431 Btype*
432 Gcc_backend::function_type(const Btyped_identifier& receiver,
433                            const std::vector<Btyped_identifier>& parameters,
434                            const std::vector<Btyped_identifier>& results,
435                            Location location)
436 {
437   tree args = NULL_TREE;
438   tree* pp = &args;
439   if (receiver.btype != NULL)
440     {
441       tree t = receiver.btype->get_tree();
442       if (t == error_mark_node)
443         return this->error_type();
444       *pp = tree_cons(NULL_TREE, t, NULL_TREE);
445       pp = &TREE_CHAIN(*pp);
446     }
447
448   for (std::vector<Btyped_identifier>::const_iterator p = parameters.begin();
449        p != parameters.end();
450        ++p)
451     {
452       tree t = p->btype->get_tree();
453       if (t == error_mark_node)
454         return this->error_type();
455       *pp = tree_cons(NULL_TREE, t, NULL_TREE);
456       pp = &TREE_CHAIN(*pp);
457     }
458
459   // Varargs is handled entirely at the Go level.  When converted to
460   // GENERIC functions are not varargs.
461   *pp = void_list_node;
462
463   tree result;
464   if (results.empty())
465     result = void_type_node;
466   else if (results.size() == 1)
467     result = results.front().btype->get_tree();
468   else
469     {
470       result = make_node(RECORD_TYPE);
471       tree field_trees = NULL_TREE;
472       pp = &field_trees;
473       for (std::vector<Btyped_identifier>::const_iterator p = results.begin();
474            p != results.end();
475            ++p)
476         {
477           const std::string name = (p->name.empty()
478                                     ? "UNNAMED"
479                                     : p->name);
480           tree name_tree = get_identifier_from_string(name);
481           tree field_type_tree = p->btype->get_tree();
482           if (field_type_tree == error_mark_node)
483             return this->error_type();
484           gcc_assert(TYPE_SIZE(field_type_tree) != NULL_TREE);
485           tree field = build_decl(location.gcc_location(), FIELD_DECL,
486                                   name_tree, field_type_tree);
487           DECL_CONTEXT(field) = result;
488           *pp = field;
489           pp = &DECL_CHAIN(field);
490         }
491       TYPE_FIELDS(result) = field_trees;
492       layout_type(result);
493     }
494   if (result == error_mark_node)
495     return this->error_type();
496
497   tree fntype = build_function_type(result, args);
498   if (fntype == error_mark_node)
499     return this->error_type();
500
501   return this->make_type(build_pointer_type(fntype));
502 }
503
504 // Make a struct type.
505
506 Btype*
507 Gcc_backend::struct_type(const std::vector<Btyped_identifier>& fields)
508 {
509   return this->fill_in_struct(this->make_type(make_node(RECORD_TYPE)), fields);
510 }
511
512 // Fill in the fields of a struct type.
513
514 Btype*
515 Gcc_backend::fill_in_struct(Btype* fill,
516                             const std::vector<Btyped_identifier>& fields)
517 {
518   tree fill_tree = fill->get_tree();
519   tree field_trees = NULL_TREE;
520   tree* pp = &field_trees;
521   for (std::vector<Btyped_identifier>::const_iterator p = fields.begin();
522        p != fields.end();
523        ++p)
524     {
525       tree name_tree = get_identifier_from_string(p->name);
526       tree type_tree = p->btype->get_tree();
527       if (type_tree == error_mark_node)
528         return this->error_type();
529       tree field = build_decl(p->location.gcc_location(), FIELD_DECL, name_tree,
530                               type_tree);
531       DECL_CONTEXT(field) = fill_tree;
532       *pp = field;
533       pp = &DECL_CHAIN(field);
534     }
535   TYPE_FIELDS(fill_tree) = field_trees;
536   layout_type(fill_tree);
537   return fill;
538 }
539
540 // Make an array type.
541
542 Btype*
543 Gcc_backend::array_type(Btype* element_btype, Bexpression* length)
544 {
545   return this->fill_in_array(this->make_type(make_node(ARRAY_TYPE)),
546                              element_btype, length);
547 }
548
549 // Fill in an array type.
550
551 Btype*
552 Gcc_backend::fill_in_array(Btype* fill, Btype* element_type,
553                            Bexpression* length)
554 {
555   tree element_type_tree = element_type->get_tree();
556   tree length_tree = length->get_tree();
557   if (element_type_tree == error_mark_node || length_tree == error_mark_node)
558     return this->error_type();
559
560   gcc_assert(TYPE_SIZE(element_type_tree) != NULL_TREE);
561
562   length_tree = fold_convert(sizetype, length_tree);
563
564   // build_index_type takes the maximum index, which is one less than
565   // the length.
566   tree index_type_tree = build_index_type(fold_build2(MINUS_EXPR, sizetype,
567                                                       length_tree,
568                                                       size_one_node));
569
570   tree fill_tree = fill->get_tree();
571   TREE_TYPE(fill_tree) = element_type_tree;
572   TYPE_DOMAIN(fill_tree) = index_type_tree;
573   TYPE_ADDR_SPACE(fill_tree) = TYPE_ADDR_SPACE(element_type_tree);
574   layout_type(fill_tree);
575
576   if (TYPE_STRUCTURAL_EQUALITY_P(element_type_tree))
577     SET_TYPE_STRUCTURAL_EQUALITY(fill_tree);
578   else if (TYPE_CANONICAL(element_type_tree) != element_type_tree
579            || TYPE_CANONICAL(index_type_tree) != index_type_tree)
580     TYPE_CANONICAL(fill_tree) =
581       build_array_type(TYPE_CANONICAL(element_type_tree),
582                        TYPE_CANONICAL(index_type_tree));
583
584   return fill;
585 }
586
587 // Create a placeholder for a pointer type.
588
589 Btype*
590 Gcc_backend::placeholder_pointer_type(const std::string& name,
591                                       Location location, bool)
592 {
593   tree ret = build_variant_type_copy(ptr_type_node);
594   if (!name.empty())
595     {
596       tree decl = build_decl(location.gcc_location(), TYPE_DECL,
597                              get_identifier_from_string(name),
598                              ret);
599       TYPE_NAME(ret) = decl;
600     }
601   return this->make_type(ret);
602 }
603
604 // Set the real target type for a placeholder pointer type.
605
606 bool
607 Gcc_backend::set_placeholder_pointer_type(Btype* placeholder,
608                                           Btype* to_type)
609 {
610   tree pt = placeholder->get_tree();
611   if (pt == error_mark_node)
612     return false;
613   gcc_assert(TREE_CODE(pt) == POINTER_TYPE);
614   tree tt = to_type->get_tree();
615   if (tt == error_mark_node)
616     {
617       TREE_TYPE(pt) = tt;
618       return false;
619     }
620   gcc_assert(TREE_CODE(tt) == POINTER_TYPE);
621   TREE_TYPE(pt) = TREE_TYPE(tt);
622   if (TYPE_NAME(pt) != NULL_TREE)
623     {
624       // Build the data structure gcc wants to see for a typedef.
625       tree copy = build_variant_type_copy(pt);
626       TYPE_NAME(copy) = NULL_TREE;
627       DECL_ORIGINAL_TYPE(TYPE_NAME(pt)) = copy;
628     }
629   return true;
630 }
631
632 // Set the real values for a placeholder function type.
633
634 bool
635 Gcc_backend::set_placeholder_function_type(Btype* placeholder, Btype* ft)
636 {
637   return this->set_placeholder_pointer_type(placeholder, ft);
638 }
639
640 // Create a placeholder for a struct type.
641
642 Btype*
643 Gcc_backend::placeholder_struct_type(const std::string& name,
644                                      Location location)
645 {
646   tree ret = make_node(RECORD_TYPE);
647   tree decl = build_decl(location.gcc_location(), TYPE_DECL,
648                          get_identifier_from_string(name),
649                          ret);
650   TYPE_NAME(ret) = decl;
651   return this->make_type(ret);
652 }
653
654 // Fill in the fields of a placeholder struct type.
655
656 bool
657 Gcc_backend::set_placeholder_struct_type(
658     Btype* placeholder,
659     const std::vector<Btyped_identifier>& fields)
660 {
661   tree t = placeholder->get_tree();
662   gcc_assert(TREE_CODE(t) == RECORD_TYPE && TYPE_FIELDS(t) == NULL_TREE);
663   Btype* r = this->fill_in_struct(placeholder, fields);
664
665   // Build the data structure gcc wants to see for a typedef.
666   tree copy = build_variant_type_copy(t);
667   TYPE_NAME(copy) = NULL_TREE;
668   DECL_ORIGINAL_TYPE(TYPE_NAME(t)) = copy;
669
670   return r->get_tree() != error_mark_node;
671 }
672
673 // Create a placeholder for an array type.
674
675 Btype*
676 Gcc_backend::placeholder_array_type(const std::string& name,
677                                     Location location)
678 {
679   tree ret = make_node(ARRAY_TYPE);
680   tree decl = build_decl(location.gcc_location(), TYPE_DECL,
681                          get_identifier_from_string(name),
682                          ret);
683   TYPE_NAME(ret) = decl;
684   return this->make_type(ret);
685 }
686
687 // Fill in the fields of a placeholder array type.
688
689 bool
690 Gcc_backend::set_placeholder_array_type(Btype* placeholder,
691                                         Btype* element_btype,
692                                         Bexpression* length)
693 {
694   tree t = placeholder->get_tree();
695   gcc_assert(TREE_CODE(t) == ARRAY_TYPE && TREE_TYPE(t) == NULL_TREE);
696   Btype* r = this->fill_in_array(placeholder, element_btype, length);
697
698   // Build the data structure gcc wants to see for a typedef.
699   tree copy = build_variant_type_copy(t);
700   TYPE_NAME(copy) = NULL_TREE;
701   DECL_ORIGINAL_TYPE(TYPE_NAME(t)) = copy;
702
703   return r->get_tree() != error_mark_node;
704 }
705
706 // Return a named version of a type.
707
708 Btype*
709 Gcc_backend::named_type(const std::string& name, Btype* btype,
710                         Location location)
711 {
712   tree type = btype->get_tree();
713   if (type == error_mark_node)
714     return this->error_type();
715   tree copy = build_variant_type_copy(type);
716   tree decl = build_decl(location.gcc_location(), TYPE_DECL,
717                          get_identifier_from_string(name),
718                          copy);
719   DECL_ORIGINAL_TYPE(decl) = type;
720   TYPE_NAME(copy) = decl;
721   return this->make_type(copy);
722 }
723
724 // Return a pointer type used as a marker for a circular type.
725
726 Btype*
727 Gcc_backend::circular_pointer_type(Btype*, bool)
728 {
729   return this->make_type(ptr_type_node);
730 }
731
732 // Return whether we might be looking at a circular type.
733
734 bool
735 Gcc_backend::is_circular_pointer_type(Btype* btype)
736 {
737   return btype->get_tree() == ptr_type_node;
738 }
739
740 // Return the zero value for a type.
741
742 Bexpression*
743 Gcc_backend::zero_expression(Btype* btype)
744 {
745   tree t = btype->get_tree();
746   tree ret;
747   if (t == error_mark_node)
748     ret = error_mark_node;
749   else
750     ret = build_zero_cst(t);
751   return tree_to_expr(ret);
752 }
753
754 // An expression as a statement.
755
756 Bstatement*
757 Gcc_backend::expression_statement(Bexpression* expr)
758 {
759   return this->make_statement(expr->get_tree());
760 }
761
762 // Variable initialization.
763
764 Bstatement*
765 Gcc_backend::init_statement(Bvariable* var, Bexpression* init)
766 {
767   tree var_tree = var->get_tree();
768   tree init_tree = init->get_tree();
769   if (var_tree == error_mark_node || init_tree == error_mark_node)
770     return this->error_statement();
771   gcc_assert(TREE_CODE(var_tree) == VAR_DECL);
772   DECL_INITIAL(var_tree) = init_tree;
773   return this->make_statement(build1_loc(DECL_SOURCE_LOCATION(var_tree),
774                                          DECL_EXPR, void_type_node, var_tree));
775 }
776
777 // Assignment.
778
779 Bstatement*
780 Gcc_backend::assignment_statement(Bexpression* lhs, Bexpression* rhs,
781                                   Location location)
782 {
783   tree lhs_tree = lhs->get_tree();
784   tree rhs_tree = rhs->get_tree();
785   if (lhs_tree == error_mark_node || rhs_tree == error_mark_node)
786     return this->error_statement();
787   return this->make_statement(fold_build2_loc(location.gcc_location(),
788                                               MODIFY_EXPR,
789                                               void_type_node,
790                                               lhs_tree, rhs_tree));
791 }
792
793 // Return.
794
795 Bstatement*
796 Gcc_backend::return_statement(Bfunction* bfunction,
797                               const std::vector<Bexpression*>& vals,
798                               Location location)
799 {
800   tree fntree = bfunction->get_tree();
801   if (fntree == error_mark_node)
802     return this->error_statement();
803   tree result = DECL_RESULT(fntree);
804   if (result == error_mark_node)
805     return this->error_statement();
806   tree ret;
807   if (vals.empty())
808     ret = fold_build1_loc(location.gcc_location(), RETURN_EXPR, void_type_node,
809                           NULL_TREE);
810   else if (vals.size() == 1)
811     {
812       tree val = vals.front()->get_tree();
813       if (val == error_mark_node)
814         return this->error_statement();
815       tree set = fold_build2_loc(location.gcc_location(), MODIFY_EXPR,
816                                  void_type_node, result,
817                                  vals.front()->get_tree());
818       ret = fold_build1_loc(location.gcc_location(), RETURN_EXPR,
819                             void_type_node, set);
820     }
821   else
822     {
823       // To return multiple values, copy the values into a temporary
824       // variable of the right structure type, and then assign the
825       // temporary variable to the DECL_RESULT in the return
826       // statement.
827       tree stmt_list = NULL_TREE;
828       tree rettype = TREE_TYPE(result);
829       tree rettmp = create_tmp_var(rettype, "RESULT");
830       tree field = TYPE_FIELDS(rettype);
831       for (std::vector<Bexpression*>::const_iterator p = vals.begin();
832            p != vals.end();
833            p++, field = DECL_CHAIN(field))
834         {
835           gcc_assert(field != NULL_TREE);
836           tree ref = fold_build3_loc(location.gcc_location(), COMPONENT_REF,
837                                      TREE_TYPE(field), rettmp, field,
838                                      NULL_TREE);
839           tree val = (*p)->get_tree();
840           if (val == error_mark_node)
841             return this->error_statement();
842           tree set = fold_build2_loc(location.gcc_location(), MODIFY_EXPR,
843                                      void_type_node,
844                                      ref, (*p)->get_tree());
845           append_to_statement_list(set, &stmt_list);
846         }
847       gcc_assert(field == NULL_TREE);
848       tree set = fold_build2_loc(location.gcc_location(), MODIFY_EXPR,
849                                  void_type_node,
850                                  result, rettmp);
851       tree ret_expr = fold_build1_loc(location.gcc_location(), RETURN_EXPR,
852                                       void_type_node, set);
853       append_to_statement_list(ret_expr, &stmt_list);
854       ret = stmt_list;
855     }
856   return this->make_statement(ret);
857 }
858
859 // If.
860
861 Bstatement*
862 Gcc_backend::if_statement(Bexpression* condition, Bblock* then_block,
863                           Bblock* else_block, Location location)
864 {
865   tree cond_tree = condition->get_tree();
866   tree then_tree = then_block->get_tree();
867   tree else_tree = else_block == NULL ? NULL_TREE : else_block->get_tree();
868   if (cond_tree == error_mark_node
869       || then_tree == error_mark_node
870       || else_tree == error_mark_node)
871     return this->error_statement();
872   tree ret = build3_loc(location.gcc_location(), COND_EXPR, void_type_node,
873                         cond_tree, then_tree, else_tree);
874   return this->make_statement(ret);
875 }
876
877 // Switch.
878
879 Bstatement*
880 Gcc_backend::switch_statement(
881     Bexpression* value,
882     const std::vector<std::vector<Bexpression*> >& cases,
883     const std::vector<Bstatement*>& statements,
884     Location switch_location)
885 {
886   gcc_assert(cases.size() == statements.size());
887
888   tree stmt_list = NULL_TREE;
889   std::vector<std::vector<Bexpression*> >::const_iterator pc = cases.begin();
890   for (std::vector<Bstatement*>::const_iterator ps = statements.begin();
891        ps != statements.end();
892        ++ps, ++pc)
893     {
894       if (pc->empty())
895         {
896           source_location loc = (*ps != NULL
897                                  ? EXPR_LOCATION((*ps)->get_tree())
898                                  : UNKNOWN_LOCATION);
899           tree label = create_artificial_label(loc);
900           tree c = build_case_label(NULL_TREE, NULL_TREE, label);
901           append_to_statement_list(c, &stmt_list);
902         }
903       else
904         {
905           for (std::vector<Bexpression*>::const_iterator pcv = pc->begin();
906                pcv != pc->end();
907                ++pcv)
908             {
909               tree t = (*pcv)->get_tree();
910               if (t == error_mark_node)
911                 return this->error_statement();
912               source_location loc = EXPR_LOCATION(t);
913               tree label = create_artificial_label(loc);
914               tree c = build_case_label((*pcv)->get_tree(), NULL_TREE, label);
915               append_to_statement_list(c, &stmt_list);
916             }
917         }
918
919       if (*ps != NULL)
920         {
921           tree t = (*ps)->get_tree();
922           if (t == error_mark_node)
923             return this->error_statement();
924           append_to_statement_list(t, &stmt_list);
925         }
926     }
927
928   tree tv = value->get_tree();
929   if (tv == error_mark_node)
930     return this->error_statement();
931   tree t = build3_loc(switch_location.gcc_location(), SWITCH_EXPR,
932                       void_type_node, tv, stmt_list, NULL_TREE);
933   return this->make_statement(t);
934 }
935
936 // Pair of statements.
937
938 Bstatement*
939 Gcc_backend::compound_statement(Bstatement* s1, Bstatement* s2)
940 {
941   tree stmt_list = NULL_TREE;
942   tree t = s1->get_tree();
943   if (t == error_mark_node)
944     return this->error_statement();
945   append_to_statement_list(t, &stmt_list);
946   t = s2->get_tree();
947   if (t == error_mark_node)
948     return this->error_statement();
949   append_to_statement_list(t, &stmt_list);
950   return this->make_statement(stmt_list);
951 }
952
953 // List of statements.
954
955 Bstatement*
956 Gcc_backend::statement_list(const std::vector<Bstatement*>& statements)
957 {
958   tree stmt_list = NULL_TREE;
959   for (std::vector<Bstatement*>::const_iterator p = statements.begin();
960        p != statements.end();
961        ++p)
962     {
963       tree t = (*p)->get_tree();
964       if (t == error_mark_node)
965         return this->error_statement();
966       append_to_statement_list(t, &stmt_list);
967     }
968   return this->make_statement(stmt_list);
969 }
970
971 // Make a block.  For some reason gcc uses a dual structure for
972 // blocks: BLOCK tree nodes and BIND_EXPR tree nodes.  Since the
973 // BIND_EXPR node points to the BLOCK node, we store the BIND_EXPR in
974 // the Bblock.
975
976 Bblock*
977 Gcc_backend::block(Bfunction* function, Bblock* enclosing,
978                    const std::vector<Bvariable*>& vars,
979                    Location start_location,
980                    Location)
981 {
982   tree block_tree = make_node(BLOCK);
983   if (enclosing == NULL)
984     {
985       // FIXME: Permitting FUNCTION to be NULL is a temporary measure
986       // until we have a proper representation of the init function.
987       tree fndecl;
988       if (function == NULL)
989         fndecl = current_function_decl;
990       else
991         fndecl = function->get_tree();
992       gcc_assert(fndecl != NULL_TREE);
993
994       // We may have already created a block for local variables when
995       // we take the address of a parameter.
996       if (DECL_INITIAL(fndecl) == NULL_TREE)
997         {
998           BLOCK_SUPERCONTEXT(block_tree) = fndecl;
999           DECL_INITIAL(fndecl) = block_tree;
1000         }
1001       else
1002         {
1003           tree superblock_tree = DECL_INITIAL(fndecl);
1004           BLOCK_SUPERCONTEXT(block_tree) = superblock_tree;
1005           tree* pp;
1006           for (pp = &BLOCK_SUBBLOCKS(superblock_tree);
1007                *pp != NULL_TREE;
1008                pp = &BLOCK_CHAIN(*pp))
1009             ;
1010           *pp = block_tree;
1011         }
1012     }
1013   else
1014     {
1015       tree superbind_tree = enclosing->get_tree();
1016       tree superblock_tree = BIND_EXPR_BLOCK(superbind_tree);
1017       gcc_assert(TREE_CODE(superblock_tree) == BLOCK);
1018
1019       BLOCK_SUPERCONTEXT(block_tree) = superblock_tree;
1020       tree* pp;
1021       for (pp = &BLOCK_SUBBLOCKS(superblock_tree);
1022            *pp != NULL_TREE;
1023            pp = &BLOCK_CHAIN(*pp))
1024         ;
1025       *pp = block_tree;
1026     }
1027
1028   tree* pp = &BLOCK_VARS(block_tree);
1029   for (std::vector<Bvariable*>::const_iterator pv = vars.begin();
1030        pv != vars.end();
1031        ++pv)
1032     {
1033       *pp = (*pv)->get_tree();
1034       if (*pp != error_mark_node)
1035         pp = &DECL_CHAIN(*pp);
1036     }
1037   *pp = NULL_TREE;
1038
1039   TREE_USED(block_tree) = 1;
1040
1041   tree bind_tree = build3_loc(start_location.gcc_location(), BIND_EXPR,
1042                               void_type_node, BLOCK_VARS(block_tree),
1043                               NULL_TREE, block_tree);
1044   TREE_SIDE_EFFECTS(bind_tree) = 1;
1045
1046   return new Bblock(bind_tree);
1047 }
1048
1049 // Add statements to a block.
1050
1051 void
1052 Gcc_backend::block_add_statements(Bblock* bblock,
1053                                   const std::vector<Bstatement*>& statements)
1054 {
1055   tree stmt_list = NULL_TREE;
1056   for (std::vector<Bstatement*>::const_iterator p = statements.begin();
1057        p != statements.end();
1058        ++p)
1059     {
1060       tree s = (*p)->get_tree();
1061       if (s != error_mark_node)
1062         append_to_statement_list(s, &stmt_list);
1063     }
1064
1065   tree bind_tree = bblock->get_tree();
1066   gcc_assert(TREE_CODE(bind_tree) == BIND_EXPR);
1067   BIND_EXPR_BODY(bind_tree) = stmt_list;
1068 }
1069
1070 // Return a block as a statement.
1071
1072 Bstatement*
1073 Gcc_backend::block_statement(Bblock* bblock)
1074 {
1075   tree bind_tree = bblock->get_tree();
1076   gcc_assert(TREE_CODE(bind_tree) == BIND_EXPR);
1077   return this->make_statement(bind_tree);
1078 }
1079
1080 // Make a global variable.
1081
1082 Bvariable*
1083 Gcc_backend::global_variable(const std::string& package_name,
1084                              const std::string& unique_prefix,
1085                              const std::string& name,
1086                              Btype* btype,
1087                              bool is_external,
1088                              bool is_hidden,
1089                              Location location)
1090 {
1091   tree type_tree = btype->get_tree();
1092   if (type_tree == error_mark_node)
1093     return this->error_variable();
1094
1095   std::string var_name(package_name);
1096   var_name.push_back('.');
1097   var_name.append(name);
1098   tree decl = build_decl(location.gcc_location(), VAR_DECL,
1099                          get_identifier_from_string(var_name),
1100                          type_tree);
1101   if (is_external)
1102     DECL_EXTERNAL(decl) = 1;
1103   else
1104     TREE_STATIC(decl) = 1;
1105   if (!is_hidden)
1106     {
1107       TREE_PUBLIC(decl) = 1;
1108
1109       std::string asm_name(unique_prefix);
1110       asm_name.push_back('.');
1111       asm_name.append(var_name);
1112       SET_DECL_ASSEMBLER_NAME(decl, get_identifier_from_string(asm_name));
1113     }
1114   TREE_USED(decl) = 1;
1115
1116   go_preserve_from_gc(decl);
1117
1118   return new Bvariable(decl);
1119 }
1120
1121 // Set the initial value of a global variable.
1122
1123 void
1124 Gcc_backend::global_variable_set_init(Bvariable* var, Bexpression* expr)
1125 {
1126   tree expr_tree = expr->get_tree();
1127   if (expr_tree == error_mark_node)
1128     return;
1129   gcc_assert(TREE_CONSTANT(expr_tree));
1130   tree var_decl = var->get_tree();
1131   if (var_decl == error_mark_node)
1132     return;
1133   DECL_INITIAL(var_decl) = expr_tree;
1134 }
1135
1136 // Make a local variable.
1137
1138 Bvariable*
1139 Gcc_backend::local_variable(Bfunction* function, const std::string& name,
1140                             Btype* btype, bool is_address_taken,
1141                             Location location)
1142 {
1143   tree type_tree = btype->get_tree();
1144   if (type_tree == error_mark_node)
1145     return this->error_variable();
1146   tree decl = build_decl(location.gcc_location(), VAR_DECL,
1147                          get_identifier_from_string(name),
1148                          type_tree);
1149   DECL_CONTEXT(decl) = function->get_tree();
1150   TREE_USED(decl) = 1;
1151   if (is_address_taken)
1152     TREE_ADDRESSABLE(decl) = 1;
1153   go_preserve_from_gc(decl);
1154   return new Bvariable(decl);
1155 }
1156
1157 // Make a function parameter variable.
1158
1159 Bvariable*
1160 Gcc_backend::parameter_variable(Bfunction* function, const std::string& name,
1161                                 Btype* btype, bool is_address_taken,
1162                                 Location location)
1163 {
1164   tree type_tree = btype->get_tree();
1165   if (type_tree == error_mark_node)
1166     return this->error_variable();
1167   tree decl = build_decl(location.gcc_location(), PARM_DECL,
1168                          get_identifier_from_string(name),
1169                          type_tree);
1170   DECL_CONTEXT(decl) = function->get_tree();
1171   DECL_ARG_TYPE(decl) = type_tree;
1172   TREE_USED(decl) = 1;
1173   if (is_address_taken)
1174     TREE_ADDRESSABLE(decl) = 1;
1175   go_preserve_from_gc(decl);
1176   return new Bvariable(decl);
1177 }
1178
1179 // Make a temporary variable.
1180
1181 Bvariable*
1182 Gcc_backend::temporary_variable(Bfunction* function, Bblock* bblock,
1183                                 Btype* btype, Bexpression* binit,
1184                                 bool is_address_taken,
1185                                 Location location,
1186                                 Bstatement** pstatement)
1187 {
1188   tree type_tree = btype->get_tree();
1189   tree init_tree = binit == NULL ? NULL_TREE : binit->get_tree();
1190   if (type_tree == error_mark_node || init_tree == error_mark_node)
1191     {
1192       *pstatement = this->error_statement();
1193       return this->error_variable();
1194     }
1195
1196   tree var;
1197   // We can only use create_tmp_var if the type is not addressable.
1198   if (!TREE_ADDRESSABLE(type_tree))
1199     var = create_tmp_var(type_tree, "GOTMP");
1200   else
1201     {
1202       gcc_assert(bblock != NULL);
1203       var = build_decl(location.gcc_location(), VAR_DECL,
1204                        create_tmp_var_name("GOTMP"),
1205                        type_tree);
1206       DECL_ARTIFICIAL(var) = 1;
1207       DECL_IGNORED_P(var) = 1;
1208       TREE_USED(var) = 1;
1209       // FIXME: Permitting function to be NULL here is a temporary
1210       // measure until we have a proper representation of the init
1211       // function.
1212       if (function != NULL)
1213         DECL_CONTEXT(var) = function->get_tree();
1214       else
1215         {
1216           gcc_assert(current_function_decl != NULL_TREE);
1217           DECL_CONTEXT(var) = current_function_decl;
1218         }
1219
1220       // We have to add this variable to the BLOCK and the BIND_EXPR.
1221       tree bind_tree = bblock->get_tree();
1222       gcc_assert(TREE_CODE(bind_tree) == BIND_EXPR);
1223       tree block_tree = BIND_EXPR_BLOCK(bind_tree);
1224       gcc_assert(TREE_CODE(block_tree) == BLOCK);
1225       DECL_CHAIN(var) = BLOCK_VARS(block_tree);
1226       BLOCK_VARS(block_tree) = var;
1227       BIND_EXPR_VARS(bind_tree) = BLOCK_VARS(block_tree);
1228     }
1229
1230   if (init_tree != NULL_TREE)
1231     DECL_INITIAL(var) = fold_convert_loc(location.gcc_location(), type_tree,
1232                                          init_tree);
1233
1234   if (is_address_taken)
1235     TREE_ADDRESSABLE(var) = 1;
1236
1237   *pstatement = this->make_statement(build1_loc(location.gcc_location(),
1238                                                 DECL_EXPR,
1239                                                 void_type_node, var));
1240   return new Bvariable(var);
1241 }
1242
1243 // Create a named immutable initialized data structure.
1244
1245 Bvariable*
1246 Gcc_backend::immutable_struct(const std::string& name, bool, Btype* btype,
1247                               Location location)
1248 {
1249   tree type_tree = btype->get_tree();
1250   if (type_tree == error_mark_node)
1251     return this->error_variable();
1252   gcc_assert(TREE_CODE(type_tree) == RECORD_TYPE);
1253   tree decl = build_decl(location.gcc_location(), VAR_DECL,
1254                          get_identifier_from_string(name),
1255                          build_qualified_type(type_tree, TYPE_QUAL_CONST));
1256   TREE_STATIC(decl) = 1;
1257   TREE_READONLY(decl) = 1;
1258   TREE_CONSTANT(decl) = 1;
1259   TREE_USED(decl) = 1;
1260   DECL_ARTIFICIAL(decl) = 1;
1261
1262   // We don't call rest_of_decl_compilation until we have the
1263   // initializer.
1264
1265   go_preserve_from_gc(decl);
1266   return new Bvariable(decl);
1267 }
1268
1269 // Set the initializer for a variable created by immutable_struct.
1270 // This is where we finish compiling the variable.
1271
1272 void
1273 Gcc_backend::immutable_struct_set_init(Bvariable* var, const std::string&,
1274                                        bool is_common, Btype*,
1275                                        Location,
1276                                        Bexpression* initializer)
1277 {
1278   tree decl = var->get_tree();
1279   tree init_tree = initializer->get_tree();
1280   if (decl == error_mark_node || init_tree == error_mark_node)
1281     return;
1282
1283   DECL_INITIAL(decl) = init_tree;
1284
1285   // We can't call make_decl_one_only until we set DECL_INITIAL.
1286   if (!is_common)
1287     TREE_PUBLIC(decl) = 1;
1288   else
1289     {
1290       make_decl_one_only(decl, DECL_ASSEMBLER_NAME(decl));
1291       resolve_unique_section(decl, 1, 0);
1292     }
1293
1294   rest_of_decl_compilation(decl, 1, 0);
1295 }
1296
1297 // Return a reference to an immutable initialized data structure
1298 // defined in another package.
1299
1300 Bvariable*
1301 Gcc_backend::immutable_struct_reference(const std::string& name, Btype* btype,
1302                                         Location location)
1303 {
1304   tree type_tree = btype->get_tree();
1305   if (type_tree == error_mark_node)
1306     return this->error_variable();
1307   gcc_assert(TREE_CODE(type_tree) == RECORD_TYPE);
1308   tree decl = build_decl(location.gcc_location(), VAR_DECL,
1309                          get_identifier_from_string(name),
1310                          build_qualified_type(type_tree, TYPE_QUAL_CONST));
1311   TREE_READONLY(decl) = 1;
1312   TREE_CONSTANT(decl) = 1;
1313   DECL_ARTIFICIAL(decl) = 1;
1314   TREE_PUBLIC(decl) = 1;
1315   DECL_EXTERNAL(decl) = 1;
1316   go_preserve_from_gc(decl);
1317   return new Bvariable(decl);
1318 }
1319
1320 // Make a label.
1321
1322 Blabel*
1323 Gcc_backend::label(Bfunction* function, const std::string& name,
1324                    Location location)
1325 {
1326   tree decl;
1327   if (name.empty())
1328     decl = create_artificial_label(location.gcc_location());
1329   else
1330     {
1331       tree id = get_identifier_from_string(name);
1332       decl = build_decl(location.gcc_location(), LABEL_DECL, id,
1333                         void_type_node);
1334       DECL_CONTEXT(decl) = function->get_tree();
1335     }
1336   return new Blabel(decl);
1337 }
1338
1339 // Make a statement which defines a label.
1340
1341 Bstatement*
1342 Gcc_backend::label_definition_statement(Blabel* label)
1343 {
1344   tree lab = label->get_tree();
1345   tree ret = fold_build1_loc(DECL_SOURCE_LOCATION(lab), LABEL_EXPR,
1346                              void_type_node, lab);
1347   return this->make_statement(ret);
1348 }
1349
1350 // Make a goto statement.
1351
1352 Bstatement*
1353 Gcc_backend::goto_statement(Blabel* label, Location location)
1354 {
1355   tree lab = label->get_tree();
1356   tree ret = fold_build1_loc(location.gcc_location(), GOTO_EXPR, void_type_node,
1357                              lab);
1358   return this->make_statement(ret);
1359 }
1360
1361 // Get the address of a label.
1362
1363 Bexpression*
1364 Gcc_backend::label_address(Blabel* label, Location location)
1365 {
1366   tree lab = label->get_tree();
1367   TREE_USED(lab) = 1;
1368   TREE_ADDRESSABLE(lab) = 1;
1369   tree ret = fold_convert_loc(location.gcc_location(), ptr_type_node,
1370                               build_fold_addr_expr_loc(location.gcc_location(),
1371                                                        lab));
1372   return this->make_expression(ret);
1373 }
1374
1375 // The single backend.
1376
1377 static Gcc_backend gcc_backend;
1378
1379 // Return the backend generator.
1380
1381 Backend*
1382 go_get_backend()
1383 {
1384   return &gcc_backend;
1385 }
1386
1387 // FIXME: Temporary functions while converting to the new backend
1388 // interface.
1389
1390 Btype*
1391 tree_to_type(tree t)
1392 {
1393   return new Btype(t);
1394 }
1395
1396 Bexpression*
1397 tree_to_expr(tree t)
1398 {
1399   return new Bexpression(t);
1400 }
1401
1402 Bstatement*
1403 tree_to_stat(tree t)
1404 {
1405   return new Bstatement(t);
1406 }
1407
1408 Bfunction*
1409 tree_to_function(tree t)
1410 {
1411   return new Bfunction(t);
1412 }
1413
1414 Bblock*
1415 tree_to_block(tree t)
1416 {
1417   gcc_assert(TREE_CODE(t) == BIND_EXPR);
1418   return new Bblock(t);
1419 }
1420
1421 tree
1422 type_to_tree(Btype* bt)
1423 {
1424   return bt->get_tree();
1425 }
1426
1427 tree
1428 expr_to_tree(Bexpression* be)
1429 {
1430   return be->get_tree();
1431 }
1432
1433 tree
1434 stat_to_tree(Bstatement* bs)
1435 {
1436   return bs->get_tree();
1437 }
1438
1439 tree
1440 block_to_tree(Bblock* bb)
1441 {
1442   return bb->get_tree();
1443 }
1444
1445 tree
1446 var_to_tree(Bvariable* bv)
1447 {
1448   return bv->get_tree();
1449 }