| /* Copyright (C) 1992, 1993, 1994, 1998 Free Software Foundation, Inc. |
| |
| This file is part of GNU CC. |
| |
| GNU CC is free software; you can redistribute it and/or modify |
| it under the terms of the GNU General Public License as published by |
| the Free Software Foundation; either version 2, or (at your option) |
| any later version. |
| |
| GNU CC is distributed in the hope that it will be useful, |
| but WITHOUT ANY WARRANTY; without even the implied warranty of |
| MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| GNU General Public License for more details. |
| |
| You should have received a copy of the GNU General Public License |
| along with GNU CC; see the file COPYING. If not, write to |
| the Free Software Foundation, 59 Temple Place - Suite 330, |
| Boston, MA 02111-1307, USA. */ |
| |
| |
| #if 0 |
| tree |
| build_component_ref (datum, field_name) |
| tree datum, field_name; |
| { |
| return build_chill_component_ref (datum, field_name); |
| } |
| |
| /* Mark EXP saying that we need to be able to take the |
| address of it; it should not be allocated in a register. |
| Value is 1 if successful. */ |
| |
| int |
| mark_addressable (exp) |
| tree exp; |
| { |
| register tree x = exp; |
| while (1) |
| switch (TREE_CODE (x)) |
| { |
| case ADDR_EXPR: |
| case COMPONENT_REF: |
| case ARRAY_REF: |
| case REALPART_EXPR: |
| case IMAGPART_EXPR: |
| x = TREE_OPERAND (x, 0); |
| break; |
| |
| case CONSTRUCTOR: |
| TREE_ADDRESSABLE (x) = 1; |
| return 1; |
| |
| case VAR_DECL: |
| case CONST_DECL: |
| case PARM_DECL: |
| case RESULT_DECL: |
| if (DECL_REGISTER (x) && !TREE_ADDRESSABLE (x) |
| && DECL_NONLOCAL (x)) |
| { |
| if (TREE_PUBLIC (x)) |
| { |
| error ("global register variable `%s' used in nested function", |
| IDENTIFIER_POINTER (DECL_NAME (x))); |
| return 0; |
| } |
| pedwarn ("register variable `%s' used in nested function", |
| IDENTIFIER_POINTER (DECL_NAME (x))); |
| } |
| else if (DECL_REGISTER (x) && !TREE_ADDRESSABLE (x)) |
| { |
| if (TREE_PUBLIC (x)) |
| { |
| error ("address of global register variable `%s' requested", |
| IDENTIFIER_POINTER (DECL_NAME (x))); |
| return 0; |
| } |
| |
| /* If we are making this addressable due to its having |
| volatile components, give a different error message. Also |
| handle the case of an unnamed parameter by not trying |
| to give the name. */ |
| |
| else if (C_TYPE_FIELDS_VOLATILE (TREE_TYPE (x))) |
| { |
| error ("cannot put object with volatile field into register"); |
| return 0; |
| } |
| |
| pedwarn ("address of register variable `%s' requested", |
| IDENTIFIER_POINTER (DECL_NAME (x))); |
| } |
| put_var_into_stack (x); |
| |
| /* drops in */ |
| case FUNCTION_DECL: |
| TREE_ADDRESSABLE (x) = 1; |
| #if 0 /* poplevel deals with this now. */ |
| if (DECL_CONTEXT (x) == 0) |
| TREE_ADDRESSABLE (DECL_ASSEMBLER_NAME (x)) = 1; |
| #endif |
| |
| default: |
| return 1; |
| } |
| } |
| |
| /* Return an unsigned type the same as TYPE in other respects. */ |
| |
| tree |
| unsigned_type (type) |
| tree type; |
| { |
| tree type1 = TYPE_MAIN_VARIANT (type); |
| if (type1 == signed_char_type_node || type1 == char_type_node) |
| return unsigned_char_type_node; |
| if (type1 == integer_type_node) |
| return unsigned_type_node; |
| if (type1 == short_integer_type_node) |
| return short_unsigned_type_node; |
| if (type1 == long_integer_type_node) |
| return long_unsigned_type_node; |
| if (type1 == long_long_integer_type_node) |
| return long_long_unsigned_type_node; |
| return type; |
| } |
| |
| /* Return a signed type the same as TYPE in other respects. */ |
| |
| tree |
| signed_type (type) |
| tree type; |
| { |
| tree type1 = TYPE_MAIN_VARIANT (type); |
| if (type1 == unsigned_char_type_node || type1 == char_type_node) |
| return signed_char_type_node; |
| if (type1 == unsigned_type_node) |
| return integer_type_node; |
| if (type1 == short_unsigned_type_node) |
| return short_integer_type_node; |
| if (type1 == long_unsigned_type_node) |
| return long_integer_type_node; |
| if (type1 == long_long_unsigned_type_node) |
| return long_long_integer_type_node; |
| return type; |
| } |
| |
| /* Return a type the same as TYPE except unsigned or |
| signed according to UNSIGNEDP. */ |
| |
| tree |
| signed_or_unsigned_type (unsignedp, type) |
| int unsignedp; |
| tree type; |
| { |
| if (! INTEGRAL_TYPE_P (type)) |
| return type; |
| if (TYPE_PRECISION (type) == TYPE_PRECISION (signed_char_type_node)) |
| return unsignedp ? unsigned_char_type_node : signed_char_type_node; |
| if (TYPE_PRECISION (type) == TYPE_PRECISION (integer_type_node)) |
| return unsignedp ? unsigned_type_node : integer_type_node; |
| if (TYPE_PRECISION (type) == TYPE_PRECISION (short_integer_type_node)) |
| return unsignedp ? short_unsigned_type_node : short_integer_type_node; |
| if (TYPE_PRECISION (type) == TYPE_PRECISION (long_integer_type_node)) |
| return unsignedp ? long_unsigned_type_node : long_integer_type_node; |
| if (TYPE_PRECISION (type) == TYPE_PRECISION (long_long_integer_type_node)) |
| return (unsignedp ? long_long_unsigned_type_node |
| : long_long_integer_type_node); |
| return type; |
| } |
| |
| extern tree intHI_type_node; |
| extern tree intSI_type_node; |
| extern tree intDI_type_node; |
| |
| extern tree unsigned_intHI_type_node; |
| extern tree unsigned_intSI_type_node; |
| extern tree unsigned_intDI_type_node; |
| |
| /* Return an integer type with BITS bits of precision, |
| that is unsigned if UNSIGNEDP is nonzero, otherwise signed. */ |
| |
| tree |
| type_for_size (bits, unsignedp) |
| unsigned bits; |
| int unsignedp; |
| { |
| if (bits == TYPE_PRECISION (signed_char_type_node)) |
| return unsignedp ? unsigned_char_type_node : signed_char_type_node; |
| |
| if (bits == TYPE_PRECISION (short_integer_type_node)) |
| return unsignedp ? short_unsigned_type_node : short_integer_type_node; |
| |
| if (bits == TYPE_PRECISION (integer_type_node)) |
| return unsignedp ? unsigned_type_node : integer_type_node; |
| |
| if (bits == TYPE_PRECISION (long_integer_type_node)) |
| return unsignedp ? long_unsigned_type_node : long_integer_type_node; |
| |
| if (bits == TYPE_PRECISION (long_long_integer_type_node)) |
| return (unsignedp ? long_long_unsigned_type_node |
| : long_long_integer_type_node); |
| |
| if (bits <= TYPE_PRECISION (intHI_type_node)) |
| return unsignedp ? unsigned_intHI_type_node : intHI_type_node; |
| |
| if (bits <= TYPE_PRECISION (intSI_type_node)) |
| return unsignedp ? unsigned_intSI_type_node : intSI_type_node; |
| |
| if (bits <= TYPE_PRECISION (intDI_type_node)) |
| return unsignedp ? unsigned_intDI_type_node : intDI_type_node; |
| |
| return 0; |
| } |
| |
| /* Return a data type that has machine mode MODE. |
| If the mode is an integer, |
| then UNSIGNEDP selects between signed and unsigned types. */ |
| |
| tree |
| type_for_mode (mode, unsignedp) |
| enum machine_mode mode; |
| int unsignedp; |
| { |
| if (mode == TYPE_MODE (signed_char_type_node)) |
| return unsignedp ? unsigned_char_type_node : signed_char_type_node; |
| |
| if (mode == TYPE_MODE (short_integer_type_node)) |
| return unsignedp ? short_unsigned_type_node : short_integer_type_node; |
| |
| if (mode == TYPE_MODE (integer_type_node)) |
| return unsignedp ? unsigned_type_node : integer_type_node; |
| |
| if (mode == TYPE_MODE (long_integer_type_node)) |
| return unsignedp ? long_unsigned_type_node : long_integer_type_node; |
| |
| if (mode == TYPE_MODE (long_long_integer_type_node)) |
| return unsignedp ? long_long_unsigned_type_node : long_long_integer_type_node; |
| |
| if (mode == TYPE_MODE (intHI_type_node)) |
| return unsignedp ? unsigned_intHI_type_node : intHI_type_node; |
| |
| if (mode == TYPE_MODE (intSI_type_node)) |
| return unsignedp ? unsigned_intSI_type_node : intSI_type_node; |
| |
| if (mode == TYPE_MODE (intDI_type_node)) |
| return unsignedp ? unsigned_intDI_type_node : intDI_type_node; |
| |
| if (mode == TYPE_MODE (float_type_node)) |
| return float_type_node; |
| |
| if (mode == TYPE_MODE (double_type_node)) |
| return double_type_node; |
| |
| if (mode == TYPE_MODE (long_double_type_node)) |
| return long_double_type_node; |
| |
| if (mode == TYPE_MODE (build_pointer_type (char_type_node))) |
| return build_pointer_type (char_type_node); |
| |
| if (mode == TYPE_MODE (build_pointer_type (integer_type_node))) |
| return build_pointer_type (integer_type_node); |
| |
| return 0; |
| } |
| |
| tree |
| truthvalue_conversion (expr) |
| tree expr; |
| { |
| return chill_truthvalue_conversion (expr); |
| } |
| #endif |