* types.h include fixes.
[cacao.git] / src / vm / jit / powerpc / asmpart.S
1 /* src/vm/jit/powerpc/asmpart.S - Java-C interface functions for PowerPC
2                 
3    Copyright (C) 1996-2005 R. Grafl, A. Krall, C. Kruegel, C. Oates,
4    R. Obermaisser, M. Platter, M. Probst, S. Ring, E. Steiner,
5    C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, J. Wenninger,
6    Institut f. Computersprachen - TU Wien
7
8    This file is part of CACAO.
9
10    This program is free software.text;  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.
14
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.
19
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., 59 Temple Place - Suite 330, Boston, MA
23    02111-1307, USA.
24
25    Contact: cacao@complang.tuwien.ac.at
26
27    Authors: Andreas Krall
28             Reinhard Grafl
29             Stefan Ring
30
31    Changes: Christian Thalinger
32
33    $Id: asmpart.S 3234 2005-09-21 12:11:58Z twisti $
34
35 */
36
37
38 #include "config.h"
39
40 #include "md-abi.h"
41 #include "md-asm.h"
42
43 #include "vm/jit/methodheader.h"
44 #include "vm/jit/powerpc/offsets.h"
45
46
47         .text
48
49         .align 2
50
51         .globl asm_calljavafunction
52         .globl asm_calljavafunction_int
53
54         .globl asm_calljavafunction2
55         .globl asm_calljavafunction2int
56         .globl asm_calljavafunction2long
57         .globl asm_calljavafunction2float
58         .globl asm_calljavafunction2double
59
60         .globl asm_call_jit_compiler
61
62         .globl asm_handle_nat_exception
63         .globl asm_handle_exception
64
65         .globl asm_wrapper_patcher
66
67         .globl asm_cacheflush
68         .globl asm_initialize_thread_stack
69         .globl asm_perform_threadswitch
70         .globl asm_switchstackandcall
71         .globl asm_criticalsections
72         .globl asm_getclassvalues_atomic
73
74
75 /********************* function asm_calljavafunction ***************************
76 *                                                                              *
77 *   This function calls a Java-method (which possibly needs compilation)       *
78 *   with up to 4 address parameters.                                           *
79 *                                                                              *
80 *   This functions calls the JIT-compiler which eventually translates the      *
81 *   method into machine code.                                                  *
82 *                                                                              *
83 *   C-prototype:                                                               *
84 *    javaobject_header *asm_calljavamethod (methodinfo *m,                     *
85 *         void *arg1, void *arg2, void *arg3, void *arg4);                     *
86 *                                                                              *
87 *******************************************************************************/
88                 
89         .align 2
90
91         .long   0                         /* catch type all                       */
92         .long   calljava_xhandler         /* handler pc                           */
93         .long   calljava_xhandler         /* end pc                               */
94         .long   asm_calljavafunction      /* start pc                             */
95         .long   1                         /* extable size                         */
96         .long   0                         /* line number table start              */
97         .long   0                         /* line number table size               */
98         .long   0                         /* fltsave                              */
99         .long   0                         /* intsave                              */
100         .long   0                         /* isleaf                               */
101         .long   0                         /* IsSync                               */
102         .long   24                        /* frame size                           */
103         .long   0                         /* method pointer (pointer to name)     */
104
105 asm_calljavafunction:
106 asm_calljavafunction_int:
107         mflr    r0
108         stw     r31,-4(r1)
109 /*      stw     r30,-8(r1)*/
110         stw     pv,-12(r1)
111         stw     r0,LA_LR_OFFSET(r1)
112         stwu    r1,-148(r1)
113
114 #if defined(__DARWIN__)
115         bl      0f
116 0:
117         mflr    r31
118 #endif
119
120         stw     t0,40(r1)
121         stw     t1,44(r1)
122         stw     t2,48(r1)
123         stw     t3,52(r1)
124         stw     t4,56(r1)
125         stw     t5,60(r1)
126         stw     t6,64(r1)
127 /*      stw     t7,68(r1) */
128
129         stfd    ftmp1,72(r1)
130         stfd    ftmp2,80(r1)
131         stfd    ft0,88(r1)
132         stfd    ft1,96(r1)
133         stfd    ft2,104(r1)
134         stfd    ft3,112(r1)
135         stfd    ft4,120(r1)
136         stfd    ft5,128(r1)
137
138         stw     a0,36(r1)
139         addi    itmp1,r1,36
140         mr      a0,a1
141         mr      a1,a2
142         mr      a2,a3
143         mr      a3,a4
144
145 #if defined(__DARWIN__)
146 /*      addis   mptr,r31,ha16(_asm_call_jit_compiler-0b)*/
147         addi    mptr,r31,lo16(asm_call_jit_compiler-0b)
148 #else
149 /*      addi    mptr,r31,(asm_call_jit_compiler-0b)@l*/
150         lis     mptr,asm_call_jit_compiler@ha
151         addi    mptr,mptr,asm_call_jit_compiler@l
152 #endif
153         stw     mptr,32(r1)
154         addi    mptr,r1,28
155
156         lwz     pv,4(mptr)
157         mtctr   pv
158         bctrl
159
160 1:
161         mflr    itmp1
162 #if defined(__DARWIN__)
163         addi    pv,itmp1,lo16(asm_calljavafunction-1b)
164 #else
165         addi    pv,itmp1,(asm_calljavafunction-1b)@l
166 #endif
167
168 calljava_regrestore:
169         lwz     t0,40(r1)
170         lwz     t1,44(r1)
171         lwz     t2,48(r1)
172         lwz     t3,52(r1)
173         lwz     t4,56(r1)
174         lwz     t5,60(r1)
175         lwz     t6,64(r1)
176 /*      lwz     t7,68(r1) */
177
178         lfd     ftmp1,72(r1)
179         lfd     ftmp2,80(r1)
180         lfd     ft0,88(r1)
181         lfd     ft1,96(r1)
182         lfd     ft2,104(r1)
183         lfd     ft3,112(r1)
184         lfd     ft4,120(r1)
185         lfd     ft5,128(r1)
186
187         lwz     r0,148+LA_LR_OFFSET(r1)
188         mtlr    r0
189         addi    r1,r1,148
190         lwz     pv,-12(r1)
191 /*      lwz     r30,-8(r1)*/
192         lwz     r31,-4(r1)
193         blr
194
195 calljava_xhandler:
196         mr      a0,itmp1
197         bl      builtin_throw_exception
198         li      v0,0                      /* return NULL                          */
199         b       calljava_regrestore
200
201
202
203
204         .align 2
205
206         .long   0                         /* catch type all                       */
207         .long   calljava_xhandler2        /* handler pc                           */
208         .long   calljava_xhandler2        /* end pc                               */
209         .long   asm_calljavafunction2     /* start pc                             */
210         .long   1                         /* extable size                         */
211         .long   0                         /* line number table start              */
212         .long   0                         /* line number table size               */
213         .long   0                         /* fltsave                              */
214         .long   0                         /* intsave                              */
215         .long   0                         /* isleaf                               */
216         .long   0                         /* IsSync                               */
217         .long   24                        /* frame size                           */
218         .long   0                         /* method pointer (pointer to name)     */
219
220 asm_calljavafunction2:
221 asm_calljavafunction2int:
222 asm_calljavafunction2long:
223 asm_calljavafunction2float:
224 asm_calljavafunction2double:
225         mflr    r0
226         stw     r31,-4(r1)
227 /*      stw     r30,-8(r1)*/
228         stw     pv,-12(r1)
229         stw     r0,LA_LR_OFFSET(r1)
230         stwu    r1,-148(r1)
231         bl      0f
232 0:
233         mflr    r31
234
235         stw     r16,40(r1)
236         stw     r17,44(r1)
237         stw     r18,48(r1)
238         stw     r19,52(r1)
239         stw     r20,56(r1)
240         stw     r21,60(r1)
241         stw     r22,64(r1)
242         stw     r23,68(r1)
243
244         stfd    fr16,72(r1)
245         stfd    fr17,80(r1)
246         stfd    fr18,88(r1)
247         stfd    fr19,96(r1)
248         stfd    fr20,104(r1)
249         stfd    fr21,112(r1)
250         stfd    fr22,120(r1)
251         stfd    fr23,128(r1)
252
253         stw     r3,36(r1)                 /* save method pointer for compiler     */
254         mr      itmp1,r6                  /* pointer to arg block                 */
255         mr      itmp2,r4                  /* arg count                            */
256
257         mr.     itmp2,itmp2
258         ble     calljava_argsloaded
259
260         addi    itmp2,itmp2,-1
261         lwz     r3,offjniitem+4(itmp1)
262         mr.     itmp2,itmp2
263         ble     calljava_argsloaded
264
265         addi    itmp2,itmp2,-1
266         lwz     r4,offjniitem+sizejniblock*1+4(itmp1)
267         mr.     itmp2,itmp2
268         ble     calljava_argsloaded
269         addi    itmp2,itmp2,-1
270
271         addi    itmp2,itmp2,-1
272         lwz     r5,offjniitem+sizejniblock*2+4(itmp1)
273         mr.     itmp2,itmp2
274         ble     calljava_argsloaded
275         addi    itmp2,itmp2,-1
276
277         addi    itmp2,itmp2,-1
278         lwz     r6,offjniitem+sizejniblock*3+4(itmp1)
279         mr.     itmp2,itmp2
280         ble     calljava_argsloaded
281         addi    itmp2,itmp2,-1
282
283 calljava_argsloaded:
284         addi    itmp1,r1,36
285 #if defined(__DARWIN__)
286 /*      addis   mptr,r31,ha16(_asm_call_jit_compiler-0b)*/
287         addi    mptr,r31,lo16(asm_call_jit_compiler-0b)
288 #else
289         addi    mptr,r31,(asm_call_jit_compiler-0b)@l
290 #endif
291         stw     mptr,32(r1)
292         addi    mptr,r1,28
293
294         lwz     pv,4(mptr)
295         mtctr   pv
296         bctrl
297 1:
298         mflr    itmp1
299 #if defined(__DARWIN__)
300         addi    pv,itmp1,lo16(asm_calljavafunction2-1b)
301 #else
302         addi    pv,itmp1,(asm_calljavafunction2-1b)@l
303 #endif
304
305 calljava_regrestore2:
306         lwz     r16,40(r1)
307         lwz     r17,44(r1)
308         lwz     r18,48(r1)
309         lwz     r19,52(r1)
310         lwz     r20,56(r1)
311         lwz     r21,60(r1)
312         lwz     r22,64(r1)
313         lwz     r23,68(r1)
314
315         lfd     fr16,72(r1)
316         lfd     fr17,80(r1)
317         lfd     fr18,88(r1)
318         lfd     fr19,96(r1)
319         lfd     fr20,104(r1)
320         lfd     fr21,112(r1)
321         lfd     fr22,120(r1)
322         lfd     fr23,128(r1)
323
324         lwz     r0,148+LA_LR_OFFSET(r1)
325         mtlr    r0
326         addi    r1,r1,148
327         lwz     pv,-12(r1)
328 /*      lwz     r30,-8(r1)*/
329         lwz     r31,-4(r1)
330         blr
331
332 calljava_xhandler2:
333         mr      r3,itmp1
334         bl      builtin_throw_exception
335         li      v0,0                      /* return NULL                          */
336         b       calljava_regrestore2
337
338
339 /* asm_call_jit_compiler *******************************************************
340
341    Invokes the compiler for untranslated JavaVM methods.
342
343 *******************************************************************************/
344
345 asm_call_jit_compiler:
346         mflr    r0
347         stw     r0,LA_LR_OFFSET(r1)         /* save return address                */
348         stwu    r1,-((LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)+sizestackframeinfo)(r1)
349         stw     itmp1,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 1*4)(r1)
350
351         mr      itmp1,r0                    /* save return address to other reg.  */
352         lwz     itmp3,-12(itmp1)
353         srwi    itmp3,itmp3,16
354         andi.   itmp3,itmp3,31
355         cmpwi   itmp3,mptrn
356         beq     noregchange
357         lwz     itmp3,4(itmp1)
358         extsh   itmp3,itmp3
359         add     mptr,itmp3,itmp1
360         lwz     itmp3,8(itmp1)
361         srwi    itmp3,itmp3,16
362         cmpwi   itmp3,0x3dad
363         bne     noregchange
364         lwz     itmp3,8(itmp1)
365         slwi    itmp3,itmp3,16
366         add     mptr,mptr,itmp3
367                 
368 noregchange:
369         stw     mptr,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 2*4)(r1)
370
371 #if defined(__DARWIN__)
372         stw     a0,28(r1)
373         stw     a1,32(r1)
374         stw     a2,36(r1)
375         stw     a3,40(r1)
376         stw     a4,44(r1)
377         stw     a5,48(r1)
378         stw     a6,52(r1)
379         stw     a7,56(r1)
380
381         stfd    fa0,60(r1)
382         stfd    fa1,68(r1)
383         stfd    fa2,76(r1)
384         stfd    fa3,84(r1)
385         stfd    fa4,92(r1)
386         stfd    fa5,100(r1)
387         stfd    fa6,108(r1)
388         stfd    fa7,116(r1)
389         stfd    fa8,124(r1)
390         stfd    fa9,132(r1)
391         stfd    fa10,140(r1)
392         stfd    fa11,148(r1)
393         stfd    fa12,156(r1)
394 #else
395         SAVE_ARGUMENT_REGISTERS(LA_WORD_SIZE+1)
396 #endif
397
398         addi    a0,sp,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)
399         li      a1,0                        /* we don't have pv handy             */
400         addi    a2,sp,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)+sizestackframeinfo
401         lwz     a3,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)+sizestackframeinfo+LA_LR_OFFSET(sp)
402         mr      a4,a3                       /* xpc is equal to ra                 */
403         bl      stacktrace_create_extern_stackframeinfo
404
405         lwz     itmp1,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 1*4)(r1)
406         lwz     a0,0(itmp1)
407         bl      jit_compile                 /* compile the Java method            */
408         mr      pv,r3                       /* move address to pv register        */
409
410         addi    a0,sp,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)
411         bl      stacktrace_remove_stackframeinfo
412
413 #if defined(__DARWIN__)
414         lwz     a0,28(r1)
415         lwz     a1,32(r1)
416         lwz     a2,36(r1)
417         lwz     a3,40(r1)
418         lwz     a4,44(r1)
419         lwz     a5,48(r1)
420         lwz     a6,52(r1)
421         lwz     a7,56(r1)
422
423         lfd     fa0,60(r1)
424         lfd     fa1,68(r1)
425         lfd     fa2,76(r1)
426         lfd     fa3,84(r1)
427         lfd     fa4,92(r1)
428         lfd     fa5,100(r1)
429         lfd     fa6,108(r1)
430         lfd     fa7,116(r1)
431         lfd     fa8,124(r1)
432         lfd     fa9,132(r1)
433         lfd     fa10,140(r1)
434         lfd     fa11,148(r1)
435         lfd     fa12,156(r1)
436 #else
437         RESTORE_ARGUMENT_REGISTERS(LA_WORD_SIZE+1)
438 #endif
439
440         lwz     mptr,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 2*4)(r1)
441
442         lwz     itmp1,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)+sizestackframeinfo+LA_LR_OFFSET(r1)
443         mtlr    itmp1
444         addi    r1,r1,(LA_SIZE + 5*4 + INT_ARG_CNT*4 + FLT_ARG_CNT*8 + 3*4)+sizestackframeinfo
445
446         mr.     pv,pv                       /* test for exception                 */
447         beq     L_asm_call_jit_compiler_exception
448
449         lwz     itmp3,-12(itmp1)
450         extsh   itmp3,itmp3
451         add     mptr,mptr,itmp3
452         stw     pv,0(mptr)                  /* store method address               */
453
454         mtctr   pv                          /* move method address to control reg */
455         bctr                                /* and call the Java method           */
456
457 L_asm_call_jit_compiler_exception:
458 #if defined(USE_THREADS) && defined(NATIVE_THREADS)
459         mflr    r0
460         stw     r0,LA_LR_OFFSET(r1)
461         stwu    r1,-LA_SIZE_ALIGNED(r1)     /* preserve linkage area              */
462         bl      builtin_asm_get_exceptionptrptr
463         lwz     r0,LA_SIZE_ALIGNED+LA_LR_OFFSET(r1)
464         mtlr    r0      
465         addi    r1,r1,LA_SIZE_ALIGNED
466 #else
467 # if defined(__DARWIN__)
468         lwz     v0,lo16(_exceptionptr-0b)(pv)
469 # else
470         lis     v0,_exceptionptr@ha
471         addi    v0,v0,_exceptionptr@l
472 # endif
473 #endif
474         lwz     xptr,0(v0)                  /* get the exception pointer          */
475         li      itmp3,0
476         stw     itmp3,0(v0)                 /* clear the exception pointer        */
477
478         mflr    xpc
479         addi    xpc,xpc,-4
480         b       asm_handle_nat_exception
481
482
483 /********************* function asm_handle_exception ***************************
484 *                                                                              *
485 *   This function handles an exception. It does not use the usual calling      *
486 *   conventions. The exception pointer is passed in REG_ITMP1 and the          *
487 *   pc from the exception raising position is passed in REG_ITMP2. It searches *
488 *   the local exception table for a handler. If no one is found, it unwinds    *
489 *   stacks and continues searching the callers.                                *
490 *                                                                              *
491 *   void asm_handle_exception (exceptionptr, exceptionpc);                     *
492 *                                                                              *
493 *******************************************************************************/
494                 
495 asm_handle_nat_exception:
496         mflr    r9
497         lwz     itmp3,4(r9)
498         extsh   itmp3,itmp3
499         add     pv,itmp3,r9
500         lwz     itmp3,8(r9)
501         srwi    itmp3,itmp3,16
502         cmpwi   itmp3,0x3dad
503         bne     asm_handle_exception
504         lwz     itmp3,8(r9)
505         slwi    itmp3,itmp3,16
506         add     pv,pv,itmp3
507
508 asm_handle_exception:
509         addi    r1,r1,-18*4
510         stw     r0,0*4(r1)
511         stw     r2,1*4(r1)
512         stw     r3,2*4(r1)
513         stw     r4,3*4(r1)
514         stw     r5,4*4(r1)
515         stw     r6,5*4(r1)
516         stw     r7,6*4(r1)
517         stw     r8,7*4(r1)
518         stw     r9,8*4(r1)
519         stw     r10,9*4(r1)
520         stw     r16,10*4(r1)
521         stw     r17,11*4(r1)
522         stw     r18,12*4(r1)
523         stw     r19,13*4(r1)
524         stw     r20,14*4(r1)
525         stw     r21,15*4(r1)
526         stw     r22,16*4(r1)
527         stw     r23,17*4(r1)
528
529         li      r9,1
530 ex_stack_loop:
531         addi    r1,r1,-4*4            /* allocate stack                           */
532         stw     xptr,0*4(r1)          /* save used register                       */
533         stw     xpc,1*4(r1)
534         mflr    xptr
535         stw     xptr,2*4(r1)
536         stw     r9,3*4(r1)
537
538         lwz     r3,0*4(r1)            /* exception pointer                        */
539         lwz     r4,MethodPointer(pv)  /* method pointer                           */
540         mr      r5,xpc                /* exception pc                             */
541 /*      mr      r6,r9 */
542         li      r6,0                  /* line number                              */
543         li      r7,4                  /* set no unwind flag                       */
544
545         /* XXX no valid stack frame chaining here */
546         addi    r1,r1,-(24+5*4)       /* 24 linkage area + 5 argument * 4         */
547         bl      builtin_trace_exception
548         addi    r1,r1,(24+5*4)
549
550         lwz     xptr,2*4(r1)
551         mtlr    xptr
552         lwz     xptr,0*4(r1)          /* restore xptr                             */
553         lwz     xpc,1*4(r1)
554         lwz     r9,3*4(r1)
555         addi    r1,r1,4*4
556
557         lwz     r3,ExTableSize(pv)    /* r3 = exception table size                */
558         mr.     r3,r3                 /* if empty table skip                      */
559         beq     empty_table
560
561         addi    r4,pv,ExTableStart    /* r4 = start of exception table            */
562
563 ex_table_loop:
564         lwz     r5,ExStartPC(r4)      /* r5 = exception start pc                  */
565         cmplw   r5,xpc                /* (startpc <= xpc)                         */
566         bgt     ex_table_cont
567         lwz     r5,ExEndPC(r4)        /* r5 = exception end pc                    */
568         cmplw   xpc,r5                /* (xpc < endpc)                            */
569         bge     ex_table_cont
570         lwz     r7,ExCatchType(r4)    /* r7 = exception catch type                */
571         mr.     r7,r7
572         beq     ex_handle_it
573
574         lwz     itmp3,offclassloaded(r7)
575         mr.     itmp3,itmp3
576         bne     L_class_loaded
577
578         /* XXX no valid stack frame chaining here */
579         addi    r1,r1,-16*4           /* allocate stack                           */
580         stw     r3,7*4(r1)            /* save used registers                      */
581         stw     r4,8*4(r1)            /* 6*4 (linkage) + 1*4 (arg1) + 7*4 (save)  */
582         stw     r9,9*4(r1)
583         stw     xptr,10*4(r1)
584         stw     xpc,11*4(r1)
585         mflr    xptr
586         stw     xptr,12*4(r1)
587         stw     r7,13*4(r1)
588
589         mr      r3,r7                 /* arg1 = exceptionclass                    */
590         bl      load_class_bootstrap
591
592         lwz     r3,7*4(r1)
593         lwz     r4,8*4(r1)
594         lwz     r9,9*4(r1)
595         lwz     xptr,10*4(r1)
596         lwz     xpc,11*4(r1)
597         lwz     itmp3,12*4(r1)
598         mtlr    itmp3
599         lwz     r7,13*4(r1)     
600         addi    r1,r1,16*4
601
602 L_class_loaded:
603         lwz     itmp3,offclasslinked(r7)
604         mr.     itmp3,itmp3
605         /* XXX no valid stack frame chaining here */
606         addi    r1,r1,-16*4           /* allocate stack                           */
607         stw     r7,13*4(r1)
608         bne     L_class_linked
609
610         stw     r3,7*4(r1)            /* save used registers                      */
611         stw     r4,8*4(r1)            /* 6*4 (linkage) + 1*4 (arg1) + 7*4 (save)  */
612         stw     r9,9*4(r1)
613         stw     xptr,10*4(r1)
614         stw     xpc,11*4(r1)
615         mflr    xptr
616         stw     xptr,12*4(r1)
617
618         mr      r3,r7                 /* arg1 = exceptionclass                    */
619         bl      link_class
620
621         lwz     r3,7*4(r1)
622         lwz     r4,8*4(r1)
623         lwz     r9,9*4(r1)
624         lwz     xptr,10*4(r1)
625         lwz     xpc,11*4(r1)
626         lwz     itmp3,12*4(r1)
627         mtlr    itmp3
628
629 L_class_linked:
630 _crit_restart1:
631         lwz     r7,13*4(r1)
632 _crit_begin1:
633         lwz     r6,offobjvftbl(xptr)  /* r6 = vftblptr(xptr)                      */
634         lwz     r7,offclassvftbl(r7)  /* r7 = vftblptr(catchtype) class (not obj) */
635         lwz     r6,offbaseval(r6)     /* r6 = baseval(xptr)                       */
636         lwz     r8,offbaseval(r7)     /* r8 = baseval(catchtype)                  */
637         lwz     r7,offdiffval(r7)     /* r7 = diffval(catchtype)                  */
638 _crit_end1:
639         subf    r6,r8,r6              /* r6 = baseval(xptr) - baseval(catchtype)  */
640         cmplw   r6,r7                 /* xptr is instanceof catchtype             */
641         addi    r1,r1,16*4
642         bgt     ex_table_cont         /* if (false) continue                      */
643
644 ex_handle_it:
645         lwz     xpc,ExHandlerPC(r4)   /* xpc = exception handler pc               */
646         mr.     r9,r9
647         beq     ex_jump
648
649         lwz     r0,0*4(r1)
650         lwz     r2,1*4(r1)
651         lwz     r3,2*4(r1)
652         lwz     r4,3*4(r1)
653         lwz     r5,4*4(r1)
654         lwz     r6,5*4(r1)
655         lwz     r7,6*4(r1)
656         lwz     r8,7*4(r1)
657         lwz     r9,8*4(r1)
658         lwz     r10,9*4(r1)
659         lwz     r16,10*4(r1)
660         lwz     r17,11*4(r1)
661         lwz     r18,12*4(r1)
662         lwz     r19,13*4(r1)
663         lwz     r20,14*4(r1)
664         lwz     r21,15*4(r1)
665         lwz     r22,16*4(r1)
666         lwz     r23,17*4(r1)
667         addi    r1,r1,18*4
668
669 ex_jump:
670         mtctr   xpc
671         bctr
672
673 ex_table_cont:
674         addi    r4,r4,ExEntrySize     /* next exception table entry               */
675         addic.  r3,r3,-1              /* decrement entry counter                  */
676         bgt     ex_table_loop         /* if (t0 > 0) next entry                   */
677
678 empty_table:
679         mr.     r9,r9                 /* if here the first time, then             */
680         beq     ex_already_cleared
681         addi    r1,r1,18*4            /* deallocate stack and                     */
682         li      r9,0                  /* clear the no unwind flag                 */
683 ex_already_cleared:
684         lwz     r3,IsSync(pv)         /* t0 = SyncOffset                          */
685         mr.     r3,r3
686         beq     no_monitor_exit       /* if zero no monitorexit                   */
687
688 #if defined(USE_THREADS)
689         add     r3,r1,r3
690         lwz     r6,-4(r3)
691
692         addi    r1,r1,-6*4
693         stw     r3,0*4(r1)
694         stw     r4,1*4(r1)
695         stw     r9,2*4(r1)
696         stw     xptr,3*4(r1)
697         stw     xpc,4*4(r1)
698         mflr    xptr
699         stw     xptr,5*4(r1)
700
701         mr      r3,r6
702         /* XXX no valid stack frame chaining here */
703         addi    r1,r1,-40
704         bl      builtin_monitorexit
705         addi    r1,r1,40
706
707         lwz     xptr,5*4(r1)
708         mtlr    xptr
709         lwz     r3,0*4(r1)
710         lwz     r4,1*4(r1)
711         lwz     r9,2*4(r1)
712         lwz     xptr,3*4(r1)
713         lwz     xpc,4*4(r1)
714         addi    r1,r1,6*4
715 #endif
716
717 no_monitor_exit:
718         lwz     r3,FrameSize(pv)      /* r3 = frame size                          */
719         add     r1,r1,r3              /* unwind stack                             */
720         mr      r3,r1                 /* r3 = pointer to save area                */
721         lwz     r4,IsLeaf(pv)         /* r4 = is leaf procedure                   */
722         mr.     r4,r4
723         bne     ex_no_restore         /* if (leaf) skip                           */
724         lwz     r4,LA_LR_OFFSET(r3)   /* restore ra                               */
725         mtlr    r4                    /* t0--                                     */
726 ex_no_restore:
727         mflr    r4                    /* the new xpc is ra                        */
728         mr      xpc,r4
729         lwz     r4,IntSave(pv)        /* r4 = saved int register count            */
730         bl      ex_int1
731 ex_int1:
732         mflr    r5
733 #if defined(__DARWIN__)
734         addi    r5,r5,lo16(ex_int2-ex_int1)
735 #else
736         addi    r5,r5,(ex_int2-ex_int1)@l
737 #endif
738         slwi    r4,r4,2
739         subf    r5,r4,r5
740         mtctr   r5
741         bctr
742         lwz     s0,-40(r3)
743         lwz     s1,-36(r3)
744         lwz     s2,-32(r3)
745         lwz     s3,-28(r3)
746         lwz     s4,-24(r3)
747         lwz     s5,-20(r3)
748         lwz     s6,-16(r3)
749         lwz     s7,-12(r3)
750         lwz     s8,-8(r3)
751         lwz     s9,-4(r3)
752
753 ex_int2:
754         subf    r3,r4,r3
755
756         lwz     r4,FltSave(pv)
757         bl      ex_flt1
758 ex_flt1:
759         mflr    r5
760 #if defined(__DARWIN__)
761         addi    r5,r5,lo16(ex_flt2-ex_flt1)
762 #else
763         addi    r5,r5,(ex_flt2-ex_flt1)@l
764 #endif
765         slwi    r4,r4,2
766         subf    r5,r4,r5
767         mtctr   r5
768         bctr
769         lfd     fs0,-80(r3)
770         lfd     fs1,-72(r3)
771         lfd     fs2,-64(r3)
772         lfd     fs3,-56(r3)
773         lfd     fs4,-48(r3)
774         lfd     fs5,-40(r3)
775         lfd     fs6,-32(r3)
776         lfd     fs7,-24(r3)
777         lfd     fs8,-16(r3)
778         lfd     fs9,-8(r3)
779
780 ex_flt2:
781         mtlr    xpc
782         lwz     itmp3,4(xpc)
783         extsh   itmp3,itmp3
784         add     pv,itmp3,xpc
785         lwz     itmp3,8(xpc)
786         srwi    itmp3,itmp3,16
787         cmpwi   itmp3,0x3dad
788         bne     ex_stack_loop
789         lwz     itmp3,8(xpc)
790         slwi    itmp3,itmp3,16
791         add     pv,pv,itmp3
792         b       ex_stack_loop
793
794
795 /* asm_wrapper_patcher *********************************************************
796
797    XXX
798
799    Stack layout:
800      20   return address into JIT code (patch position)
801      16   pointer to virtual java_objectheader
802      12   machine code (which is patched back later)
803       8   unresolved class/method/field reference
804       4   data segment displacement from load instructions
805       0   patcher function pointer to call (pv is saved here afterwards)
806
807 *******************************************************************************/
808
809 asm_wrapper_patcher:
810         mflr    r0
811         stw     r0,8*4+LA_LR_OFFSET(r1) /* skip stack frame of patcher stub       */
812                                       /* keep stack 16-bytes aligned: 6+1+37 = 44 */
813         stwu    r1,-(LA_SIZE+(5+38)*4+sizestackframeinfo)(r1)
814
815 #if 1
816         stw     a0,LA_SIZE+(5+0)*4(r1)      /* save argument registers            */
817         stw     a1,LA_SIZE+(5+1)*4(r1)      /* preserve linkage area (24 bytes)   */
818         stw     a2,LA_SIZE+(5+2)*4(r1)      /* and 4 bytes for 4 argument         */
819         stw     a3,LA_SIZE+(5+3)*4(r1)
820         stw     a4,LA_SIZE+(5+4)*4(r1)
821         stw     a5,LA_SIZE+(5+5)*4(r1)
822         stw     a6,LA_SIZE+(5+6)*4(r1)
823         stw     a7,LA_SIZE+(5+7)*4(r1)
824
825         stfd    fa0,LA_SIZE+(5+8)*4(sp)
826         stfd    fa1,LA_SIZE+(5+10)*4(sp)
827         stfd    fa2,LA_SIZE+(5+12)*4(sp)
828         stfd    fa3,LA_SIZE+(5+14)*4(sp)
829         stfd    fa4,LA_SIZE+(5+16)*4(sp)
830         stfd    fa5,LA_SIZE+(5+18)*4(sp)
831         stfd    fa6,LA_SIZE+(5+20)*4(sp)
832         stfd    fa7,LA_SIZE+(5+22)*4(sp)
833         stfd    fa8,LA_SIZE+(5+24)*4(sp)
834         stfd    fa9,LA_SIZE+(5+26)*4(sp)
835         stfd    fa10,LA_SIZE+(5+28)*4(sp)
836         stfd    fa11,LA_SIZE+(5+30)*4(sp)
837         stfd    fa12,LA_SIZE+(5+32)*4(sp)
838 #else
839         SAVE_ARGUMENT_REGISTERS(LA_WORD_SIZE+1) /* save 8 int/13 float arguments  */
840 #endif
841
842 #if 0
843         stw     r2,25*8(r1)
844         stw     r16,26*8(r1)
845         stw     r17,27*8(r1)
846         stw     r18,28*8(r1)
847         stw     r19,29*8(r1)
848         stw     r20,30*8(r1)
849         stw     r21,31*8(r1)
850         stw     r22,32*8(r1)
851         stw     r23,33*8(r1)
852 #endif
853
854         stw     itmp1,LA_SIZE+(5+34)*4(sp)
855         stw     itmp2,LA_SIZE+(5+35)*4(sp)
856         stw     pv,LA_SIZE+(5+36)*4(sp)
857
858         addi    a0,sp,LA_SIZE+(5+38)*4      /* create stackframe info             */
859         mr      a1,pv
860         addi    a2,sp,(8+LA_WORD_SIZE+5+38)*4+sizestackframeinfo
861         mr      a3,r0                       /* this is correct for leafs          */
862         mr      a4,a3                       /* pass xpc                           */
863         bl      stacktrace_create_extern_stackframeinfo
864
865         addi    a0,sp,(0+LA_WORD_SIZE+5+38)*4+sizestackframeinfo  /* pass sp      */
866         lwz     pv,(0+LA_WORD_SIZE+5+38)*4+sizestackframeinfo(sp) /* get function */
867         lwz     itmp1,LA_SIZE+(5+36)*4(sp)  /* move pv to position of fp          */
868         stw     itmp1,(0+LA_WORD_SIZE+5+38)*4+sizestackframeinfo(sp)
869         mtctr   pv                          /* call the patcher function          */
870         bctrl
871         stw     r3,LA_SIZE+(5+37)*4(sp)     /* save return value                  */
872
873         addi    a0,sp,LA_SIZE+(5+38)*4
874         bl      stacktrace_remove_stackframeinfo /* remove stackframe info        */
875
876         lwz     itmp3,LA_SIZE+(5+37)*4(sp)  /* restore return value into temp reg.*/
877
878 #if 1
879         lwz     a0,LA_SIZE+(5+0)*4(r1)
880         lwz     a1,LA_SIZE+(5+1)*4(r1)
881         lwz     a2,LA_SIZE+(5+2)*4(r1)
882         lwz     a3,LA_SIZE+(5+3)*4(r1)
883         lwz     a4,LA_SIZE+(5+4)*4(r1)
884         lwz     a5,LA_SIZE+(5+5)*4(r1)
885         lwz     a6,LA_SIZE+(5+6)*4(r1)
886         lwz     a7,LA_SIZE+(5+7)*4(r1)
887
888         lfd     fa0,LA_SIZE+(5+8)*4(sp)
889         lfd     fa1,LA_SIZE+(5+10)*4(sp)
890         lfd     fa2,LA_SIZE+(5+12)*4(sp)
891         lfd     fa3,LA_SIZE+(5+14)*4(sp)
892         lfd     fa4,LA_SIZE+(5+16)*4(sp)
893         lfd     fa5,LA_SIZE+(5+18)*4(sp)
894         lfd     fa6,LA_SIZE+(5+20)*4(sp)
895         lfd     fa7,LA_SIZE+(5+22)*4(sp)
896         lfd     fa8,LA_SIZE+(5+24)*4(sp)
897         lfd     fa9,LA_SIZE+(5+26)*4(sp)
898         lfd     fa10,LA_SIZE+(5+28)*4(sp)
899         lfd     fa11,LA_SIZE+(5+30)*4(sp)
900         lfd     fa12,LA_SIZE+(5+32)*4(sp)
901 #else
902         RESTORE_ARGUMENT_REGISTERS(LA_WORD_SIZE+4)/* restore 8 int/13 float args  */
903 #endif
904
905 #if 0
906         lwz     r2,25*8(r1)
907         lwz     r16,26*8(r1)
908         lwz     r17,27*8(r1)
909         lwz     r18,28*8(r1)
910         lwz     r19,29*8(r1)
911         lwz     r20,30*8(r1)
912         lwz     r21,31*8(r1)
913         lwz     r22,32*8(r1)
914         lwz     r23,33*8(r1)            
915 #endif
916
917                                       /* get return address (into JIT code)       */
918         lwz     itmp1,(5+LA_WORD_SIZE+5+38)*4+sizestackframeinfo(sp)
919         mtlr    itmp1
920
921         lwz     itmp1,LA_SIZE+(5+34)*4(sp)
922         lwz     itmp2,LA_SIZE+(5+35)*4(sp)
923         lwz     pv,LA_SIZE+(5+36)*4(sp)
924
925                                       /* remove stack frame + patcher stub stack  */
926         addi    r1,r1,(8+LA_WORD_SIZE+5+38)*4+sizestackframeinfo
927
928         mr.     itmp3,itmp3           /* check for an exception                   */
929         beq     L_asm_wrapper_patcher_exception
930
931         blr                           /* jump to new patched code                 */
932
933 L_asm_wrapper_patcher_exception:
934 #if defined(USE_THREADS) && defined(NATIVE_THREADS)
935         mflr    r0
936         stw     r0,LA_LR_OFFSET(r1)
937         stwu    r1,-LA_SIZE_ALIGNED(r1) /* preserve linkage area                  */
938         bl      builtin_asm_get_exceptionptrptr
939         lwz     r0,LA_SIZE_ALIGNED+LA_LR_OFFSET(r1)
940         mtlr    r0      
941         addi    r1,r1,LA_SIZE_ALIGNED
942 #else
943 # if defined(__DARWIN__)
944         lwz     v0,lo16(_exceptionptr-0b)(pv)
945 # else
946         lis     v0,_exceptionptr@ha
947         addi    v0,v0,_exceptionptr@l
948 # endif
949 #endif
950
951         lwz     xptr,0(v0)            /* get the exception pointer                */
952         li      itmp3,0
953         stw     itmp3,0(v0)           /* clear the exception pointer              */
954
955         mflr    xpc
956         b       asm_handle_exception
957
958
959 asm_cacheflush:
960         add     r4,r3,r4
961         rlwinm  r3,r3,0,0,26
962         addi    r4,r4,31
963         rlwinm  r4,r4,0,0,26
964         mr      r5,r3
965 1:
966         cmplw   r3,r4
967         bge     0f
968         dcbst   0,r3
969         addi    r3,r3,32
970         b       1b
971 0:
972         sync
973 1:
974         cmplw   r5,r4
975         bge     0f
976         icbi    0,r5
977         addi    r5,r5,32
978         b       1b
979 0:
980         sync
981         isync
982         blr
983
984
985         .align 3
986 doublezero:
987         .double 0.0
988
989 asm_initialize_thread_stack:
990         addi r4,r4,-256
991         stw r3,120(r4)
992         li r3,0
993         stw r3,124(r4)
994         stw r3,0(r4)
995         stw r3,4(r4)
996         stw r3,8(r4)
997         stw r3,12(r4)
998         stw r3,16(r4)
999         stw r3,20(r4)
1000         stw r3,24(r4)
1001         stw r3,28(r4)
1002         stw r3,32(r4)
1003         stw r3,36(r4)
1004
1005         stw r3,128(r4)
1006         stw r3,132(r4)
1007         stw r3,136(r4)
1008         stw r3,140(r4)
1009         stw r3,144(r4)
1010         stw r3,148(r4)
1011         stw r3,152(r4)
1012         stw r3,156(r4)
1013
1014         mflr r0
1015         bl 0f
1016 0:
1017         mflr r3
1018         mtlr r0
1019 #if defined(__DARWIN__)
1020         lfd fr0,lo16(doublezero-0b)(r3)
1021 #else
1022         lfd fr0,(doublezero-0b)@l(r3)
1023 #endif
1024
1025         stfd fr0,40(r4)
1026         stfd fr0,48(r4)
1027         stfd fr0,56(r4)
1028         stfd fr0,64(r4)
1029         stfd fr0,72(r4)
1030         stfd fr0,80(r4)
1031         stfd fr0,88(r4)
1032         stfd fr0,96(r4)
1033         stfd fr0,104(r4)
1034         stfd fr0,112(r4)
1035
1036         stfd fr0,160(r4)
1037         stfd fr0,168(r4)
1038         stfd fr0,176(r4)
1039         stfd fr0,184(r4)
1040         stfd fr0,192(r4)
1041         stfd fr0,200(r4)
1042         stfd fr0,208(r4)
1043         stfd fr0,216(r4)
1044
1045         mr r3,r4
1046         blr
1047
1048
1049 asm_perform_threadswitch:
1050         mflr r0
1051         addi r1,r1,-224
1052         stw r0,120(r1)
1053         stw pv,124(r1)
1054         stw r14,0(r1)
1055         stw r15,4(r1)
1056         stw r24,8(r1)
1057         stw r25,12(r1)
1058         stw r26,16(r1)
1059         stw r27,20(r1)
1060         stw r28,24(r1)
1061         stw r29,28(r1)
1062         stw r30,32(r1)
1063         stw r31,36(r1)
1064         stfd fr14,40(r1)
1065         stfd fr15,48(r1)
1066         stfd fr24,56(r1)
1067         stfd fr25,64(r1)
1068         stfd fr26,72(r1)
1069         stfd fr27,80(r1)
1070         stfd fr28,88(r1)
1071         stfd fr29,96(r1)
1072         stfd fr30,104(r1)
1073         stfd fr31,112(r1)
1074
1075         stw r16,128(r1)
1076         stw r17,132(r1)
1077         stw r18,136(r1)
1078         stw r19,140(r1)
1079         stw r20,144(r1)
1080         stw r21,148(r1)
1081         stw r22,152(r1)
1082         stw r23,156(r1)
1083         stfd fr16,160(r1)
1084         stfd fr17,168(r1)
1085         stfd fr18,176(r1)
1086         stfd fr19,184(r1)
1087         stfd fr20,192(r1)
1088         stfd fr21,200(r1)
1089         stfd fr22,208(r1)
1090         stfd fr23,216(r1)
1091
1092         stw r1,0(r3)
1093         stw r1,0(r5)
1094         lwz r1,0(r4)
1095
1096         lwz r0,120(r1)
1097         lwz pv,124(r1)
1098         lwz r14,0(r1)
1099         lwz r15,4(r1)
1100         lwz r24,8(r1)
1101         lwz r25,12(r1)
1102         lwz r26,16(r1)
1103         lwz r27,20(r1)
1104         lwz r28,24(r1)
1105         lwz r29,28(r1)
1106         lwz r30,32(r1)
1107         lwz r31,36(r1)
1108         lfd fr14,40(r1)
1109         lfd fr15,48(r1)
1110         lfd fr24,56(r1)
1111         lfd fr25,64(r1)
1112         lfd fr26,72(r1)
1113         lfd fr27,80(r1)
1114         lfd fr28,88(r1)
1115         lfd fr29,96(r1)
1116         lfd fr30,104(r1)
1117         lfd fr31,112(r1)
1118
1119         lwz r16,128(r1)
1120         lwz r17,132(r1)
1121         lwz r18,136(r1)
1122         lwz r19,140(r1)
1123         lwz r20,144(r1)
1124         lwz r21,148(r1)
1125         lwz r22,152(r1)
1126         lwz r23,156(r1)
1127         lfd fr16,160(r1)
1128         lfd fr17,168(r1)
1129         lfd fr18,176(r1)
1130         lfd fr19,184(r1)
1131         lfd fr20,192(r1)
1132         lfd fr21,200(r1)
1133         lfd fr22,208(r1)
1134         lfd fr23,216(r1)
1135
1136         mtlr r0
1137         addi r1,r1,224
1138         blr
1139
1140
1141 asm_switchstackandcall:
1142         mflr r0
1143         stwu r3,-48(r3)
1144         stw r0,40(r3)
1145         stw r1,44(r3)
1146         stw r1,0(r5)
1147         mr r1,r3
1148
1149         mtctr r4
1150         mr r3,r6
1151         bctrl
1152
1153         lwz r0,40(r1)
1154         mtlr r0
1155         lwz r1,44(r1)
1156         blr
1157
1158
1159 asm_getclassvalues_atomic:
1160 _crit_restart2:
1161 _crit_begin2:
1162         lwz     r6,offbaseval(r3)
1163         lwz     r7,offdiffval(r3)
1164         lwz     r8,offbaseval(r4)
1165 _crit_end2:
1166         stw     r6,offcast_super_baseval(r5)
1167         stw     r7,offcast_super_diffval(r5)
1168         stw     r8,offcast_sub_baseval(r5)
1169         blr
1170
1171         .data
1172
1173 asm_criticalsections:
1174 #if defined(USE_THREADS) && defined(NATIVE_THREADS)
1175         .long   _crit_begin1
1176         .long   _crit_end1
1177         .long   _crit_restart1
1178         .long   _crit_begin2
1179         .long   _crit_end2
1180         .long   _crit_restart2
1181 #endif
1182         .long 0
1183
1184
1185 /*
1186  * These are local overrides for various environment variables in Emacs.
1187  * Please do not remove this and leave it at the end of the file, where
1188  * Emacs will automagically detect them.
1189  * ---------------------------------------------------------------------
1190  * Local variables:
1191  * mode: asm
1192  * indent-tabs-mode: t
1193  * c-basic-offset: 4
1194  * tab-width: 4
1195  * End:
1196  */