1 /* Handle verification of bytecoded methods for the GNU compiler for
3 Copyright (C) 1997, 1998, 1999, 2000 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. */
29 #include "java-tree.h"
31 #include "java-opcodes.h"
33 #include "java-except.h"
36 static void push_pending_label PARAMS ((tree));
37 static tree merge_types PARAMS ((tree, tree));
38 static const char *check_pending_block PARAMS ((tree));
39 static void type_stack_dup PARAMS ((int, int));
40 static int start_pc_cmp PARAMS ((const PTR, const PTR));
42 extern int stack_pointer;
44 /* During verification, start of the current subroutine (jsr target). */
47 /* A list of pending blocks, chained using LABEL_PENDING_CHAIN.
48 A pending block is one that has LABEL_CHANGED set, which means
49 it requires (re-) verification. */
52 /* Append TARGET_LABEL to the pending_block stack unless already in it. */
55 push_pending_label (target_label)
58 if (! LABEL_CHANGED (target_label))
60 LABEL_PENDING_CHAIN (target_label) = pending_blocks;
61 pending_blocks = target_label;
62 LABEL_CHANGED (target_label) = 1;
66 /* Note that TARGET_LABEL is a possible successor instruction.
67 Merge the type state etc.
68 Return NULL on sucess, or an error message on failure. */
71 check_pending_block (target_label)
74 int changed = merge_type_state (target_label);
79 return "types could not be merged";
80 push_pending_label (target_label);
83 if (current_subr == NULL)
85 if (LABEL_IN_SUBR (target_label))
86 return "might transfer control into subroutine";
90 if (LABEL_IN_SUBR (target_label))
92 if (LABEL_SUBR_START (target_label) != current_subr)
93 return "transfer out of subroutine";
95 else if (! LABEL_VERIFIED (target_label))
97 LABEL_IN_SUBR (target_label) = 1;
98 LABEL_SUBR_START (target_label) = current_subr;
101 return "transfer out of subroutine";
106 /* Return the "merged" types of TYPE1 and TYPE2.
107 If either is primitive, the other must match (after promotion to int).
108 For reference types, return the common super-class.
109 Return TYPE_UNKNOWN if the types cannot be merged. */
112 merge_types (type1, type2)
117 if (type1 == TYPE_UNKNOWN || type2 == TYPE_UNKNOWN
118 || type1 == TYPE_RETURN_ADDR || type2 == TYPE_RETURN_ADDR)
120 if (TREE_CODE (type1) == POINTER_TYPE && TREE_CODE (type2) == POINTER_TYPE)
124 /* ptr_type_node is only used for a null reference,
125 which is compatible with any reference type. */
126 if (type1 == ptr_type_node || type2 == object_ptr_type_node)
128 if (type2 == ptr_type_node || type1 == object_ptr_type_node)
131 tt1 = HANDLE_TO_CLASS_TYPE (TREE_TYPE (type1));
132 tt2 = HANDLE_TO_CLASS_TYPE (TREE_TYPE (type2));
134 /* If tt{1,2} haven't been properly loaded, now is a good time
136 if (!TYPE_SIZE (tt1))
139 safe_layout_class (tt1);
142 if (!TYPE_SIZE (tt2))
145 safe_layout_class (tt2);
148 if (TYPE_ARRAY_P (tt1) || TYPE_ARRAY_P (tt2))
150 if (TYPE_ARRAY_P (tt1) == TYPE_ARRAY_P (tt2))
152 tree el_type1 = TYPE_ARRAY_ELEMENT (tt1);
153 tree el_type2 = TYPE_ARRAY_ELEMENT (tt2);
154 tree el_type = NULL_TREE;
155 if (el_type1 == el_type2)
157 else if (TREE_CODE (el_type1) == POINTER_TYPE
158 && TREE_CODE (el_type2) == POINTER_TYPE)
159 el_type = merge_types (el_type1, el_type2);
160 if (el_type != NULL_TREE)
162 HOST_WIDE_INT len1 = java_array_type_length (tt1);
163 HOST_WIDE_INT len2 = java_array_type_length (tt2);
166 else if (el_type1 == el_type2)
168 return promote_type (build_java_array_type (el_type, len1));
171 return object_ptr_type_node;
174 if (CLASS_INTERFACE (TYPE_NAME (tt1)))
176 /* FIXME: should see if two interfaces have a common
178 if (CLASS_INTERFACE (TYPE_NAME (tt2)))
180 /* This is a kludge, but matches what Sun's verifier does.
181 It can be tricked, but is safe as long as type errors
182 (i.e. interface method calls) are caught at run-time. */
183 return object_ptr_type_node;
187 if (can_widen_reference_to (tt2, tt1))
190 return object_ptr_type_node;
193 else if (CLASS_INTERFACE (TYPE_NAME (tt2)))
195 if (can_widen_reference_to (tt1, tt2))
198 return object_ptr_type_node;
204 depth1 = class_depth (type1);
205 depth2 = class_depth (type2);
206 for ( ; depth1 > depth2; depth1--)
207 type1 = TYPE_BINFO_BASETYPE (type1, 0);
208 for ( ; depth2 > depth1; depth2--)
209 type2 = TYPE_BINFO_BASETYPE (type2, 0);
210 while (type1 != type2)
212 type1 = TYPE_BINFO_BASETYPE (type1, 0);
213 type2 = TYPE_BINFO_BASETYPE (type2, 0);
215 return promote_type (type1);
217 if (INTEGRAL_TYPE_P (type1) && INTEGRAL_TYPE_P (type2)
218 && TYPE_PRECISION (type1) <= 32 && TYPE_PRECISION (type2) <= 32)
219 return int_type_node;
223 /* Merge the current type state with that at LABEL.
224 Return -1 the the states are incompatible (i.e. on error),
225 0 if there was no change, and 1 if there was a change. */
228 merge_type_state (label)
231 int nlocals = DECL_MAX_LOCALS (current_function_decl);
232 int cur_length = stack_pointer + nlocals;
233 tree vec = LABEL_TYPE_STATE (label);
235 if (vec == NULL_TREE)
239 vec = make_tree_vec (cur_length);
240 LABEL_TYPE_STATE (label) = vec;
242 while (--cur_length >= 0)
243 TREE_VEC_ELT (vec, cur_length) = type_map [cur_length];
250 if (LABEL_IS_SUBR_START (label) && LABEL_VERIFIED (label)
251 && current_subr != label)
252 return_map = LABEL_RETURN_TYPE_STATE (label);
254 return_map = NULL_TREE;
255 if (TREE_VEC_LENGTH (vec) != cur_length)
259 for (i = 0; i < cur_length; i++)
261 tree old_type = TREE_VEC_ELT (vec, i);
262 tree new_type = merge_types (old_type, type_map [i]);
263 if (TREE_VEC_ELT (vec, i) != new_type)
265 /* If there has been a change, note that since we must re-verify.
266 However, if the label is the start of a subroutine,
267 we don't care about local variables that are neither
268 set nor used in the sub-routine. */
269 if (return_map == NULL_TREE || i >= nlocals
270 || TREE_VEC_ELT (return_map, i) != TYPE_UNUSED
271 || (TYPE_IS_WIDE (new_type)
272 && TREE_VEC_ELT (return_map, i+1) != TYPE_UNUSED))
275 TREE_VEC_ELT (vec, i) = new_type;
276 if (new_type == TYPE_UNKNOWN)
281 else if (TYPE_IS_WIDE (new_type))
288 /* Handle dup-like operations. */
291 type_stack_dup (size, offset)
296 if (size + offset > stack_pointer)
297 error ("stack underflow - dup* operation");
298 for (index = 0; index < size + offset; index++)
300 type[index] = stack_type_map[stack_pointer - 1];
301 if (type[index] == void_type_node)
304 type[index] = stack_type_map[stack_pointer - 2];
305 if (! TYPE_IS_WIDE (type[index]))
306 fatal ("internal error - dup operation");
307 if (index == size || index == size + offset)
308 fatal ("dup operation splits 64-bit number");
310 pop_type (type[index]);
312 for (index = size; --index >= 0; )
314 if (type[index] != void_type_node)
315 push_type (type[index]);
318 for (index = size + offset; --index >= 0; )
320 if (type[index] != void_type_node)
321 push_type (type[index]);
325 /* This keeps track of a start PC and corresponding initial index. */
332 /* A helper that is used when sorting exception ranges. */
334 start_pc_cmp (xp, yp)
338 const struct pc_index *x = (const struct pc_index *) xp;
339 const struct pc_index *y = (const struct pc_index *) yp;
340 return x->start_pc - y->start_pc;
343 /* This causes the next iteration to ignore the next instruction
344 and look for some other unhandled instruction. */
345 #define INVALIDATE_PC (prevpc = -1, oldpc = PC, PC = INVALID_PC)
346 #define INVALID_PC (-1)
348 #define VERIFICATION_ERROR(MESSAGE) \
349 do { message = MESSAGE; goto verify_error; } while (0)
351 #define VERIFICATION_ERROR_WITH_INDEX(MESSAGE) \
352 do { message = MESSAGE; goto error_with_index; } while (0)
354 /* Recursive helper function to pop argument types during verifiation.
355 ARG_TYPES is the list of formal parameter types.
356 Return NULL on success and a freshly malloc'd error message on failure. */
359 pop_argument_types (arg_types)
362 if (arg_types == end_params_node)
364 if (TREE_CODE (arg_types) == TREE_LIST)
366 char *message = pop_argument_types (TREE_CHAIN (arg_types));
368 pop_type_0 (TREE_VALUE (arg_types), &message);
374 #define POP_TYPE(TYPE, MESSAGE) \
375 do { pmessage = NULL; pop_type_0 (TYPE, &pmessage); \
376 if (pmessage != NULL) goto pop_type_error; \
379 #define POP_TYPE_CONV(TYPE, POPPED_TYPE, MESSAGE) \
380 do { pmessage = NULL; POPPED_TYPE = pop_type_0 (TYPE, &pmessage); \
381 if (pmessage != NULL) goto pop_type_error; \
384 #define PUSH_TYPE(TYPE) \
385 do { if (! push_type_0 (TYPE)) { goto stack_overflow; }} while (0)
387 #define PUSH_PENDING(LABEL) \
388 do { tree tmplab = LABEL; \
389 if ((message = check_pending_block (tmplab)) != NULL) \
390 { oldpc = LABEL_PC (tmplab); goto verify_error; }} while (0)
393 #define CHECK_PC_IN_RANGE(PC) ({if (PC < 0 || PC > length) goto bad_pc; (void)1;})
395 #define CHECK_PC_IN_RANGE(PC) (PC < 0 || PC > length ? \
396 (fatal("Bad byte codes.\n"), 0) : 1)
399 #define BCODE byte_ops
401 /* Verify the bytecodes of the current method.
402 Return 1 on sucess, 0 on failure. */
404 verify_jvm_instructions (jcf, byte_ops, length)
406 const unsigned char *byte_ops;
413 int oldpc = 0; /* PC of start of instruction. */
414 int prevpc = 0; /* If >= 0, PC of previous instruction. */
419 register unsigned char *p;
420 struct eh_range *prev_eh_ranges = NULL_EH_RANGE;
421 struct eh_range *eh_ranges;
422 tree return_type = TREE_TYPE (TREE_TYPE (current_function_decl));
423 struct pc_index *starts;
428 pending_blocks = NULL_TREE;
430 /* Handle the exception table. */
431 method_init_exceptions ();
432 JCF_SEEK (jcf, DECL_CODE_OFFSET (current_function_decl) + length);
433 eh_count = JCF_readu2 (jcf);
435 /* We read the exception handlers in order of increasing start PC.
436 To do this we first read and sort the start PCs. */
437 starts = (struct pc_index *) xmalloc (eh_count * sizeof (struct pc_index));
438 for (i = 0; i < eh_count; ++i)
440 starts[i].start_pc = GET_u2 (jcf->read_ptr + 8 * i);
443 qsort (starts, eh_count, sizeof (struct pc_index), start_pc_cmp);
445 for (i = 0; i < eh_count; ++i)
447 int start_pc, end_pc, handler_pc, catch_type;
449 p = jcf->read_ptr + 8 * starts[i].index;
451 start_pc = GET_u2 (p);
452 end_pc = GET_u2 (p+2);
453 handler_pc = GET_u2 (p+4);
454 catch_type = GET_u2 (p+6);
456 if (start_pc < 0 || start_pc >= length
457 || end_pc < 0 || end_pc > length || start_pc >= end_pc
458 || handler_pc < 0 || handler_pc >= length
459 || (handler_pc >= start_pc && handler_pc < end_pc)
460 || ! (instruction_bits [start_pc] & BCODE_INSTRUCTION_START)
461 || (end_pc < length &&
462 ! (instruction_bits [end_pc] & BCODE_INSTRUCTION_START))
463 || ! (instruction_bits [handler_pc] & BCODE_INSTRUCTION_START))
465 error ("bad pc in exception_table");
470 add_handler (start_pc, end_pc,
471 lookup_label (handler_pc),
472 catch_type == 0 ? NULL_TREE
473 : get_class_constant (jcf, catch_type));
475 instruction_bits [handler_pc] |= BCODE_EXCEPTION_TARGET;
479 handle_nested_ranges ();
484 if (((PC != INVALID_PC
485 && instruction_bits [PC] & BCODE_TARGET) != 0)
488 PUSH_PENDING (lookup_label (PC));
491 /* Check if there are any more pending blocks in the current
492 subroutine. Because we push pending blocks in a
493 last-in-first-out order, and because we don't push anything
494 from our caller until we are done with this subroutine or
495 anything nested in it, then we are done if the top of the
496 pending_blocks stack is not in a subroutine, or it is in our
501 tree caller = LABEL_SUBR_CONTEXT (current_subr);
503 if (pending_blocks == NULL_TREE
504 || ! LABEL_IN_SUBR (pending_blocks)
505 || LABEL_SUBR_START (pending_blocks) == caller)
507 int size = DECL_MAX_LOCALS(current_function_decl)+stack_pointer;
508 tree ret_map = LABEL_RETURN_TYPE_STATE (current_subr);
509 tmp = LABEL_RETURN_LABELS (current_subr);
511 /* FIXME: If we exit a subroutine via a throw, we might
512 have returned to an earlier caller. Obviously a
513 "ret" can only return one level, but a throw may
514 return many levels.*/
515 current_subr = caller;
517 if (RETURN_MAP_ADJUSTED (ret_map))
519 /* Since we are done with this subroutine , set up
520 the (so far known) return address as pending -
521 with the merged type state. */
522 for ( ; tmp != NULL_TREE; tmp = TREE_CHAIN (tmp))
524 tree return_label = TREE_VALUE (tmp);
525 tree return_state = LABEL_TYPE_STATE (return_label);
526 if (return_state == NULL_TREE)
528 /* This means means we had not verified the
529 subroutine earlier, so this is the first jsr to
530 call it. In this case, the type_map of the return
531 address is just the current type_map - and that
532 is handled by the following PUSH_PENDING. */
536 /* In this case we have to do a merge. But first
537 restore the type_map for unused slots to those
538 that were in effect at the jsr. */
539 for (index = size; --index >= 0; )
541 type_map[index] = TREE_VEC_ELT (ret_map, index);
542 if (type_map[index] == TYPE_UNUSED)
544 = TREE_VEC_ELT (return_state, index);
547 PUSH_PENDING (return_label);
552 if (PC == INVALID_PC)
554 label = pending_blocks;
555 if (label == NULL_TREE)
556 break; /* We're done! */
557 pending_blocks = LABEL_PENDING_CHAIN (label);
558 LABEL_CHANGED (label) = 0;
560 if (LABEL_IN_SUBR (label))
561 current_subr = LABEL_SUBR_START (label);
563 current_subr = NULL_TREE;
565 /* Restore type_map and stack_pointer from
566 LABEL_TYPE_STATE (label), and continue
567 compiling from there. */
568 load_type_state (label);
569 PC = LABEL_PC (label);
571 else if (PC >= length)
572 VERIFICATION_ERROR ("falling through end of method");
574 /* fprintf (stderr, "** %d\n", PC); */
578 if (!(instruction_bits [PC] & BCODE_INSTRUCTION_START) && ! wide)
579 VERIFICATION_ERROR ("PC not at instruction start");
581 instruction_bits[PC] |= BCODE_VERIFIED;
583 eh_ranges = find_handler (oldpc);
585 op_code = byte_ops[PC++];
588 int is_static, is_putting;
591 case OPCODE_iconst_m1:
592 case OPCODE_iconst_0: case OPCODE_iconst_1: case OPCODE_iconst_2:
593 case OPCODE_iconst_3: case OPCODE_iconst_4: case OPCODE_iconst_5:
594 i = op_code - OPCODE_iconst_0;
597 if (byte_ops[PC] == OPCODE_newarray
598 || byte_ops[PC] == OPCODE_newarray)
600 PUSH_TYPE (int_type_node); break;
601 case OPCODE_lconst_0: case OPCODE_lconst_1:
602 PUSH_TYPE (long_type_node); break;
603 case OPCODE_fconst_0: case OPCODE_fconst_1: case OPCODE_fconst_2:
604 PUSH_TYPE (float_type_node); break;
605 case OPCODE_dconst_0: case OPCODE_dconst_1:
606 PUSH_TYPE (double_type_node); break;
613 case OPCODE_iload: type = int_type_node; goto general_load;
614 case OPCODE_lload: type = long_type_node; goto general_load;
615 case OPCODE_fload: type = float_type_node; goto general_load;
616 case OPCODE_dload: type = double_type_node; goto general_load;
617 case OPCODE_aload: type = ptr_type_node; goto general_load;
619 index = wide ? IMMEDIATE_u2 : IMMEDIATE_u1;
622 case OPCODE_iload_0: type = int_type_node; index = 0; goto load;
623 case OPCODE_iload_1: type = int_type_node; index = 1; goto load;
624 case OPCODE_iload_2: type = int_type_node; index = 2; goto load;
625 case OPCODE_iload_3: type = int_type_node; index = 3; goto load;
626 case OPCODE_lload_0: type = long_type_node; index = 0; goto load;
627 case OPCODE_lload_1: type = long_type_node; index = 1; goto load;
628 case OPCODE_lload_2: type = long_type_node; index = 2; goto load;
629 case OPCODE_lload_3: type = long_type_node; index = 3; goto load;
630 case OPCODE_fload_0: type = float_type_node; index = 0; goto load;
631 case OPCODE_fload_1: type = float_type_node; index = 1; goto load;
632 case OPCODE_fload_2: type = float_type_node; index = 2; goto load;
633 case OPCODE_fload_3: type = float_type_node; index = 3; goto load;
634 case OPCODE_dload_0: type = double_type_node; index = 0; goto load;
635 case OPCODE_dload_1: type = double_type_node; index = 1; goto load;
636 case OPCODE_dload_2: type = double_type_node; index = 2; goto load;
637 case OPCODE_dload_3: type = double_type_node; index = 3; goto load;
638 case OPCODE_aload_0: type = ptr_type_node; index = 0; goto load;
639 case OPCODE_aload_1: type = ptr_type_node; index = 1; goto load;
640 case OPCODE_aload_2: type = ptr_type_node; index = 2; goto load;
641 case OPCODE_aload_3: type = ptr_type_node; index = 3; goto load;
644 || (index + TYPE_IS_WIDE (type)
645 >= DECL_MAX_LOCALS (current_function_decl)))
646 VERIFICATION_ERROR_WITH_INDEX
647 ("invalid local variable index %d in load");
648 tmp = type_map[index];
649 if (tmp == TYPE_UNKNOWN)
650 VERIFICATION_ERROR_WITH_INDEX
651 ("loading local variable %d which has unknown type");
652 else if (tmp == TYPE_SECOND
653 || (TYPE_IS_WIDE (type)
654 && type_map[index+1] != void_type_node)
655 || (type == ptr_type_node
656 ? TREE_CODE (tmp) != POINTER_TYPE
657 : type == int_type_node
658 ? (! INTEGRAL_TYPE_P (tmp) || TYPE_PRECISION (tmp) > 32)
660 VERIFICATION_ERROR_WITH_INDEX
661 ("loading local variable %d which has invalid type");
664 case OPCODE_istore: type = int_type_node; goto general_store;
665 case OPCODE_lstore: type = long_type_node; goto general_store;
666 case OPCODE_fstore: type = float_type_node; goto general_store;
667 case OPCODE_dstore: type = double_type_node; goto general_store;
668 case OPCODE_astore: type = object_ptr_type_node; goto general_store;
670 index = wide ? IMMEDIATE_u2 : IMMEDIATE_u1;
673 case OPCODE_istore_0: type = int_type_node; index = 0; goto store;
674 case OPCODE_istore_1: type = int_type_node; index = 1; goto store;
675 case OPCODE_istore_2: type = int_type_node; index = 2; goto store;
676 case OPCODE_istore_3: type = int_type_node; index = 3; goto store;
677 case OPCODE_lstore_0: type = long_type_node; index=0; goto store;
678 case OPCODE_lstore_1: type = long_type_node; index=1; goto store;
679 case OPCODE_lstore_2: type = long_type_node; index=2; goto store;
680 case OPCODE_lstore_3: type = long_type_node; index=3; goto store;
681 case OPCODE_fstore_0: type=float_type_node; index=0; goto store;
682 case OPCODE_fstore_1: type=float_type_node; index=1; goto store;
683 case OPCODE_fstore_2: type=float_type_node; index=2; goto store;
684 case OPCODE_fstore_3: type=float_type_node; index=3; goto store;
685 case OPCODE_dstore_0: type=double_type_node; index=0; goto store;
686 case OPCODE_dstore_1: type=double_type_node; index=1; goto store;
687 case OPCODE_dstore_2: type=double_type_node; index=2; goto store;
688 case OPCODE_dstore_3: type=double_type_node; index=3; goto store;
689 case OPCODE_astore_0: type = ptr_type_node; index = 0; goto store;
690 case OPCODE_astore_1: type = ptr_type_node; index = 1; goto store;
691 case OPCODE_astore_2: type = ptr_type_node; index = 2; goto store;
692 case OPCODE_astore_3: type = ptr_type_node; index = 3; goto store;
695 || (index + TYPE_IS_WIDE (type)
696 >= DECL_MAX_LOCALS (current_function_decl)))
698 VERIFICATION_ERROR_WITH_INDEX
699 ("invalid local variable index %d in store");
702 POP_TYPE_CONV (type, type, NULL);
703 type_map[index] = type;
705 /* If local variable changed, we need to reconsider eh handlers. */
706 prev_eh_ranges = NULL_EH_RANGE;
708 /* Allocate decl and rtx for this variable now, so if we're not
709 optmizing, we get a temporary that survives the whole method. */
710 find_local_variable (index, type, oldpc);
712 if (TYPE_IS_WIDE (type))
713 type_map[index+1] = TYPE_SECOND;
714 /* ... fall through to note_used ... */
716 /* For store or load, note that local variable INDEX is used.
717 This is needed to verify try-finally sub-routines. */
720 tree vec = LABEL_RETURN_TYPE_STATE (current_subr);
721 tree subr_vec = LABEL_TYPE_STATE (current_subr);
722 int len = 1 + TYPE_IS_WIDE (type);
725 if (TREE_VEC_ELT (vec, index) == TYPE_UNUSED)
726 TREE_VEC_ELT (vec, index) = TREE_VEC_ELT (subr_vec, index);
741 type = int_type_node; goto binop;
746 type = int_type_node; goto unop;
755 type = long_type_node; goto binop;
757 type = long_type_node; goto unop;
758 case OPCODE_fadd: case OPCODE_fsub:
759 case OPCODE_fmul: case OPCODE_fdiv: case OPCODE_frem:
760 type = float_type_node; goto binop;
762 type = float_type_node; goto unop;
763 case OPCODE_dadd: case OPCODE_dsub:
764 case OPCODE_dmul: case OPCODE_ddiv: case OPCODE_drem:
765 type = double_type_node; goto binop;
767 type = double_type_node; goto unop;
780 pop_type (int_type_node);
781 pop_type (long_type_node);
782 PUSH_TYPE (long_type_node);
785 index = wide ? IMMEDIATE_u2 : IMMEDIATE_u1;
788 if (index < 0 || index >= DECL_MAX_LOCALS (current_function_decl))
789 VERIFICATION_ERROR ("invalid local variable index in iinc");
790 tmp = type_map[index];
792 || ! INTEGRAL_TYPE_P (tmp) || TYPE_PRECISION (tmp) > 32)
793 VERIFICATION_ERROR ("invalid local variable type in iinc");
796 pop_type (int_type_node); PUSH_TYPE (long_type_node); break;
798 pop_type (int_type_node); PUSH_TYPE (float_type_node); break;
800 pop_type (int_type_node); PUSH_TYPE (double_type_node); break;
802 pop_type (long_type_node); PUSH_TYPE (int_type_node); break;
804 pop_type (long_type_node); PUSH_TYPE (float_type_node); break;
806 pop_type (long_type_node); PUSH_TYPE (double_type_node); break;
808 pop_type (float_type_node); PUSH_TYPE (int_type_node); break;
810 pop_type (float_type_node); PUSH_TYPE (long_type_node); break;
812 pop_type (float_type_node); PUSH_TYPE (double_type_node); break;
814 pop_type (double_type_node); PUSH_TYPE (int_type_node); break;
816 pop_type (double_type_node); PUSH_TYPE (long_type_node); break;
818 pop_type (double_type_node); PUSH_TYPE (float_type_node); break;
820 type = long_type_node; goto compare;
823 type = float_type_node; goto compare;
826 type = double_type_node; goto compare;
828 pop_type (type); pop_type (type);
829 PUSH_TYPE (int_type_node); break;
836 pop_type (int_type_node); goto cond;
838 case OPCODE_ifnonnull:
839 pop_type (ptr_type_node ); goto cond;
840 case OPCODE_if_icmpeq:
841 case OPCODE_if_icmpne:
842 case OPCODE_if_icmplt:
843 case OPCODE_if_icmpge:
844 case OPCODE_if_icmpgt:
845 case OPCODE_if_icmple:
846 pop_type (int_type_node); pop_type (int_type_node); goto cond;
847 case OPCODE_if_acmpeq:
848 case OPCODE_if_acmpne:
849 pop_type (object_ptr_type_node); pop_type (object_ptr_type_node);
852 PUSH_PENDING (lookup_label (oldpc + IMMEDIATE_s2));
855 PUSH_PENDING (lookup_label (oldpc + IMMEDIATE_s2));
859 switch (byte_ops[PC])
861 case OPCODE_iload: case OPCODE_lload:
862 case OPCODE_fload: case OPCODE_dload: case OPCODE_aload:
863 case OPCODE_istore: case OPCODE_lstore:
864 case OPCODE_fstore: case OPCODE_dstore: case OPCODE_astore:
870 VERIFICATION_ERROR ("invalid use of wide instruction");
873 case OPCODE_return: type = void_type_node; goto ret;
875 if ((TREE_CODE (return_type) == BOOLEAN_TYPE
876 || TREE_CODE (return_type) == CHAR_TYPE
877 || TREE_CODE (return_type) == INTEGER_TYPE)
878 && TYPE_PRECISION (return_type) <= 32)
883 case OPCODE_lreturn: type = long_type_node; goto ret;
884 case OPCODE_freturn: type = float_type_node; goto ret;
885 case OPCODE_dreturn: type = double_type_node; goto ret;
887 if (TREE_CODE (return_type) == POINTER_TYPE)
893 if (type != return_type)
894 VERIFICATION_ERROR ("incorrect ?return opcode");
895 if (type != void_type_node)
896 POP_TYPE(type, "return value has wrong type");
899 case OPCODE_getstatic: is_putting = 0; is_static = 1; goto field;
900 case OPCODE_putstatic: is_putting = 1; is_static = 1; goto field;
901 case OPCODE_getfield: is_putting = 0; is_static = 0; goto field;
902 case OPCODE_putfield: is_putting = 1; is_static = 0; goto field;
905 int index = IMMEDIATE_u2;
906 tree field_signature = COMPONENT_REF_SIGNATURE (¤t_jcf->cpool, index);
907 tree field_type = get_type_from_signature (field_signature);
909 POP_TYPE (field_type, "incorrect type for field");
912 int clindex = COMPONENT_REF_CLASS_INDEX (¤t_jcf->cpool,
914 tree self_type = get_class_constant (current_jcf, clindex);
915 /* Defer actual checking until next pass. */
916 POP_TYPE(self_type, "incorrect type for field reference");
919 PUSH_TYPE (field_type);
923 PUSH_TYPE (get_class_constant (jcf, IMMEDIATE_u2));
925 case OPCODE_dup: type_stack_dup (1, 0); break;
926 case OPCODE_dup_x1: type_stack_dup (1, 1); break;
927 case OPCODE_dup_x2: type_stack_dup (1, 2); break;
928 case OPCODE_dup2: type_stack_dup (2, 0); break;
929 case OPCODE_dup2_x1: type_stack_dup (2, 1); break;
930 case OPCODE_dup2_x2: type_stack_dup (2, 2); break;
931 case OPCODE_pop: index = 1; goto pop;
932 case OPCODE_pop2: index = 2; goto pop;
934 if (stack_pointer < index)
935 VERIFICATION_ERROR ("stack underflow");
936 stack_pointer -= index;
939 if (stack_pointer < 2)
940 VERIFICATION_ERROR ("stack underflow (in swap)");
943 tree type1 = stack_type_map[stack_pointer - 1];
944 tree type2 = stack_type_map[stack_pointer - 2];
945 if (type1 == void_type_node || type2 == void_type_node)
946 VERIFICATION_ERROR ("verifier (swap): double or long value");
947 stack_type_map[stack_pointer - 2] = type1;
948 stack_type_map[stack_pointer - 1] = type2;
951 case OPCODE_ldc: index = IMMEDIATE_u1; goto ldc;
954 index = IMMEDIATE_u2; goto ldc;
956 if (index <= 0 || index >= JPOOL_SIZE(current_jcf))
957 VERIFICATION_ERROR ("bad constant pool index in ldc");
959 switch (JPOOL_TAG (current_jcf, index) & ~CONSTANT_ResolvedFlag)
961 case CONSTANT_Integer: type = int_type_node; goto check_ldc;
962 case CONSTANT_Float: type = float_type_node; goto check_ldc;
963 case CONSTANT_String: type = string_type_node; goto check_ldc;
964 case CONSTANT_Long: type = long_type_node; goto check_ldc;
965 case CONSTANT_Double: type = double_type_node; goto check_ldc;
967 if (TYPE_IS_WIDE (type) == (op_code == OPCODE_ldc2_w))
969 /* ... else fall through ... */
971 VERIFICATION_ERROR ("bad constant pool tag in ldc");
973 if (type == int_type_node)
975 i = TREE_INT_CST_LOW (get_constant (current_jcf, index));
981 case OPCODE_invokevirtual:
982 case OPCODE_invokespecial:
983 case OPCODE_invokestatic:
984 case OPCODE_invokeinterface:
986 int index = IMMEDIATE_u2;
987 tree sig = COMPONENT_REF_SIGNATURE (¤t_jcf->cpool, index);
988 tree self_type = get_class_constant
989 (current_jcf, COMPONENT_REF_CLASS_INDEX (¤t_jcf->cpool,
991 tree method_name = COMPONENT_REF_NAME (¤t_jcf->cpool, index);
993 method_type = parse_signature_string (IDENTIFIER_POINTER (sig),
994 IDENTIFIER_LENGTH (sig));
995 if (TREE_CODE (method_type) != FUNCTION_TYPE)
996 VERIFICATION_ERROR ("bad method signature");
997 pmessage = pop_argument_types (TYPE_ARG_TYPES (method_type));
998 if (pmessage != NULL)
1000 message = "invalid argument type";
1001 goto pop_type_error;
1004 /* Can't invoke <clinit> */
1005 if (ID_CLINIT_P (method_name))
1006 VERIFICATION_ERROR ("invoke opcode can't invoke <clinit>");
1007 /* Apart invokespecial, can't invoke <init> */
1008 if (op_code != OPCODE_invokespecial && ID_INIT_P (method_name))
1009 VERIFICATION_ERROR ("invoke opcode can't invoke <init>");
1011 if (op_code != OPCODE_invokestatic)
1012 POP_TYPE (self_type,
1013 "stack type not subclass of invoked method's class");
1017 case OPCODE_invokeinterface:
1019 int nargs = IMMEDIATE_u1;
1020 int notZero = IMMEDIATE_u1;
1022 if (!nargs || notZero)
1024 ("invalid argument number in invokeinterface");
1029 if (TREE_TYPE (method_type) != void_type_node)
1030 PUSH_TYPE (TREE_TYPE (method_type));
1034 case OPCODE_arraylength:
1035 /* Type checking actually made during code generation */
1036 pop_type( ptr_type_node );
1037 PUSH_TYPE( int_type_node );
1040 /* Q&D verification *or* more checking done during code generation
1041 for byte/boolean/char/short, the value popped is a int coerced
1042 into the right type before being stored. */
1043 case OPCODE_iastore: type = int_type_node; goto astore;
1044 case OPCODE_lastore: type = long_type_node; goto astore;
1045 case OPCODE_fastore: type = float_type_node; goto astore;
1046 case OPCODE_dastore: type = double_type_node; goto astore;
1047 case OPCODE_aastore: type = ptr_type_node; goto astore;
1048 case OPCODE_bastore: type = int_type_node; goto astore;
1049 case OPCODE_castore: type = int_type_node; goto astore;
1050 case OPCODE_sastore: type = int_type_node; goto astore;
1052 /* FIXME - need better verification here */
1053 pop_type (type); /* new value */
1054 pop_type (int_type_node); /* index */
1055 pop_type (ptr_type_node); /* array */
1058 /* Q&D verification *or* more checking done during code generation
1059 for byte/boolean/char/short, the value pushed is a int. */
1060 case OPCODE_iaload: type = int_type_node; goto aload;
1061 case OPCODE_laload: type = long_type_node; goto aload;
1062 case OPCODE_faload: type = float_type_node; goto aload;
1063 case OPCODE_daload: type = double_type_node; goto aload;
1064 case OPCODE_aaload: type = ptr_type_node; goto aload;
1065 case OPCODE_baload: type = promote_type (byte_type_node); goto aload;
1066 case OPCODE_caload: type = promote_type (char_type_node); goto aload;
1067 case OPCODE_saload: type = promote_type (short_type_node); goto aload;
1069 pop_type (int_type_node);
1070 tmp = pop_type (ptr_type_node);
1071 if (is_array_type_p (tmp))
1072 type = TYPE_ARRAY_ELEMENT (TREE_TYPE (tmp));
1073 else if (tmp != TYPE_NULL)
1074 VERIFICATION_ERROR ("array load from non-array type");
1078 case OPCODE_anewarray:
1079 type = get_class_constant (current_jcf, IMMEDIATE_u2);
1080 type = promote_type (type);
1083 case OPCODE_newarray:
1084 index = IMMEDIATE_u1;
1085 type = decode_newarray_type (index);
1086 if (type == NULL_TREE)
1087 VERIFICATION_ERROR ("invalid type code in newarray opcode");
1091 if (int_value >= 0 && prevpc >= 0)
1093 /* If previous instruction pushed int constant,
1094 we want to use it. */
1095 switch (byte_ops[prevpc])
1097 case OPCODE_iconst_0: case OPCODE_iconst_1:
1098 case OPCODE_iconst_2: case OPCODE_iconst_3:
1099 case OPCODE_iconst_4: case OPCODE_iconst_5:
1100 case OPCODE_bipush: case OPCODE_sipush:
1101 case OPCODE_ldc: case OPCODE_ldc_w:
1109 type = build_java_array_type (type, int_value);
1110 pop_type (int_type_node);
1114 case OPCODE_multianewarray:
1117 index = IMMEDIATE_u2;
1118 ndim = IMMEDIATE_u1;
1121 VERIFICATION_ERROR ("number of dimension lower that 1 in multianewarray" );
1123 for( i = 0; i < ndim; i++ )
1124 pop_type (int_type_node);
1125 PUSH_TYPE (get_class_constant (current_jcf, index));
1129 case OPCODE_aconst_null:
1130 PUSH_TYPE (ptr_type_node);
1134 /* FIXME: athrow also empties the stack. */
1135 pop_type (throwable_type_node);
1139 case OPCODE_checkcast:
1140 pop_type (ptr_type_node);
1141 type = get_class_constant (current_jcf, IMMEDIATE_u2);
1144 case OPCODE_instanceof:
1145 pop_type (ptr_type_node);
1146 get_class_constant (current_jcf, IMMEDIATE_u2);
1147 PUSH_TYPE (int_type_node);
1150 case OPCODE_tableswitch:
1154 pop_type (int_type_node);
1158 VERIFICATION_ERROR ("bad alignment in tableswitch pad");
1160 PUSH_PENDING (lookup_label (oldpc+IMMEDIATE_s4));
1162 high = IMMEDIATE_s4;
1165 VERIFICATION_ERROR ("unsorted low/high value in tableswitch");
1167 while (low++ <= high)
1168 PUSH_PENDING (lookup_label (oldpc + IMMEDIATE_s4));
1173 case OPCODE_lookupswitch:
1175 jint npairs, last = 0, not_registered = 1;
1177 pop_type (int_type_node);
1181 VERIFICATION_ERROR ("bad alignment in lookupswitch pad");
1184 PUSH_PENDING (lookup_label (oldpc+IMMEDIATE_s4));
1185 npairs = IMMEDIATE_s4;
1188 VERIFICATION_ERROR ("invalid number of targets in lookupswitch");
1192 int match = IMMEDIATE_s4;
1195 else if (last >= match)
1196 VERIFICATION_ERROR ("unsorted match value in lookupswitch");
1199 PUSH_PENDING (lookup_label (oldpc + IMMEDIATE_s4));
1205 case OPCODE_monitorenter:
1207 case OPCODE_monitorexit:
1208 pop_type (ptr_type_node);
1212 PUSH_PENDING (lookup_label (oldpc + IMMEDIATE_s4));
1218 tree target = lookup_label (oldpc + IMMEDIATE_s2);
1219 tree return_label = lookup_label (PC);
1220 PUSH_TYPE (return_address_type_node);
1221 /* The return label chain will be null if this is the first
1222 time we've seen this jsr target. */
1223 if (LABEL_RETURN_LABEL (target) == NULL_TREE)
1225 tree return_type_map;
1226 int nlocals = DECL_MAX_LOCALS (current_function_decl);
1227 index = nlocals + DECL_MAX_STACK (current_function_decl);
1228 return_type_map = make_tree_vec (index);
1229 while (index > nlocals)
1230 TREE_VEC_ELT (return_type_map, --index) = TYPE_UNKNOWN;
1232 TREE_VEC_ELT (return_type_map, --index) = TYPE_UNUSED;
1233 LABEL_RETURN_LABEL (target)
1234 = build_decl (LABEL_DECL, NULL_TREE, TREE_TYPE (target));
1235 LABEL_PC (LABEL_RETURN_LABEL (target)) = -1;
1236 LABEL_RETURN_TYPE_STATE (target) = return_type_map;
1237 LABEL_IS_SUBR_START (target) = 1;
1238 LABEL_IN_SUBR (target) = 1;
1239 LABEL_SUBR_START (target) = target;
1240 LABEL_SUBR_CONTEXT (target) = current_subr;
1242 else if (! LABEL_IS_SUBR_START (target)
1243 || LABEL_SUBR_CONTEXT (target) != current_subr)
1244 VERIFICATION_ERROR ("label part of different subroutines");
1246 i = merge_type_state (target);
1250 VERIFICATION_ERROR ("types could not be merged at jsr");
1251 push_pending_label (target);
1253 current_subr = target;
1255 /* Chain return_pc onto LABEL_RETURN_LABELS (target) if needed. */
1256 if (! value_member (return_label, LABEL_RETURN_LABELS (target)))
1258 LABEL_RETURN_LABELS (target)
1259 = tree_cons (NULL_TREE, return_label,
1260 LABEL_RETURN_LABELS (target));
1263 if (LABEL_VERIFIED (target))
1265 tree return_map = LABEL_RETURN_TYPE_STATE (target);
1266 int len = TREE_VEC_LENGTH (return_map);
1267 stack_pointer = len - DECL_MAX_LOCALS (current_function_decl);
1270 if (TREE_VEC_ELT (return_map, len) != TYPE_UNUSED)
1271 type_map[len] = TREE_VEC_ELT (return_map, len);
1273 current_subr = LABEL_SUBR_CONTEXT (target);
1274 PUSH_PENDING (return_label);
1281 if (current_subr == NULL)
1282 VERIFICATION_ERROR ("ret instruction not in a jsr subroutine");
1285 tree ret_map = LABEL_RETURN_TYPE_STATE (current_subr);
1286 int size = DECL_MAX_LOCALS(current_function_decl)+stack_pointer;
1287 index = wide ? IMMEDIATE_u2 : IMMEDIATE_u1;
1290 if (index < 0 || index >= DECL_MAX_LOCALS (current_function_decl)
1291 || type_map[index] != TYPE_RETURN_ADDR)
1292 VERIFICATION_ERROR ("invalid ret index");
1294 /* The next chunk of code is similar to an inlined version of
1295 * merge_type_state (LABEL_RETURN_LABEL (current_subr)).
1296 * The main differences are that LABEL_RETURN_LABEL is
1297 * pre-allocated by the jsr (but we don't know the size then);
1298 * and that we have to handle TYPE_UNUSED. */
1300 if (! RETURN_MAP_ADJUSTED (ret_map))
1301 { /* First return from this subroutine - fix stack pointer. */
1302 TREE_VEC_LENGTH (ret_map) = size;
1303 for (index = size; --index >= 0; )
1305 if (TREE_VEC_ELT (ret_map, index) != TYPE_UNUSED)
1306 TREE_VEC_ELT (ret_map, index) = type_map[index];
1308 RETURN_MAP_ADJUSTED (ret_map) = 1;
1312 if (TREE_VEC_LENGTH (ret_map) != size)
1313 VERIFICATION_ERROR ("inconsistent stack size on ret");
1314 for (index = 0; index < size; index++)
1316 tree type = TREE_VEC_ELT (ret_map, index);
1317 if (type != TYPE_UNUSED)
1319 type = merge_types (type, type_map [index]);
1320 TREE_VEC_ELT (ret_map, index) = type;
1321 if (type == TYPE_UNKNOWN)
1323 if (index >= size - stack_pointer)
1325 ("inconsistent types on ret from jsr");
1327 else if (TYPE_IS_WIDE (type))
1339 error ("unknown opcode %d@pc=%d during verification", op_code, PC-1);
1345 /* The following test is true if we have entered or exited an exception
1346 handler range *or* we have done a store to a local variable.
1347 In either case we need to consider any exception handlers that
1348 might "follow" this instruction. */
1350 if (eh_ranges != prev_eh_ranges)
1352 int save_stack_pointer = stack_pointer;
1353 int index = DECL_MAX_LOCALS (current_function_decl);
1354 tree save_type = type_map[index];
1355 tree save_current_subr = current_subr;
1356 struct eh_range *ranges = find_handler (oldpc);
1358 for (; ranges != NULL_EH_RANGE; ranges = ranges->outer)
1360 tree chain = ranges->handlers;
1362 /* We need to determine if the handler is part of current_subr.
1363 The are two cases: (1) The exception catch range
1364 is entirely within current_subr. In that case the handler
1365 is also part of current_subr.
1366 (2) Some of the catch range is not in current_subr.
1367 In that case, the handler is *not* part of current_subr.
1369 Figuring out which is the case is not necessarily obvious,
1370 in the presence of clever code generators (and obfuscators).
1371 We make a simplifying assumption that in case (2) we
1372 have that the current_subr is entirely within the catch range.
1373 In that case we can assume if that if a caller (the jsr) of
1374 a subroutine is within the catch range, then the handler is
1375 *not* part of the subroutine, and vice versa. */
1377 current_subr = save_current_subr;
1378 for ( ; current_subr != NULL_TREE;
1379 current_subr = LABEL_SUBR_CONTEXT (current_subr))
1381 tree return_labels = LABEL_RETURN_LABELS (current_subr);
1382 /* There could be multiple return_labels, but
1383 we only need to check one. */
1384 int return_pc = LABEL_PC (TREE_VALUE (return_labels));
1385 if (return_pc <= ranges->start_pc
1386 || return_pc > ranges->end_pc)
1390 for ( ; chain != NULL_TREE; chain = TREE_CHAIN (chain))
1392 tree handler = TREE_VALUE (chain);
1393 tree type = TREE_PURPOSE (chain);
1394 if (type == NULL_TREE) /* a finally handler */
1395 type = throwable_type_node;
1396 type_map[index] = promote_type (type);
1398 PUSH_PENDING (handler);
1401 stack_pointer = save_stack_pointer;
1402 current_subr = save_current_subr;
1403 type_map[index] = save_type;
1404 prev_eh_ranges = eh_ranges;
1409 error ("verification error at PC=%d", oldpc);
1410 if (message != NULL)
1411 error ("%s", message);
1412 error ("%s", pmessage);
1416 message = "stack overflow";
1419 message = "program counter out of range";
1422 error ("verification error at PC=%d", oldpc);
1423 error (message, index);
1426 error ("verification error at PC=%d", oldpc);
1427 error ("%s", message);