1 /* src/vm/jit/mips/patcher.c - MIPS code patching functions
3 Copyright (C) 1996-2005, 2006 R. Grafl, A. Krall, C. Kruegel,
4 C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring,
5 E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich,
6 J. Wenninger, Institut f. Computersprachen - TU Wien
8 This file is part of CACAO.
10 This program is free software; you can redistribute it and/or
11 modify it under the terms of the GNU General Public License as
12 published by the Free Software Foundation; either version 2, or (at
13 your option) any later version.
15 This program is distributed in the hope that it will be useful, but
16 WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
25 Contact: cacao@cacaojvm.org
27 Authors: Christian Thalinger
31 $Id: patcher.c 4640 2006-03-16 17:24:18Z twisti $
39 #include "mm/memory.h"
40 #include "native/native.h"
41 #include "vm/builtin.h"
44 #include "vm/initialize.h"
45 #include "vm/options.h"
46 #include "vm/resolve.h"
47 #include "vm/references.h"
48 #include "vm/jit/asmpart.h"
49 #include "vm/jit/patcher.h"
52 /* patcher_get_putstatic *******************************************************
56 <patched call position>
57 dfc1ffb8 ld at,-72(s8)
60 *******************************************************************************/
62 bool patcher_get_putstatic(u1 *sp)
66 #if SIZEOF_VOID_P == 8
76 /* get stuff from the stack */
78 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
79 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
80 #if SIZEOF_VOID_P == 8
81 mcode = *((u8 *) (sp + 3 * 8));
83 mcode[0] = *((u4 *) (sp + 3 * 8));
84 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
86 uf = (unresolved_field *) *((ptrint *) (sp + 2 * 8));
87 disp = *((s4 *) (sp + 1 * 8));
88 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
92 /* get the fieldinfo */
94 if (!(fi = resolve_field_eager(uf))) {
100 /* check if the field's class is initialized */
102 if (!(fi->class->state & CLASS_INITIALIZED)) {
103 if (!initialize_class(fi->class)) {
110 /* patch back original code */
112 #if SIZEOF_VOID_P == 8
113 *((u4 *) (ra + 0 * 4)) = mcode;
114 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
116 *((u4 *) (ra + 0 * 4)) = mcode[0];
117 *((u4 *) (ra + 1 * 4)) = mcode[1];
120 /* synchronize instruction cache */
122 md_icacheflush(ra, 2 * 4);
124 /* patch the field value's address */
126 *((ptrint *) (pv + disp)) = (ptrint) &(fi->value);
128 /* synchronize data cache */
130 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
132 PATCHER_MARK_PATCHED_MONITOREXIT;
138 /* patcher_get_putfield ********************************************************
142 <patched call position>
143 8ee90020 lw a5,32(s7)
145 *******************************************************************************/
147 bool patcher_get_putfield(u1 *sp)
150 java_objectheader *o;
151 #if SIZEOF_VOID_P == 8
156 unresolved_field *uf;
159 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
160 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
161 #if SIZEOF_VOID_P == 8
162 mcode = *((u8 *) (sp + 3 * 8));
164 mcode[0] = *((u4 *) (sp + 3 * 8));
165 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
167 uf = (unresolved_field *) *((ptrint *) (sp + 2 * 8));
169 PATCHER_MONITORENTER;
171 /* get the fieldinfo */
173 if (!(fi = resolve_field_eager(uf))) {
179 /* patch back original code */
181 #if SIZEOF_VOID_P == 8
182 *((u4 *) (ra + 0 * 4)) = mcode;
183 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
185 *((u4 *) (ra + 0 * 4)) = mcode[0];
186 *((u4 *) (ra + 1 * 4)) = mcode[1];
189 /* if we show disassembly, we have to skip the nop's */
191 if (opt_showdisassemble)
194 /* patch the field's offset */
196 #if SIZEOF_VOID_P == 4
197 if (fi->type == TYPE_LNG) {
198 # if WORDS_BIGENDIAN == 1
199 /* ATTENTION: order of these instructions depend on M_LLD_INTERN */
200 *((u4 *) (ra + 0 * 4)) |= (s2) ((fi->offset + 0) & 0x0000ffff);
201 *((u4 *) (ra + 1 * 4)) |= (s2) ((fi->offset + 4) & 0x0000ffff);
203 /* ATTENTION: order of these instructions depend on M_LLD_INTERN */
204 *((u4 *) (ra + 0 * 4)) |= (s2) ((fi->offset + 4) & 0x0000ffff);
205 *((u4 *) (ra + 1 * 4)) |= (s2) ((fi->offset + 0) & 0x0000ffff);
209 *((u4 *) ra) |= (s2) (fi->offset & 0x0000ffff);
211 /* synchronize instruction cache */
213 if (opt_showdisassemble) {
214 #if SIZEOF_VOID_P == 4
215 if (fi->type == TYPE_LNG) {
216 md_icacheflush(ra - 2 * 4, 4 * 4);
219 md_icacheflush(ra - 2 * 4, 3 * 4);
221 md_icacheflush(ra, 2 * 4);
224 PATCHER_MARK_PATCHED_MONITOREXIT;
230 /* patcher_aconst **************************************************************
234 <patched call postition>
235 dfc4ff98 ld a0,-104(s8)
237 *******************************************************************************/
239 bool patcher_aconst(u1 *sp)
242 java_objectheader *o;
243 #if SIZEOF_VOID_P == 8
248 constant_classref *cr;
253 /* get stuff from the stack */
255 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
256 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
257 #if SIZEOF_VOID_P == 8
258 mcode = *((u8 *) (sp + 3 * 8));
260 mcode[0] = *((u4 *) (sp + 3 * 8));
261 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
263 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
264 disp = *((s4 *) (sp + 1 * 8));
265 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
267 PATCHER_MONITORENTER;
269 /* get the classinfo */
271 if (!(c = resolve_classref_eager(cr))) {
277 /* patch back original code */
279 #if SIZEOF_VOID_P == 8
280 *((u4 *) (ra + 0 * 4)) = mcode;
281 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
283 *((u4 *) (ra + 0 * 4)) = mcode[0];
284 *((u4 *) (ra + 1 * 4)) = mcode[1];
287 /* synchronize instruction cache */
289 md_icacheflush(ra, 2 * 4);
291 /* patch the classinfo pointer */
293 *((ptrint *) (pv + disp)) = (ptrint) c;
295 /* synchronize data cache */
297 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
299 PATCHER_MARK_PATCHED_MONITOREXIT;
305 /* patcher_builtin_multianewarray **********************************************
309 <patched call position>
310 dfc5ff90 ld a1,-112(s8)
312 dfd9ff88 ld t9,-120(s8)
316 *******************************************************************************/
318 bool patcher_builtin_multianewarray(u1 *sp)
321 java_objectheader *o;
322 #if SIZEOF_VOID_P == 8
327 constant_classref *cr;
332 /* get stuff from the stack */
334 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
335 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
336 #if SIZEOF_VOID_P == 8
337 mcode = *((u8 *) (sp + 3 * 8));
339 mcode[0] = *((u4 *) (sp + 3 * 8));
340 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
342 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
343 disp = *((s4 *) (sp + 1 * 8));
344 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
346 PATCHER_MONITORENTER;
348 /* get the classinfo */
350 if (!(c = resolve_classref_eager(cr))) {
356 /* patch back original code */
358 #if SIZEOF_VOID_P == 8
359 *((u4 *) (ra + 0 * 4)) = mcode;
360 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
362 *((u4 *) (ra + 0 * 4)) = mcode[0];
363 *((u4 *) (ra + 1 * 4)) = mcode[1];
366 /* synchronize instruction cache */
368 md_icacheflush(ra, 2 * 4);
370 /* patch the classinfo pointer */
372 *((ptrint *) (pv + disp)) = (ptrint) c;
374 /* synchronize data cache */
376 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
378 PATCHER_MARK_PATCHED_MONITOREXIT;
384 /* patcher_builtin_arraycheckcast **********************************************
388 <patched call position>
389 dfc5ffc0 ld a1,-64(s8)
390 dfd9ffb8 ld t9,-72(s8)
394 *******************************************************************************/
396 bool patcher_builtin_arraycheckcast(u1 *sp)
399 java_objectheader *o;
400 #if SIZEOF_VOID_P == 8
405 constant_classref *cr;
410 /* get stuff from the stack */
412 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
413 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
414 #if SIZEOF_VOID_P == 8
415 mcode = *((u8 *) (sp + 3 * 8));
417 mcode[0] = *((u4 *) (sp + 3 * 8));
418 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
420 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
421 disp = *((s4 *) (sp + 1 * 8));
422 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
424 PATCHER_MONITORENTER;
426 /* get the classinfo */
428 if (!(c = resolve_classref_eager(cr))) {
434 /* patch back original code */
436 #if SIZEOF_VOID_P == 8
437 *((u4 *) (ra + 0 * 4)) = mcode;
438 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
440 *((u4 *) (ra + 0 * 4)) = mcode[0];
441 *((u4 *) (ra + 1 * 4)) = mcode[1];
444 /* synchronize instruction cache */
446 md_icacheflush(ra, 2 * 4);
448 /* patch the classinfo pointer */
450 *((ptrint *) (pv + disp)) = (ptrint) c;
452 /* synchronize data cache */
454 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
456 PATCHER_MARK_PATCHED_MONITOREXIT;
462 /* patcher_invokestatic_special ************************************************
466 <patched call position>
467 dfdeffc0 ld s8,-64(s8)
471 ******************************************************************************/
473 bool patcher_invokestatic_special(u1 *sp)
476 java_objectheader *o;
477 #if SIZEOF_VOID_P == 8
482 unresolved_method *um;
487 /* get stuff from the stack */
489 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
490 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
491 #if SIZEOF_VOID_P == 8
492 mcode = *((u8 *) (sp + 3 * 8));
494 mcode[0] = *((u4 *) (sp + 3 * 8));
495 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
497 um = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
498 disp = *((s4 *) (sp + 1 * 8));
499 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
501 PATCHER_MONITORENTER;
503 /* get the fieldinfo */
505 if (!(m = resolve_method_eager(um))) {
511 /* patch back original code */
513 #if SIZEOF_VOID_P == 8
514 *((u4 *) (ra + 0 * 4)) = mcode;
515 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
517 *((u4 *) (ra + 0 * 4)) = mcode[0];
518 *((u4 *) (ra + 1 * 4)) = mcode[1];
521 /* synchronize instruction cache */
523 md_icacheflush(ra, 2 * 4);
525 /* patch stubroutine */
527 *((ptrint *) (pv + disp)) = (ptrint) m->stubroutine;
529 /* synchronize data cache */
531 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
533 PATCHER_MARK_PATCHED_MONITOREXIT;
539 /* patcher_invokevirtual *******************************************************
543 <patched call position>
545 df3e0040 ld s8,64(t9)
549 *******************************************************************************/
551 bool patcher_invokevirtual(u1 *sp)
554 java_objectheader *o;
555 #if SIZEOF_VOID_P == 8
560 unresolved_method *um;
563 /* get stuff from the stack */
565 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
566 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
567 #if SIZEOF_VOID_P == 8
568 mcode = *((u8 *) (sp + 3 * 8));
570 mcode[0] = *((u4 *) (sp + 3 * 8));
571 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
573 um = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
575 PATCHER_MONITORENTER;
577 /* get the fieldinfo */
579 if (!(m = resolve_method_eager(um))) {
585 /* patch back original code */
587 #if SIZEOF_VOID_P == 8
588 *((u4 *) (ra + 0 * 4)) = mcode;
589 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
591 *((u4 *) (ra + 0 * 4)) = mcode[0];
592 *((u4 *) (ra + 1 * 4)) = mcode[1];
595 /* if we show disassembly, we have to skip the nop's */
597 if (opt_showdisassemble)
600 /* patch vftbl index */
602 *((s4 *) (ra + 1 * 4)) |= (s4) ((OFFSET(vftbl_t, table[0]) +
603 sizeof(methodptr) * m->vftblindex) & 0x0000ffff);
605 /* synchronize instruction cache */
607 if (opt_showdisassemble)
608 md_icacheflush(ra - 2 * 4, 4 * 4);
610 md_icacheflush(ra, 2 * 4);
612 PATCHER_MARK_PATCHED_MONITOREXIT;
618 /* patcher_invokeinterface *****************************************************
622 <patched call position>
624 df39ffa0 ld t9,-96(t9)
625 df3e0018 ld s8,24(t9)
629 *******************************************************************************/
631 bool patcher_invokeinterface(u1 *sp)
634 java_objectheader *o;
635 #if SIZEOF_VOID_P == 8
640 unresolved_method *um;
643 /* get stuff from the stack */
645 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
646 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
647 #if SIZEOF_VOID_P == 8
648 mcode = *((u8 *) (sp + 3 * 8));
650 mcode[0] = *((u4 *) (sp + 3 * 8));
651 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
653 um = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
655 PATCHER_MONITORENTER;
657 /* get the fieldinfo */
659 if (!(m = resolve_method_eager(um))) {
665 /* patch back original code */
667 #if SIZEOF_VOID_P == 8
668 *((u4 *) (ra + 0 * 4)) = mcode;
669 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
671 *((u4 *) (ra + 0 * 4)) = mcode[0];
672 *((u4 *) (ra + 1 * 4)) = mcode[1];
675 /* if we show disassembly, we have to skip the nop's */
677 if (opt_showdisassemble)
680 /* patch interfacetable index */
682 *((s4 *) (ra + 1 * 4)) |= (s4) ((OFFSET(vftbl_t, interfacetable[0]) -
683 sizeof(methodptr*) * m->class->index) & 0x0000ffff);
685 /* patch method offset */
687 *((s4 *) (ra + 2 * 4)) |=
688 (s4) ((sizeof(methodptr) * (m - m->class->methods)) & 0x0000ffff);
690 /* synchronize instruction cache */
692 if (opt_showdisassemble)
693 md_icacheflush(ra - 2 * 4, 5 * 4);
695 md_icacheflush(ra, 3 * 4);
697 PATCHER_MARK_PATCHED_MONITOREXIT;
703 /* patcher_checkcast_instanceof_flags ******************************************
707 <patched call position>
708 8fc3ff24 lw v1,-220(s8)
709 30630200 andi v1,v1,512
710 1060000d beq v1,zero,0x000000001051824c
713 *******************************************************************************/
715 bool patcher_checkcast_instanceof_flags(u1 *sp)
718 java_objectheader *o;
719 #if SIZEOF_VOID_P == 8
724 constant_classref *cr;
729 /* get stuff from the stack */
731 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
732 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
733 #if SIZEOF_VOID_P == 8
734 mcode = *((u8 *) (sp + 3 * 8));
736 mcode[0] = *((u4 *) (sp + 3 * 8));
737 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
739 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
740 disp = *((s4 *) (sp + 1 * 8));
741 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
743 PATCHER_MONITORENTER;
745 /* get the fieldinfo */
747 if (!(c = resolve_classref_eager(cr))) {
753 /* patch back original code */
755 #if SIZEOF_VOID_P == 8
756 *((u4 *) (ra + 0 * 4)) = mcode;
757 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
759 *((u4 *) (ra + 0 * 4)) = mcode[0];
760 *((u4 *) (ra + 1 * 4)) = mcode[1];
763 /* synchronize instruction cache */
765 md_icacheflush(ra, 2 * 4);
767 /* patch class flags */
769 *((s4 *) (pv + disp)) = (s4) c->flags;
771 /* synchronize data cache */
773 md_dcacheflush(pv + disp, sizeof(s4));
775 PATCHER_MARK_PATCHED_MONITOREXIT;
781 /* patcher_checkcast_instanceof_interface **************************************
785 <patched call position>
787 8c79001c lw t9,28(v1)
788 27390000 addiu t9,t9,0
789 1b200082 blez t9,zero,0x000000001051843c
793 *******************************************************************************/
795 bool patcher_checkcast_instanceof_interface(u1 *sp)
798 java_objectheader *o;
799 #if SIZEOF_VOID_P == 8
804 constant_classref *cr;
807 /* get stuff from the stack */
809 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
810 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
811 #if SIZEOF_VOID_P == 8
812 mcode = *((u8 *) (sp + 3 * 8));
814 mcode[0] = *((u4 *) (sp + 3 * 8));
815 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
817 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
819 PATCHER_MONITORENTER;
821 /* get the fieldinfo */
823 if (!(c = resolve_classref_eager(cr))) {
829 /* patch back original code */
831 #if SIZEOF_VOID_P == 8
832 *((u4 *) (ra + 0 * 4)) = mcode;
833 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
835 *((u4 *) (ra + 0 * 4)) = mcode[0];
836 *((u4 *) (ra + 1 * 4)) = mcode[1];
839 /* if we show disassembly, we have to skip the nop's */
841 if (opt_showdisassemble)
844 /* patch super class index */
846 *((s4 *) (ra + 2 * 4)) |= (s4) (-(c->index) & 0x0000ffff);
848 *((s4 *) (ra + 5 * 4)) |= (s4) ((OFFSET(vftbl_t, interfacetable[0]) -
849 c->index * sizeof(methodptr*)) & 0x0000ffff);
851 /* synchronize instruction cache */
853 if (opt_showdisassemble)
854 md_icacheflush(ra - 2 * 4, 8 * 4);
856 md_icacheflush(ra, 6 * 4);
858 PATCHER_MARK_PATCHED_MONITOREXIT;
864 /* patcher_checkcast_instanceof_class ******************************************
868 <patched call position>
870 dfd9ff18 ld t9,-232(s8)
872 *******************************************************************************/
874 bool patcher_checkcast_instanceof_class(u1 *sp)
877 java_objectheader *o;
878 #if SIZEOF_VOID_P == 8
883 constant_classref *cr;
888 /* get stuff from the stack */
890 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
891 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
892 #if SIZEOF_VOID_P == 8
893 mcode = *((u8 *) (sp + 3 * 8));
895 mcode[0] = *((u4 *) (sp + 3 * 8));
896 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
898 cr = (constant_classref *) *((ptrint *) (sp + 2 * 8));
899 disp = *((s4 *) (sp + 1 * 8));
900 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
902 PATCHER_MONITORENTER;
904 /* get the fieldinfo */
906 if (!(c = resolve_classref_eager(cr))) {
912 /* patch back original code */
914 #if SIZEOF_VOID_P == 8
915 *((u4 *) (ra + 0 * 4)) = mcode;
916 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
918 *((u4 *) (ra + 0 * 4)) = mcode[0];
919 *((u4 *) (ra + 1 * 4)) = mcode[1];
922 /* synchronize instruction cache */
924 md_icacheflush(ra, 2 * 4);
926 /* patch super class' vftbl */
928 *((ptrint *) (pv + disp)) = (ptrint) c->vftbl;
930 /* synchronize data cache */
932 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
934 PATCHER_MARK_PATCHED_MONITOREXIT;
940 /* patcher_clinit **************************************************************
942 No special machine code.
944 *******************************************************************************/
946 bool patcher_clinit(u1 *sp)
949 java_objectheader *o;
950 #if SIZEOF_VOID_P == 8
957 /* get stuff from the stack */
959 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
960 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
961 #if SIZEOF_VOID_P == 8
962 mcode = *((u8 *) (sp + 3 * 8));
964 mcode[0] = *((u4 *) (sp + 3 * 8));
965 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
967 c = (classinfo *) *((ptrint *) (sp + 2 * 8));
969 PATCHER_MONITORENTER;
971 /* check if the class is initialized */
973 if (!(c->state & CLASS_INITIALIZED)) {
974 if (!initialize_class(c)) {
981 /* patch back original code */
983 #if SIZEOF_VOID_P == 8
984 *((u4 *) (ra + 0 * 4)) = mcode;
985 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
987 *((u4 *) (ra + 0 * 4)) = mcode[0];
988 *((u4 *) (ra + 1 * 4)) = mcode[1];
991 /* synchronize instruction cache */
993 md_icacheflush(ra, 2 * 4);
995 PATCHER_MARK_PATCHED_MONITOREXIT;
1001 /* patcher_athrow_areturn ******************************************************
1005 <patched call position>
1007 *******************************************************************************/
1009 #ifdef ENABLE_VERIFIER
1010 bool patcher_athrow_areturn(u1 *sp)
1013 java_objectheader *o;
1014 #if SIZEOF_VOID_P == 8
1019 unresolved_class *uc;
1022 /* get stuff from the stack */
1024 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
1025 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
1026 #if SIZEOF_VOID_P == 8
1027 mcode = *((u8 *) (sp + 3 * 8));
1029 mcode[0] = *((u4 *) (sp + 3 * 8));
1030 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
1032 uc = (unresolved_class *) *((ptrint *) (sp + 2 * 8));
1034 PATCHER_MONITORENTER;
1036 /* resolve the class */
1038 if (!resolve_class(uc, resolveEager, false, &c)) {
1039 PATCHER_MONITOREXIT;
1044 /* patch back original code */
1046 #if SIZEOF_VOID_P == 8
1047 *((u4 *) (ra + 0 * 4)) = mcode;
1048 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
1050 *((u4 *) (ra + 0 * 4)) = mcode[0];
1051 *((u4 *) (ra + 1 * 4)) = mcode[1];
1054 /* synchronize instruction cache */
1056 md_icacheflush(ra, 2 * 4);
1058 PATCHER_MARK_PATCHED_MONITOREXIT;
1062 #endif /* ENABLE_VERIFIER */
1065 /* patcher_resolve_native ******************************************************
1069 *******************************************************************************/
1071 #if !defined(WITH_STATIC_CLASSPATH)
1072 bool patcher_resolve_native(u1 *sp)
1075 java_objectheader *o;
1076 #if SIZEOF_VOID_P == 8
1086 /* get stuff from the stack */
1088 ra = (u1 *) *((ptrint *) (sp + 5 * 8));
1089 o = (java_objectheader *) *((ptrint *) (sp + 4 * 8));
1090 #if SIZEOF_VOID_P == 8
1091 mcode = *((u8 *) (sp + 3 * 8));
1093 mcode[0] = *((u4 *) (sp + 3 * 8));
1094 mcode[1] = *((u4 *) (sp + 3 * 8 + 4));
1096 m = (methodinfo *) *((ptrint *) (sp + 2 * 8));
1097 disp = *((s4 *) (sp + 1 * 8));
1098 pv = (u1 *) *((ptrint *) (sp + 0 * 8));
1100 /* calculate and set the new return address */
1103 *((ptrint *) (sp + 5 * 8)) = (ptrint) ra;
1105 PATCHER_MONITORENTER;
1107 /* resolve native function */
1109 if (!(f = native_resolve_function(m))) {
1110 PATCHER_MONITOREXIT;
1115 /* patch back original code */
1117 #if SIZEOF_VOID_P == 8
1118 *((u4 *) (ra + 0 * 4)) = mcode;
1119 *((u4 *) (ra + 1 * 4)) = mcode >> 32;
1121 *((u4 *) (ra + 0 * 4)) = mcode[0];
1122 *((u4 *) (ra + 1 * 4)) = mcode[1];
1125 /* synchronize instruction cache */
1127 md_icacheflush(ra, 2 * 4);
1129 /* patch native function pointer */
1131 *((ptrint *) (pv + disp)) = (ptrint) f;
1133 /* synchronize data cache */
1135 md_dcacheflush(pv + disp, SIZEOF_VOID_P);
1137 PATCHER_MARK_PATCHED_MONITOREXIT;
1141 #endif /* !defined(WITH_STATIC_CLASSPATH) */
1145 * These are local overrides for various environment variables in Emacs.
1146 * Please do not remove this and leave it at the end of the file, where
1147 * Emacs will automagically detect them.
1148 * ---------------------------------------------------------------------
1151 * indent-tabs-mode: t
1155 * vim:noexpandtab:sw=4:ts=4: