OSDN Git Service

86th Cygnus<->FSF quick merge
[pf3gnuchains/gcc-fork.git] / gcc / cp / method.c
1 /* Handle the hair of processing (but not expanding) inline functions.
2    Also manage function and variable name overloading.
3    Copyright (C) 1987, 89, 92, 93, 94, 95, 1996 Free Software Foundation, Inc.
4    Contributed by Michael Tiemann (tiemann@cygnus.com)
5
6    This file is part of GNU CC.
7    
8 GNU CC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 GNU CC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GNU CC; see the file COPYING.  If not, write to
20 the Free Software Foundation, 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA.  */
22
23
24 #ifndef PARM_CAN_BE_ARRAY_TYPE
25 #define PARM_CAN_BE_ARRAY_TYPE 1
26 #endif
27
28 /* Handle method declarations.  */
29 #include <stdio.h>
30 #include "config.h"
31 #include "tree.h"
32 #include "cp-tree.h"
33 #include "class.h"
34 #include "obstack.h"
35 #include <ctype.h>
36 #include "rtl.h"
37 #include "expr.h"
38 #include "output.h"
39 #include "hard-reg-set.h"
40 #include "flags.h"
41
42 #ifndef SUPPORTS_ONE_ONLY
43 #define SUPPORTS_ONE_ONLY 0
44 #endif
45
46 /* TREE_LIST of the current inline functions that need to be
47    processed.  */
48 struct pending_inline *pending_inlines;
49
50 #define obstack_chunk_alloc xmalloc
51 #define obstack_chunk_free free
52
53 /* Obstack where we build text strings for overloading, etc.  */
54 static struct obstack scratch_obstack;
55 static char *scratch_firstobj;
56
57 # define OB_INIT() (scratch_firstobj ? (obstack_free (&scratch_obstack, scratch_firstobj), 0) : 0)
58 # define OB_PUTC(C) (obstack_1grow (&scratch_obstack, (C)))
59 # define OB_PUTC2(C1,C2)        \
60   (obstack_1grow (&scratch_obstack, (C1)), obstack_1grow (&scratch_obstack, (C2)))
61 # define OB_PUTS(S) (obstack_grow (&scratch_obstack, (S), sizeof (S) - 1))
62 # define OB_PUTID(ID)  \
63   (obstack_grow (&scratch_obstack, IDENTIFIER_POINTER (ID),     \
64                  IDENTIFIER_LENGTH (ID)))
65 # define OB_PUTCP(S) (obstack_grow (&scratch_obstack, (S), strlen (S)))
66 # define OB_FINISH() (obstack_1grow (&scratch_obstack, '\0'))
67 # define OB_LAST() (obstack_next_free (&scratch_obstack)[-1])
68
69 #ifdef NO_AUTO_OVERLOAD
70 int is_overloaded ();
71 #endif
72
73 void
74 init_method ()
75 {
76   gcc_obstack_init (&scratch_obstack);
77   scratch_firstobj = (char *)obstack_alloc (&scratch_obstack, 0);
78 }
79
80 /* This must be large enough to hold any printed integer or floating-point
81    value.  */
82 static char digit_buffer[128];
83
84 /* Move inline function definitions out of structure so that they
85    can be processed normally.  CNAME is the name of the class
86    we are working from, METHOD_LIST is the list of method lists
87    of the structure.  We delete friend methods here, after
88    saving away their inline function definitions (if any).  */
89
90 void
91 do_inline_function_hair (type, friend_list)
92      tree type, friend_list;
93 {
94   tree method = TYPE_METHODS (type);
95
96   if (method && TREE_CODE (method) == TREE_VEC)
97     {
98       if (TREE_VEC_ELT (method, 1))
99         method = TREE_VEC_ELT (method, 1);
100       else if (TREE_VEC_ELT (method, 0))
101         method = TREE_VEC_ELT (method, 0);
102       else
103         method = TREE_VEC_ELT (method, 2);
104     }
105
106   while (method)
107     {
108       /* Do inline member functions.  */
109       struct pending_inline *info = DECL_PENDING_INLINE_INFO (method);
110       if (info)
111         {
112           tree args;
113
114           my_friendly_assert (info->fndecl == method, 238);
115           args = DECL_ARGUMENTS (method);
116           while (args)
117             {
118               DECL_CONTEXT (args) = method;
119               args = TREE_CHAIN (args);
120             }
121
122           /* Allow this decl to be seen in global scope.  Don't do this for
123              local class methods, though.  */
124           if (! current_function_decl)
125             IDENTIFIER_GLOBAL_VALUE (DECL_ASSEMBLER_NAME (method)) = method;
126         }
127       method = TREE_CHAIN (method);
128     }
129   while (friend_list)
130     {
131       tree fndecl = TREE_VALUE (friend_list);
132       struct pending_inline *info = DECL_PENDING_INLINE_INFO (fndecl);
133       if (info)
134         {
135           tree args;
136
137           my_friendly_assert (info->fndecl == fndecl, 239);
138           args = DECL_ARGUMENTS (fndecl);
139           while (args)
140             {
141               DECL_CONTEXT (args) = fndecl;
142               args = TREE_CHAIN (args);
143             }
144
145           /* Allow this decl to be seen in global scope */
146           if (! current_function_decl)
147             IDENTIFIER_GLOBAL_VALUE (DECL_ASSEMBLER_NAME (fndecl)) = fndecl;
148         }
149
150       friend_list = TREE_CHAIN (friend_list);
151     }
152 }
153 \f
154 /* Report an argument type mismatch between the best declared function
155    we could find and the current argument list that we have.  */
156 void
157 report_type_mismatch (cp, parmtypes, name_kind)
158      struct candidate *cp;
159      tree parmtypes;
160      char *name_kind;
161 {
162   int i = cp->u.bad_arg;
163   tree ttf, tta;
164   char *tmp_firstobj;
165
166   switch (i)
167     {
168     case -4:
169       my_friendly_assert (TREE_CODE (cp->function) == TEMPLATE_DECL, 240);
170       cp_error ("type unification failed for function template `%#D'",
171                 cp->function);
172       return;
173
174     case -2:
175       cp_error ("too few arguments for %s `%#D'", name_kind, cp->function);
176       return;
177     case -1:
178       cp_error ("too many arguments for %s `%#D'", name_kind, cp->function);
179       return;
180     case 0:
181       if (TREE_CODE (TREE_TYPE (cp->function)) != METHOD_TYPE)
182         break;
183     case -3:
184       /* Happens when the implicit object parameter is rejected.  */
185       my_friendly_assert (! TYPE_READONLY (TREE_TYPE (TREE_VALUE (parmtypes))),
186                           241);
187       if (TYPE_VOLATILE (TREE_TYPE (TREE_TYPE (TREE_VALUE (parmtypes))))
188           && ! TYPE_VOLATILE (TREE_TYPE (TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (cp->function))))))
189         cp_error ("call to non-volatile %s `%#D' with volatile object",
190                   name_kind, cp->function);
191       else
192         cp_error ("call to non-const %s `%#D' with const object",
193                   name_kind, cp->function);
194       return;
195     }
196
197   ttf = TYPE_ARG_TYPES (TREE_TYPE (cp->function));
198   tta = parmtypes;
199
200   while (i-- > 0)
201     {
202       ttf = TREE_CHAIN (ttf);
203       tta = TREE_CHAIN (tta);
204     }
205
206   OB_INIT ();
207   OB_PUTS ("bad argument ");
208   sprintf (digit_buffer, "%d", cp->u.bad_arg
209            - (TREE_CODE (TREE_TYPE (cp->function)) == METHOD_TYPE)
210            + 1);
211   OB_PUTCP (digit_buffer);
212
213   OB_PUTS (" for function `");
214   OB_PUTCP (decl_as_string (cp->function, 1));
215   OB_PUTS ("' (type was ");
216
217   /* Reset `i' so that type printing routines do the right thing.  */
218   if (tta)
219     {
220       enum tree_code code = TREE_CODE (TREE_TYPE (TREE_VALUE (tta)));
221       if (code == ERROR_MARK)
222         OB_PUTS ("(failed type instantiation)");
223       else
224         {
225           i = (code == FUNCTION_TYPE || code == METHOD_TYPE);
226           OB_PUTCP (type_as_string (TREE_TYPE (TREE_VALUE (tta)), 1));
227         }
228     }
229   else OB_PUTS ("void");
230   OB_PUTC (')');
231   OB_FINISH ();
232
233   tmp_firstobj = (char *)alloca (obstack_object_size (&scratch_obstack));
234   bcopy (obstack_base (&scratch_obstack), tmp_firstobj,
235          obstack_object_size (&scratch_obstack));
236   error (tmp_firstobj);
237 }
238 \f
239 /* Here is where overload code starts.  */
240
241 /* Array of types seen so far in top-level call to `build_overload_name'.
242    Allocated and deallocated by caller.  */
243 static tree *typevec;
244
245 /* Number of types interned by `build_overload_name' so far.  */
246 static int maxtype;
247
248 /* Number of occurrences of last type seen.  */
249 static int nrepeats;
250
251 /* Nonzero if we should not try folding parameter types.  */
252 static int nofold;
253
254 #define ALLOCATE_TYPEVEC(PARMTYPES) \
255   do { maxtype = 0, nrepeats = 0; \
256        typevec = (tree *)alloca (list_length (PARMTYPES) * sizeof (tree)); } while (0)
257
258 #define DEALLOCATE_TYPEVEC(PARMTYPES) \
259   do { tree t = (PARMTYPES); \
260        while (t) { TREE_USED (TREE_VALUE (t)) = 0; t = TREE_CHAIN (t); } \
261   } while (0)
262
263 /* Code to concatenate an asciified integer to a string.  */
264 static
265 #ifdef __GNUC__
266 __inline
267 #endif
268 void
269 icat (i)
270      int i;
271 {
272   /* Handle this case first, to go really quickly.  For many common values,
273      the result of i/10 below is 1.  */
274   if (i == 1)
275     {
276       OB_PUTC ('1');
277       return;
278     }
279
280   if (i < 0)
281     {
282       OB_PUTC ('m');
283       i = -i;
284     }
285   if (i < 10)
286     OB_PUTC ('0' + i);
287   else
288     {
289       icat (i / 10);
290       OB_PUTC ('0' + (i % 10));
291     }
292 }
293
294 static
295 #ifdef __GNUC__
296 __inline
297 #endif
298 void
299 flush_repeats (type)
300      tree type;
301 {
302   int tindex = 0;
303
304   while (typevec[tindex] != type)
305     tindex++;
306
307   if (nrepeats > 1)
308     {
309       OB_PUTC ('N');
310       icat (nrepeats);
311       if (nrepeats > 9)
312         OB_PUTC ('_');
313     }
314   else
315     OB_PUTC ('T');
316   nrepeats = 0;
317   icat (tindex);
318   if (tindex > 9)
319     OB_PUTC ('_');
320 }
321
322 static int numeric_output_need_bar;
323 static void build_overload_identifier ();
324
325 static void
326 build_overload_nested_name (decl)
327      tree decl;
328 {
329   if (DECL_CONTEXT (decl))
330     {
331       tree context = DECL_CONTEXT (decl);
332       if (TREE_CODE_CLASS (TREE_CODE (context)) == 't')
333         context = TYPE_MAIN_DECL (context);
334       build_overload_nested_name (context);
335     }
336
337   if (TREE_CODE (decl) == FUNCTION_DECL)
338     {
339       tree name = DECL_ASSEMBLER_NAME (decl);
340       char *label;
341       extern int var_labelno;
342
343       ASM_FORMAT_PRIVATE_NAME (label, IDENTIFIER_POINTER (name), var_labelno);
344       var_labelno++;
345
346       if (numeric_output_need_bar)
347         {
348           OB_PUTC ('_');
349           numeric_output_need_bar = 0;
350         }
351       icat (strlen (label));
352       OB_PUTCP (label);
353     }
354   else                          /* TYPE_DECL */
355     build_overload_identifier (decl);
356 }
357
358 /* Encoding for an INTEGER_CST value. */
359 static void
360 build_overload_int (value)
361      tree value;
362 {
363   if (TREE_CODE (value) == TEMPLATE_CONST_PARM)
364     {
365       OB_PUTC ('Y');
366       if (TEMPLATE_CONST_IDX (value) > 9)
367         OB_PUTC ('_');
368       icat (TEMPLATE_CONST_IDX (value)); 
369       if (TEMPLATE_CONST_IDX (value) > 9)
370         OB_PUTC ('_');
371       return;
372     }
373   else if (current_template_parms
374            && TREE_CODE (value) != INTEGER_CST)
375     /* We don't ever want this output, but it's inconvenient not to
376        be able to build the string.  This should cause assembler
377        errors we'll notice.  */
378     {
379       static int n;
380       sprintf (digit_buffer, " *%d", n++);
381       OB_PUTCP (digit_buffer);
382       return;
383     }
384
385   my_friendly_assert (TREE_CODE (value) == INTEGER_CST, 243);
386   if (TYPE_PRECISION (value) == 2 * HOST_BITS_PER_WIDE_INT)
387     {
388       if (tree_int_cst_lt (value, integer_zero_node))
389         {
390           OB_PUTC ('m');
391           value = build_int_2 (~ TREE_INT_CST_LOW (value),
392                                - TREE_INT_CST_HIGH (value));
393         }
394       if (TREE_INT_CST_HIGH (value)
395           != (TREE_INT_CST_LOW (value) >> (HOST_BITS_PER_WIDE_INT - 1)))
396         {
397           /* need to print a DImode value in decimal */
398           sorry ("conversion of long long as PT parameter");
399         }
400       /* else fall through to print in smaller mode */
401     }
402   /* Wordsize or smaller */
403   icat (TREE_INT_CST_LOW (value));
404 }
405
406 static void
407 build_overload_value (type, value)
408      tree type, value;
409 {
410   while (TREE_CODE (value) == NON_LVALUE_EXPR
411          || TREE_CODE (value) == NOP_EXPR)
412     value = TREE_OPERAND (value, 0);
413   my_friendly_assert (TREE_CODE (type) == PARM_DECL, 242);
414   type = TREE_TYPE (type);
415
416   if (numeric_output_need_bar)
417     {
418       OB_PUTC ('_');
419       numeric_output_need_bar = 0;
420     }
421
422   if (TREE_CODE (type) == POINTER_TYPE
423       && TREE_CODE (TREE_TYPE (type)) == OFFSET_TYPE)
424     {
425       /* Handle a pointer to data member as a template instantiation
426          parameter, boy, what fun!  */
427       type = integer_type_node;
428       if (TREE_CODE (value) != INTEGER_CST)
429         {
430           sorry ("unknown pointer to member constant");
431           return;
432         }
433     }
434
435   if (TYPE_PTRMEMFUNC_P (type))
436     type = TYPE_PTRMEMFUNC_FN_TYPE (type);
437
438   switch (TREE_CODE (type))
439     {
440     case INTEGER_TYPE:
441     case ENUMERAL_TYPE:
442     case BOOLEAN_TYPE:
443       {
444         build_overload_int (value);
445         numeric_output_need_bar = 1;
446         return;
447       }
448 #ifndef REAL_IS_NOT_DOUBLE
449     case REAL_TYPE:
450       {
451         REAL_VALUE_TYPE val;
452         char *bufp = digit_buffer;
453         extern char *index ();
454
455         my_friendly_assert (TREE_CODE (value) == REAL_CST, 244);
456         val = TREE_REAL_CST (value);
457         if (val < 0)
458           {
459             val = -val;
460             *bufp++ = 'm';
461           }
462         sprintf (bufp, "%e", val);
463         bufp = (char *) index (bufp, 'e');
464         if (!bufp)
465           strcat (digit_buffer, "e0");
466         else
467           {
468             char *p;
469             bufp++;
470             if (*bufp == '-')
471               {
472                 *bufp++ = 'm';
473               }
474             p = bufp;
475             if (*p == '+')
476               p++;
477             while (*p == '0')
478               p++;
479             if (*p == 0)
480               {
481                 *bufp++ = '0';
482                 *bufp = 0;
483               }
484             else if (p != bufp)
485               {
486                 while (*p)
487                   *bufp++ = *p++;
488                 *bufp = 0;
489               }
490           }
491         OB_PUTCP (digit_buffer);
492         numeric_output_need_bar = 1;
493         return;
494       }
495 #endif
496     case POINTER_TYPE:
497       if (TREE_CODE (TREE_TYPE (type)) == METHOD_TYPE
498           && TREE_CODE (value) != ADDR_EXPR)
499         {
500           if (TREE_CODE (value) == CONSTRUCTOR)
501             {
502               /* This is dangerous code, crack built up pointer to members. */
503               tree args = CONSTRUCTOR_ELTS (value);
504               tree a1 = TREE_VALUE (args);
505               tree a2 = TREE_VALUE (TREE_CHAIN (args));
506               tree a3 = CONSTRUCTOR_ELTS (TREE_VALUE (TREE_CHAIN (TREE_CHAIN (args))));
507               a3 = TREE_VALUE (a3);
508               STRIP_NOPS (a3);
509               if (TREE_CODE (a1) == INTEGER_CST
510                   && TREE_CODE (a2) == INTEGER_CST)
511                 {
512                   build_overload_int (a1);
513                   OB_PUTC ('_');
514                   build_overload_int (a2);
515                   OB_PUTC ('_');
516                   if (TREE_CODE (a3) == ADDR_EXPR)
517                     {
518                       a3 = TREE_OPERAND (a3, 0);
519                       if (TREE_CODE (a3) == FUNCTION_DECL)
520                         {
521                           numeric_output_need_bar = 0;
522                           build_overload_identifier (DECL_ASSEMBLER_NAME (a3));
523                           return;
524                         }
525                     }
526                   else if (TREE_CODE (a3) == INTEGER_CST)
527                     {
528                       OB_PUTC ('i');
529                       build_overload_int (a3);
530                       numeric_output_need_bar = 1;
531                       return;
532                     }
533                 }
534             }
535           sorry ("template instantiation with pointer to method that is too complex");
536           return;
537         }
538       if (TREE_CODE (value) == INTEGER_CST)
539         {
540           build_overload_int (value);
541           numeric_output_need_bar = 1;
542           return;
543         }
544       value = TREE_OPERAND (value, 0);
545       if (TREE_CODE (value) == VAR_DECL)
546         {
547           my_friendly_assert (DECL_NAME (value) != 0, 245);
548           build_overload_identifier (DECL_ASSEMBLER_NAME (value));
549           return;
550         }
551       else if (TREE_CODE (value) == FUNCTION_DECL)
552         {
553           my_friendly_assert (DECL_NAME (value) != 0, 246);
554           build_overload_identifier (DECL_ASSEMBLER_NAME (value));
555           return;
556         }
557       else
558         my_friendly_abort (71);
559       break; /* not really needed */
560
561     default:
562       sorry ("conversion of %s as template parameter",
563              tree_code_name [(int) TREE_CODE (type)]);
564       my_friendly_abort (72);
565     }
566 }
567
568 static void
569 build_overload_identifier (name)
570      tree name;
571 {
572   if (TREE_CODE (name) == TYPE_DECL
573       && IS_AGGR_TYPE (TREE_TYPE (name))
574       && CLASSTYPE_TEMPLATE_INFO (TREE_TYPE (name))
575       && PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (TREE_TYPE (name))))
576     {
577       tree template, parmlist, arglist, tname;
578       int i, nparms;
579       template = CLASSTYPE_TEMPLATE_INFO (TREE_TYPE (name));
580       arglist = TREE_VALUE (template);
581       template = TREE_PURPOSE (template);
582       tname = DECL_NAME (template);
583       parmlist = DECL_ARGUMENTS (template);
584       nparms = TREE_VEC_LENGTH (parmlist);
585       OB_PUTC ('t');
586       icat (IDENTIFIER_LENGTH (tname));
587       OB_PUTID (tname);
588       icat (nparms);
589       for (i = 0; i < nparms; i++)
590         {
591           tree parm = TREE_VALUE (TREE_VEC_ELT (parmlist, i));
592           tree arg = TREE_VEC_ELT (arglist, i);
593           if (TREE_CODE (parm) == TYPE_DECL)
594             {
595               /* This parameter is a type.  */
596               OB_PUTC ('Z');
597               build_overload_name (arg, 0, 0);
598             }
599           else
600             {
601               parm = tsubst (parm, &TREE_VEC_ELT (arglist, 0),
602                              TREE_VEC_LENGTH (arglist), NULL_TREE);
603               /* It's a PARM_DECL.  */
604               build_overload_name (TREE_TYPE (parm), 0, 0);
605               build_overload_value (parm, arg);
606             }
607         }
608     }
609   else
610     {
611       if (TREE_CODE (name) == TYPE_DECL)
612         name = DECL_NAME (name);
613       if (numeric_output_need_bar)
614         {
615           OB_PUTC ('_');
616           numeric_output_need_bar = 0;
617         }
618       icat (IDENTIFIER_LENGTH (name));
619       OB_PUTID (name);
620     }
621 }
622
623 /* Given a list of parameters in PARMTYPES, create an unambiguous
624    overload string. Should distinguish any type that C (or C++) can
625    distinguish. I.e., pointers to functions are treated correctly.
626
627    Caller must deal with whether a final `e' goes on the end or not.
628
629    Any default conversions must take place before this function
630    is called.
631
632    BEGIN and END control initialization and finalization of the
633    obstack where we build the string.  */
634
635 char *
636 build_overload_name (parmtypes, begin, end)
637      tree parmtypes;
638      int begin, end;
639 {
640   int just_one;
641   tree parmtype;
642
643   if (begin) OB_INIT ();
644   numeric_output_need_bar = 0;
645
646   if ((just_one = (TREE_CODE (parmtypes) != TREE_LIST)))
647     {
648       parmtype = parmtypes;
649       goto only_one;
650     }
651
652   while (parmtypes)
653     {
654       parmtype = TREE_VALUE (parmtypes);
655
656     only_one:
657
658       if (! nofold && ! just_one)
659         {
660           /* Every argument gets counted.  */
661           typevec[maxtype++] = parmtype;
662
663           if (TREE_USED (parmtype) && parmtype == typevec[maxtype-2])
664             {
665               nrepeats++;
666               goto next;
667             }
668
669           if (nrepeats)
670             flush_repeats (typevec[maxtype-2]);
671
672           if (TREE_USED (parmtype))
673             {
674               flush_repeats (parmtype);
675               goto next;
676             }
677
678           /* Only cache types which take more than one character.  */
679           if (parmtype != TYPE_MAIN_VARIANT (parmtype)
680               || (TREE_CODE (parmtype) != INTEGER_TYPE
681                   && TREE_CODE (parmtype) != REAL_TYPE))
682             TREE_USED (parmtype) = 1;
683         }
684
685       if (TYPE_PTRMEMFUNC_P (parmtype))
686         parmtype = TYPE_PTRMEMFUNC_FN_TYPE (parmtype);
687
688       if (TREE_READONLY (parmtype))
689         OB_PUTC ('C');
690       if (TREE_CODE (parmtype) == INTEGER_TYPE
691           && TYPE_MAIN_VARIANT (parmtype) == unsigned_type (TYPE_MAIN_VARIANT (parmtype)))
692         OB_PUTC ('U');
693       if (TYPE_VOLATILE (parmtype))
694         OB_PUTC ('V');
695
696       switch (TREE_CODE (parmtype))
697         {
698         case OFFSET_TYPE:
699           OB_PUTC ('O');
700           build_overload_name (TYPE_OFFSET_BASETYPE (parmtype), 0, 0);
701           OB_PUTC ('_');
702           build_overload_name (TREE_TYPE (parmtype), 0, 0);
703           break;
704
705         case REFERENCE_TYPE:
706           OB_PUTC ('R');
707           goto more;
708
709         case ARRAY_TYPE:
710 #if PARM_CAN_BE_ARRAY_TYPE
711           {
712             tree length;
713
714             OB_PUTC ('A');
715             if (TYPE_DOMAIN (parmtype) == NULL_TREE)
716               error ("pointer or reference to array of unknown bound in parm type");
717             else
718               {
719                 length = array_type_nelts (parmtype);
720                 if (TREE_CODE (length) == INTEGER_CST)
721                   icat (TREE_INT_CST_LOW (length) + 1);
722               }
723             OB_PUTC ('_');
724             goto more;
725           }
726 #else
727           OB_PUTC ('P');
728           goto more;
729 #endif
730
731         case POINTER_TYPE:
732           OB_PUTC ('P');
733         more:
734           build_overload_name (TREE_TYPE (parmtype), 0, 0);
735           break;
736
737         case FUNCTION_TYPE:
738         case METHOD_TYPE:
739           {
740             tree firstarg = TYPE_ARG_TYPES (parmtype);
741             /* Otherwise have to implement reentrant typevecs,
742                unmark and remark types, etc.  */
743             int old_nofold = nofold;
744             nofold = 1;
745
746             if (nrepeats)
747               flush_repeats (typevec[maxtype-1]);
748
749             /* @@ It may be possible to pass a function type in
750                which is not preceded by a 'P'.  */
751             if (TREE_CODE (parmtype) == FUNCTION_TYPE)
752               {
753                 OB_PUTC ('F');
754                 if (firstarg == NULL_TREE)
755                   OB_PUTC ('e');
756                 else if (firstarg == void_list_node)
757                   OB_PUTC ('v');
758                 else
759                   build_overload_name (firstarg, 0, 0);
760               }
761             else
762               {
763                 int constp = TYPE_READONLY (TREE_TYPE (TREE_VALUE (firstarg)));
764                 int volatilep = TYPE_VOLATILE (TREE_TYPE (TREE_VALUE (firstarg)));
765                 OB_PUTC ('M');
766                 firstarg = TREE_CHAIN (firstarg);
767
768                 build_overload_name (TYPE_METHOD_BASETYPE (parmtype), 0, 0);
769                 if (constp)
770                   OB_PUTC ('C');
771                 if (volatilep)
772                   OB_PUTC ('V');
773
774                 /* For cfront 2.0 compatibility.  */
775                 OB_PUTC ('F');
776
777                 if (firstarg == NULL_TREE)
778                   OB_PUTC ('e');
779                 else if (firstarg == void_list_node)
780                   OB_PUTC ('v');
781                 else
782                   build_overload_name (firstarg, 0, 0);
783               }
784
785             /* Separate args from return type.  */
786             OB_PUTC ('_');
787             build_overload_name (TREE_TYPE (parmtype), 0, 0);
788             nofold = old_nofold;
789             break;
790           }
791
792         case INTEGER_TYPE:
793           parmtype = TYPE_MAIN_VARIANT (parmtype);
794           if (parmtype == integer_type_node
795               || parmtype == unsigned_type_node)
796             OB_PUTC ('i');
797           else if (parmtype == long_integer_type_node
798                    || parmtype == long_unsigned_type_node)
799             OB_PUTC ('l');
800           else if (parmtype == short_integer_type_node
801                    || parmtype == short_unsigned_type_node)
802             OB_PUTC ('s');
803           else if (parmtype == signed_char_type_node)
804             {
805               OB_PUTC ('S');
806               OB_PUTC ('c');
807             }
808           else if (parmtype == char_type_node
809                    || parmtype == unsigned_char_type_node)
810             OB_PUTC ('c');
811           else if (parmtype == wchar_type_node)
812             OB_PUTC ('w');
813           else if (parmtype == long_long_integer_type_node
814               || parmtype == long_long_unsigned_type_node)
815             OB_PUTC ('x');
816 #if 0
817           /* it would seem there is no way to enter these in source code,
818              yet.  (mrs) */
819           else if (parmtype == long_long_long_integer_type_node
820               || parmtype == long_long_long_unsigned_type_node)
821             OB_PUTC ('q');
822 #endif
823           else
824             my_friendly_abort (73);
825           break;
826
827         case BOOLEAN_TYPE:
828           OB_PUTC ('b');
829           break;
830
831         case REAL_TYPE:
832           parmtype = TYPE_MAIN_VARIANT (parmtype);
833           if (parmtype == long_double_type_node)
834             OB_PUTC ('r');
835           else if (parmtype == double_type_node)
836             OB_PUTC ('d');
837           else if (parmtype == float_type_node)
838             OB_PUTC ('f');
839           else my_friendly_abort (74);
840           break;
841
842         case VOID_TYPE:
843           if (! just_one)
844             {
845 #if 0
846               extern tree void_list_node;
847
848               /* See if anybody is wasting memory.  */
849               my_friendly_assert (parmtypes == void_list_node, 247);
850 #endif
851               /* This is the end of a parameter list.  */
852               if (end) OB_FINISH ();
853               return (char *)obstack_base (&scratch_obstack);
854             }
855           OB_PUTC ('v');
856           break;
857
858         case ERROR_MARK:        /* not right, but nothing is anyway */
859           break;
860
861           /* have to do these */
862         case UNION_TYPE:
863         case RECORD_TYPE:
864           if (! just_one)
865             /* Make this type signature look incompatible
866                with AT&T.  */
867             OB_PUTC ('G');
868           goto common;
869         case ENUMERAL_TYPE:
870         common:
871           {
872             tree name = TYPE_NAME (parmtype);
873             int i = 1;
874
875             if (TREE_CODE (name) == TYPE_DECL)
876               {
877                 tree context = name;
878
879                 /* If DECL_ASSEMBLER_NAME has been set properly, use it. */
880                 if (DECL_ASSEMBLER_NAME (context) != DECL_NAME (context))
881                   {
882                     OB_PUTID (DECL_ASSEMBLER_NAME (context));
883                     break;
884                   }
885                 while (DECL_CONTEXT (context))
886                   {
887                     i += 1;
888                     context = DECL_CONTEXT (context);
889                     if (TREE_CODE_CLASS (TREE_CODE (context)) == 't')
890                       context = TYPE_NAME (context);
891                   }
892                 name = DECL_NAME (name);
893               }
894             my_friendly_assert (TREE_CODE (name) == IDENTIFIER_NODE, 248);
895             if (i > 1)
896               {
897                 OB_PUTC ('Q');
898                 if (i > 9)
899                   OB_PUTC ('_');
900                 icat (i);
901                 if (i > 9)
902                   OB_PUTC ('_');
903                 numeric_output_need_bar = 0;
904                 build_overload_nested_name (TYPE_MAIN_DECL (parmtype));
905               }
906             else              
907               build_overload_identifier (TYPE_MAIN_DECL (parmtype));
908             break;
909           }
910
911         case UNKNOWN_TYPE:
912           /* This will take some work.  */
913           OB_PUTC ('?');
914           break;
915
916         case TEMPLATE_TYPE_PARM:
917           OB_PUTC ('X');
918           if (TEMPLATE_TYPE_IDX (parmtype) > 9)
919             OB_PUTC ('_');
920           icat (TEMPLATE_TYPE_IDX (parmtype)); 
921           if (TEMPLATE_TYPE_IDX (parmtype) > 9)
922             OB_PUTC ('_');
923           break;
924             
925         case TYPENAME_TYPE:
926           /* We don't ever want this output, but it's inconvenient not to
927              be able to build the string.  This should cause assembler
928              errors we'll notice.  */
929           {
930             static int n;
931             sprintf (digit_buffer, " *%d", n++);
932             OB_PUTCP (digit_buffer);
933           }
934           break;
935
936         default:
937           my_friendly_abort (75);
938         }
939
940     next:
941       if (just_one) break;
942       parmtypes = TREE_CHAIN (parmtypes);
943     }
944   if (! just_one)
945     {
946       if (nrepeats)
947         flush_repeats (typevec[maxtype-1]);
948
949       /* To get here, parms must end with `...'. */
950       OB_PUTC ('e');
951     }
952
953   if (end) OB_FINISH ();
954   return (char *)obstack_base (&scratch_obstack);
955 }
956
957 tree
958 build_static_name (basetype, name)
959   tree basetype, name;
960 {
961   char *basename  = build_overload_name (basetype, 1, 1);
962   char *buf = (char *) alloca (IDENTIFIER_LENGTH (name)
963                                + sizeof (STATIC_NAME_FORMAT)
964                                + strlen (basename));
965   sprintf (buf, STATIC_NAME_FORMAT, basename, IDENTIFIER_POINTER (name));
966   return get_identifier (buf);
967 }  
968 \f
969 /* Change the name of a function definition so that it may be
970    overloaded. NAME is the name of the function to overload,
971    PARMS is the parameter list (which determines what name the
972    final function obtains).
973
974    FOR_METHOD is 1 if this overload is being performed
975    for a method, rather than a function type.  It is 2 if
976    this overload is being performed for a constructor.  */
977 tree
978 build_decl_overload (dname, parms, for_method)
979      tree dname;
980      tree parms;
981      int for_method;
982 {
983   char *name = IDENTIFIER_POINTER (dname);
984
985   /* member operators new and delete look like methods at this point.  */
986   if (! for_method && parms != NULL_TREE && TREE_CODE (parms) == TREE_LIST)
987     {
988       if (dname == ansi_opname[(int) DELETE_EXPR])
989         return get_identifier ("__builtin_delete");
990       else if (dname == ansi_opname[(int) VEC_DELETE_EXPR])
991         return get_identifier ("__builtin_vec_delete");
992       else if (TREE_CHAIN (parms) == void_list_node)
993         {
994           if (dname == ansi_opname[(int) NEW_EXPR])
995             return get_identifier ("__builtin_new");
996           else if (dname == ansi_opname[(int) VEC_NEW_EXPR])
997             return get_identifier ("__builtin_vec_new");
998         }
999     }
1000
1001   OB_INIT ();
1002   if (for_method != 2)
1003     OB_PUTCP (name);
1004   /* Otherwise, we can divine that this is a constructor,
1005      and figure out its name without any extra encoding.  */
1006
1007   OB_PUTC2 ('_', '_');
1008   if (for_method)
1009     {
1010 #if 0
1011       /* We can get away without doing this.  */
1012       OB_PUTC ('M');
1013 #endif
1014       {
1015         tree this_type = TREE_VALUE (parms);
1016
1017         if (TREE_CODE (this_type) == RECORD_TYPE)  /* a signature pointer */
1018           parms = temp_tree_cons (NULL_TREE, SIGNATURE_TYPE (this_type),
1019                                   TREE_CHAIN (parms));
1020         else
1021           parms = temp_tree_cons (NULL_TREE, TREE_TYPE (this_type),
1022                                   TREE_CHAIN (parms));
1023       }
1024     }
1025   else
1026     OB_PUTC ('F');
1027
1028   if (parms == NULL_TREE)
1029     OB_PUTC2 ('e', '\0');
1030   else if (parms == void_list_node)
1031     OB_PUTC2 ('v', '\0');
1032   else
1033     {
1034       ALLOCATE_TYPEVEC (parms);
1035       nofold = 0;
1036       if (for_method)
1037         {
1038           build_overload_name (TREE_VALUE (parms), 0, 0);
1039
1040           typevec[maxtype++] = TREE_VALUE (parms);
1041           TREE_USED (TREE_VALUE (parms)) = 1;
1042
1043           if (TREE_CHAIN (parms))
1044             build_overload_name (TREE_CHAIN (parms), 0, 1);
1045           else
1046             OB_PUTC2 ('e', '\0');
1047         }
1048       else
1049         build_overload_name (parms, 0, 1);
1050       DEALLOCATE_TYPEVEC (parms);
1051     }
1052   {
1053     tree n = get_identifier (obstack_base (&scratch_obstack));
1054     if (IDENTIFIER_OPNAME_P (dname))
1055       IDENTIFIER_OPNAME_P (n) = 1;
1056     return n;
1057   }
1058 }
1059
1060 /* Build an overload name for the type expression TYPE.  */
1061 tree
1062 build_typename_overload (type)
1063      tree type;
1064 {
1065   tree id;
1066
1067   OB_INIT ();
1068   OB_PUTID (ansi_opname[(int) TYPE_EXPR]);
1069   nofold = 1;
1070   build_overload_name (type, 0, 1);
1071   id = get_identifier (obstack_base (&scratch_obstack));
1072   IDENTIFIER_OPNAME_P (id) = 1;
1073 #if 0
1074   IDENTIFIER_GLOBAL_VALUE (id) = TYPE_NAME (type);
1075 #endif
1076   TREE_TYPE (id) = type;
1077   return id;
1078 }
1079
1080 tree
1081 build_overload_with_type (name, type)
1082      tree name, type;
1083 {
1084   OB_INIT ();
1085   OB_PUTID (name);
1086   nofold = 1;
1087
1088   build_overload_name (type, 0, 1);
1089   return get_identifier (obstack_base (&scratch_obstack));
1090 }
1091
1092 tree
1093 get_id_2 (name, name2)
1094      char *name;
1095      tree name2;
1096 {
1097   OB_INIT ();
1098   OB_PUTCP (name);
1099   OB_PUTID (name2);
1100   OB_FINISH ();
1101   return get_identifier (obstack_base (&scratch_obstack));
1102 }
1103
1104 /* Top-level interface to explicit overload requests. Allow NAME
1105    to be overloaded. Error if NAME is already declared for the current
1106    scope. Warning if function is redundantly overloaded. */
1107
1108 void
1109 declare_overloaded (name)
1110      tree name;
1111 {
1112 #ifdef NO_AUTO_OVERLOAD
1113   if (is_overloaded (name))
1114     warning ("function `%s' already declared overloaded",
1115              IDENTIFIER_POINTER (name));
1116   else if (IDENTIFIER_GLOBAL_VALUE (name))
1117     error ("overloading function `%s' that is already defined",
1118            IDENTIFIER_POINTER (name));
1119   else
1120     {
1121       TREE_OVERLOADED (name) = 1;
1122       IDENTIFIER_GLOBAL_VALUE (name) = build_tree_list (name, NULL_TREE);
1123       TREE_TYPE (IDENTIFIER_GLOBAL_VALUE (name)) = unknown_type_node;
1124     }
1125 #else
1126   if (current_lang_name == lang_name_cplusplus)
1127     {
1128       if (0)
1129         warning ("functions are implicitly overloaded in C++");
1130     }
1131   else if (current_lang_name == lang_name_c)
1132     error ("overloading function `%s' cannot be done in C language context");
1133   else
1134     my_friendly_abort (76);
1135 #endif
1136 }
1137
1138 #ifdef NO_AUTO_OVERLOAD
1139 /* Check to see if NAME is overloaded. For first approximation,
1140    check to see if its TREE_OVERLOADED is set.  This is used on
1141    IDENTIFIER nodes.  */
1142 int
1143 is_overloaded (name)
1144      tree name;
1145 {
1146   /* @@ */
1147   return (TREE_OVERLOADED (name)
1148           && (! IDENTIFIER_CLASS_VALUE (name) || current_class_type == 0)
1149           && ! IDENTIFIER_LOCAL_VALUE (name));
1150 }
1151 #endif
1152 \f
1153 /* Given a tree_code CODE, and some arguments (at least one),
1154    attempt to use an overloaded operator on the arguments.
1155
1156    For unary operators, only the first argument need be checked.
1157    For binary operators, both arguments may need to be checked.
1158
1159    Member functions can convert class references to class pointers,
1160    for one-level deep indirection.  More than that is not supported.
1161    Operators [](), ()(), and ->() must be member functions.
1162
1163    We call function call building calls with LOOKUP_COMPLAIN if they
1164    are our only hope.  This is true when we see a vanilla operator
1165    applied to something of aggregate type.  If this fails, we are free
1166    to return `error_mark_node', because we will have reported the
1167    error.
1168
1169    Operators NEW and DELETE overload in funny ways: operator new takes
1170    a single `size' parameter, and operator delete takes a pointer to the
1171    storage being deleted.  When overloading these operators, success is
1172    assumed.  If there is a failure, report an error message and return
1173    `error_mark_node'.  */
1174
1175 /* NOSTRICT */
1176 tree
1177 build_opfncall (code, flags, xarg1, xarg2, arg3)
1178      enum tree_code code;
1179      int flags;
1180      tree xarg1, xarg2, arg3;
1181 {
1182   tree rval = 0;
1183   tree arg1, arg2;
1184   tree type1, type2, fnname;
1185   tree fields1 = 0, parms = 0;
1186   tree global_fn;
1187   int try_second;
1188   int binary_is_unary;
1189
1190   if (xarg1 == error_mark_node)
1191     return error_mark_node;
1192
1193   if (code == COND_EXPR)
1194     {
1195       if (TREE_CODE (xarg2) == ERROR_MARK
1196           || TREE_CODE (arg3) == ERROR_MARK)
1197         return error_mark_node;
1198     }
1199   if (code == COMPONENT_REF)
1200     if (TREE_CODE (TREE_TYPE (xarg1)) == POINTER_TYPE)
1201       return rval;
1202
1203   /* First, see if we can work with the first argument */
1204   type1 = TREE_TYPE (xarg1);
1205
1206   /* Some tree codes have length > 1, but we really only want to
1207      overload them if their first argument has a user defined type.  */
1208   switch (code)
1209     {
1210     case PREINCREMENT_EXPR:
1211     case PREDECREMENT_EXPR:
1212     case POSTINCREMENT_EXPR:
1213     case POSTDECREMENT_EXPR:
1214     case COMPONENT_REF:
1215       binary_is_unary = 1;
1216       try_second = 0;
1217       break;
1218
1219       /* ARRAY_REFs and CALL_EXPRs must overload successfully.
1220          If they do not, return error_mark_node instead of NULL_TREE.  */
1221     case ARRAY_REF:
1222       if (xarg2 == error_mark_node)
1223         return error_mark_node;
1224     case CALL_EXPR:
1225       rval = error_mark_node;
1226       binary_is_unary = 0;
1227       try_second = 0;
1228       break;
1229
1230     case VEC_NEW_EXPR:
1231     case NEW_EXPR:
1232       {
1233         tree args = tree_cons (NULL_TREE, xarg2, arg3);
1234         fnname = ansi_opname[(int) code];
1235         if (flags & LOOKUP_GLOBAL)
1236           return build_overload_call (fnname, args, flags & LOOKUP_COMPLAIN,
1237                                       (struct candidate *)0);
1238
1239         rval = build_method_call
1240           (build_indirect_ref (build1 (NOP_EXPR, xarg1, error_mark_node),
1241                                "new"),
1242            fnname, args, NULL_TREE, flags);
1243         if (rval == error_mark_node)
1244           /* User might declare fancy operator new, but invoke it
1245              like standard one.  */
1246           return rval;
1247
1248         TREE_TYPE (rval) = xarg1;
1249         TREE_CALLS_NEW (rval) = 1;
1250         return rval;
1251       }
1252       break;
1253
1254     case VEC_DELETE_EXPR:
1255     case DELETE_EXPR:
1256       {
1257         fnname = ansi_opname[(int) code];
1258         if (flags & LOOKUP_GLOBAL)
1259           return build_overload_call (fnname,
1260                                       build_tree_list (NULL_TREE, xarg1),
1261                                       flags & LOOKUP_COMPLAIN,
1262                                       (struct candidate *)0);
1263         arg1 = TREE_TYPE (xarg1);
1264
1265         /* This handles the case where we're trying to delete
1266            X (*a)[10];
1267            a=new X[5][10];
1268            delete[] a; */
1269            
1270         if (TREE_CODE (TREE_TYPE (arg1)) == ARRAY_TYPE)
1271           {
1272             /* Strip off the pointer and the array. */
1273             arg1 = TREE_TYPE (TREE_TYPE (arg1));
1274
1275             while (TREE_CODE (arg1) == ARRAY_TYPE)
1276                 arg1 = (TREE_TYPE (arg1));
1277
1278             arg1 = build_pointer_type (arg1);
1279           }
1280
1281         rval = build_method_call
1282           (build_indirect_ref (build1 (NOP_EXPR, arg1,
1283                                        error_mark_node),
1284                                NULL_PTR),
1285            fnname, tree_cons (NULL_TREE, xarg1,
1286                                build_tree_list (NULL_TREE, xarg2)),
1287            NULL_TREE, flags);
1288 #if 0
1289         /* This can happen when operator delete is protected.  */
1290         my_friendly_assert (rval != error_mark_node, 250);
1291         TREE_TYPE (rval) = void_type_node;
1292 #endif
1293         return rval;
1294       }
1295       break;
1296
1297     default:
1298       binary_is_unary = 0;
1299       try_second = tree_code_length [(int) code] == 2;
1300       if (try_second && xarg2 == error_mark_node)
1301         return error_mark_node;
1302       break;
1303     }
1304
1305   if (try_second && xarg2 == error_mark_node)
1306     return error_mark_node;
1307
1308   /* What ever it was, we do not know how to deal with it.  */
1309   if (type1 == NULL_TREE)
1310     return rval;
1311
1312   if (TREE_CODE (type1) == OFFSET_TYPE)
1313     type1 = TREE_TYPE (type1);
1314
1315   if (TREE_CODE (type1) == REFERENCE_TYPE)
1316     {
1317       arg1 = convert_from_reference (xarg1);
1318       type1 = TREE_TYPE (arg1);
1319     }
1320   else
1321     {
1322       arg1 = xarg1;
1323     }
1324
1325   if (!IS_AGGR_TYPE (type1) || TYPE_PTRMEMFUNC_P (type1))
1326     {
1327       /* Try to fail. First, fail if unary */
1328       if (! try_second)
1329         return rval;
1330       /* Second, see if second argument is non-aggregate. */
1331       type2 = TREE_TYPE (xarg2);
1332       if (TREE_CODE (type2) == OFFSET_TYPE)
1333         type2 = TREE_TYPE (type2);
1334       if (TREE_CODE (type2) == REFERENCE_TYPE)
1335         {
1336           arg2 = convert_from_reference (xarg2);
1337           type2 = TREE_TYPE (arg2);
1338         }
1339       else
1340         {
1341           arg2 = xarg2;
1342         }
1343
1344       if (!IS_AGGR_TYPE (type2))
1345         return rval;
1346       try_second = 0;
1347     }
1348
1349   if (try_second)
1350     {
1351       /* First arg may succeed; see whether second should.  */
1352       type2 = TREE_TYPE (xarg2);
1353       if (TREE_CODE (type2) == OFFSET_TYPE)
1354         type2 = TREE_TYPE (type2);
1355       if (TREE_CODE (type2) == REFERENCE_TYPE)
1356         {
1357           arg2 = convert_from_reference (xarg2);
1358           type2 = TREE_TYPE (arg2);
1359         }
1360       else
1361         {
1362           arg2 = xarg2;
1363         }
1364
1365       if (! IS_AGGR_TYPE (type2))
1366         try_second = 0;
1367     }
1368
1369   if (type1 == unknown_type_node
1370       || (try_second && TREE_TYPE (xarg2) == unknown_type_node))
1371     {
1372       /* This will not be implemented in the foreseeable future.  */
1373       return rval;
1374     }
1375
1376   if (code == MODIFY_EXPR)
1377     fnname = ansi_assopname[(int) TREE_CODE (arg3)];
1378   else
1379     fnname = ansi_opname[(int) code];
1380
1381   global_fn = lookup_name_nonclass (fnname);
1382
1383   /* This is the last point where we will accept failure.  This
1384      may be too eager if we wish an overloaded operator not to match,
1385      but would rather a normal operator be called on a type-converted
1386      argument.  */
1387
1388   if (IS_AGGR_TYPE (type1))
1389     {
1390       fields1 = lookup_fnfields (TYPE_BINFO (type1), fnname, 0);
1391       /* ARM $13.4.7, prefix/postfix ++/--.  */
1392       if (code == POSTINCREMENT_EXPR || code == POSTDECREMENT_EXPR)
1393         {
1394           xarg2 = integer_zero_node;
1395           binary_is_unary = 0;
1396
1397           if (fields1)
1398             {
1399               tree t, t2;
1400               int have_postfix = 0;
1401
1402               /* Look for an `operator++ (int)'.  If they didn't have
1403                  one, then we fall back to the old way of doing things.  */
1404               for (t = TREE_VALUE (fields1); t ; t = DECL_CHAIN (t))
1405                 {
1406                   t2 = TYPE_ARG_TYPES (TREE_TYPE (t));
1407                   if (TREE_CHAIN (t2) != NULL_TREE
1408                       && TREE_VALUE (TREE_CHAIN (t2)) == integer_type_node)
1409                     {
1410                       have_postfix = 1;
1411                       break;
1412                     }
1413                 }
1414
1415               if (! have_postfix)
1416                 {
1417                   char *op = POSTINCREMENT_EXPR ? "++" : "--";
1418
1419                   /* There's probably a LOT of code in the world that
1420                      relies upon this old behavior.  */
1421                   if (! flag_traditional)
1422                     pedwarn ("no `operator%s (int)' declared for postfix `%s', using prefix operator instead",
1423                              op, op);
1424                   xarg2 = NULL_TREE;
1425                   binary_is_unary = 1;
1426                 }
1427             }
1428         }
1429     }
1430
1431   if (fields1 == NULL_TREE && global_fn == NULL_TREE)
1432     return rval;
1433
1434   /* If RVAL winds up being `error_mark_node', we will return
1435      that... There is no way that normal semantics of these
1436      operators will succeed.  */
1437
1438   /* This argument may be an uncommitted OFFSET_REF.  This is
1439      the case for example when dealing with static class members
1440      which are referenced from their class name rather than
1441      from a class instance.  */
1442   if (TREE_CODE (xarg1) == OFFSET_REF
1443       && TREE_CODE (TREE_OPERAND (xarg1, 1)) == VAR_DECL)
1444     xarg1 = TREE_OPERAND (xarg1, 1);
1445   if (try_second && xarg2 && TREE_CODE (xarg2) == OFFSET_REF
1446       && TREE_CODE (TREE_OPERAND (xarg2, 1)) == VAR_DECL)
1447     xarg2 = TREE_OPERAND (xarg2, 1);
1448
1449   if (global_fn)
1450     flags |= LOOKUP_GLOBAL;
1451
1452   if (code == CALL_EXPR)
1453     {
1454       /* This can only be a member function.  */
1455       return build_method_call (xarg1, fnname, xarg2,
1456                                 NULL_TREE, LOOKUP_NORMAL);
1457     }
1458   else if (tree_code_length[(int) code] == 1 || binary_is_unary)
1459     {
1460       parms = NULL_TREE;
1461       rval = build_method_call (xarg1, fnname, NULL_TREE, NULL_TREE, flags);
1462     }
1463   else if (code == COND_EXPR)
1464     {
1465       parms = tree_cons (0, xarg2, build_tree_list (NULL_TREE, arg3));
1466       rval = build_method_call (xarg1, fnname, parms, NULL_TREE, flags);
1467     }
1468   else if (code == METHOD_CALL_EXPR)
1469     {
1470       /* must be a member function.  */
1471       parms = tree_cons (NULL_TREE, xarg2, arg3);
1472       return build_method_call (xarg1, fnname, parms, NULL_TREE,
1473                                 LOOKUP_NORMAL);
1474     }
1475   else if (fields1)
1476     {
1477       parms = build_tree_list (NULL_TREE, xarg2);
1478       rval = build_method_call (xarg1, fnname, parms, NULL_TREE, flags);
1479     }
1480   else
1481     {
1482       parms = tree_cons (NULL_TREE, xarg1,
1483                          build_tree_list (NULL_TREE, xarg2));
1484       rval = build_overload_call (fnname, parms, flags,
1485                                   (struct candidate *)0);
1486     }
1487
1488   return rval;
1489 }
1490 \f
1491 /* This function takes an identifier, ID, and attempts to figure out what
1492    it means. There are a number of possible scenarios, presented in increasing
1493    order of hair:
1494
1495    1) not in a class's scope
1496    2) in class's scope, member name of the class's method
1497    3) in class's scope, but not a member name of the class
1498    4) in class's scope, member name of a class's variable
1499
1500    NAME is $1 from the bison rule. It is an IDENTIFIER_NODE.
1501    VALUE is $$ from the bison rule. It is the value returned by lookup_name ($1)
1502
1503    As a last ditch, try to look up the name as a label and return that
1504    address.
1505
1506    Values which are declared as being of REFERENCE_TYPE are
1507    automatically dereferenced here (as a hack to make the
1508    compiler faster).  */
1509
1510 tree
1511 hack_identifier (value, name)
1512      tree value, name;
1513 {
1514   tree type, context;
1515
1516   if (TREE_CODE (value) == ERROR_MARK)
1517     {
1518       if (current_class_name)
1519         {
1520           tree fields = lookup_fnfields (TYPE_BINFO (current_class_type), name, 1);
1521           if (fields == error_mark_node)
1522             return error_mark_node;
1523           if (fields)
1524             {
1525               tree fndecl;
1526
1527               fndecl = TREE_VALUE (fields);
1528               my_friendly_assert (TREE_CODE (fndecl) == FUNCTION_DECL, 251);
1529               if (DECL_CHAIN (fndecl) == NULL_TREE)
1530                 {
1531                   warning ("methods cannot be converted to function pointers");
1532                   return fndecl;
1533                 }
1534               else
1535                 {
1536                   error ("ambiguous request for method pointer `%s'",
1537                          IDENTIFIER_POINTER (name));
1538                   return error_mark_node;
1539                 }
1540             }
1541         }
1542       if (flag_labels_ok && IDENTIFIER_LABEL_VALUE (name))
1543         {
1544           return IDENTIFIER_LABEL_VALUE (name);
1545         }
1546       return error_mark_node;
1547     }
1548
1549   type = TREE_TYPE (value);
1550   if (TREE_CODE (value) == FIELD_DECL)
1551     {
1552       if (current_class_decl == NULL_TREE)
1553         {
1554           error ("request for member `%s' in static member function",
1555                  IDENTIFIER_POINTER (DECL_NAME (value)));
1556           return error_mark_node;
1557         }
1558       TREE_USED (current_class_decl) = 1;
1559
1560       /* Mark so that if we are in a constructor, and then find that
1561          this field was initialized by a base initializer,
1562          we can emit an error message.  */
1563       TREE_USED (value) = 1;
1564       value = build_component_ref (C_C_D, name, 0, 1);
1565     }
1566   else if (really_overloaded_fn (value))
1567     {
1568 #if 0
1569       tree t = get_first_fn (value);
1570       for (; t; t = DECL_CHAIN (t))
1571         {
1572           if (TREE_CODE (t) == TEMPLATE_DECL)
1573             continue;
1574
1575           assemble_external (t);
1576           TREE_USED (t) = 1;
1577         }
1578 #endif
1579     }
1580   else if (TREE_CODE (value) == TREE_LIST)
1581     {
1582       /* Ambiguous reference to base members, possibly other cases?.  */
1583       tree t = value;
1584       while (t && TREE_CODE (t) == TREE_LIST)
1585         {
1586           mark_used (TREE_VALUE (t));
1587           t = TREE_CHAIN (t);
1588         }
1589     }
1590   else
1591     mark_used (value);
1592
1593   if (TREE_CODE (value) == VAR_DECL || TREE_CODE (value) == PARM_DECL)
1594     {
1595       tree context = decl_function_context (value);
1596       if (context != NULL_TREE && context != current_function_decl
1597           && ! TREE_STATIC (value))
1598         {
1599           cp_error ("use of %s from containing function",
1600                       (TREE_CODE (value) == VAR_DECL
1601                        ? "`auto' variable" : "parameter"));
1602           cp_error_at ("  `%#D' declared here", value);
1603           value = error_mark_node;
1604         }
1605     }
1606
1607   if (TREE_CODE_CLASS (TREE_CODE (value)) == 'd' && DECL_NONLOCAL (value))
1608     {
1609       if (DECL_LANG_SPECIFIC (value)
1610           && DECL_CLASS_CONTEXT (value) != current_class_type)
1611         {
1612           tree path, access;
1613           register tree context
1614             = (TREE_CODE (value) == FUNCTION_DECL && DECL_VIRTUAL_P (value))
1615               ? DECL_CLASS_CONTEXT (value)
1616               : DECL_CONTEXT (value);
1617
1618           get_base_distance (context, current_class_type, 0, &path);
1619           if (path)
1620             {
1621               access = compute_access (path, value);
1622               if (access != access_public_node)
1623                 {
1624                   if (TREE_CODE (value) == VAR_DECL)
1625                     error ("static member `%s' is %s",
1626                            IDENTIFIER_POINTER (name),
1627                            TREE_PRIVATE (value) ? "private" :
1628                            "from a private base class");
1629                   else
1630                     error ("enum `%s' is from private base class",
1631                            IDENTIFIER_POINTER (name));
1632                   return error_mark_node;
1633                 }
1634             }
1635         }
1636       return value;
1637     }
1638   if (TREE_CODE (value) == TREE_LIST && TREE_NONLOCAL_FLAG (value))
1639     {
1640       if (type == 0)
1641         {
1642           error ("request for member `%s' is ambiguous in multiple inheritance lattice",
1643                  IDENTIFIER_POINTER (name));
1644           return error_mark_node;
1645         }
1646
1647       return value;
1648     }
1649
1650   if (TREE_CODE (type) == REFERENCE_TYPE && ! current_template_parms)
1651     value = convert_from_reference (value);
1652   return value;
1653 }
1654
1655 \f
1656 #if 0
1657 /* Given an object OF, and a type conversion operator COMPONENT
1658    build a call to the conversion operator, if a call is requested,
1659    or return the address (as a pointer to member function) if one is not.
1660
1661    OF can be a TYPE_DECL or any kind of datum that would normally
1662    be passed to `build_component_ref'.  It may also be NULL_TREE,
1663    in which case `current_class_type' and `current_class_decl'
1664    provide default values.
1665
1666    BASETYPE_PATH, if non-null, is the path of basetypes
1667    to go through before we get the the instance of interest.
1668
1669    PROTECT says whether we apply C++ scoping rules or not.  */
1670 tree
1671 build_component_type_expr (of, component, basetype_path, protect)
1672      tree of, component, basetype_path;
1673      int protect;
1674 {
1675   tree cname = NULL_TREE;
1676   tree tmp, last;
1677   tree name;
1678   int flags = protect ? LOOKUP_NORMAL : LOOKUP_COMPLAIN;
1679
1680   if (of)
1681     my_friendly_assert (IS_AGGR_TYPE (TREE_TYPE (of)), 253);
1682   my_friendly_assert (TREE_CODE (component) == TYPE_EXPR, 254);
1683
1684   tmp = TREE_OPERAND (component, 0);
1685   last = NULL_TREE;
1686
1687   while (tmp)
1688     {
1689       switch (TREE_CODE (tmp))
1690         {
1691         case CALL_EXPR:
1692           if (last)
1693             TREE_OPERAND (last, 0) = TREE_OPERAND (tmp, 0);
1694           else
1695             TREE_OPERAND (component, 0) = TREE_OPERAND (tmp, 0);
1696
1697           last = groktypename (build_tree_list (TREE_TYPE (component),
1698                                                 TREE_OPERAND (component, 0)));
1699           name = build_typename_overload (last);
1700           TREE_TYPE (name) = last;
1701
1702           if (TREE_OPERAND (tmp, 0)
1703               && TREE_OPERAND (tmp, 0) != void_list_node)
1704             {
1705               cp_error ("`operator %T' requires empty parameter list", last);
1706               TREE_OPERAND (tmp, 0) = NULL_TREE;
1707             }
1708
1709           if (of && TREE_CODE (of) != TYPE_DECL)
1710             return build_method_call (of, name, NULL_TREE, NULL_TREE, flags);
1711           else if (of)
1712             {
1713               tree this_this;
1714
1715               if (current_class_decl == NULL_TREE)
1716                 {
1717                   cp_error ("object required for `operator %T' call",
1718                             TREE_TYPE (name));
1719                   return error_mark_node;
1720                 }
1721
1722               this_this = convert_pointer_to (TREE_TYPE (of),
1723                                               current_class_decl);
1724               this_this = build_indirect_ref (this_this, NULL_PTR);
1725               return build_method_call (this_this, name, NULL_TREE,
1726                                         NULL_TREE, flags | LOOKUP_NONVIRTUAL);
1727             }
1728           else if (current_class_decl)
1729             return build_method_call (tmp, name, NULL_TREE, NULL_TREE, flags);
1730
1731           cp_error ("object required for `operator %T' call",
1732                     TREE_TYPE (name));
1733           return error_mark_node;
1734
1735         case INDIRECT_REF:
1736         case ADDR_EXPR:
1737         case ARRAY_REF:
1738           break;
1739
1740         case SCOPE_REF:
1741           my_friendly_assert (cname == 0, 255);
1742           cname = TREE_OPERAND (tmp, 0);
1743           tmp = TREE_OPERAND (tmp, 1);
1744           break;
1745
1746         default:
1747           my_friendly_abort (77);
1748         }
1749       last = tmp;
1750       tmp = TREE_OPERAND (tmp, 0);
1751     }
1752
1753   last = groktypename (build_tree_list (TREE_TYPE (component), TREE_OPERAND (component, 0)));
1754   name = build_typename_overload (last);
1755   TREE_TYPE (name) = last;
1756   if (of && TREE_CODE (of) == TYPE_DECL)
1757     {
1758       if (cname == NULL_TREE)
1759         {
1760           cname = DECL_NAME (of);
1761           of = NULL_TREE;
1762         }
1763       else my_friendly_assert (cname == DECL_NAME (of), 256);
1764     }
1765
1766   if (of)
1767     {
1768       tree this_this;
1769
1770       if (current_class_decl == NULL_TREE)
1771         {
1772           cp_error ("object required for `operator %T' call",
1773                     TREE_TYPE (name));
1774           return error_mark_node;
1775         }
1776
1777       this_this = convert_pointer_to (TREE_TYPE (of), current_class_decl);
1778       return build_component_ref (this_this, name, 0, protect);
1779     }
1780   else if (cname)
1781     return build_offset_ref (cname, name);
1782   else if (current_class_name)
1783     return build_offset_ref (current_class_name, name);
1784
1785   cp_error ("object required for `operator %T' member reference",
1786             TREE_TYPE (name));
1787   return error_mark_node;
1788 }
1789 #endif
1790 \f
1791 static char *
1792 thunk_printable_name (decl)
1793      tree decl;
1794 {
1795   return "<thunk function>";
1796 }
1797
1798 tree
1799 make_thunk (function, delta)
1800      tree function;
1801      int delta;
1802 {
1803   char buffer[250];
1804   tree thunk_fndecl, thunk_id;
1805   tree thunk;
1806   char *func_name;
1807   static int thunk_number = 0;
1808   tree func_decl;
1809   if (TREE_CODE (function) != ADDR_EXPR)
1810     abort ();
1811   func_decl = TREE_OPERAND (function, 0);
1812   if (TREE_CODE (func_decl) != FUNCTION_DECL)
1813     abort ();
1814   func_name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (func_decl));
1815   if (delta<=0)
1816     sprintf (buffer, "__thunk_%d_%s", -delta, func_name);
1817   else
1818     sprintf (buffer, "__thunk_n%d_%s", delta, func_name);
1819   thunk_id = get_identifier (buffer);
1820   thunk = IDENTIFIER_GLOBAL_VALUE (thunk_id);
1821   if (thunk && TREE_CODE (thunk) != THUNK_DECL)
1822     {
1823       cp_error ("implementation-reserved name `%D' used", thunk_id);
1824       IDENTIFIER_GLOBAL_VALUE (thunk_id) = thunk = NULL_TREE;
1825     }
1826   if (thunk == NULL_TREE)
1827     {
1828       thunk = build_decl (FUNCTION_DECL, thunk_id, TREE_TYPE (func_decl));
1829       DECL_RESULT (thunk)
1830         = build_decl (RESULT_DECL, 0, TYPE_MAIN_VARIANT (TREE_TYPE (vtable_entry_type)));
1831       TREE_READONLY (thunk) = TYPE_READONLY (TREE_TYPE (vtable_entry_type));
1832       TREE_THIS_VOLATILE (thunk) = TYPE_VOLATILE (TREE_TYPE (vtable_entry_type));
1833       make_function_rtl (thunk);
1834       TREE_SET_CODE (thunk, THUNK_DECL);
1835       DECL_INITIAL (thunk) = function;
1836       THUNK_DELTA (thunk) = delta;
1837       DECL_EXTERNAL (thunk) = 1;
1838 #ifdef DECL_ONE_ONLY
1839       if (SUPPORTS_ONE_ONLY)
1840         {
1841           DECL_ONE_ONLY (thunk) = 1;
1842           TREE_PUBLIC (thunk) = 1;
1843         }
1844       else
1845 #endif
1846         TREE_PUBLIC (thunk) = 0;
1847       /* So that finish_file can write out any thunks that need to be: */
1848       pushdecl_top_level (thunk);
1849     }
1850   return thunk;
1851 }
1852
1853 void
1854 emit_thunk (thunk_fndecl)
1855   tree thunk_fndecl;
1856 {
1857   rtx insns;
1858   char buffer[250];
1859   tree argp;
1860   struct args_size stack_args_size;
1861   tree function = TREE_OPERAND (DECL_INITIAL (thunk_fndecl), 0);
1862   int delta = THUNK_DELTA (thunk_fndecl);
1863   char *fnname = XSTR (XEXP (DECL_RTL (thunk_fndecl), 0), 0);
1864   int tem;
1865   int failure = 0;
1866
1867   /* Used to remember which regs we need to emit a USE rtx for. */
1868   rtx need_use[FIRST_PSEUDO_REGISTER];
1869   int need_use_count = 0;
1870
1871   /* rtx for the 'this' parameter. */
1872   rtx this_rtx = 0, this_reg_rtx = 0, fixed_this_rtx;
1873
1874   char *(*save_decl_printable_name) () = decl_printable_name;
1875   /* Data on reg parms scanned so far.  */
1876   CUMULATIVE_ARGS args_so_far;
1877
1878   if (TREE_ASM_WRITTEN (thunk_fndecl))
1879     return;
1880
1881   TREE_ASM_WRITTEN (thunk_fndecl) = 1;
1882
1883   TREE_ADDRESSABLE (function) = 1;
1884   mark_used (function);
1885
1886   decl_printable_name = thunk_printable_name;
1887   if (current_function_decl)
1888     abort ();
1889   current_function_decl = thunk_fndecl;
1890 #ifdef ASM_OUTPUT_MI_THUNK
1891   assemble_start_function (thunk_fndecl, fnname);
1892   ASM_OUTPUT_MI_THUNK (asm_out_file, thunk_fndecl, delta, function);
1893   assemble_end_function (thunk_fndecl, fnname);
1894 #else
1895   init_function_start (thunk_fndecl, input_filename, lineno);
1896   pushlevel (0);
1897   expand_start_bindings (1);
1898
1899   temporary_allocation ();
1900
1901   /* Start updating where the next arg would go.  */
1902   INIT_CUMULATIVE_ARGS (args_so_far, TREE_TYPE (function), NULL_RTX, 0);
1903   stack_args_size.constant = 0;
1904   stack_args_size.var = 0;
1905   /* SETUP for possible structure return address FIXME */
1906
1907   /* Now look through all the parameters, make sure that we
1908      don't clobber any registers used for parameters.
1909      Also, pick up an rtx for the first "this" parameter. */
1910   for (argp = TYPE_ARG_TYPES (TREE_TYPE (function));
1911        argp != NULL_TREE;
1912        argp = TREE_CHAIN (argp))
1913
1914     {
1915       tree passed_type = TREE_VALUE (argp);
1916       register rtx entry_parm;
1917       int named = 1; /* FIXME */
1918       struct args_size stack_offset;
1919       struct args_size arg_size;
1920
1921       if (passed_type == void_type_node)
1922         break;
1923
1924       if ((TREE_CODE (TYPE_SIZE (passed_type)) != INTEGER_CST
1925            && contains_placeholder_p (TYPE_SIZE (passed_type)))
1926 #ifdef FUNCTION_ARG_PASS_BY_REFERENCE
1927           || FUNCTION_ARG_PASS_BY_REFERENCE (args_so_far,
1928                                              TYPE_MODE (passed_type),
1929                                              passed_type, named)
1930 #endif
1931           )
1932         passed_type = build_pointer_type (passed_type);
1933
1934       entry_parm = FUNCTION_ARG (args_so_far,
1935                                  TYPE_MODE (passed_type),
1936                                  passed_type,
1937                                  named);
1938       if (entry_parm != 0)
1939         need_use[need_use_count++] = entry_parm;
1940
1941       locate_and_pad_parm (TYPE_MODE (passed_type), passed_type,
1942 #ifdef STACK_PARMS_IN_REG_PARM_AREA
1943                            1,
1944 #else
1945                            entry_parm != 0,
1946 #endif
1947                            thunk_fndecl,
1948                            &stack_args_size, &stack_offset, &arg_size);
1949
1950 /*    REGNO (entry_parm);*/
1951       if (this_rtx == 0)
1952         {
1953           this_reg_rtx = entry_parm;
1954           if (!entry_parm)
1955             {
1956               rtx offset_rtx = ARGS_SIZE_RTX (stack_offset);
1957
1958               rtx internal_arg_pointer, stack_parm;
1959
1960               if ((ARG_POINTER_REGNUM == STACK_POINTER_REGNUM
1961                    || ! (fixed_regs[ARG_POINTER_REGNUM]
1962                          || ARG_POINTER_REGNUM == FRAME_POINTER_REGNUM)))
1963                 internal_arg_pointer = copy_to_reg (virtual_incoming_args_rtx);
1964               else
1965                 internal_arg_pointer = virtual_incoming_args_rtx;
1966
1967               if (offset_rtx == const0_rtx)
1968                 entry_parm = gen_rtx (MEM, TYPE_MODE (passed_type),
1969                                       internal_arg_pointer);
1970               else
1971                 entry_parm = gen_rtx (MEM, TYPE_MODE (passed_type),
1972                                       gen_rtx (PLUS, Pmode,
1973                                                internal_arg_pointer, 
1974                                                offset_rtx));
1975             }
1976           
1977           this_rtx = entry_parm;
1978         }
1979
1980       FUNCTION_ARG_ADVANCE (args_so_far,
1981                             TYPE_MODE (passed_type),
1982                             passed_type,
1983                             named);
1984     }
1985
1986   fixed_this_rtx = plus_constant (this_rtx, delta);
1987   if (this_rtx != fixed_this_rtx)
1988     emit_move_insn (this_rtx, fixed_this_rtx);
1989
1990   if (this_reg_rtx)
1991     emit_insn (gen_rtx (USE, VOIDmode, this_reg_rtx));
1992
1993   emit_indirect_jump (XEXP (DECL_RTL (function), 0));
1994
1995   while (need_use_count > 0)
1996     emit_insn (gen_rtx (USE, VOIDmode, need_use[--need_use_count]));
1997
1998   expand_end_bindings (NULL, 1, 0);
1999   poplevel (0, 0, 1);
2000
2001   /* From now on, allocate rtl in current_obstack, not in saveable_obstack.
2002      Note that that may have been done above, in save_for_inline_copying.
2003      The call to resume_temporary_allocation near the end of this function
2004      goes back to the usual state of affairs.  */
2005
2006   rtl_in_current_obstack ();
2007
2008   insns = get_insns ();
2009
2010   /* Copy any shared structure that should not be shared.  */
2011
2012   unshare_all_rtl (insns);
2013
2014   /* Instantiate all virtual registers.  */
2015
2016   instantiate_virtual_regs (current_function_decl, get_insns ());
2017
2018   /* We are no longer anticipating cse in this function, at least.  */
2019
2020   cse_not_expected = 1;
2021
2022   /* Now we choose between stupid (pcc-like) register allocation
2023      (if we got the -noreg switch and not -opt)
2024      and smart register allocation.  */
2025
2026   if (optimize > 0)                     /* Stupid allocation probably won't work */
2027     obey_regdecls = 0;          /* if optimizations being done.  */
2028
2029   regclass_init ();
2030
2031   regclass (insns, max_reg_num ());
2032   if (obey_regdecls)
2033     {
2034       stupid_life_analysis (insns, max_reg_num (), NULL);
2035       failure = reload (insns, 0, NULL);
2036     }
2037   else
2038     {
2039       /* Do control and data flow analysis,
2040          and write some of the results to dump file.  */
2041
2042       flow_analysis (insns, max_reg_num (), NULL);
2043       local_alloc ();
2044       failure = global_alloc (NULL);
2045     }
2046
2047   reload_completed = 1;
2048
2049 #ifdef LEAF_REGISTERS
2050   leaf_function = 0;
2051   if (optimize > 0 && only_leaf_regs_used () && leaf_function_p ())
2052     leaf_function = 1;
2053 #endif
2054
2055   /* If a machine dependent reorganization is needed, call it.  */
2056 #ifdef MACHINE_DEPENDENT_REORG
2057    MACHINE_DEPENDENT_REORG (insns);
2058 #endif
2059
2060   /* Now turn the rtl into assembler code.  */
2061
2062   assemble_start_function (thunk_fndecl, fnname);
2063   final (insns, asm_out_file, optimize, 0);
2064   assemble_end_function (thunk_fndecl, fnname);
2065
2066  exit_rest_of_compilation:
2067
2068   reload_completed = 0;
2069
2070   /* Cancel the effect of rtl_in_current_obstack.  */
2071
2072   permanent_allocation (1);
2073 #endif /* ASM_OUTPUT_MI_THUNK */
2074
2075   decl_printable_name = save_decl_printable_name;
2076   current_function_decl = 0;
2077 }
2078 \f
2079 /* Code for synthesizing methods which have default semantics defined.  */
2080
2081 /* For the anonymous union in TYPE, return the member that is at least as
2082    large as the rest of the members, so we can copy it.  */
2083 static tree
2084 largest_union_member (type)
2085      tree type;
2086 {
2087   tree f, type_size = TYPE_SIZE (type);
2088
2089   for (f = TYPE_FIELDS (type); f; f = TREE_CHAIN (f))
2090     if (simple_cst_equal (DECL_SIZE (f), type_size) == 1)
2091       return f;
2092
2093   /* We should always find one.  */
2094   my_friendly_abort (323);
2095   return NULL_TREE;
2096 }
2097
2098 /* Generate code for default X(X&) constructor.  */
2099 void
2100 do_build_copy_constructor (fndecl)
2101      tree fndecl;
2102 {
2103   tree parm = TREE_CHAIN (DECL_ARGUMENTS (fndecl));
2104   tree t;
2105
2106   clear_last_expr ();
2107   push_momentary ();
2108
2109   if (TYPE_USES_VIRTUAL_BASECLASSES (current_class_type))
2110     parm = TREE_CHAIN (parm);
2111   parm = convert_from_reference (parm);
2112
2113   if (TYPE_HAS_TRIVIAL_INIT_REF (current_class_type))
2114     {
2115       t = build (INIT_EXPR, void_type_node, C_C_D, parm);
2116       TREE_SIDE_EFFECTS (t) = 1;
2117       cplus_expand_expr_stmt (t);
2118     }
2119   else
2120     {
2121       tree fields = TYPE_FIELDS (current_class_type);
2122       int n_bases = CLASSTYPE_N_BASECLASSES (current_class_type);
2123       tree binfos = TYPE_BINFO_BASETYPES (current_class_type);
2124       int i;
2125
2126       for (t = CLASSTYPE_VBASECLASSES (current_class_type); t;
2127            t = TREE_CHAIN (t))
2128         {
2129           tree basetype = BINFO_TYPE (t);
2130           tree p = convert_to_reference
2131             (build_reference_type (basetype), parm,
2132              CONV_IMPLICIT|CONV_CONST, LOOKUP_COMPLAIN, NULL_TREE);
2133           p = convert_from_reference (p);
2134           current_base_init_list = tree_cons (basetype,
2135                                               p, current_base_init_list);
2136         }
2137         
2138       for (i = 0; i < n_bases; ++i)
2139         {
2140           tree p, basetype = TREE_VEC_ELT (binfos, i);
2141           if (TREE_VIA_VIRTUAL (basetype))
2142             continue; 
2143
2144           basetype = BINFO_TYPE (basetype);
2145           p = convert_to_reference
2146             (build_reference_type (basetype), parm,
2147              CONV_IMPLICIT|CONV_CONST, LOOKUP_COMPLAIN, NULL_TREE);
2148           p = convert_from_reference (p);
2149           current_base_init_list = tree_cons (basetype,
2150                                               p, current_base_init_list);
2151         }
2152       for (; fields; fields = TREE_CHAIN (fields))
2153         {
2154           tree name, init, t;
2155           tree field = fields;
2156
2157           if (TREE_CODE (field) != FIELD_DECL)
2158             continue;
2159           if (DECL_NAME (field))
2160             {
2161               if (VFIELD_NAME_P (DECL_NAME (field)))
2162                 continue;
2163               if (VBASE_NAME_P (DECL_NAME (field)))
2164                 continue;
2165
2166               /* True for duplicate members.  */
2167               if (IDENTIFIER_CLASS_VALUE (DECL_NAME (field)) != field)
2168                 continue;
2169             }
2170           else if ((t = TREE_TYPE (field)) != NULL_TREE
2171                    && TREE_CODE (t) == UNION_TYPE
2172                    && ANON_AGGRNAME_P (TYPE_IDENTIFIER (t))
2173                    && TYPE_FIELDS (t) != NULL_TREE)
2174             field = largest_union_member (t);
2175           else
2176             continue;
2177
2178           init = build (COMPONENT_REF, TREE_TYPE (field), parm, field);
2179           init = build_tree_list (NULL_TREE, init);
2180
2181           current_member_init_list
2182             = tree_cons (DECL_NAME (field), init, current_member_init_list);
2183         }
2184       current_member_init_list = nreverse (current_member_init_list);
2185       current_base_init_list = nreverse (current_base_init_list);
2186       setup_vtbl_ptr ();
2187     }
2188
2189   pop_momentary ();
2190 }
2191
2192 void
2193 do_build_assign_ref (fndecl)
2194      tree fndecl;
2195 {
2196   tree parm = TREE_CHAIN (DECL_ARGUMENTS (fndecl));
2197
2198   clear_last_expr ();
2199   push_momentary ();
2200
2201   parm = convert_from_reference (parm);
2202
2203   if (TYPE_HAS_TRIVIAL_ASSIGN_REF (current_class_type))
2204     {
2205       tree t = build (MODIFY_EXPR, void_type_node, C_C_D, parm);
2206       TREE_SIDE_EFFECTS (t) = 1;
2207       cplus_expand_expr_stmt (t);
2208     }
2209   else
2210     {
2211       tree fields = TYPE_FIELDS (current_class_type);
2212       int n_bases = CLASSTYPE_N_BASECLASSES (current_class_type);
2213       tree binfos = TYPE_BINFO_BASETYPES (current_class_type);
2214       int i;
2215
2216       for (i = 0; i < n_bases; ++i)
2217         {
2218           tree basetype = BINFO_TYPE (TREE_VEC_ELT (binfos, i));
2219           if (TYPE_HAS_ASSIGN_REF (basetype))
2220             {
2221               tree p = convert_to_reference
2222                 (build_reference_type (basetype), parm,
2223                  CONV_IMPLICIT|CONV_CONST, LOOKUP_COMPLAIN, NULL_TREE);
2224               p = convert_from_reference (p);
2225               p = build_member_call (basetype, ansi_opname [MODIFY_EXPR],
2226                                      build_tree_list (NULL_TREE, p));
2227               expand_expr_stmt (p);
2228             }
2229         }
2230       for (; fields; fields = TREE_CHAIN (fields))
2231         {
2232           tree comp, init, t;
2233           tree field = fields;
2234
2235           if (TREE_CODE (field) != FIELD_DECL)
2236             continue;
2237           if (DECL_NAME (field))
2238             {
2239               if (VFIELD_NAME_P (DECL_NAME (field)))
2240                 continue;
2241               if (VBASE_NAME_P (DECL_NAME (field)))
2242                 continue;
2243
2244               /* True for duplicate members.  */
2245               if (IDENTIFIER_CLASS_VALUE (DECL_NAME (field)) != field)
2246                 continue;
2247             }
2248           else if ((t = TREE_TYPE (field)) != NULL_TREE
2249                    && TREE_CODE (t) == UNION_TYPE
2250                    && ANON_AGGRNAME_P (TYPE_IDENTIFIER (t))
2251                    && TYPE_FIELDS (t) != NULL_TREE)
2252             field = largest_union_member (t);
2253           else
2254             continue;
2255
2256           comp = build (COMPONENT_REF, TREE_TYPE (field), C_C_D, field);
2257           init = build (COMPONENT_REF, TREE_TYPE (field), parm, field);
2258
2259           expand_expr_stmt (build_modify_expr (comp, NOP_EXPR, init));
2260         }
2261     }
2262   c_expand_return (C_C_D);
2263   pop_momentary ();
2264 }
2265
2266 void
2267 synthesize_method (fndecl)
2268      tree fndecl;
2269 {
2270   int nested = (current_function_decl != NULL_TREE);
2271   tree context = hack_decl_function_context (fndecl);
2272   tree base = DECL_CLASS_CONTEXT (fndecl);
2273
2274   if (nested)
2275     push_cp_function_context (context);
2276
2277   interface_unknown = 1;
2278   start_function (NULL_TREE, fndecl, NULL_TREE, NULL_TREE, 1);
2279   store_parm_decls ();
2280
2281   if (DECL_NAME (fndecl) == ansi_opname[MODIFY_EXPR])
2282     do_build_assign_ref (fndecl);
2283   else if (DESTRUCTOR_NAME_P (DECL_ASSEMBLER_NAME (fndecl)))
2284     ;
2285   else
2286     {
2287       tree arg_chain = FUNCTION_ARG_CHAIN (fndecl);
2288       if (DECL_CONSTRUCTOR_FOR_VBASE_P (fndecl))
2289         arg_chain = TREE_CHAIN (arg_chain);
2290       if (arg_chain != void_list_node)
2291         do_build_copy_constructor (fndecl);
2292       else if (TYPE_NEEDS_CONSTRUCTING (current_class_type))
2293         setup_vtbl_ptr ();
2294     }
2295
2296   finish_function (lineno, 0, nested);
2297
2298   /* Do we really *want* to inline this function?  */
2299   if (DECL_INLINE (fndecl))
2300     {
2301       /* Turn off DECL_INLINE for the moment so function_cannot_inline_p
2302          will check our size.  */
2303       DECL_INLINE (fndecl) = 0;
2304       if (function_cannot_inline_p (fndecl) == 0)
2305         DECL_INLINE (fndecl) = 1;
2306     }
2307
2308   extract_interface_info ();
2309   if (nested)
2310     pop_cp_function_context (context);
2311 }