home *** CD-ROM | disk | FTP | other *** search
/ Fresh Fish 7 / FreshFishVol7.bin / bbs / gnu / gcc-2.3.3-src.lha / GNU / src / amiga / gcc-2.3.3 / c-common.c < prev    next >
C/C++ Source or Header  |  1994-02-06  |  30KB  |  1,010 lines

  1. /* Subroutines shared by all languages that are variants of C.
  2.    Copyright (C) 1992 Free Software Foundation, Inc.
  3.  
  4. This file is part of GNU CC.
  5.  
  6. GNU CC is free software; you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation; either version 2, or (at your option)
  9. any later version.
  10.  
  11. GNU CC is distributed in the hope that it will be useful,
  12. but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. GNU General Public License for more details.
  15.  
  16. You should have received a copy of the GNU General Public License
  17. along with GNU CC; see the file COPYING.  If not, write to
  18. the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  19.  
  20. #include "config.h"
  21. #include "tree.h"
  22. #include "c-lex.h"
  23. #include "c-tree.h"
  24. #include "flags.h"
  25. #include <stdio.h>
  26.  
  27. /* Make bindings for __FUNCTION__ and __PRETTY_FUNCTION__.  */
  28.  
  29. void
  30. declare_function_name ()
  31. {
  32.   tree decl, init;
  33.   char *name, *printable_name;
  34.  
  35.   if (current_function_decl == NULL)
  36.     {
  37.       name = "";
  38.       printable_name = "top level";
  39.     }
  40.   else
  41.     {
  42.       char *kind = "function";
  43.       if (TREE_CODE (TREE_TYPE (current_function_decl)) == METHOD_TYPE)
  44.     kind = "method";
  45.       /* Allow functions to be nameless (such as artificial ones).  */
  46.       if (DECL_NAME (current_function_decl))
  47.         name = IDENTIFIER_POINTER (DECL_NAME (current_function_decl));
  48.       else
  49.     name = "";
  50.       printable_name = (*decl_printable_name) (current_function_decl, &kind);
  51.     }
  52.  
  53.   push_obstacks_nochange ();
  54.   decl = build_decl (VAR_DECL, get_identifier ("__FUNCTION__"),
  55.              char_array_type_node);
  56.   TREE_STATIC (decl) = 1;
  57.   TREE_READONLY (decl) = 1;
  58.   DECL_SOURCE_LINE (decl) = 0;
  59.   DECL_IN_SYSTEM_HEADER (decl) = 1;
  60.   DECL_IGNORED_P (decl) = 1;
  61.   init = build_string (strlen (name) + 1, name);
  62.   TREE_TYPE (init) = char_array_type_node;
  63.   DECL_INITIAL (decl) = init;
  64.   finish_decl (pushdecl (decl), init, NULL_TREE);
  65.  
  66.   push_obstacks_nochange ();
  67.   decl = build_decl (VAR_DECL, get_identifier ("__PRETTY_FUNCTION__"),
  68.              char_array_type_node);
  69.   TREE_STATIC (decl) = 1;
  70.   TREE_READONLY (decl) = 1;
  71.   DECL_SOURCE_LINE (decl) = 0;
  72.   DECL_IN_SYSTEM_HEADER (decl) = 1;
  73.   DECL_IGNORED_P (decl) = 1;
  74.   init = build_string (strlen (printable_name) + 1, printable_name);
  75.   TREE_TYPE (init) = char_array_type_node;
  76.   DECL_INITIAL (decl) = init;
  77.   finish_decl (pushdecl (decl), init, NULL_TREE);
  78. }
  79.  
  80. /* Given a chain of STRING_CST nodes,
  81.    concatenate them into one STRING_CST
  82.    and give it a suitable array-of-chars data type.  */
  83.  
  84. tree
  85. combine_strings (strings)
  86.      tree strings;
  87. {
  88.   register tree value, t;
  89.   register int length = 1;
  90.   int wide_length = 0;
  91.   int wide_flag = 0;
  92.   int wchar_bytes = TYPE_PRECISION (wchar_type_node) / BITS_PER_UNIT;
  93.   int nchars;
  94.  
  95.   if (TREE_CHAIN (strings))
  96.     {
  97.       /* More than one in the chain, so concatenate.  */
  98.       register char *p, *q;
  99.  
  100.       /* Don't include the \0 at the end of each substring,
  101.      except for the last one.
  102.      Count wide strings and ordinary strings separately.  */
  103.       for (t = strings; t; t = TREE_CHAIN (t))
  104.     {
  105.       if (TREE_TYPE (t) == wchar_array_type_node)
  106.         {
  107.           wide_length += (TREE_STRING_LENGTH (t) - wchar_bytes);
  108.           wide_flag = 1;
  109.         }
  110.       else
  111.         length += (TREE_STRING_LENGTH (t) - 1);
  112.     }
  113.  
  114.       /* If anything is wide, the non-wides will be converted,
  115.      which makes them take more space.  */
  116.       if (wide_flag)
  117.     length = length * wchar_bytes + wide_length;
  118.  
  119.       p = savealloc (length);
  120.  
  121.       /* Copy the individual strings into the new combined string.
  122.      If the combined string is wide, convert the chars to ints
  123.      for any individual strings that are not wide.  */
  124.  
  125.       q = p;
  126.       for (t = strings; t; t = TREE_CHAIN (t))
  127.     {
  128.       int len = (TREE_STRING_LENGTH (t)
  129.              - ((TREE_TYPE (t) == wchar_array_type_node)
  130.             ? wchar_bytes : 1));
  131.       if ((TREE_TYPE (t) == wchar_array_type_node) == wide_flag)
  132.         {
  133.           bcopy (TREE_STRING_POINTER (t), q, len);
  134.           q += len;
  135.         }
  136.       else
  137.         {
  138.           int i;
  139.           for (i = 0; i < len; i++)
  140.         ((int *) q)[i] = TREE_STRING_POINTER (t)[i];
  141.           q += len * wchar_bytes;
  142.         }
  143.     }
  144.       if (wide_flag)
  145.     {
  146.       int i;
  147.       for (i = 0; i < wchar_bytes; i++)
  148.         *q++ = 0;
  149.     }
  150.       else
  151.     *q = 0;
  152.  
  153.       value = make_node (STRING_CST);
  154.       TREE_STRING_POINTER (value) = p;
  155.       TREE_STRING_LENGTH (value) = length;
  156.       TREE_CONSTANT (value) = 1;
  157.     }
  158.   else
  159.     {
  160.       value = strings;
  161.       length = TREE_STRING_LENGTH (value);
  162.       if (TREE_TYPE (value) == wchar_array_type_node)
  163.     wide_flag = 1;
  164.     }
  165.  
  166.   /* Compute the number of elements, for the array type.  */ 
  167.   nchars = wide_flag ? length / wchar_bytes : length;
  168.  
  169.   /* Create the array type for the string constant.
  170.      -Wwrite-strings says make the string constant an array of const char
  171.      so that copying it to a non-const pointer will get a warning.  */
  172.   if (warn_write_strings
  173.       && (! flag_traditional  && ! flag_writable_strings))
  174.     {
  175.       tree elements
  176.     = build_type_variant (wide_flag ? wchar_type_node : char_type_node,
  177.                   1, 0);
  178.       TREE_TYPE (value)
  179.     = build_array_type (elements,
  180.                 build_index_type (build_int_2 (nchars - 1, 0)));
  181.     }
  182.   else
  183.     TREE_TYPE (value)
  184.       = build_array_type (wide_flag ? wchar_type_node : char_type_node,
  185.               build_index_type (build_int_2 (nchars - 1, 0)));
  186.   TREE_CONSTANT (value) = 1;
  187.   TREE_STATIC (value) = 1;
  188.   return value;
  189. }
  190.  
  191. /* Process the attributes listed in ATTRIBUTES
  192.    and install them in DECL.  */
  193.  
  194. void
  195. decl_attributes (decl, attributes)
  196.      tree decl, attributes;
  197. {
  198.   tree a;
  199.   for (a = attributes; a; a = TREE_CHAIN (a))
  200.     if (TREE_VALUE (a) == get_identifier ("packed"))
  201.       {
  202.     if (TREE_CODE (decl) == FIELD_DECL)
  203.       DECL_PACKED (decl) = 1;
  204.     /* We can't set DECL_PACKED for a VAR_DECL, because the bit is
  205.        used for DECL_REGISTER.  It wouldn't mean anything anyway.  */
  206.       }
  207.     else if (TREE_VALUE (a) != 0
  208.          && TREE_CODE (TREE_VALUE (a)) == TREE_LIST
  209.          && TREE_PURPOSE (TREE_VALUE (a)) == get_identifier ("mode"))
  210.       {
  211.     int i;
  212.     char *specified_name
  213.       = IDENTIFIER_POINTER (TREE_VALUE (TREE_VALUE (a)));
  214.  
  215.     /* Give this decl a type with the specified mode.  */
  216.     for (i = 0; i < NUM_MACHINE_MODES; i++)
  217.       if (!strcmp (specified_name, GET_MODE_NAME (i)))
  218.         {
  219.           tree type
  220.         = type_for_mode (i, TREE_UNSIGNED (TREE_TYPE (decl)));
  221.           if (type != 0)
  222.         {
  223.           TREE_TYPE (decl) = type;
  224.           DECL_SIZE (decl) = 0;
  225.           layout_decl (decl, 0);
  226.         }
  227.           else
  228.         error ("no data type for mode `%s'", specified_name);
  229.           break;
  230.         }
  231.     if (i == NUM_MACHINE_MODES)
  232.       error ("unknown machine mode `%s'", specified_name);
  233.       }
  234.     else if (TREE_VALUE (a) != 0
  235.          && TREE_CODE (TREE_VALUE (a)) == TREE_LIST
  236.          && TREE_PURPOSE (TREE_VALUE (a)) == get_identifier ("aligned"))
  237.       {
  238.     int align = TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (a)))
  239.             * BITS_PER_UNIT;
  240.     
  241.     if (exact_log2 (align) == -1)
  242.       error_with_decl (decl,
  243.                "requested alignment of `%s' is not a power of 2");
  244.     else if (TREE_CODE (decl) != VAR_DECL
  245.          && TREE_CODE (decl) != FIELD_DECL)
  246.       error_with_decl (decl,
  247.                "alignment specified for `%s'");
  248.     else
  249.       DECL_ALIGN (decl) = align;
  250.       }
  251.     else if (TREE_VALUE (a) != 0
  252.          && TREE_CODE (TREE_VALUE (a)) == TREE_LIST
  253.          && TREE_PURPOSE (TREE_VALUE (a)) == get_identifier ("format"))
  254.       {
  255.         tree list = TREE_VALUE (TREE_VALUE (a));
  256.         tree format_type = TREE_PURPOSE (list);
  257.     int format_num = TREE_INT_CST_LOW (TREE_PURPOSE (TREE_VALUE (list)));
  258.     int first_arg_num = TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (list)));
  259.     int is_scan;
  260.     
  261.     if (TREE_CODE (decl) != FUNCTION_DECL)
  262.       {
  263.         error_with_decl (decl,
  264.                  "argument format specified for non-function `%s'");
  265.         return;
  266.       }
  267.     
  268.     if (format_type == get_identifier ("printf"))
  269.       is_scan = 0;
  270.     else if (format_type == get_identifier ("scanf"))
  271.       is_scan = 1;
  272.     else
  273.       {
  274.         error_with_decl (decl, "unrecognized format specifier for `%s'");
  275.         return;
  276.       }
  277.     
  278.     if (first_arg_num != 0 && first_arg_num <= format_num)
  279.       {
  280.         error_with_decl