1 /* Process expressions for the GNU compiler for the Java(TM) language.
2 Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001
3 Free Software Foundation, Inc.
5 This file is part of GNU CC.
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING. If not, write to
19 the Free Software Foundation, 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA.
22 Java and all Java-based marks are trademarks or registered trademarks
23 of Sun Microsystems, Inc. in the United States and other countries.
24 The Free Software Foundation is independent of Sun Microsystems, Inc. */
26 /* Hacked by Per Bothner <bothner@cygnus.com> February 1996. */
35 #include "java-tree.h"
37 #include "java-opcodes.h"
39 #include "java-except.h"
45 static void flush_quick_stack
PARAMS ((void));
46 static void push_value
PARAMS ((tree
));
47 static tree pop_value
PARAMS ((tree
));
48 static void java_stack_swap
PARAMS ((void));
49 static void java_stack_dup
PARAMS ((int, int));
50 static void build_java_athrow
PARAMS ((tree
));
51 static void build_java_jsr
PARAMS ((tree
, tree
));
52 static void build_java_ret
PARAMS ((tree
));
53 static void expand_java_multianewarray
PARAMS ((tree
, int));
54 static void expand_java_arraystore
PARAMS ((tree
));
55 static void expand_java_arrayload
PARAMS ((tree
));
56 static void expand_java_array_length
PARAMS ((void));
57 static tree build_java_monitor
PARAMS ((tree
, tree
));
58 static void expand_java_pushc
PARAMS ((int, tree
));
59 static void expand_java_return
PARAMS ((tree
));
60 static void expand_java_NEW
PARAMS ((tree
));
61 static void expand_java_INSTANCEOF
PARAMS ((tree
));
62 static void expand_java_CHECKCAST
PARAMS ((tree
));
63 static void expand_iinc
PARAMS ((unsigned int, int, int));
64 static void expand_java_binop
PARAMS ((tree
, enum tree_code
));
65 static void note_label
PARAMS ((int, int));
66 static void expand_compare
PARAMS ((enum tree_code
, tree
, tree
, int));
67 static void expand_test
PARAMS ((enum tree_code
, tree
, int));
68 static void expand_cond
PARAMS ((enum tree_code
, tree
, int));
69 static void expand_java_goto
PARAMS ((int));
71 static void expand_java_call
PARAMS ((int, int));
72 static void expand_java_ret
PARAMS ((tree
));
74 static tree pop_arguments
PARAMS ((tree
));
75 static void expand_invoke
PARAMS ((int, int, int));
76 static void expand_java_field_op
PARAMS ((int, int, int));
77 static void java_push_constant_from_pool
PARAMS ((struct JCF
*, int));
78 static void java_stack_pop
PARAMS ((int));
79 static tree build_java_throw_out_of_bounds_exception
PARAMS ((tree
));
80 static tree build_java_check_indexed_type
PARAMS ((tree
, tree
));
81 static tree java_array_data_offset
PARAMS ((tree
));
82 static tree case_identity
PARAMS ((tree
, tree
));
83 static unsigned char peek_opcode_at_pc
PARAMS ((struct JCF
*, int, int));
85 static tree operand_type
[59];
86 extern struct obstack permanent_obstack
;
88 static tree methods_ident
= NULL_TREE
;
89 static tree ncode_ident
= NULL_TREE
;
90 tree dtable_ident
= NULL_TREE
;
92 /* Set to non-zero value in order to emit class initilization code
93 before static field references. */
94 int always_initialize_class_p
;
96 /* We store the stack state in two places:
97 Within a basic block, we use the quick_stack, which is a
98 pushdown list (TREE_LISTs) of expression nodes.
99 This is the top part of the stack; below that we use find_stack_slot.
100 At the end of a basic block, the quick_stack must be flushed
101 to the stack slot array (as handled by find_stack_slot).
102 Using quick_stack generates better code (especially when
103 compiled without optimization), because we do not have to
104 explicitly store and load trees to temporary variables.
106 If a variable is on the quick stack, it means the value of variable
107 when the quick stack was last flushed. Conceptually, flush_quick_stack
108 saves all the the quick_stack elements in parellel. However, that is
109 complicated, so it actually saves them (i.e. copies each stack value
110 to is home virtual register) from low indexes. This allows a quick_stack
111 element at index i (counting from the bottom of stack the) to references
112 slot virtuals for register that are >= i, but not those that are deeper.
113 This convention makes most operations easier. For example iadd works
114 even when the stack contains (reg[0], reg[1]): It results in the
115 stack containing (reg[0]+reg[1]), which is OK. However, some stack
116 operations are more complicated. For example dup given a stack
117 containing (reg[0]) would yield (reg[0], reg[0]), which would violate
118 the convention, since stack value 1 would refer to a register with
119 lower index (reg[0]), which flush_quick_stack does not safely handle.
120 So dup cannot just add an extra element to the quick_stack, but iadd can.
123 static tree quick_stack
= NULL_TREE
;
125 /* A free-list of unused permamnet TREE_LIST nodes. */
126 static tree tree_list_free_list
= NULL_TREE
;
128 /* The stack pointer of the Java virtual machine.
129 This does include the size of the quick_stack. */
133 const unsigned char *linenumber_table
;
134 int linenumber_count
;
137 init_expr_processing()
139 operand_type
[21] = operand_type
[54] = int_type_node
;
140 operand_type
[22] = operand_type
[55] = long_type_node
;
141 operand_type
[23] = operand_type
[56] = float_type_node
;
142 operand_type
[24] = operand_type
[57] = double_type_node
;
143 operand_type
[25] = operand_type
[58] = ptr_type_node
;
144 ggc_add_tree_root (operand_type
, 59);
145 ggc_add_tree_root (&methods_ident
, 1);
146 ggc_add_tree_root (&ncode_ident
, 1);
147 ggc_add_tree_root (&quick_stack
, 1);
148 ggc_add_tree_root (&tree_list_free_list
, 1);
152 truthvalue_conversion (expr
)
155 /* It is simpler and generates better code to have only TRUTH_*_EXPR
156 or comparison expressions as truth values at this level.
158 This function should normally be identity for Java. */
160 switch (TREE_CODE (expr
))
163 case NE_EXPR
: case LE_EXPR
: case GE_EXPR
: case LT_EXPR
: case GT_EXPR
:
164 case TRUTH_ANDIF_EXPR
:
165 case TRUTH_ORIF_EXPR
:
172 return integer_zerop (expr
) ? boolean_false_node
: boolean_true_node
;
175 return real_zerop (expr
) ? boolean_false_node
: boolean_true_node
;
177 /* are these legal? XXX JH */
182 /* These don't change whether an object is non-zero or zero. */
183 return truthvalue_conversion (TREE_OPERAND (expr
, 0));
186 /* Distribute the conversion into the arms of a COND_EXPR. */
187 return fold (build (COND_EXPR
, boolean_type_node
, TREE_OPERAND (expr
, 0),
188 truthvalue_conversion (TREE_OPERAND (expr
, 1)),
189 truthvalue_conversion (TREE_OPERAND (expr
, 2))));
192 /* If this is widening the argument, we can ignore it. */
193 if (TYPE_PRECISION (TREE_TYPE (expr
))
194 >= TYPE_PRECISION (TREE_TYPE (TREE_OPERAND (expr
, 0))))
195 return truthvalue_conversion (TREE_OPERAND (expr
, 0));
196 /* fall through to default */
199 return fold (build (NE_EXPR
, boolean_type_node
, expr
, boolean_false_node
));
203 #ifdef JAVA_USE_HANDLES
204 /* Given a pointer to a handle, get a pointer to an object. */
210 tree field
, handle_type
;
211 expr
= build1 (INDIRECT_REF
, TREE_TYPE (TREE_TYPE (expr
)), expr
);
212 handle_type
= TREE_TYPE (expr
);
213 field
= TYPE_FIELDS (handle_type
);
214 expr
= build (COMPONENT_REF
, TREE_TYPE (field
), expr
, field
);
219 /* Save any stack slots that happen to be in the quick_stack into their
220 home virtual register slots.
222 The copy order is from low stack index to high, to support the invariant
223 that the expression for a slot may contain decls for stack slots with
224 higher (or the same) index, but not lower. */
229 int stack_index
= stack_pointer
;
230 register tree prev
, cur
, next
;
232 /* First reverse the quick_stack, and count the number of slots it has. */
233 for (cur
= quick_stack
, prev
= NULL_TREE
; cur
!= NULL_TREE
; cur
= next
)
235 next
= TREE_CHAIN (cur
);
236 TREE_CHAIN (cur
) = prev
;
238 stack_index
-= 1 + TYPE_IS_WIDE (TREE_TYPE (TREE_VALUE (cur
)));
242 while (quick_stack
!= NULL_TREE
)
245 tree node
= quick_stack
, type
;
246 quick_stack
= TREE_CHAIN (node
);
247 TREE_CHAIN (node
) = tree_list_free_list
;
248 tree_list_free_list
= node
;
249 node
= TREE_VALUE (node
);
250 type
= TREE_TYPE (node
);
252 decl
= find_stack_slot (stack_index
, type
);
254 expand_assignment (decl
, node
, 0, 0);
255 stack_index
+= 1 + TYPE_IS_WIDE (type
);
259 /* Push TYPE on the type stack.
260 Return true on success, 0 on overflow. */
267 type
= promote_type (type
);
268 n_words
= 1 + TYPE_IS_WIDE (type
);
269 if (stack_pointer
+ n_words
> DECL_MAX_STACK (current_function_decl
))
271 stack_type_map
[stack_pointer
++] = type
;
273 while (--n_words
>= 0)
274 stack_type_map
[stack_pointer
++] = TYPE_SECOND
;
282 if (! push_type_0 (type
))
290 tree type
= TREE_TYPE (value
);
291 if (TYPE_PRECISION (type
) < 32 && INTEGRAL_TYPE_P (type
))
293 type
= promote_type (type
);
294 value
= convert (type
, value
);
297 if (tree_list_free_list
== NULL_TREE
)
298 quick_stack
= tree_cons (NULL_TREE
, value
, quick_stack
);
301 tree node
= tree_list_free_list
;
302 tree_list_free_list
= TREE_CHAIN (tree_list_free_list
);
303 TREE_VALUE (node
) = value
;
304 TREE_CHAIN (node
) = quick_stack
;
309 /* Pop a type from the type stack.
310 TYPE is the expected type. Return the actual type, which must be
312 On an error, *MESSAGEP is set to a freshly malloc'd error message. */
315 pop_type_0 (type
, messagep
)
322 if (TREE_CODE (type
) == RECORD_TYPE
)
323 type
= promote_type (type
);
324 n_words
= 1 + TYPE_IS_WIDE (type
);
325 if (stack_pointer
< n_words
)
327 *messagep
= xstrdup ("stack underflow");
330 while (--n_words
> 0)
332 if (stack_type_map
[--stack_pointer
] != void_type_node
)
334 *messagep
= xstrdup ("Invalid multi-word value on type stack");
338 t
= stack_type_map
[--stack_pointer
];
339 if (type
== NULL_TREE
|| t
== type
)
341 if (INTEGRAL_TYPE_P (type
) && INTEGRAL_TYPE_P (t
)
342 && TYPE_PRECISION (type
) <= 32 && TYPE_PRECISION (t
) <= 32)
344 if (TREE_CODE (type
) == POINTER_TYPE
&& TREE_CODE (t
) == POINTER_TYPE
)
346 if (type
== ptr_type_node
|| type
== object_ptr_type_node
)
348 else if (t
== ptr_type_node
) /* Special case for null reference. */
350 else if (can_widen_reference_to (t
, type
))
352 /* This is a kludge, but matches what Sun's verifier does.
353 It can be tricked, but is safe as long as type errors
354 (i.e. interface method calls) are caught at run-time. */
355 else if (CLASS_INTERFACE (TYPE_NAME (TREE_TYPE (type
))))
356 return object_ptr_type_node
;
359 const char *str1
= "expected type '";
360 const char *str3
= "' but stack contains '";
361 const char *str5
= "'";
362 int len1
= strlen (str1
);
363 int len2
= strlen (lang_printable_name (type
, 0));
364 int len3
= strlen (str3
);
365 int len4
= strlen (lang_printable_name (t
, 0));
366 int len5
= strlen (str5
);
367 char *msg
= xmalloc (len1
+ len2
+ len3
+ len4
+ len5
+ 1);
369 strcpy (msg
, str1
); msg
+= len1
;
370 strcpy (msg
, lang_printable_name (type
, 0)); msg
+= len2
;
371 strcpy (msg
, str3
); msg
+= len3
;
372 strcpy (msg
, lang_printable_name (t
, 0)); msg
+= len4
;
378 /* Pop a type from the type stack.
379 TYPE is the expected type. Return the actual type, which must be
380 convertible to TYPE, otherwise call error. */
386 char *message
= NULL
;
387 type
= pop_type_0 (type
, &message
);
396 /* Return 1f if SOURCE_TYPE can be safely widened to TARGET_TYPE.
397 Handles array types and interfaces. */
400 can_widen_reference_to (source_type
, target_type
)
401 tree source_type
, target_type
;
403 if (source_type
== ptr_type_node
|| target_type
== object_ptr_type_node
)
406 /* Get rid of pointers */
407 if (TREE_CODE (source_type
) == POINTER_TYPE
)
408 source_type
= TREE_TYPE (source_type
);
409 if (TREE_CODE (target_type
) == POINTER_TYPE
)
410 target_type
= TREE_TYPE (target_type
);
412 if (source_type
== target_type
)
416 source_type
= HANDLE_TO_CLASS_TYPE (source_type
);
417 target_type
= HANDLE_TO_CLASS_TYPE (target_type
);
418 if (TYPE_ARRAY_P (source_type
) || TYPE_ARRAY_P (target_type
))
420 HOST_WIDE_INT source_length
, target_length
;
421 if (TYPE_ARRAY_P (source_type
) != TYPE_ARRAY_P (target_type
))
423 target_length
= java_array_type_length (target_type
);
424 if (target_length
>= 0)
426 source_length
= java_array_type_length (source_type
);
427 if (source_length
!= target_length
)
430 source_type
= TYPE_ARRAY_ELEMENT (source_type
);
431 target_type
= TYPE_ARRAY_ELEMENT (target_type
);
432 if (source_type
== target_type
)
434 if (TREE_CODE (source_type
) != POINTER_TYPE
435 || TREE_CODE (target_type
) != POINTER_TYPE
)
437 return can_widen_reference_to (source_type
, target_type
);
441 int source_depth
= class_depth (source_type
);
442 int target_depth
= class_depth (target_type
);
444 /* class_depth can return a negative depth if an error occurred */
445 if (source_depth
< 0 || target_depth
< 0)
448 if (CLASS_INTERFACE (TYPE_NAME (target_type
)))
450 /* target_type is OK if source_type or source_type ancestors
451 implement target_type. We handle multiple sub-interfaces */
453 tree basetype_vec
= TYPE_BINFO_BASETYPES (source_type
);
454 int n
= TREE_VEC_LENGTH (basetype_vec
), i
;
455 for (i
=0 ; i
< n
; i
++)
456 if (can_widen_reference_to
457 (TREE_TYPE (TREE_VEC_ELT (basetype_vec
, i
)),
464 for ( ; source_depth
> target_depth
; source_depth
--)
466 source_type
= TYPE_BINFO_BASETYPE (source_type
, 0);
468 return source_type
== target_type
;
477 type
= pop_type (type
);
480 tree node
= quick_stack
;
481 quick_stack
= TREE_CHAIN (quick_stack
);
482 TREE_CHAIN (node
) = tree_list_free_list
;
483 tree_list_free_list
= node
;
484 node
= TREE_VALUE (node
);
488 return find_stack_slot (stack_pointer
, promote_type (type
));
492 /* Pop and discrad the top COUNT stack slots. */
495 java_stack_pop (count
)
502 if (stack_pointer
== 0)
505 type
= stack_type_map
[stack_pointer
- 1];
506 if (type
== TYPE_SECOND
)
509 if (stack_pointer
== 1 || count
<= 0)
512 type
= stack_type_map
[stack_pointer
- 2];
514 val
= pop_value (type
);
519 /* Implement the 'swap' operator (to swap two top stack slots). */
528 if (stack_pointer
< 2
529 || (type1
= stack_type_map
[stack_pointer
- 1]) == TYPE_UNKNOWN
530 || (type2
= stack_type_map
[stack_pointer
- 2]) == TYPE_UNKNOWN
531 || type1
== TYPE_SECOND
|| type2
== TYPE_SECOND
532 || TYPE_IS_WIDE (type1
) || TYPE_IS_WIDE (type2
))
533 /* Bad stack swap. */
536 flush_quick_stack ();
537 decl1
= find_stack_slot (stack_pointer
- 1, type1
);
538 decl2
= find_stack_slot (stack_pointer
- 2, type2
);
539 temp
= copy_to_reg (DECL_RTL (decl1
));
540 emit_move_insn (DECL_RTL (decl1
), DECL_RTL (decl2
));
541 emit_move_insn (DECL_RTL (decl2
), temp
);
542 stack_type_map
[stack_pointer
- 1] = type2
;
543 stack_type_map
[stack_pointer
- 2] = type1
;
547 java_stack_dup (size
, offset
)
550 int low_index
= stack_pointer
- size
- offset
;
553 error ("stack underflow - dup* operation");
555 flush_quick_stack ();
557 stack_pointer
+= size
;
558 dst_index
= stack_pointer
;
560 for (dst_index
= stack_pointer
; --dst_index
>= low_index
; )
563 int src_index
= dst_index
- size
;
564 if (src_index
< low_index
)
565 src_index
= dst_index
+ size
+ offset
;
566 type
= stack_type_map
[src_index
];
567 if (type
== TYPE_SECOND
)
569 if (src_index
<= low_index
)
570 /* Dup operation splits 64-bit number. */
573 stack_type_map
[dst_index
] = type
;
574 src_index
--; dst_index
--;
575 type
= stack_type_map
[src_index
];
576 if (! TYPE_IS_WIDE (type
))
579 else if (TYPE_IS_WIDE (type
))
582 if (src_index
!= dst_index
)
584 tree src_decl
= find_stack_slot (src_index
, type
);
585 tree dst_decl
= find_stack_slot (dst_index
, type
);
586 emit_move_insn (DECL_RTL (dst_decl
), DECL_RTL (src_decl
));
587 stack_type_map
[dst_index
] = type
;
592 /* Calls _Jv_Throw or _Jv_Sjlj_Throw. Discard the contents of the
596 build_java_athrow (node
)
601 call
= build (CALL_EXPR
,
603 build_address_of (throw_node
[USING_SJLJ_EXCEPTIONS
? 1 : 0]),
604 build_tree_list (NULL_TREE
, node
),
606 TREE_SIDE_EFFECTS (call
) = 1;
607 expand_expr_stmt (call
);
608 java_stack_pop (stack_pointer
);
611 /* Implementation for jsr/ret */
614 build_java_jsr (where
, ret
)
618 tree ret_label
= fold (build1 (ADDR_EXPR
, return_address_type_node
, ret
));
619 push_value (ret_label
);
620 flush_quick_stack ();
621 emit_jump (label_rtx (where
));
626 build_java_ret (location
)
629 expand_computed_goto (location
);
632 /* Implementation of operations on array: new, load, store, length */
634 /* Array core info access macros */
636 #define JAVA_ARRAY_LENGTH_OFFSET(A) \
637 byte_position (TREE_CHAIN (TYPE_FIELDS (TREE_TYPE (TREE_TYPE (A)))))
640 decode_newarray_type (atype
)
645 case 4: return boolean_type_node
;
646 case 5: return char_type_node
;
647 case 6: return float_type_node
;
648 case 7: return double_type_node
;
649 case 8: return byte_type_node
;
650 case 9: return short_type_node
;
651 case 10: return int_type_node
;
652 case 11: return long_type_node
;
653 default: return NULL_TREE
;
657 /* Map primitive type to the code used by OPCODE_newarray. */
660 encode_newarray_type (type
)
663 if (type
== boolean_type_node
)
665 else if (type
== char_type_node
)
667 else if (type
== float_type_node
)
669 else if (type
== double_type_node
)
671 else if (type
== byte_type_node
)
673 else if (type
== short_type_node
)
675 else if (type
== int_type_node
)
677 else if (type
== long_type_node
)
683 /* Build a call to _Jv_ThrowBadArrayIndex(), the
684 ArrayIndexOfBoundsException exception handler. */
687 build_java_throw_out_of_bounds_exception (index
)
690 tree node
= build (CALL_EXPR
, int_type_node
,
691 build_address_of (soft_badarrayindex_node
),
692 build_tree_list (NULL_TREE
, index
), NULL_TREE
);
693 TREE_SIDE_EFFECTS (node
) = 1; /* Allows expansion within ANDIF */
697 /* Return the length of an array. Doesn't perform any checking on the nature
698 or value of the array NODE. May be used to implement some bytecodes. */
701 build_java_array_length_access (node
)
704 tree type
= TREE_TYPE (node
);
705 HOST_WIDE_INT length
;
707 if (!is_array_type_p (type
))
710 length
= java_array_type_length (type
);
712 return build_int_2 (length
, 0);
713 return fold (build1 (INDIRECT_REF
, int_type_node
,
714 fold (build (PLUS_EXPR
, ptr_type_node
,
715 java_check_reference (node
, 1),
716 JAVA_ARRAY_LENGTH_OFFSET(node
)))));
719 /* Optionally checks a reference against the NULL pointer. ARG1: the
720 expr, ARG2: we should check the reference. Don't generate extra
721 checks if we're not generating code. */
724 java_check_reference (expr
, check
)
728 if (!flag_syntax_only
&& check
)
731 expr
= save_expr (expr
);
732 cond
= build (COND_EXPR
, void_type_node
,
733 build (EQ_EXPR
, boolean_type_node
, expr
, null_pointer_node
),
734 build (CALL_EXPR
, void_type_node
,
735 build_address_of (soft_nullpointer_node
),
736 NULL_TREE
, NULL_TREE
),
738 expr
= build (COMPOUND_EXPR
, TREE_TYPE (expr
), cond
, expr
);
744 /* Reference an object: just like an INDIRECT_REF, but with checking. */
747 build_java_indirect_ref (type
, expr
, check
)
752 return build1 (INDIRECT_REF
, type
, java_check_reference (expr
, check
));
756 java_array_data_offset (array
)
759 tree array_type
= TREE_TYPE (TREE_TYPE (array
));
760 tree data_fld
= TREE_CHAIN (TREE_CHAIN (TYPE_FIELDS (array_type
)));
762 if (data_fld
== NULL_TREE
)
763 return size_in_bytes (array_type
);
765 return byte_position (data_fld
);
768 /* Implement array indexing (either as l-value or r-value).
769 Returns a tree for ARRAY[INDEX], assume TYPE is the element type.
770 Optionally performs bounds checking and/or test to NULL.
771 At this point, ARRAY should have been verified as an array. */
774 build_java_arrayaccess (array
, type
, index
)
775 tree array
, type
, index
;
777 tree arith
, node
, throw = NULL_TREE
;
779 arith
= fold (build (PLUS_EXPR
, int_type_node
,
780 java_array_data_offset (array
),
781 fold (build (MULT_EXPR
, int_type_node
,
782 index
, size_in_bytes(type
)))));
784 if (flag_bounds_check
)
787 * (unsigned jint) INDEX >= (unsigned jint) LEN
788 * && throw ArrayIndexOutOfBoundsException.
789 * Note this is equivalent to and more efficient than:
790 * INDEX < 0 || INDEX >= LEN && throw ... */
792 tree len
= build_java_array_length_access (array
);
793 TREE_TYPE (len
) = unsigned_int_type_node
;
794 test
= fold (build (GE_EXPR
, boolean_type_node
,
795 convert (unsigned_int_type_node
, index
),
797 if (! integer_zerop (test
))
799 throw = build (TRUTH_ANDIF_EXPR
, int_type_node
, test
,
800 build_java_throw_out_of_bounds_exception (index
));
801 /* allows expansion within COMPOUND */
802 TREE_SIDE_EFFECTS( throw ) = 1;
806 node
= build1 (INDIRECT_REF
, type
,
807 fold (build (PLUS_EXPR
, ptr_type_node
,
808 java_check_reference (array
, flag_check_references
),
809 (throw ? build (COMPOUND_EXPR
, int_type_node
,
816 /* Makes sure that INDEXED_TYPE is appropriate. If not, make it from
817 ARRAY_NODE. This function is used to retrieve something less vague than
818 a pointer type when indexing the first dimension of something like [[<t>.
819 May return a corrected type, if necessary, otherwise INDEXED_TYPE is
821 As a side effect, it also makes sure that ARRAY_NODE is an array. */
824 build_java_check_indexed_type (array_node
, indexed_type
)
830 if (!is_array_type_p (TREE_TYPE (array_node
)))
833 elt_type
= (TYPE_ARRAY_ELEMENT (TREE_TYPE (TREE_TYPE (array_node
))));
835 if (indexed_type
== ptr_type_node
)
836 return promote_type (elt_type
);
838 /* BYTE/BOOLEAN store and load are used for both type */
839 if (indexed_type
== byte_type_node
&& elt_type
== boolean_type_node
)
840 return boolean_type_node
;
842 if (indexed_type
!= elt_type
)
848 /* newarray triggers a call to _Jv_NewPrimArray. This function should be
849 called with an integer code (the type of array to create), and the length
850 of the array to create. */
853 build_newarray (atype_value
, length
)
859 tree prim_type
= decode_newarray_type (atype_value
);
861 = build_java_array_type (prim_type
,
862 host_integerp (length
, 0) == INTEGER_CST
863 ? tree_low_cst (length
, 0) : -1);
865 /* If compiling to native, pass a reference to the primitive type class
866 and save the runtime some work. However, the bytecode generator
867 expects to find the type_code int here. */
868 if (flag_emit_class_files
)
869 type_arg
= build_int_2 (atype_value
, 0);
871 type_arg
= build_class_ref (prim_type
);
873 return build (CALL_EXPR
, promote_type (type
),
874 build_address_of (soft_newarray_node
),
875 tree_cons (NULL_TREE
,
877 build_tree_list (NULL_TREE
, length
)),
881 /* Generates anewarray from a given CLASS_TYPE. Gets from the stack the size
885 build_anewarray (class_type
, length
)
890 = build_java_array_type (class_type
,
891 host_integerp (length
, 0)
892 ? tree_low_cst (length
, 0) : -1);
894 return build (CALL_EXPR
, promote_type (type
),
895 build_address_of (soft_anewarray_node
),
896 tree_cons (NULL_TREE
, length
,
897 tree_cons (NULL_TREE
, build_class_ref (class_type
),
898 build_tree_list (NULL_TREE
,
899 null_pointer_node
))),
903 /* Return a node the evaluates 'new TYPE[LENGTH]'. */
906 build_new_array (type
, length
)
910 if (JPRIMITIVE_TYPE_P (type
))
911 return build_newarray (encode_newarray_type (type
), length
);
913 return build_anewarray (TREE_TYPE (type
), length
);
916 /* Generates a call to _Jv_NewMultiArray. multianewarray expects a
917 class pointer, a number of dimensions and the matching number of
918 dimensions. The argument list is NULL terminated. */
921 expand_java_multianewarray (class_type
, ndim
)
926 tree args
= build_tree_list( NULL_TREE
, null_pointer_node
);
928 for( i
= 0; i
< ndim
; i
++ )
929 args
= tree_cons (NULL_TREE
, pop_value (int_type_node
), args
);
931 push_value (build (CALL_EXPR
,
932 promote_type (class_type
),
933 build_address_of (soft_multianewarray_node
),
934 tree_cons (NULL_TREE
, build_class_ref (class_type
),
935 tree_cons (NULL_TREE
,
936 build_int_2 (ndim
, 0), args
)),
940 /* ARRAY[INDEX] <- RHS. build_java_check_indexed_type makes sure that
941 ARRAY is an array type. May expand some bound checking and NULL
942 pointer checking. RHS_TYPE_NODE we are going to store. In the case
943 of the CHAR/BYTE/BOOLEAN SHORT, the type popped of the stack is an
944 INT. In those cases, we make the convertion.
946 if ARRAy is a reference type, the assignment is checked at run-time
947 to make sure that the RHS can be assigned to the array element
948 type. It is not necessary to generate this code if ARRAY is final. */
951 expand_java_arraystore (rhs_type_node
)
954 tree rhs_node
= pop_value ((INTEGRAL_TYPE_P (rhs_type_node
)
955 && TYPE_PRECISION (rhs_type_node
) <= 32) ?
956 int_type_node
: rhs_type_node
);
957 tree index
= pop_value (int_type_node
);
958 tree array
= pop_value (ptr_type_node
);
960 rhs_type_node
= build_java_check_indexed_type (array
, rhs_type_node
);
962 flush_quick_stack ();
964 index
= save_expr (index
);
965 array
= save_expr (array
);
967 if (TREE_CODE (rhs_type_node
) == POINTER_TYPE
)
969 tree check
= build (CALL_EXPR
, void_type_node
,
970 build_address_of (soft_checkarraystore_node
),
971 tree_cons (NULL_TREE
, array
,
972 build_tree_list (NULL_TREE
, rhs_node
)),
974 TREE_SIDE_EFFECTS (check
) = 1;
975 expand_expr_stmt (check
);
978 expand_assignment (build_java_arrayaccess (array
,
984 /* Expand the evaluation of ARRAY[INDEX]. build_java_check_indexed_type makes
985 sure that LHS is an array type. May expand some bound checking and NULL
987 LHS_TYPE_NODE is the type of ARRAY[INDEX]. But in the case of CHAR/BYTE/
988 BOOLEAN/SHORT, we push a promoted type back to the stack.
992 expand_java_arrayload (lhs_type_node
)
996 tree index_node
= pop_value (int_type_node
);
997 tree array_node
= pop_value (ptr_type_node
);
999 index_node
= save_expr (index_node
);
1000 array_node
= save_expr (array_node
);
1001 lhs_type_node
= build_java_check_indexed_type (array_node
, lhs_type_node
);
1003 load_node
= build_java_arrayaccess (array_node
,
1007 if (INTEGRAL_TYPE_P (lhs_type_node
) && TYPE_PRECISION (lhs_type_node
) <= 32)
1008 load_node
= fold (build1 (NOP_EXPR
, int_type_node
, load_node
));
1009 push_value (load_node
);
1012 /* Expands .length. Makes sure that we deal with and array and may expand
1013 a NULL check on the array object. */
1016 expand_java_array_length ()
1018 tree array
= pop_value (ptr_type_node
);
1019 tree length
= build_java_array_length_access (array
);
1021 push_value (length
);
1024 /* Emit code for the call to _Jv_Monitor{Enter,Exit}. CALL can be
1025 either soft_monitorenter_node or soft_monitorexit_node. */
1028 build_java_monitor (call
, object
)
1032 return (build (CALL_EXPR
,
1034 build_address_of (call
),
1035 build_tree_list (NULL_TREE
, object
),
1039 /* Emit code for one of the PUSHC instructions. */
1042 expand_java_pushc (ival
, type
)
1047 if (type
== ptr_type_node
&& ival
== 0)
1048 value
= null_pointer_node
;
1049 else if (type
== int_type_node
|| type
== long_type_node
)
1051 value
= build_int_2 (ival
, ival
< 0 ? -1 : 0);
1052 TREE_TYPE (value
) = type
;
1054 else if (type
== float_type_node
|| type
== double_type_node
)
1057 #ifdef REAL_ARITHMETIC
1058 REAL_VALUE_FROM_INT (x
, ival
, 0, TYPE_MODE (type
));
1062 value
= build_real (type
, x
);
1071 expand_java_return (type
)
1074 if (type
== void_type_node
)
1075 expand_null_return ();
1078 tree retval
= pop_value (type
);
1079 tree res
= DECL_RESULT (current_function_decl
);
1080 retval
= build (MODIFY_EXPR
, TREE_TYPE (res
), res
, retval
);
1082 /* Handle the situation where the native integer type is smaller
1083 than the JVM integer. It can happen for many cross compilers.
1084 The whole if expression just goes away if INT_TYPE_SIZE < 32
1086 if (INT_TYPE_SIZE
< 32
1087 && (GET_MODE_SIZE (TYPE_MODE (TREE_TYPE (res
)))
1088 < GET_MODE_SIZE (TYPE_MODE (type
))))
1089 retval
= build1(NOP_EXPR
, TREE_TYPE(res
), retval
);
1091 TREE_SIDE_EFFECTS (retval
) = 1;
1092 expand_return (retval
);
1097 build_address_of (value
)
1100 return build1 (ADDR_EXPR
, build_pointer_type (TREE_TYPE (value
)), value
);
1104 expand_java_NEW (type
)
1107 if (! CLASS_LOADED_P (type
))
1108 load_class (type
, 1);
1109 safe_layout_class (type
);
1110 push_value (build (CALL_EXPR
, promote_type (type
),
1111 build_address_of (alloc_object_node
),
1112 tree_cons (NULL_TREE
, build_class_ref (type
),
1113 build_tree_list (NULL_TREE
,
1114 size_in_bytes (type
))),
1118 /* This returns an expression which will extract the class of an
1122 build_get_class (value
)
1125 tree class_field
= lookup_field (&dtable_type
, get_identifier ("class"));
1126 tree vtable_field
= lookup_field (&object_type_node
,
1127 get_identifier ("vtable"));
1128 return build (COMPONENT_REF
, class_ptr_type
,
1129 build1 (INDIRECT_REF
, dtable_type
,
1130 build (COMPONENT_REF
, dtable_ptr_type
,
1131 build_java_indirect_ref (object_type_node
, value
,
1132 flag_check_references
),
1137 /* This builds the tree representation of the `instanceof' operator.
1138 It tries various tricks to optimize this in cases where types are
1142 build_instanceof (value
, type
)
1146 tree itype
= TREE_TYPE (TREE_TYPE (soft_instanceof_node
));
1147 tree valtype
= TREE_TYPE (TREE_TYPE (value
));
1148 tree valclass
= TYPE_NAME (valtype
);
1151 /* When compiling from bytecode, we need to ensure that TYPE has
1153 if (CLASS_P (type
) && ! CLASS_LOADED_P (type
))
1155 load_class (type
, 1);
1156 safe_layout_class (type
);
1157 if (! TYPE_SIZE (type
) || TREE_CODE (TYPE_SIZE (type
)) == ERROR_MARK
)
1158 return error_mark_node
;
1160 klass
= TYPE_NAME (type
);
1162 if (type
== object_type_node
|| inherits_from_p (valtype
, type
))
1164 /* Anything except `null' is an instance of Object. Likewise,
1165 if the object is known to be an instance of the class, then
1166 we only need to check for `null'. */
1167 expr
= build (COND_EXPR
, itype
,
1169 boolean_true_node
, boolean_false_node
);
1171 else if (! TYPE_ARRAY_P (type
)
1172 && ! TYPE_ARRAY_P (valtype
)
1173 && DECL_P (klass
) && DECL_P (valclass
)
1174 && ! CLASS_INTERFACE (valclass
)
1175 && ! CLASS_INTERFACE (klass
)
1176 && ! inherits_from_p (type
, valtype
)
1177 && (CLASS_FINAL (klass
)
1178 || ! inherits_from_p (valtype
, type
)))
1180 /* The classes are from different branches of the derivation
1181 tree, so we immediately know the answer. */
1182 expr
= boolean_false_node
;
1184 else if (DECL_P (klass
) && CLASS_FINAL (klass
))
1186 tree save
= save_expr (value
);
1187 expr
= build (COND_EXPR
, itype
,
1189 build (EQ_EXPR
, itype
,
1190 build_get_class (save
),
1191 build_class_ref (type
)),
1192 boolean_false_node
);
1196 expr
= build (CALL_EXPR
, itype
,
1197 build_address_of (soft_instanceof_node
),
1198 tree_cons (NULL_TREE
, value
,
1199 build_tree_list (NULL_TREE
,
1200 build_class_ref (type
))),
1203 TREE_SIDE_EFFECTS (expr
) = TREE_SIDE_EFFECTS (value
);
1208 expand_java_INSTANCEOF (type
)
1211 tree value
= pop_value (object_ptr_type_node
);
1212 value
= build_instanceof (value
, type
);
1217 expand_java_CHECKCAST (type
)
1220 tree value
= pop_value (ptr_type_node
);
1221 value
= build (CALL_EXPR
, promote_type (type
),
1222 build_address_of (soft_checkcast_node
),
1223 tree_cons (NULL_TREE
, build_class_ref (type
),
1224 build_tree_list (NULL_TREE
, value
)),
1230 expand_iinc (local_var_index
, ival
, pc
)
1231 unsigned int local_var_index
;
1235 tree local_var
, res
;
1236 tree constant_value
;
1238 flush_quick_stack ();
1239 local_var
= find_local_variable (local_var_index
, int_type_node
, pc
);
1240 constant_value
= build_int_2 (ival
, ival
< 0 ? -1 : 0);
1241 res
= fold (build (PLUS_EXPR
, int_type_node
, local_var
, constant_value
));
1242 expand_assignment (local_var
, res
, 0, 0);
1247 build_java_soft_divmod (op
, type
, op1
, op2
)
1249 tree type
, op1
, op2
;
1252 tree arg1
= convert (type
, op1
);
1253 tree arg2
= convert (type
, op2
);
1255 if (type
== int_type_node
)
1259 case TRUNC_DIV_EXPR
:
1260 call
= soft_idiv_node
;
1262 case TRUNC_MOD_EXPR
:
1263 call
= soft_irem_node
;
1269 else if (type
== long_type_node
)
1273 case TRUNC_DIV_EXPR
:
1274 call
= soft_ldiv_node
;
1276 case TRUNC_MOD_EXPR
:
1277 call
= soft_lrem_node
;
1287 call
= build (CALL_EXPR
, type
,
1288 build_address_of (call
),
1289 tree_cons (NULL_TREE
, arg1
,
1290 build_tree_list (NULL_TREE
, arg2
)),
1297 build_java_binop (op
, type
, arg1
, arg2
)
1299 tree type
, arg1
, arg2
;
1306 tree u_type
= unsigned_type (type
);
1307 arg1
= convert (u_type
, arg1
);
1308 arg1
= build_java_binop (RSHIFT_EXPR
, u_type
, arg1
, arg2
);
1309 return convert (type
, arg1
);
1313 mask
= build_int_2 (TYPE_PRECISION (TREE_TYPE (arg1
)) - 1, 0);
1314 arg2
= fold (build (BIT_AND_EXPR
, int_type_node
, arg2
, mask
));
1317 case COMPARE_L_EXPR
: /* arg1 > arg2 ? 1 : arg1 == arg2 ? 0 : -1 */
1318 case COMPARE_G_EXPR
: /* arg1 < arg2 ? -1 : arg1 == arg2 ? 0 : 1 */
1319 arg1
= save_expr (arg1
); arg2
= save_expr (arg2
);
1321 tree ifexp1
= fold ( build (op
== COMPARE_L_EXPR
? GT_EXPR
: LT_EXPR
,
1322 boolean_type_node
, arg1
, arg2
));
1323 tree ifexp2
= fold ( build (EQ_EXPR
, boolean_type_node
, arg1
, arg2
));
1324 tree second_compare
= fold (build (COND_EXPR
, int_type_node
,
1325 ifexp2
, integer_zero_node
,
1326 op
== COMPARE_L_EXPR
1327 ? integer_minus_one_node
1328 : integer_one_node
));
1329 return fold (build (COND_EXPR
, int_type_node
, ifexp1
,
1330 op
== COMPARE_L_EXPR
? integer_one_node
1331 : integer_minus_one_node
,
1335 arg1
= save_expr (arg1
); arg2
= save_expr (arg2
);
1337 tree ifexp1
= fold ( build (LT_EXPR
, boolean_type_node
, arg1
, arg2
));
1338 tree ifexp2
= fold ( build (GT_EXPR
, boolean_type_node
, arg1
, arg2
));
1339 tree second_compare
= fold ( build (COND_EXPR
, int_type_node
,
1340 ifexp2
, integer_one_node
,
1341 integer_zero_node
));
1342 return fold (build (COND_EXPR
, int_type_node
,
1343 ifexp1
, integer_minus_one_node
, second_compare
));
1345 case TRUNC_DIV_EXPR
:
1346 case TRUNC_MOD_EXPR
:
1347 if (TREE_CODE (type
) == REAL_TYPE
1348 && op
== TRUNC_MOD_EXPR
)
1351 if (type
!= double_type_node
)
1353 arg1
= convert (double_type_node
, arg1
);
1354 arg2
= convert (double_type_node
, arg2
);
1356 call
= build (CALL_EXPR
, double_type_node
,
1357 build_address_of (soft_fmod_node
),
1358 tree_cons (NULL_TREE
, arg1
,
1359 build_tree_list (NULL_TREE
, arg2
)),
1361 if (type
!= double_type_node
)
1362 call
= convert (type
, call
);
1366 if (TREE_CODE (type
) == INTEGER_TYPE
1367 && flag_use_divide_subroutine
1368 && ! flag_syntax_only
)
1369 return build_java_soft_divmod (op
, type
, arg1
, arg2
);
1374 return fold (build (op
, type
, arg1
, arg2
));
1378 expand_java_binop (type
, op
)
1379 tree type
; enum tree_code op
;
1389 rtype
= int_type_node
;
1390 rarg
= pop_value (rtype
);
1393 rarg
= pop_value (rtype
);
1395 larg
= pop_value (ltype
);
1396 push_value (build_java_binop (op
, type
, larg
, rarg
));
1399 /* Lookup the field named NAME in *TYPEP or its super classes.
1400 If not found, return NULL_TREE.
1401 (If the *TYPEP is not found, or if the field reference is
1402 ambiguous, return error_mark_node.)
1403 If found, return the FIELD_DECL, and set *TYPEP to the
1404 class containing the field. */
1407 lookup_field (typep
, name
)
1411 if (CLASS_P (*typep
) && !CLASS_LOADED_P (*typep
))
1413 load_class (*typep
, 1);
1414 safe_layout_class (*typep
);
1415 if (!TYPE_SIZE (*typep
) || TREE_CODE (TYPE_SIZE (*typep
)) == ERROR_MARK
)
1416 return error_mark_node
;
1420 tree field
, basetype_vec
;
1424 for (field
= TYPE_FIELDS (*typep
); field
; field
= TREE_CHAIN (field
))
1425 if (DECL_NAME (field
) == name
)
1428 /* If *typep is an innerclass, lookup the field in its enclosing
1430 if (INNER_CLASS_TYPE_P (*typep
))
1432 tree outer_type
= TREE_TYPE (DECL_CONTEXT (TYPE_NAME (*typep
)));
1434 if ((field
= lookup_field (&outer_type
, name
)))
1438 /* Process implemented interfaces. */
1439 basetype_vec
= TYPE_BINFO_BASETYPES (*typep
);
1440 n
= TREE_VEC_LENGTH (basetype_vec
);
1441 save_field
= NULL_TREE
;
1442 for (i
= 0; i
< n
; i
++)
1444 tree t
= BINFO_TYPE (TREE_VEC_ELT (basetype_vec
, i
));
1445 if ((field
= lookup_field (&t
, name
)))
1447 if (save_field
== field
)
1449 if (save_field
== NULL_TREE
)
1453 tree i1
= DECL_CONTEXT (save_field
);
1454 tree i2
= DECL_CONTEXT (field
);
1455 error ("reference `%s' is ambiguous: appears in interface `%s' and interface `%s'",
1456 IDENTIFIER_POINTER (name
),
1457 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (i1
))),
1458 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (i2
))));
1459 return error_mark_node
;
1464 if (save_field
!= NULL_TREE
)
1467 *typep
= CLASSTYPE_SUPER (*typep
);
1472 /* Look up the field named NAME in object SELF_VALUE,
1473 which has class SELF_CLASS (a non-handle RECORD_TYPE).
1474 SELF_VALUE is NULL_TREE if looking for a static field. */
1477 build_field_ref (self_value
, self_class
, name
)
1478 tree self_value
, self_class
, name
;
1480 tree base_class
= self_class
;
1481 tree field_decl
= lookup_field (&base_class
, name
);
1482 if (field_decl
== NULL_TREE
)
1484 error ("field `%s' not found", IDENTIFIER_POINTER (name
));
1485 return error_mark_node
;
1487 if (self_value
== NULL_TREE
)
1489 return build_static_field_ref (field_decl
);
1493 tree base_handle_type
= promote_type (base_class
);
1494 if (base_handle_type
!= TREE_TYPE (self_value
))
1495 self_value
= fold (build1 (NOP_EXPR
, base_handle_type
, self_value
));
1496 #ifdef JAVA_USE_HANDLES
1497 self_value
= unhand_expr (self_value
);
1499 self_value
= build_java_indirect_ref (TREE_TYPE (TREE_TYPE (self_value
)),
1500 self_value
, flag_check_references
);
1501 return fold (build (COMPONENT_REF
, TREE_TYPE (field_decl
),
1502 self_value
, field_decl
));
1512 ASM_GENERATE_INTERNAL_LABEL(buf
, "LJpc=", pc
);
1513 name
= get_identifier (buf
);
1514 if (IDENTIFIER_LOCAL_VALUE (name
))
1515 return IDENTIFIER_LOCAL_VALUE (name
);
1518 /* The type of the address of a label is return_address_type_node. */
1519 tree decl
= create_label_decl (name
);
1520 LABEL_PC (decl
) = pc
;
1522 return pushdecl (decl
);
1526 /* Generate a unique name for the purpose of loops and switches
1527 labels, and try-catch-finally blocks label or temporary variables. */
1532 static int l_number
= 0;
1534 ASM_GENERATE_INTERNAL_LABEL(buff
, "LJv", l_number
);
1536 return get_identifier (buff
);
1540 create_label_decl (name
)
1544 decl
= build_decl (LABEL_DECL
, name
,
1545 TREE_TYPE (return_address_type_node
));
1546 DECL_CONTEXT (decl
) = current_function_decl
;
1547 DECL_IGNORED_P (decl
) = 1;
1551 /* This maps a bytecode offset (PC) to various flags. */
1552 char *instruction_bits
;
1555 note_label (current_pc
, target_pc
)
1556 int current_pc ATTRIBUTE_UNUSED
, target_pc
;
1558 lookup_label (target_pc
);
1559 instruction_bits
[target_pc
] |= BCODE_JUMP_TARGET
;
1562 /* Emit code to jump to TARGET_PC if VALUE1 CONDITION VALUE2,
1563 where CONDITION is one of one the compare operators. */
1566 expand_compare (condition
, value1
, value2
, target_pc
)
1567 enum tree_code condition
;
1568 tree value1
, value2
;
1571 tree target
= lookup_label (target_pc
);
1572 tree cond
= fold (build (condition
, boolean_type_node
, value1
, value2
));
1573 expand_start_cond (truthvalue_conversion (cond
), 0);
1574 expand_goto (target
);
1578 /* Emit code for a TEST-type opcode. */
1581 expand_test (condition
, type
, target_pc
)
1582 enum tree_code condition
;
1586 tree value1
, value2
;
1587 flush_quick_stack ();
1588 value1
= pop_value (type
);
1589 value2
= (type
== ptr_type_node
) ? null_pointer_node
: integer_zero_node
;
1590 expand_compare (condition
, value1
, value2
, target_pc
);
1593 /* Emit code for a COND-type opcode. */
1596 expand_cond (condition
, type
, target_pc
)
1597 enum tree_code condition
;
1601 tree value1
, value2
;
1602 flush_quick_stack ();
1603 /* note: pop values in opposite order */
1604 value2
= pop_value (type
);
1605 value1
= pop_value (type
);
1606 /* Maybe should check value1 and value2 for type compatibility ??? */
1607 expand_compare (condition
, value1
, value2
, target_pc
);
1611 expand_java_goto (target_pc
)
1614 tree target_label
= lookup_label (target_pc
);
1615 flush_quick_stack ();
1616 expand_goto (target_label
);
1621 expand_java_call (target_pc
, return_address
)
1622 int target_pc
, return_address
;
1624 tree target_label
= lookup_label (target_pc
);
1625 tree value
= build_int_2 (return_address
, return_address
< 0 ? -1 : 0);
1627 flush_quick_stack ();
1628 expand_goto (target_label
);
1632 expand_java_ret (return_address
)
1633 tree return_address ATTRIBUTE_UNUSED
;
1635 warning ("ret instruction not implemented");
1637 tree target_label
= lookup_label (target_pc
);
1638 flush_quick_stack ();
1639 expand_goto (target_label
);
1645 pop_arguments (arg_types
)
1648 if (arg_types
== end_params_node
)
1650 if (TREE_CODE (arg_types
) == TREE_LIST
)
1652 tree tail
= pop_arguments (TREE_CHAIN (arg_types
));
1653 tree type
= TREE_VALUE (arg_types
);
1654 tree arg
= pop_value (type
);
1655 if (PROMOTE_PROTOTYPES
1656 && TYPE_PRECISION (type
) < TYPE_PRECISION (integer_type_node
)
1657 && INTEGRAL_TYPE_P (type
))
1658 arg
= convert (integer_type_node
, arg
);
1659 return tree_cons (NULL_TREE
, arg
, tail
);
1664 /* Build an expression to initialize the class CLAS.
1665 if EXPR is non-NULL, returns an expression to first call the initializer
1666 (if it is needed) and then calls EXPR. */
1669 build_class_init (clas
, expr
)
1673 struct init_test_hash_entry
*ite
;
1674 if (inherits_from_p (current_class
, clas
))
1677 if (always_initialize_class_p
)
1679 init
= build (CALL_EXPR
, void_type_node
,
1680 build_address_of (soft_initclass_node
),
1681 build_tree_list (NULL_TREE
, build_class_ref (clas
)),
1683 TREE_SIDE_EFFECTS (init
) = 1;
1687 ite
= (struct init_test_hash_entry
*)
1688 hash_lookup (&DECL_FUNCTION_INIT_TEST_TABLE (current_function_decl
),
1689 (const hash_table_key
) clas
,
1692 if (ite
->init_test_decl
== 0)
1693 ite
->init_test_decl
= build_decl (VAR_DECL
, NULL_TREE
,
1695 /* Tell the check-init code to ignore this decl. */
1696 DECL_BIT_INDEX(ite
->init_test_decl
) = -1;
1698 init
= build (CALL_EXPR
, void_type_node
,
1699 build_address_of (soft_initclass_node
),
1700 build_tree_list (NULL_TREE
, build_class_ref (clas
)),
1702 TREE_SIDE_EFFECTS (init
) = 1;
1703 call
= build (COMPOUND_EXPR
, TREE_TYPE (expr
), init
,
1704 build (MODIFY_EXPR
, boolean_type_node
,
1705 ite
->init_test_decl
, boolean_true_node
));
1706 TREE_SIDE_EFFECTS (call
) = 1;
1707 init
= build (COND_EXPR
, void_type_node
,
1708 build (EQ_EXPR
, boolean_type_node
,
1709 ite
->init_test_decl
, boolean_false_node
),
1710 call
, integer_zero_node
);
1711 TREE_SIDE_EFFECTS (init
) = 1;
1714 if (expr
!= NULL_TREE
)
1716 expr
= build (COMPOUND_EXPR
, TREE_TYPE (expr
), init
, expr
);
1717 TREE_SIDE_EFFECTS (expr
) = 1;
1724 build_known_method_ref (method
, method_type
, self_type
, method_signature
, arg_list
)
1725 tree method
, method_type ATTRIBUTE_UNUSED
, self_type
,
1726 method_signature ATTRIBUTE_UNUSED
, arg_list ATTRIBUTE_UNUSED
;
1729 if (is_compiled_class (self_type
))
1731 make_decl_rtl (method
, NULL
);
1732 func
= build1 (ADDR_EXPR
, method_ptr_type_node
, method
);
1736 /* We don't know whether the method has been (statically) compiled.
1737 Compile this code to get a reference to the method's code:
1739 SELF_TYPE->methods[METHOD_INDEX].ncode
1741 This is guaranteed to work (assuming SELF_TYPE has
1742 been initialized), since if the method is not compiled yet,
1743 its ncode points to a trampoline that forces compilation. */
1745 int method_index
= 0;
1747 tree ref
= build_class_ref (self_type
);
1748 ref
= build1 (INDIRECT_REF
, class_type_node
, ref
);
1749 if (ncode_ident
== NULL_TREE
)
1750 ncode_ident
= get_identifier ("ncode");
1751 if (methods_ident
== NULL_TREE
)
1752 methods_ident
= get_identifier ("methods");
1753 ref
= build (COMPONENT_REF
, method_ptr_type_node
, ref
,
1754 lookup_field (&class_type_node
, methods_ident
));
1755 for (meth
= TYPE_METHODS (CLASS_TO_HANDLE_TYPE (self_type
));
1756 ; meth
= TREE_CHAIN (meth
))
1760 if (meth
== NULL_TREE
)
1761 fatal_error ("method '%s' not found in class",
1762 IDENTIFIER_POINTER (DECL_NAME (method
)));
1765 method_index
*= int_size_in_bytes (method_type_node
);
1766 ref
= fold (build (PLUS_EXPR
, method_ptr_type_node
,
1767 ref
, build_int_2 (method_index
, 0)));
1768 ref
= build1 (INDIRECT_REF
, method_type_node
, ref
);
1769 func
= build (COMPONENT_REF
, nativecode_ptr_type_node
,
1771 lookup_field (&method_type_node
, ncode_ident
));
1777 invoke_build_dtable (is_invoke_interface
, arg_list
)
1778 int is_invoke_interface
;
1781 tree dtable
, objectref
;
1783 TREE_VALUE (arg_list
) = save_expr (TREE_VALUE (arg_list
));
1785 /* If we're dealing with interfaces and if the objectref
1786 argument is an array then get the dispatch table of the class
1787 Object rather than the one from the objectref. */
1788 objectref
= (is_invoke_interface
1789 && is_array_type_p (TREE_TYPE (TREE_VALUE (arg_list
))) ?
1790 object_type_node
: TREE_VALUE (arg_list
));
1792 if (dtable_ident
== NULL_TREE
)
1793 dtable_ident
= get_identifier ("vtable");
1794 dtable
= build_java_indirect_ref (object_type_node
, objectref
,
1795 flag_check_references
);
1796 dtable
= build (COMPONENT_REF
, dtable_ptr_type
, dtable
,
1797 lookup_field (&object_type_node
, dtable_ident
));
1803 build_invokevirtual (dtable
, method
)
1804 tree dtable
, method
;
1807 tree nativecode_ptr_ptr_type_node
1808 = build_pointer_type (nativecode_ptr_type_node
);
1809 tree method_index
= convert (sizetype
, DECL_VINDEX (method
));
1811 /* Add one to skip "class" field of dtable, and one to skip unused
1812 vtable entry (for C++ compatibility). */
1813 method_index
= size_binop (PLUS_EXPR
, method_index
, size_int (2));
1814 method_index
= size_binop (MULT_EXPR
, method_index
,
1815 TYPE_SIZE_UNIT (nativecode_ptr_ptr_type_node
));
1816 func
= fold (build (PLUS_EXPR
, nativecode_ptr_ptr_type_node
, dtable
,
1817 convert (nativecode_ptr_ptr_type_node
, method_index
)));
1818 func
= build1 (INDIRECT_REF
, nativecode_ptr_type_node
, func
);
1824 build_invokeinterface (dtable
, method
)
1825 tree dtable
, method
;
1827 static tree class_ident
= NULL_TREE
;
1834 /* We expand invokeinterface here. _Jv_LookupInterfaceMethod() will
1835 ensure that the selected method exists, is public and not
1836 abstract nor static. */
1838 if (class_ident
== NULL_TREE
)
1840 class_ident
= get_identifier ("class");
1841 ggc_add_tree_root (&class_ident
, 1);
1844 dtable
= build_java_indirect_ref (dtable_type
, dtable
, flag_check_references
);
1845 dtable
= build (COMPONENT_REF
, class_ptr_type
, dtable
,
1846 lookup_field (&dtable_type
, class_ident
));
1848 interface
= DECL_CONTEXT (method
);
1849 layout_class_methods (interface
);
1852 for (meth
= TYPE_METHODS (interface
); ; meth
= TREE_CHAIN (meth
), i
++)
1856 idx
= build_int_2 (i
, 0);
1859 if (meth
== NULL_TREE
)
1863 lookup_arg
= tree_cons (NULL_TREE
, dtable
,
1864 tree_cons (NULL_TREE
, build_class_ref (interface
),
1865 build_tree_list (NULL_TREE
, idx
)));
1867 return build (CALL_EXPR
, ptr_type_node
,
1868 build_address_of (soft_lookupinterfacemethod_node
),
1869 lookup_arg
, NULL_TREE
);
1872 /* Expand one of the invoke_* opcodes.
1873 OCPODE is the specific opcode.
1874 METHOD_REF_INDEX is an index into the constant pool.
1875 NARGS is the number of arguments, or -1 if not specified. */
1878 expand_invoke (opcode
, method_ref_index
, nargs
)
1880 int method_ref_index
;
1881 int nargs ATTRIBUTE_UNUSED
;
1883 tree method_signature
= COMPONENT_REF_SIGNATURE(¤t_jcf
->cpool
, method_ref_index
);
1884 tree method_name
= COMPONENT_REF_NAME (¤t_jcf
->cpool
, method_ref_index
);
1885 tree self_type
= get_class_constant
1886 (current_jcf
, COMPONENT_REF_CLASS_INDEX(¤t_jcf
->cpool
, method_ref_index
));
1887 const char *self_name
1888 = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (self_type
)));
1889 tree call
, func
, method
, arg_list
, method_type
;
1890 tree check
= NULL_TREE
;
1892 if (! CLASS_LOADED_P (self_type
))
1894 load_class (self_type
, 1);
1895 safe_layout_class (self_type
);
1896 if (TREE_CODE (TYPE_SIZE (self_type
)) == ERROR_MARK
)
1897 fatal_error ("failed to find class '%s'", self_name
);
1899 layout_class_methods (self_type
);
1901 if (ID_INIT_P (method_name
))
1902 method
= lookup_java_constructor (CLASS_TO_HANDLE_TYPE (self_type
),
1905 method
= lookup_java_method (CLASS_TO_HANDLE_TYPE (self_type
),
1906 method_name
, method_signature
);
1907 if (method
== NULL_TREE
)
1909 error ("Class '%s' has no method named '%s' matching signature '%s'",
1911 IDENTIFIER_POINTER (method_name
),
1912 IDENTIFIER_POINTER (method_signature
));
1914 /* Invoke static can't invoke static/abstract method */
1915 else if (opcode
== OPCODE_invokestatic
)
1917 if (!METHOD_STATIC (method
))
1919 error ("invokestatic on non static method");
1922 else if (METHOD_ABSTRACT (method
))
1924 error ("invokestatic on abstract method");
1930 if (METHOD_STATIC (method
))
1932 error ("invoke[non-static] on static method");
1937 if (method
== NULL_TREE
)
1939 method_type
= get_type_from_signature (method_signature
);
1940 pop_arguments (TYPE_ARG_TYPES (method_type
));
1941 if (opcode
!= OPCODE_invokestatic
)
1942 pop_type (self_type
);
1943 method_type
= promote_type (TREE_TYPE (method_type
));
1944 push_value (convert (method_type
, integer_zero_node
));
1948 method_type
= TREE_TYPE (method
);
1949 arg_list
= pop_arguments (TYPE_ARG_TYPES (method_type
));
1950 flush_quick_stack ();
1953 if (opcode
== OPCODE_invokestatic
)
1954 func
= build_known_method_ref (method
, method_type
, self_type
,
1955 method_signature
, arg_list
);
1956 else if (opcode
== OPCODE_invokespecial
1957 || (opcode
== OPCODE_invokevirtual
1958 && (METHOD_PRIVATE (method
)
1959 || METHOD_FINAL (method
)
1960 || CLASS_FINAL (TYPE_NAME (self_type
)))))
1962 /* If the object for the method call is null, we throw an
1963 exception. We don't do this if the object is the current
1964 method's `this'. In other cases we just rely on an
1965 optimization pass to eliminate redundant checks. FIXME:
1966 Unfortunately there doesn't seem to be a way to determine
1967 what the current method is right now. */
1968 /* We use a SAVE_EXPR here to make sure we only evaluate
1969 the new `self' expression once. */
1970 tree save_arg
= save_expr (TREE_VALUE (arg_list
));
1971 TREE_VALUE (arg_list
) = save_arg
;
1972 check
= java_check_reference (save_arg
, 1);
1973 func
= build_known_method_ref (method
, method_type
, self_type
,
1974 method_signature
, arg_list
);
1978 tree dtable
= invoke_build_dtable (opcode
== OPCODE_invokeinterface
,
1980 if (opcode
== OPCODE_invokevirtual
)
1981 func
= build_invokevirtual (dtable
, method
);
1983 func
= build_invokeinterface (dtable
, method
);
1985 func
= build1 (NOP_EXPR
, build_pointer_type (method_type
), func
);
1986 call
= build (CALL_EXPR
, TREE_TYPE (method_type
), func
, arg_list
, NULL_TREE
);
1987 TREE_SIDE_EFFECTS (call
) = 1;
1989 if (check
!= NULL_TREE
)
1991 call
= build (COMPOUND_EXPR
, TREE_TYPE (call
), check
, call
);
1992 TREE_SIDE_EFFECTS (call
) = 1;
1995 if (TREE_CODE (TREE_TYPE (method_type
)) == VOID_TYPE
)
1996 expand_expr_stmt (call
);
2000 flush_quick_stack ();
2004 /* Create a stub which will be put into the vtable but which will call
2008 build_jni_stub (method
)
2011 tree jnifunc
, call
, args
, body
, lookup_arg
, method_sig
, arg_types
;
2012 tree jni_func_type
, tem
;
2013 tree env_var
, res_var
= NULL_TREE
, block
;
2014 tree method_args
, res_type
;
2017 tree klass
= DECL_CONTEXT (method
);
2018 int from_class
= ! CLASS_FROM_SOURCE_P (klass
);
2019 klass
= build_class_ref (klass
);
2021 if (! METHOD_NATIVE (method
) || ! flag_jni
)
2024 DECL_ARTIFICIAL (method
) = 1;
2025 DECL_EXTERNAL (method
) = 0;
2027 env_var
= build_decl (VAR_DECL
, get_identifier ("env"), ptr_type_node
);
2028 DECL_CONTEXT (env_var
) = method
;
2030 if (TREE_TYPE (TREE_TYPE (method
)) != void_type_node
)
2032 res_var
= build_decl (VAR_DECL
, get_identifier ("res"),
2033 TREE_TYPE (TREE_TYPE (method
)));
2034 DECL_CONTEXT (res_var
) = method
;
2035 TREE_CHAIN (env_var
) = res_var
;
2038 meth_var
= build_decl (VAR_DECL
, get_identifier ("meth"), ptr_type_node
);
2039 TREE_STATIC (meth_var
) = 1;
2040 TREE_PUBLIC (meth_var
) = 0;
2041 DECL_EXTERNAL (meth_var
) = 0;
2042 DECL_CONTEXT (meth_var
) = method
;
2043 make_decl_rtl (meth_var
, NULL
);
2044 meth_var
= pushdecl_top_level (meth_var
);
2046 /* One strange way that the front ends are different is that they
2047 store arguments differently. */
2049 method_args
= DECL_ARGUMENTS (method
);
2051 method_args
= BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (method
));
2052 block
= build_block (env_var
, NULL_TREE
, NULL_TREE
,
2053 method_args
, NULL_TREE
);
2054 TREE_SIDE_EFFECTS (block
) = 1;
2055 /* When compiling from source we don't set the type of the block,
2056 because that will prevent patch_return from ever being run. */
2058 TREE_TYPE (block
) = TREE_TYPE (TREE_TYPE (method
));
2060 /* Compute the local `env' by calling _Jv_GetJNIEnvNewFrame. */
2061 body
= build (MODIFY_EXPR
, ptr_type_node
, env_var
,
2062 build (CALL_EXPR
, ptr_type_node
,
2063 build_address_of (soft_getjnienvnewframe_node
),
2064 build_tree_list (NULL_TREE
, klass
),
2066 CAN_COMPLETE_NORMALLY (body
) = 1;
2068 /* All the arguments to this method become arguments to the
2069 underlying JNI function. If we had to wrap object arguments in a
2070 special way, we would do that here. */
2072 for (tem
= method_args
; tem
!= NULL_TREE
; tem
= TREE_CHAIN (tem
))
2073 args
= tree_cons (NULL_TREE
, tem
, args
);
2074 args
= nreverse (args
);
2075 arg_types
= TYPE_ARG_TYPES (TREE_TYPE (method
));
2077 /* For a static method the second argument is the class. For a
2078 non-static method the second argument is `this'; that is already
2079 available in the argument list. */
2080 if (METHOD_STATIC (method
))
2082 args
= tree_cons (NULL_TREE
, klass
, args
);
2083 arg_types
= tree_cons (NULL_TREE
, object_ptr_type_node
, arg_types
);
2086 /* The JNIEnv structure is the first argument to the JNI function. */
2087 args
= tree_cons (NULL_TREE
, env_var
, args
);
2088 arg_types
= tree_cons (NULL_TREE
, ptr_type_node
, arg_types
);
2090 /* We call _Jv_LookupJNIMethod to find the actual underlying
2091 function pointer. _Jv_LookupJNIMethod will throw the appropriate
2092 exception if this function is not found at runtime. */
2093 method_sig
= build_java_signature (TREE_TYPE (method
));
2095 build_tree_list (NULL_TREE
,
2096 build_utf8_ref (unmangle_classname
2097 (IDENTIFIER_POINTER (method_sig
),
2098 IDENTIFIER_LENGTH (method_sig
))));
2099 tem
= DECL_NAME (method
);
2101 = tree_cons (NULL_TREE
, klass
,
2102 tree_cons (NULL_TREE
, build_utf8_ref (tem
), lookup_arg
));
2105 = build_pointer_type (build_function_type (TREE_TYPE (TREE_TYPE (method
)),
2108 jnifunc
= build (COND_EXPR
, ptr_type_node
,
2110 build (MODIFY_EXPR
, ptr_type_node
,
2112 build (CALL_EXPR
, ptr_type_node
,
2113 build_address_of (soft_lookupjnimethod_node
),
2114 lookup_arg
, NULL_TREE
)));
2116 /* Now we make the actual JNI call via the resulting function
2118 call
= build (CALL_EXPR
, TREE_TYPE (TREE_TYPE (method
)),
2119 build1 (NOP_EXPR
, jni_func_type
, jnifunc
),
2122 /* If the JNI call returned a result, capture it here. If we had to
2123 unwrap JNI object results, we would do that here. */
2124 if (res_var
!= NULL_TREE
)
2125 call
= build (MODIFY_EXPR
, TREE_TYPE (TREE_TYPE (method
)),
2128 TREE_SIDE_EFFECTS (call
) = 1;
2129 CAN_COMPLETE_NORMALLY (call
) = 1;
2131 body
= build (COMPOUND_EXPR
, void_type_node
, body
, call
);
2132 TREE_SIDE_EFFECTS (body
) = 1;
2134 /* Now free the environment we allocated. */
2135 call
= build (CALL_EXPR
, ptr_type_node
,
2136 build_address_of (soft_jnipopsystemframe_node
),
2137 build_tree_list (NULL_TREE
, env_var
),
2139 TREE_SIDE_EFFECTS (call
) = 1;
2140 CAN_COMPLETE_NORMALLY (call
) = 1;
2141 body
= build (COMPOUND_EXPR
, void_type_node
, body
, call
);
2142 TREE_SIDE_EFFECTS (body
) = 1;
2144 /* Finally, do the return. When compiling from source we rely on
2145 patch_return to patch the return value -- because DECL_RESULT is
2146 not set at the time this function is called. */
2149 res_type
= void_type_node
;
2150 if (res_var
!= NULL_TREE
)
2153 if (! DECL_RESULT (method
))
2155 /* Make sure we copy the result variable to the actual
2156 result. We use the type of the DECL_RESULT because it
2157 might be different from the return type of the function:
2158 it might be promoted. */
2159 drt
= TREE_TYPE (DECL_RESULT (method
));
2160 if (drt
!= TREE_TYPE (res_var
))
2161 res_var
= build1 (CONVERT_EXPR
, drt
, res_var
);
2162 res_var
= build (MODIFY_EXPR
, drt
, DECL_RESULT (method
), res_var
);
2163 TREE_SIDE_EFFECTS (res_var
) = 1;
2168 /* This is necessary to get patch_return to run. */
2169 res_type
= NULL_TREE
;
2171 body
= build (COMPOUND_EXPR
, void_type_node
, body
,
2172 build1 (RETURN_EXPR
, res_type
, res_var
));
2173 TREE_SIDE_EFFECTS (body
) = 1;
2175 BLOCK_EXPR_BODY (block
) = body
;
2179 /* Expand an operation to extract from or store into a field.
2180 IS_STATIC is 1 iff the field is static.
2181 IS_PUTTING is 1 for putting into a field; 0 for getting from the field.
2182 FIELD_REF_INDEX is an index into the constant pool. */
2185 expand_java_field_op (is_static
, is_putting
, field_ref_index
)
2188 int field_ref_index
;
2191 get_class_constant (current_jcf
,
2192 COMPONENT_REF_CLASS_INDEX (¤t_jcf
->cpool
,
2194 const char *self_name
= IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (self_type
)));
2195 tree field_name
= COMPONENT_REF_NAME (¤t_jcf
->cpool
, field_ref_index
);
2196 tree field_signature
= COMPONENT_REF_SIGNATURE (¤t_jcf
->cpool
,
2198 tree field_type
= get_type_from_signature (field_signature
);
2199 tree new_value
= is_putting
? pop_value (field_type
) : NULL_TREE
;
2202 tree field_decl
= lookup_field (&self_type
, field_name
);
2203 if (field_decl
== error_mark_node
)
2207 else if (field_decl
== NULL_TREE
)
2209 error ("Missing field '%s' in '%s'",
2210 IDENTIFIER_POINTER (field_name
), self_name
);
2213 else if (build_java_signature (TREE_TYPE (field_decl
)) != field_signature
)
2215 error ("Mismatching signature for field '%s' in '%s'",
2216 IDENTIFIER_POINTER (field_name
), self_name
);
2219 field_ref
= is_static
? NULL_TREE
: pop_value (self_type
);
2223 push_value (convert (field_type
, integer_zero_node
));
2224 flush_quick_stack ();
2228 /* Inline references to java.lang.PRIMTYPE.TYPE.
2229 In addition to being a useful (minor) optimization,
2230 this is also needed to avoid circularities in the implementation
2231 of these fields in libjava. */
2232 if (field_name
== TYPE_identifier_node
&& ! is_putting
2233 && ! flag_emit_class_files
&& field_type
== class_ptr_type
2234 && strncmp (self_name
, "java.lang.", 10) == 0)
2236 tree typ
= build_primtype_type_ref (self_name
);
2244 field_ref
= build_field_ref (field_ref
, self_type
, field_name
);
2246 field_ref
= build_class_init (self_type
, field_ref
);
2249 flush_quick_stack ();
2250 if (FIELD_FINAL (field_decl
))
2252 if (DECL_CONTEXT (field_decl
) != current_class
)
2253 error_with_decl (field_decl
,
2254 "assignment to final field `%s' not in field's class");
2255 else if (FIELD_STATIC (field_decl
))
2257 if (!DECL_CLINIT_P (current_function_decl
))
2258 warning_with_decl (field_decl
,
2259 "assignment to final static field `%s' not in class initializer");
2263 tree cfndecl_name
= DECL_NAME (current_function_decl
);
2264 if (! DECL_CONSTRUCTOR_P (current_function_decl
)
2265 && !ID_FINIT_P (cfndecl_name
))
2266 warning_with_decl (field_decl
, "assignment to final field `%s' not in constructor");
2269 expand_assignment (field_ref
, new_value
, 0, 0);
2272 push_value (field_ref
);
2276 build_primtype_type_ref (self_name
)
2277 const char *self_name
;
2279 const char *class_name
= self_name
+10;
2281 if (strncmp(class_name
, "Byte", 4) == 0)
2282 typ
= byte_type_node
;
2283 else if (strncmp(class_name
, "Short", 5) == 0)
2284 typ
= short_type_node
;
2285 else if (strncmp(class_name
, "Integer", 7) == 0)
2286 typ
= int_type_node
;
2287 else if (strncmp(class_name
, "Long", 4) == 0)
2288 typ
= long_type_node
;
2289 else if (strncmp(class_name
, "Float", 5) == 0)
2290 typ
= float_type_node
;
2291 else if (strncmp(class_name
, "Double", 6) == 0)
2292 typ
= double_type_node
;
2293 else if (strncmp(class_name
, "Boolean", 7) == 0)
2294 typ
= boolean_type_node
;
2295 else if (strncmp(class_name
, "Char", 4) == 0)
2296 typ
= char_type_node
;
2297 else if (strncmp(class_name
, "Void", 4) == 0)
2298 typ
= void_type_node
;
2301 if (typ
!= NULL_TREE
)
2302 return build_class_ref (typ
);
2308 load_type_state (label
)
2312 tree vec
= LABEL_TYPE_STATE (label
);
2313 int cur_length
= TREE_VEC_LENGTH (vec
);
2314 stack_pointer
= cur_length
- DECL_MAX_LOCALS(current_function_decl
);
2315 for (i
= 0; i
< cur_length
; i
++)
2316 type_map
[i
] = TREE_VEC_ELT (vec
, i
);
2319 /* Do the expansion of a Java switch. With Gcc, switches are front-end
2320 dependant things, but they rely on gcc routines. This function is
2321 placed here because it uses things defined locally in parse.y. */
2324 case_identity (t
, v
)
2325 tree t
__attribute__ ((__unused__
));
2331 /* Return the name of the vtable for an array of a given primitive
2334 get_primitive_array_vtable (tree elt
)
2337 if (elt
== boolean_type_node
)
2338 r
= boolean_array_vtable
;
2339 else if (elt
== byte_type_node
)
2340 r
= byte_array_vtable
;
2341 else if (elt
== char_type_node
)
2342 r
= char_array_vtable
;
2343 else if (elt
== short_type_node
)
2344 r
= short_array_vtable
;
2345 else if (elt
== int_type_node
)
2346 r
= int_array_vtable
;
2347 else if (elt
== long_type_node
)
2348 r
= long_array_vtable
;
2349 else if (elt
== float_type_node
)
2350 r
= float_array_vtable
;
2351 else if (elt
== double_type_node
)
2352 r
= double_array_vtable
;
2355 return build_address_of (r
);
2359 java_lang_expand_expr (exp
, target
, tmode
, modifier
)
2361 rtx target ATTRIBUTE_UNUSED
;
2362 enum machine_mode tmode ATTRIBUTE_UNUSED
;
2363 enum expand_modifier modifier ATTRIBUTE_UNUSED
;
2367 switch (TREE_CODE (exp
))
2369 case NEW_ARRAY_INIT
:
2372 tree array_type
= TREE_TYPE (TREE_TYPE (exp
));
2373 tree element_type
= TYPE_ARRAY_ELEMENT (array_type
);
2374 tree data_fld
= TREE_CHAIN (TREE_CHAIN (TYPE_FIELDS (array_type
)));
2375 HOST_WIDE_INT ilength
= java_array_type_length (array_type
);
2376 tree length
= build_int_2 (ilength
, 0);
2377 tree init
= TREE_OPERAND (exp
, 0);
2380 /* See if we can generate the array statically. */
2381 if (TREE_CONSTANT (init
) && TREE_STATIC (exp
)
2382 && JPRIMITIVE_TYPE_P (element_type
))
2384 tree temp
, value
, init_decl
;
2386 START_RECORD_CONSTRUCTOR (temp
, object_type_node
);
2387 PUSH_FIELD_VALUE (temp
, "vtable",
2388 get_primitive_array_vtable (element_type
));
2389 if (! flag_hash_synchronization
)
2390 PUSH_FIELD_VALUE (temp
, "sync_info", null_pointer_node
);
2391 FINISH_RECORD_CONSTRUCTOR (temp
);
2392 START_RECORD_CONSTRUCTOR (value
, array_type
);
2393 PUSH_SUPER_VALUE (value
, temp
);
2394 PUSH_FIELD_VALUE (value
, "length", length
);
2395 PUSH_FIELD_VALUE (value
, "data", init
);
2396 FINISH_RECORD_CONSTRUCTOR (value
);
2398 init_decl
= build_decl (VAR_DECL
, generate_name (), array_type
);
2399 pushdecl_top_level (init_decl
);
2400 TREE_STATIC (init_decl
) = 1;
2401 DECL_INITIAL (init_decl
) = value
;
2402 DECL_IGNORED_P (init_decl
) = 1;
2403 TREE_READONLY (init_decl
) = 1;
2404 rest_of_decl_compilation (init_decl
, NULL
, 1, 0);
2405 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (init_decl
)) = 1;
2406 init
= build1 (ADDR_EXPR
, TREE_TYPE (exp
), init_decl
);
2407 r
= expand_expr (init
, target
, tmode
, modifier
);
2411 array_decl
= build_decl (VAR_DECL
, NULL_TREE
, TREE_TYPE (exp
));
2412 expand_decl (array_decl
);
2413 tmp
= expand_assignment (array_decl
,
2414 build_new_array (element_type
, length
),
2416 if (TREE_CONSTANT (init
)
2417 && ilength
>= 10 && JPRIMITIVE_TYPE_P (element_type
))
2420 init_decl
= build_decl (VAR_DECL
, generate_name (),
2422 pushdecl_top_level (init_decl
);
2423 TREE_STATIC (init_decl
) = 1;
2424 DECL_INITIAL (init_decl
) = init
;
2425 DECL_IGNORED_P (init_decl
) = 1;
2426 TREE_READONLY (init_decl
) = 1;
2427 rest_of_decl_compilation (init_decl
, NULL
, 1, 0);
2428 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (init_decl
)) = 1;
2431 expand_assignment (build (COMPONENT_REF
, TREE_TYPE (data_fld
),
2432 build_java_indirect_ref (array_type
,
2433 array_decl
, flag_check_references
),
2434 data_fld
), init
, 0, 0);
2438 if (BLOCK_EXPR_BODY (exp
))
2441 tree body
= BLOCK_EXPR_BODY (exp
);
2442 pushlevel (2); /* 2 and above */
2443 expand_start_bindings (0);
2444 local
= BLOCK_EXPR_DECLS (exp
);
2447 tree next
= TREE_CHAIN (local
);
2448 layout_decl (local
, 0);
2449 expand_decl (pushdecl (local
));
2452 /* Avoid deep recursion for long block. */
2453 while (TREE_CODE (body
) == COMPOUND_EXPR
)
2455 expand_expr (TREE_OPERAND (body
, 0), const0_rtx
, VOIDmode
, 0);
2457 body
= TREE_OPERAND (body
, 1);
2459 expand_expr (body
, const0_rtx
, VOIDmode
, 0);
2462 expand_end_bindings (getdecls (), 1, 0);
2470 if (pushcase (TREE_OPERAND (exp
, 0), case_identity
,
2471 build_decl (LABEL_DECL
, NULL_TREE
, NULL_TREE
),
2474 EXPR_WFL_LINECOL (wfl_operator
) = EXPR_WFL_LINECOL (exp
);
2476 (wfl_operator
, "Duplicate case label: `%s'",
2477 print_int_node (TREE_OPERAND (exp
, 0)));
2483 pushcase (NULL_TREE
, 0,
2484 build_decl (LABEL_DECL
, NULL_TREE
, NULL_TREE
), NULL
);
2488 expand_start_case (0, TREE_OPERAND (exp
, 0), int_type_node
, "switch");
2489 expand_expr_stmt (TREE_OPERAND (exp
, 1));
2490 expand_end_case (TREE_OPERAND (exp
, 0));
2494 /* We expand a try[-catch] block */
2496 /* Expand the try block */
2497 expand_eh_region_start ();
2498 expand_expr_stmt (TREE_OPERAND (exp
, 0));
2499 expand_start_all_catch ();
2501 /* Expand all catch clauses (EH handlers) */
2502 for (current
= TREE_OPERAND (exp
, 1); current
;
2503 current
= TREE_CHAIN (current
))
2506 tree
catch = TREE_OPERAND (current
, 0);
2507 tree decl
= BLOCK_EXPR_DECLS (catch);
2508 type
= (decl
? TREE_TYPE (TREE_TYPE (decl
)) : NULL_TREE
);
2509 start_catch_handler (prepare_eh_table_type (type
));
2510 expand_expr_stmt (TREE_OPERAND (current
, 0));
2512 expand_resume_after_catch ();
2513 end_catch_handler ();
2515 expand_end_all_catch ();
2519 internal_error ("Can't expand %s", tree_code_name
[TREE_CODE (exp
)]);
2523 /* Go over METHOD's bytecode and note instruction starts in
2524 instruction_bits[]. */
2527 note_instructions (jcf
, method
)
2532 unsigned char* byte_ops
;
2533 long length
= DECL_CODE_LENGTH (method
);
2538 #undef RET /* Defined by config/i386/i386.h */
2539 #undef AND /* Causes problems with opcodes for iand and land. */
2541 #define BCODE byte_ops
2542 #define BYTE_type_node byte_type_node
2543 #define SHORT_type_node short_type_node
2544 #define INT_type_node int_type_node
2545 #define LONG_type_node long_type_node
2546 #define CHAR_type_node char_type_node
2547 #define PTR_type_node ptr_type_node
2548 #define FLOAT_type_node float_type_node
2549 #define DOUBLE_type_node double_type_node
2550 #define VOID_type_node void_type_node
2551 #define CONST_INDEX_1 (saw_index = 1, IMMEDIATE_u1)
2552 #define CONST_INDEX_2 (saw_index = 1, IMMEDIATE_u2)
2553 #define VAR_INDEX_1 (saw_index = 1, IMMEDIATE_u1)
2554 #define VAR_INDEX_2 (saw_index = 1, IMMEDIATE_u2)
2556 #define CHECK_PC_IN_RANGE(PC) ((void)1) /* Already handled by verifier. */
2558 JCF_SEEK (jcf
, DECL_CODE_OFFSET (method
));
2559 byte_ops
= jcf
->read_ptr
;
2560 instruction_bits
= xrealloc (instruction_bits
, length
+ 1);
2561 memset (instruction_bits
, 0, length
+ 1);
2563 /* This pass figures out which PC can be the targets of jumps. */
2564 for (PC
= 0; PC
< length
;)
2566 int oldpc
= PC
; /* PC at instruction start. */
2567 instruction_bits
[PC
] |= BCODE_INSTRUCTION_START
;
2568 switch (byte_ops
[PC
++])
2570 #define JAVAOP(OPNAME, OPCODE, OPKIND, OPERAND_TYPE, OPERAND_VALUE) \
2572 PRE_##OPKIND(OPERAND_TYPE, OPERAND_VALUE); \
2575 #define NOTE_LABEL(PC) note_label(oldpc, PC)
2577 #define PRE_PUSHC(OPERAND_TYPE, OPERAND_VALUE) (void)(OPERAND_VALUE);
2578 #define PRE_LOAD(OPERAND_TYPE, OPERAND_VALUE) (void)(OPERAND_VALUE);
2579 #define PRE_STORE(OPERAND_TYPE, OPERAND_VALUE) (void)(OPERAND_VALUE);
2580 #define PRE_STACK(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2581 #define PRE_UNOP(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2582 #define PRE_BINOP(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2583 #define PRE_CONVERT(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2584 #define PRE_CONVERT2(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2586 #define PRE_SPECIAL(OPERAND_TYPE, INSTRUCTION) \
2587 PRE_SPECIAL_##INSTRUCTION(OPERAND_TYPE)
2588 #define PRE_SPECIAL_IINC(OPERAND_TYPE) \
2589 ((void) IMMEDIATE_u1, (void) IMMEDIATE_s1)
2590 #define PRE_SPECIAL_ENTER(IGNORE) /* nothing */
2591 #define PRE_SPECIAL_EXIT(IGNORE) /* nothing */
2592 #define PRE_SPECIAL_THROW(IGNORE) /* nothing */
2593 #define PRE_SPECIAL_BREAK(IGNORE) /* nothing */
2595 /* two forms of wide instructions */
2596 #define PRE_SPECIAL_WIDE(IGNORE) \
2598 int modified_opcode = IMMEDIATE_u1; \
2599 if (modified_opcode == OPCODE_iinc) \
2601 (void) IMMEDIATE_u2; /* indexbyte1 and indexbyte2 */ \
2602 (void) IMMEDIATE_s2; /* constbyte1 and constbyte2 */ \
2606 (void) IMMEDIATE_u2; /* indexbyte1 and indexbyte2 */ \
2610 #define PRE_IMPL(IGNORE1, IGNORE2) /* nothing */
2612 #define PRE_MONITOR(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2614 #define PRE_RETURN(OPERAND_TYPE, OPERAND_VALUE) /* nothing */
2615 #define PRE_ARRAY(OPERAND_TYPE, SUBOP) \
2616 PRE_ARRAY_##SUBOP(OPERAND_TYPE)
2617 #define PRE_ARRAY_LOAD(TYPE) /* nothing */
2618 #define PRE_ARRAY_STORE(TYPE) /* nothing */
2619 #define PRE_ARRAY_LENGTH(TYPE) /* nothing */
2620 #define PRE_ARRAY_NEW(TYPE) PRE_ARRAY_NEW_##TYPE
2621 #define PRE_ARRAY_NEW_NUM ((void) IMMEDIATE_u1)
2622 #define PRE_ARRAY_NEW_PTR ((void) IMMEDIATE_u2)
2623 #define PRE_ARRAY_NEW_MULTI ((void) IMMEDIATE_u2, (void) IMMEDIATE_u1)
2625 #define PRE_TEST(OPERAND_TYPE, OPERAND_VALUE) NOTE_LABEL (oldpc+IMMEDIATE_s2)
2626 #define PRE_COND(OPERAND_TYPE, OPERAND_VALUE) NOTE_LABEL (oldpc+IMMEDIATE_s2)
2627 #define PRE_BRANCH(OPERAND_TYPE, OPERAND_VALUE) \
2628 saw_index = 0; INT_temp = (OPERAND_VALUE); \
2629 if (!saw_index) NOTE_LABEL(oldpc + INT_temp);
2630 #define PRE_JSR(OPERAND_TYPE, OPERAND_VALUE) \
2631 saw_index = 0; INT_temp = (OPERAND_VALUE); \
2632 if (!saw_index) NOTE_LABEL(oldpc + INT_temp);
2634 #define PRE_RET(OPERAND_TYPE, OPERAND_VALUE) (void)(OPERAND_VALUE)
2636 #define PRE_SWITCH(OPERAND_TYPE, TABLE_OR_LOOKUP) \
2637 PC = (PC + 3) / 4 * 4; PRE_##TABLE_OR_LOOKUP##_SWITCH
2639 #define PRE_LOOKUP_SWITCH \
2640 { jint default_offset = IMMEDIATE_s4; jint npairs = IMMEDIATE_s4; \
2641 NOTE_LABEL (default_offset+oldpc); \
2643 while (--npairs >= 0) { \
2644 jint match ATTRIBUTE_UNUSED = IMMEDIATE_s4; \
2645 jint offset = IMMEDIATE_s4; \
2646 NOTE_LABEL (offset+oldpc); } \
2649 #define PRE_TABLE_SWITCH \
2650 { jint default_offset = IMMEDIATE_s4; \
2651 jint low = IMMEDIATE_s4; jint high = IMMEDIATE_s4; \
2652 NOTE_LABEL (default_offset+oldpc); \
2654 while (low++ <= high) { \
2655 jint offset = IMMEDIATE_s4; \
2656 NOTE_LABEL (offset+oldpc); } \
2659 #define PRE_FIELD(MAYBE_STATIC, PUT_OR_GET) (void)(IMMEDIATE_u2);
2660 #define PRE_OBJECT(MAYBE_STATIC, PUT_OR_GET) (void)(IMMEDIATE_u2);
2661 #define PRE_INVOKE(MAYBE_STATIC, IS_INTERFACE) \
2662 (void)(IMMEDIATE_u2); \
2663 PC += 2 * IS_INTERFACE /* for invokeinterface */;
2665 #include "javaop.def"
2672 expand_byte_code (jcf
, method
)
2678 const unsigned char *linenumber_pointer
;
2679 int dead_code_index
= -1;
2680 unsigned char* byte_ops
;
2681 long length
= DECL_CODE_LENGTH (method
);
2684 JCF_SEEK (jcf
, DECL_CODE_OFFSET (method
));
2685 byte_ops
= jcf
->read_ptr
;
2687 /* We make an initial pass of the line number table, to note
2688 which instructions have associated line number entries. */
2689 linenumber_pointer
= linenumber_table
;
2690 for (i
= 0; i
< linenumber_count
; i
++)
2692 int pc
= GET_u2 (linenumber_pointer
);
2693 linenumber_pointer
+= 4;
2695 warning ("invalid PC in line number table");
2698 if ((instruction_bits
[pc
] & BCODE_HAS_LINENUMBER
) != 0)
2699 instruction_bits
[pc
] |= BCODE_HAS_MULTI_LINENUMBERS
;
2700 instruction_bits
[pc
] |= BCODE_HAS_LINENUMBER
;
2704 if (! verify_jvm_instructions (jcf
, byte_ops
, length
))
2707 /* Translate bytecodes to rtl instructions. */
2708 linenumber_pointer
= linenumber_table
;
2709 for (PC
= 0; PC
< length
;)
2711 if ((instruction_bits
[PC
] & BCODE_TARGET
) != 0 || PC
== 0)
2713 tree label
= lookup_label (PC
);
2714 flush_quick_stack ();
2715 if ((instruction_bits
[PC
] & BCODE_TARGET
) != 0)
2716 expand_label (label
);
2717 if (LABEL_VERIFIED (label
) || PC
== 0)
2718 load_type_state (label
);
2721 if (! (instruction_bits
[PC
] & BCODE_VERIFIED
))
2723 if (dead_code_index
== -1)
2725 /* This is the start of a region of unreachable bytecodes.
2726 They still need to be processed in order for EH ranges
2727 to get handled correctly. However, we can simply
2728 replace these bytecodes with nops. */
2729 dead_code_index
= PC
;
2732 /* Turn this bytecode into a nop. */
2737 if (dead_code_index
!= -1)
2739 /* We've just reached the end of a region of dead code. */
2740 warning ("Unreachable bytecode from %d to before %d.",
2741 dead_code_index
, PC
);
2742 dead_code_index
= -1;
2746 /* Handle possible line number entry for this PC.
2748 This code handles out-of-order and multiple linenumbers per PC,
2749 but is optimized for the case of line numbers increasing
2750 monotonically with PC. */
2751 if ((instruction_bits
[PC
] & BCODE_HAS_LINENUMBER
) != 0)
2753 if ((instruction_bits
[PC
] & BCODE_HAS_MULTI_LINENUMBERS
) != 0
2754 || GET_u2 (linenumber_pointer
) != PC
)
2755 linenumber_pointer
= linenumber_table
;
2756 while (linenumber_pointer
< linenumber_table
+ linenumber_count
* 4)
2758 int pc
= GET_u2 (linenumber_pointer
);
2759 linenumber_pointer
+= 4;
2762 lineno
= GET_u2 (linenumber_pointer
- 2);
2763 emit_line_note (input_filename
, lineno
);
2764 if (!(instruction_bits
[PC
] & BCODE_HAS_MULTI_LINENUMBERS
))
2769 maybe_pushlevels (PC
);
2770 PC
= process_jvm_instruction (PC
, byte_ops
, length
);
2771 maybe_poplevels (PC
);
2774 if (dead_code_index
!= -1)
2776 /* We've just reached the end of a region of dead code. */
2777 warning ("Unreachable bytecode from %d to the end of the method.",
2783 java_push_constant_from_pool (jcf
, index
)
2788 if (JPOOL_TAG (jcf
, index
) == CONSTANT_String
)
2791 name
= get_name_constant (jcf
, JPOOL_USHORT1 (jcf
, index
));
2792 index
= alloc_name_constant (CONSTANT_String
, name
);
2793 c
= build_ref_from_constant_pool (index
);
2794 TREE_TYPE (c
) = promote_type (string_type_node
);
2797 c
= get_constant (jcf
, index
);
2802 process_jvm_instruction (PC
, byte_ops
, length
)
2804 const unsigned char* byte_ops
;
2805 long length ATTRIBUTE_UNUSED
;
2807 const char *opname
; /* Temporary ??? */
2808 int oldpc
= PC
; /* PC at instruction start. */
2810 /* If the instruction is at the beginning of a exception handler,
2811 replace the top of the stack with the thrown object reference */
2812 if (instruction_bits
[PC
] & BCODE_EXCEPTION_TARGET
)
2814 tree type
= pop_type (ptr_type_node
);
2815 push_value (build1 (NOP_EXPR
, type
, soft_exceptioninfo_call_node
));
2818 switch (byte_ops
[PC
++])
2820 #define JAVAOP(OPNAME, OPCODE, OPKIND, OPERAND_TYPE, OPERAND_VALUE) \
2823 OPKIND(OPERAND_TYPE, OPERAND_VALUE); \
2826 #define RET(OPERAND_TYPE, OPERAND_VALUE) \
2828 int saw_index = 0; \
2829 int index = OPERAND_VALUE; \
2830 build_java_ret (find_local_variable (index, ptr_type_node, oldpc)); \
2833 #define JSR(OPERAND_TYPE, OPERAND_VALUE) \
2835 tree where = lookup_label (oldpc+OPERAND_VALUE); \
2836 tree ret = lookup_label (PC); \
2837 build_java_jsr (where, ret); \
2838 load_type_state (ret); \
2841 /* Push a constant onto the stack. */
2842 #define PUSHC(OPERAND_TYPE, OPERAND_VALUE) \
2843 { int saw_index = 0; int ival = (OPERAND_VALUE); \
2844 if (saw_index) java_push_constant_from_pool (current_jcf, ival); \
2845 else expand_java_pushc (ival, OPERAND_TYPE##_type_node); }
2847 /* internal macro added for use by the WIDE case */
2848 #define LOAD_INTERNAL(OPTYPE, OPVALUE) \
2849 push_value (find_local_variable (OPVALUE, type_map[OPVALUE], oldpc));
2851 /* Push local variable onto the opcode stack. */
2852 #define LOAD(OPERAND_TYPE, OPERAND_VALUE) \
2854 /* have to do this since OPERAND_VALUE may have side-effects */ \
2855 int opvalue = OPERAND_VALUE; \
2856 LOAD_INTERNAL(OPERAND_TYPE##_type_node, opvalue); \
2859 #define RETURN(OPERAND_TYPE, OPERAND_VALUE) \
2860 expand_java_return (OPERAND_TYPE##_type_node)
2862 #define REM_EXPR TRUNC_MOD_EXPR
2863 #define BINOP(OPERAND_TYPE, OPERAND_VALUE) \
2864 expand_java_binop (OPERAND_TYPE##_type_node, OPERAND_VALUE##_EXPR)
2866 #define FIELD(IS_STATIC, IS_PUT) \
2867 expand_java_field_op (IS_STATIC, IS_PUT, IMMEDIATE_u2)
2869 #define TEST(OPERAND_TYPE, CONDITION) \
2870 expand_test (CONDITION##_EXPR, OPERAND_TYPE##_type_node, oldpc+IMMEDIATE_s2)
2872 #define COND(OPERAND_TYPE, CONDITION) \
2873 expand_cond (CONDITION##_EXPR, OPERAND_TYPE##_type_node, oldpc+IMMEDIATE_s2)
2875 #define BRANCH(OPERAND_TYPE, OPERAND_VALUE) \
2876 BRANCH_##OPERAND_TYPE (OPERAND_VALUE)
2878 #define BRANCH_GOTO(OPERAND_VALUE) \
2879 expand_java_goto (oldpc + OPERAND_VALUE)
2881 #define BRANCH_CALL(OPERAND_VALUE) \
2882 expand_java_call (oldpc + OPERAND_VALUE, oldpc)
2885 #define BRANCH_RETURN(OPERAND_VALUE) \
2887 tree type = OPERAND_TYPE##_type_node; \
2888 tree value = find_local_variable (OPERAND_VALUE, type, oldpc); \
2889 expand_java_ret (value); \
2893 #define NOT_IMPL(OPERAND_TYPE, OPERAND_VALUE) \
2894 fprintf (stderr, "%3d: %s ", oldpc, opname); \
2895 fprintf (stderr, "(not implemented)\n")
2896 #define NOT_IMPL1(OPERAND_VALUE) \
2897 fprintf (stderr, "%3d: %s ", oldpc, opname); \
2898 fprintf (stderr, "(not implemented)\n")
2900 #define BRANCH_RETURN(OPERAND_VALUE) NOT_IMPL1(OPERAND_VALUE)
2902 #define STACK(SUBOP, COUNT) STACK_##SUBOP (COUNT)
2904 #define STACK_POP(COUNT) java_stack_pop (COUNT)
2906 #define STACK_SWAP(COUNT) java_stack_swap()
2908 #define STACK_DUP(COUNT) java_stack_dup (COUNT, 0)
2909 #define STACK_DUPx1(COUNT) java_stack_dup (COUNT, 1)
2910 #define STACK_DUPx2(COUNT) java_stack_dup (COUNT, 2)
2912 #define SWITCH(OPERAND_TYPE, TABLE_OR_LOOKUP) \
2913 PC = (PC + 3) / 4 * 4; TABLE_OR_LOOKUP##_SWITCH
2915 #define LOOKUP_SWITCH \
2916 { jint default_offset = IMMEDIATE_s4; jint npairs = IMMEDIATE_s4; \
2917 tree selector = pop_value (INT_type_node); \
2918 tree duplicate, label; \
2919 tree type = TREE_TYPE (selector); \
2920 flush_quick_stack (); \
2921 expand_start_case (0, selector, type, "switch statement");\
2922 while (--npairs >= 0) \
2924 jint match = IMMEDIATE_s4; jint offset = IMMEDIATE_s4; \
2925 tree value = build_int_2 (match, match < 0 ? -1 : 0); \
2926 TREE_TYPE (value) = type; \
2927 label = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); \
2928 pushcase (value, convert, label, &duplicate); \
2929 expand_java_goto (oldpc + offset); \
2931 label = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); \
2932 pushcase (NULL_TREE, 0, label, &duplicate); \
2933 expand_java_goto (oldpc + default_offset); \
2934 expand_end_case (selector); \
2937 #define TABLE_SWITCH \
2938 { jint default_offset = IMMEDIATE_s4; \
2939 jint low = IMMEDIATE_s4; jint high = IMMEDIATE_s4; \
2940 tree selector = pop_value (INT_type_node); \
2941 tree duplicate, label; \
2942 tree type = TREE_TYPE (selector); \
2943 flush_quick_stack (); \
2944 expand_start_case (0, selector, type, "switch statement");\
2945 for (; low <= high; low++) \
2947 jint offset = IMMEDIATE_s4; \
2948 tree value = build_int_2 (low, low < 0 ? -1 : 0); \
2949 TREE_TYPE (value) = type; \
2950 label = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); \
2951 pushcase (value, convert, label, &duplicate); \
2952 expand_java_goto (oldpc + offset); \
2954 label = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); \
2955 pushcase (NULL_TREE, 0, label, &duplicate); \
2956 expand_java_goto (oldpc + default_offset); \
2957 expand_end_case (selector); \
2960 #define INVOKE(MAYBE_STATIC, IS_INTERFACE) \
2961 { int opcode = byte_ops[PC-1]; \
2962 int method_ref_index = IMMEDIATE_u2; \
2964 if (IS_INTERFACE) { nargs = IMMEDIATE_u1; (void) IMMEDIATE_u1; } \
2966 expand_invoke (opcode, method_ref_index, nargs); \
2969 /* Handle new, checkcast, instanceof */
2970 #define OBJECT(TYPE, OP) \
2971 expand_java_##OP (get_class_constant (current_jcf, IMMEDIATE_u2))
2973 #define ARRAY(OPERAND_TYPE, SUBOP) ARRAY_##SUBOP(OPERAND_TYPE)
2975 #define ARRAY_LOAD(OPERAND_TYPE) \
2977 expand_java_arrayload( OPERAND_TYPE##_type_node ); \
2980 #define ARRAY_STORE(OPERAND_TYPE) \
2982 expand_java_arraystore( OPERAND_TYPE##_type_node ); \
2985 #define ARRAY_LENGTH(OPERAND_TYPE) expand_java_array_length();
2986 #define ARRAY_NEW(OPERAND_TYPE) ARRAY_NEW_##OPERAND_TYPE()
2987 #define ARRAY_NEW_PTR() \
2988 push_value (build_anewarray (get_class_constant (current_jcf, \
2990 pop_value (int_type_node)));
2991 #define ARRAY_NEW_NUM() \
2993 int atype = IMMEDIATE_u1; \
2994 push_value (build_newarray (atype, pop_value (int_type_node)));\
2996 #define ARRAY_NEW_MULTI() \
2998 tree class = get_class_constant (current_jcf, IMMEDIATE_u2 ); \
2999 int ndims = IMMEDIATE_u1; \
3000 expand_java_multianewarray( class, ndims ); \
3003 #define UNOP(OPERAND_TYPE, OPERAND_VALUE) \
3004 push_value (fold (build1 (NEGATE_EXPR, OPERAND_TYPE##_type_node, \
3005 pop_value (OPERAND_TYPE##_type_node))));
3007 #define CONVERT2(FROM_TYPE, TO_TYPE) \
3009 push_value (build1 (NOP_EXPR, int_type_node, \
3010 (convert (TO_TYPE##_type_node, \
3011 pop_value (FROM_TYPE##_type_node))))); \
3014 #define CONVERT(FROM_TYPE, TO_TYPE) \
3016 push_value (convert (TO_TYPE##_type_node, \
3017 pop_value (FROM_TYPE##_type_node))); \
3020 /* internal macro added for use by the WIDE case
3021 Added TREE_TYPE (decl) assignment, apbianco */
3022 #define STORE_INTERNAL(OPTYPE, OPVALUE) \
3025 int var = OPVALUE; \
3026 tree type = OPTYPE; \
3027 value = pop_value (type); \
3028 type = TREE_TYPE (value); \
3029 decl = find_local_variable (var, type, oldpc); \
3030 set_local_type (var, type ); \
3031 expand_assignment (decl, value, 0, 0); \
3034 #define STORE(OPERAND_TYPE, OPERAND_VALUE) \
3036 /* have to do this since OPERAND_VALUE may have side-effects */ \
3037 int opvalue = OPERAND_VALUE; \
3038 STORE_INTERNAL(OPERAND_TYPE##_type_node, opvalue); \
3041 #define SPECIAL(OPERAND_TYPE, INSTRUCTION) \
3042 SPECIAL_##INSTRUCTION(OPERAND_TYPE)
3044 #define SPECIAL_ENTER(IGNORED) MONITOR_OPERATION (soft_monitorenter_node)
3045 #define SPECIAL_EXIT(IGNORED) MONITOR_OPERATION (soft_monitorexit_node)
3047 #define MONITOR_OPERATION(call) \
3049 tree o = pop_value (ptr_type_node); \
3051 flush_quick_stack (); \
3052 c = build_java_monitor (call, o); \
3053 TREE_SIDE_EFFECTS (c) = 1; \
3054 expand_expr_stmt (c); \
3057 #define SPECIAL_IINC(IGNORED) \
3059 unsigned int local_var_index = IMMEDIATE_u1; \
3060 int ival = IMMEDIATE_s1; \
3061 expand_iinc(local_var_index, ival, oldpc); \
3064 #define SPECIAL_WIDE(IGNORED) \
3066 int modified_opcode = IMMEDIATE_u1; \
3067 unsigned int local_var_index = IMMEDIATE_u2; \
3068 switch (modified_opcode) \
3072 int ival = IMMEDIATE_s2; \
3073 expand_iinc (local_var_index, ival, oldpc); \
3076 case OPCODE_iload: \
3077 case OPCODE_lload: \
3078 case OPCODE_fload: \
3079 case OPCODE_dload: \
3080 case OPCODE_aload: \
3082 /* duplicate code from LOAD macro */ \
3083 LOAD_INTERNAL(operand_type[modified_opcode], local_var_index); \
3086 case OPCODE_istore: \
3087 case OPCODE_lstore: \
3088 case OPCODE_fstore: \
3089 case OPCODE_dstore: \
3090 case OPCODE_astore: \
3092 STORE_INTERNAL(operand_type[modified_opcode], local_var_index); \
3096 error ("unrecogized wide sub-instruction"); \
3100 #define SPECIAL_THROW(IGNORED) \
3101 build_java_athrow (pop_value (throwable_type_node))
3103 #define SPECIAL_BREAK NOT_IMPL1
3104 #define IMPL NOT_IMPL
3106 #include "javaop.def"
3109 fprintf (stderr
, "%3d: unknown(%3d)\n", oldpc
, byte_ops
[PC
]);
3114 /* Return the opcode at PC in the code section pointed to by
3117 static unsigned char
3118 peek_opcode_at_pc (jcf
, code_offset
, pc
)
3120 int code_offset
, pc
;
3122 unsigned char opcode
;
3123 long absolute_offset
= (long)JCF_TELL (jcf
);
3125 JCF_SEEK (jcf
, code_offset
);
3126 opcode
= jcf
->read_ptr
[pc
];
3127 JCF_SEEK (jcf
, absolute_offset
);
3131 /* Some bytecode compilers are emitting accurate LocalVariableTable
3132 attributes. Here's an example:
3137 Attribute "LocalVariableTable"
3138 slot #<n>: ... (PC: PC+1 length: L)
3140 This is accurate because the local in slot <n> really exists after
3141 the opcode at PC is executed, hence from PC+1 to PC+1+L.
3143 This procedure recognizes this situation and extends the live range
3144 of the local in SLOT to START_PC-1 or START_PC-2 (depending on the
3145 length of the store instruction.)
3147 This function is used by `give_name_to_locals' so that a local's
3148 DECL features a DECL_LOCAL_START_PC such that the first related
3149 store operation will use DECL as a destination, not a unrelated
3150 temporary created for the occasion.
3152 This function uses a global (instruction_bits) `note_instructions' should
3153 have allocated and filled properly. */
3156 maybe_adjust_start_pc (jcf
, code_offset
, start_pc
, slot
)
3158 int code_offset
, start_pc
, slot
;
3160 int first
, index
, opcode
;
3169 /* Find last previous instruction and remember it */
3170 for (pc
= start_pc
-1; pc
; pc
--)
3171 if (instruction_bits
[pc
] & BCODE_INSTRUCTION_START
)
3175 /* Retrieve the instruction, handle `wide'. */
3176 opcode
= (int) peek_opcode_at_pc (jcf
, code_offset
, pc
++);
3177 if (opcode
== OPCODE_wide
)
3180 opcode
= (int) peek_opcode_at_pc (jcf
, code_offset
, pc
++);
3185 case OPCODE_astore_0
:
3186 case OPCODE_astore_1
:
3187 case OPCODE_astore_2
:
3188 case OPCODE_astore_3
:
3189 first
= OPCODE_astore_0
;
3192 case OPCODE_istore_0
:
3193 case OPCODE_istore_1
:
3194 case OPCODE_istore_2
:
3195 case OPCODE_istore_3
:
3196 first
= OPCODE_istore_0
;
3199 case OPCODE_lstore_0
:
3200 case OPCODE_lstore_1
:
3201 case OPCODE_lstore_2
:
3202 case OPCODE_lstore_3
:
3203 first
= OPCODE_lstore_0
;
3206 case OPCODE_fstore_0
:
3207 case OPCODE_fstore_1
:
3208 case OPCODE_fstore_2
:
3209 case OPCODE_fstore_3
:
3210 first
= OPCODE_fstore_0
;
3213 case OPCODE_dstore_0
:
3214 case OPCODE_dstore_1
:
3215 case OPCODE_dstore_2
:
3216 case OPCODE_dstore_3
:
3217 first
= OPCODE_dstore_0
;
3225 index
= peek_opcode_at_pc (jcf
, code_offset
, pc
);
3228 int other
= peek_opcode_at_pc (jcf
, code_offset
, ++pc
);
3229 index
= (other
<< 8) + index
;
3234 /* Now we decide: first >0 means we have a <t>store_<n>, index >0
3235 means we have a <t>store. */
3236 if ((first
> 0 && opcode
- first
== slot
) || (index
> 0 && index
== slot
))
3242 /* Force the (direct) sub-operands of NODE to be evaluated in left-to-right
3243 order, as specified by Java Language Specification.
3245 The problem is that while expand_expr will evaluate its sub-operands in
3246 left-to-right order, for variables it will just return an rtx (i.e.
3247 an lvalue) for the variable (rather than an rvalue). So it is possible
3248 that a later sub-operand will change the register, and when the
3249 actual operation is done, it will use the new value, when it should
3250 have used the original value.
3252 We fix this by using save_expr. This forces the sub-operand to be
3253 copied into a fresh virtual register,
3255 For method invocation, we modify the arguments so that a
3256 left-to-right order evaluation is performed. Saved expressions
3257 will, in CALL_EXPR order, be reused when the call will be expanded.
3261 force_evaluation_order (node
)
3264 if (flag_syntax_only
)
3266 if (TREE_CODE_CLASS (TREE_CODE (node
)) == '2')
3268 if (TREE_SIDE_EFFECTS (TREE_OPERAND (node
, 1)))
3269 TREE_OPERAND (node
, 0) = save_expr (TREE_OPERAND (node
, 0));
3271 else if (TREE_CODE (node
) == CALL_EXPR
|| TREE_CODE (node
) == NEW_CLASS_EXPR
)
3275 if (!TREE_OPERAND (node
, 1))
3278 /* This reverses the evaluation order. This is a desired effect. */
3279 for (cmp
= NULL_TREE
, arg
= TREE_OPERAND (node
, 1);
3280 arg
; arg
= TREE_CHAIN (arg
))
3282 tree saved
= save_expr (force_evaluation_order (TREE_VALUE (arg
)));
3283 cmp
= (cmp
== NULL_TREE
? saved
:
3284 build (COMPOUND_EXPR
, void_type_node
, cmp
, saved
));
3285 TREE_VALUE (arg
) = saved
;
3288 if (cmp
&& TREE_CODE (cmp
) == COMPOUND_EXPR
)
3289 TREE_SIDE_EFFECTS (cmp
) = 1;
3293 cmp
= save_expr (build (COMPOUND_EXPR
, TREE_TYPE (node
), cmp
, node
));
3294 CAN_COMPLETE_NORMALLY (cmp
) = CAN_COMPLETE_NORMALLY (node
);
3295 TREE_SIDE_EFFECTS (cmp
) = 1;