1 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
2 * Mupen64plus - linkage_arm.s *
3 * Copyright (C) 2009-2011 Ari64 *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. *
19 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
41 .global reg_cop1_simple
42 .hidden reg_cop1_simple
43 .global reg_cop1_double
44 .hidden reg_cop1_double
51 .global rounding_modes
52 .hidden rounding_modes
59 .global pending_exception
60 .hidden pending_exception
87 .global restore_candidate
88 .hidden restore_candidate
95 .type extra_memory, %object
96 .size extra_memory, 33554432
98 .space 33554432+64+16+16+8+8+8+8+256+8+8+128+128+128+16+8+132+4+256+512+4194304
99 dynarec_local = extra_memory + 33554432
100 .type dynarec_local, %object
101 .size dynarec_local, 64
102 next_interupt = dynarec_local + 64
103 .type next_interupt, %object
104 .size next_interupt, 4
105 cycle_count = next_interupt + 4
106 .type cycle_count, %object
108 last_count = cycle_count + 4
109 .type last_count, %object
111 pending_exception = last_count + 4
112 .type pending_exception, %object
113 .size pending_exception, 4
114 pcaddr = pending_exception + 4
115 .type pcaddr, %object
121 .type invc_ptr, %object
123 address = invc_ptr + 4
124 .type address, %object
126 readmem_dword = address + 4
127 .type readmem_dword, %object
128 .size readmem_dword, 8
129 dword = readmem_dword + 8
139 .type cpu_byte, %object
140 .size cpu_byte, 1 /* 1 byte free */
157 .type reg_cop0, %object
159 reg_cop1_simple = reg_cop0 + 128
160 .type reg_cop1_simple, %object
161 .size reg_cop1_simple, 128
162 reg_cop1_double = reg_cop1_simple + 128
163 .type reg_cop1_double, %object
164 .size reg_cop1_double, 128
165 rounding_modes = reg_cop1_double + 128
166 .type rounding_modes, %object
167 .size rounding_modes, 16
168 branch_target = rounding_modes + 16
169 .type branch_target, %object
170 .size branch_target, 4
171 PC = branch_target + 4
175 .type fake_pc, %object
177 ram_offset = fake_pc + 132
178 .type ram_offset, %object
180 mini_ht = ram_offset + 4
181 .type mini_ht, %object
183 restore_candidate = mini_ht + 256
184 .type restore_candidate, %object
185 .size restore_candidate, 512
186 memory_map = restore_candidate + 512
187 .type memory_map, %object
188 .size memory_map, 4194304
194 .type dyna_linker, %function
196 /* r0 = virtual target address */
197 /* r1 = instruction to patch */
203 ldrge r12, [r4, r5, lsl #2]
210 eor r2, r2, r12, lsr #12
211 and r6, r6, r12, lsr #12
215 ldr r5, [r3, r2, lsl #2]
231 add r1, r1, r12, asr #6
233 moveq pc, r4 /* Stale i-cache */
236 and r1, r7, #0xff000000
239 add r1, r1, r2, lsr #8
243 /* hash_table lookup */
246 eor r4, r0, r0, lsl #16
252 ldr r5, [r3, r2, lsl #2]
259 /* jump_dirty lookup */
269 /* hash_table insert */
280 bl new_recompile_block
288 .size dyna_linker, .-dyna_linker
289 .type exec_pagefault, %function
291 /* r0 = instruction pointer */
292 /* r1 = fault address */
294 ldr r3, [fp, #reg_cop0+48-dynarec_local] /* Status */
296 ldr r4, [fp, #reg_cop0+16-dynarec_local] /* Context */
297 bic r6, r6, #0x0F800000
298 str r0, [fp, #reg_cop0+56-dynarec_local] /* EPC */
300 str r1, [fp, #reg_cop0+32-dynarec_local] /* BadVAddr */
302 str r3, [fp, #reg_cop0+48-dynarec_local] /* Status */
303 and r5, r6, r1, lsr #9
304 str r2, [fp, #reg_cop0+52-dynarec_local] /* Cause */
305 and r1, r1, r6, lsl #9
306 str r1, [fp, #reg_cop0+40-dynarec_local] /* EntryHi */
308 str r4, [fp, #reg_cop0+16-dynarec_local] /* Context */
312 .size exec_pagefault, .-exec_pagefault
313 /* Special dynamic linker for the case where a page fault
314 may occur in a branch delay slot */
315 .global dyna_linker_ds
316 .hidden dyna_linker_ds
317 .type dyna_linker_ds, %function
319 /* r0 = virtual target address */
320 /* r1 = instruction to patch */
326 ldrge r12, [r4, r5, lsl #2]
333 eor r2, r2, r12, lsr #12
334 and r6, r6, r12, lsr #12
338 ldr r5, [r3, r2, lsl #2]
354 add r1, r1, r12, asr #6
356 moveq pc, r4 /* Stale i-cache */
359 and r1, r7, #0xff000000
362 add r1, r1, r2, lsr #8
366 /* hash_table lookup */
369 eor r4, r0, r0, lsl #16
375 ldr r5, [r3, r2, lsl #2]
382 /* jump_dirty lookup */
392 /* hash_table insert */
405 bl new_recompile_block
412 mov r2, #0x80000008 /* High bit set indicates pagefault in delay slot */
415 .size dyna_linker_ds, .-dyna_linker_ds
425 .global jump_vaddr_r0
426 .hidden jump_vaddr_r0
427 .type jump_vaddr_r0, %function
429 eor r2, r0, r0, lsl #16
431 .size jump_vaddr_r0, .-jump_vaddr_r0
432 .global jump_vaddr_r1
433 .hidden jump_vaddr_r1
434 .type jump_vaddr_r1, %function
436 eor r2, r1, r1, lsl #16
439 .size jump_vaddr_r1, .-jump_vaddr_r1
440 .global jump_vaddr_r2
441 .hidden jump_vaddr_r2
442 .type jump_vaddr_r2, %function
445 eor r2, r2, r2, lsl #16
447 .size jump_vaddr_r2, .-jump_vaddr_r2
448 .global jump_vaddr_r3
449 .hidden jump_vaddr_r3
450 .type jump_vaddr_r3, %function
452 eor r2, r3, r3, lsl #16
455 .size jump_vaddr_r3, .-jump_vaddr_r3
456 .global jump_vaddr_r4
457 .hidden jump_vaddr_r4
458 .type jump_vaddr_r4, %function
460 eor r2, r4, r4, lsl #16
463 .size jump_vaddr_r4, .-jump_vaddr_r4
464 .global jump_vaddr_r5
465 .hidden jump_vaddr_r5
466 .type jump_vaddr_r5, %function
468 eor r2, r5, r5, lsl #16
471 .size jump_vaddr_r5, .-jump_vaddr_r5
472 .global jump_vaddr_r6
473 .hidden jump_vaddr_r6
474 .type jump_vaddr_r6, %function
476 eor r2, r6, r6, lsl #16
479 .size jump_vaddr_r6, .-jump_vaddr_r6
480 .global jump_vaddr_r8
481 .hidden jump_vaddr_r8
482 .type jump_vaddr_r8, %function
484 eor r2, r8, r8, lsl #16
487 .size jump_vaddr_r8, .-jump_vaddr_r8
488 .global jump_vaddr_r9
489 .hidden jump_vaddr_r9
490 .type jump_vaddr_r9, %function
492 eor r2, r9, r9, lsl #16
495 .size jump_vaddr_r9, .-jump_vaddr_r9
496 .global jump_vaddr_r10
497 .hidden jump_vaddr_r10
498 .type jump_vaddr_r10, %function
500 eor r2, r10, r10, lsl #16
503 .size jump_vaddr_r10, .-jump_vaddr_r10
504 .global jump_vaddr_r12
505 .hidden jump_vaddr_r12
506 .type jump_vaddr_r12, %function
508 eor r2, r12, r12, lsl #16
511 .size jump_vaddr_r12, .-jump_vaddr_r12
512 .global jump_vaddr_r7
513 .hidden jump_vaddr_r7
514 .type jump_vaddr_r7, %function
516 eor r2, r7, r7, lsl #16
518 .size jump_vaddr_r7, .-jump_vaddr_r7
521 .type jump_vaddr, %function
525 and r2, r3, r2, lsr #12
532 str r10, [fp, #cycle_count-dynarec_local]
534 ldr r10, [fp, #cycle_count-dynarec_local]
536 .size jump_vaddr, .-jump_vaddr
538 .global verify_code_ds
539 .hidden verify_code_ds
540 .type verify_code_ds, %function
542 str r8, [fp, #branch_target-dynarec_local]
543 .size verify_code_ds, .-verify_code_ds
544 .global verify_code_vm
545 .hidden verify_code_vm
546 .type verify_code_vm, %function
548 /* r0 = instruction pointer (virtual address) */
549 /* r1 = source (virtual address) */
554 add r12, fp, #memory_map-dynarec_local
558 ldr r6, [r12, r4, lsl #2]
562 add r1, r1, r6, lsl #2
568 ldr r7, [r12, r4, lsl #2]
571 .size verify_code_vm, .-verify_code_vm
574 .type verify_code, %function
603 ldr r8, [fp, #branch_target-dynarec_local]
608 .size verify_code, .-verify_code
612 .type cc_interrupt, %function
614 ldr r0, [fp, #last_count-dynarec_local]
618 str r1, [fp, #pending_exception-dynarec_local]
619 and r2, r2, r10, lsr #17
620 add r3, fp, #restore_candidate-dynarec_local
621 str r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
629 ldr r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
630 ldr r0, [fp, #next_interupt-dynarec_local]
631 ldr r1, [fp, #pending_exception-dynarec_local]
632 ldr r2, [fp, #stop-dynarec_local]
633 str r0, [fp, #last_count-dynarec_local]
640 ldr r0, [fp, #pcaddr-dynarec_local]
645 ldmia r12, {r4, r5, r6, r7, r8, r9, sl, fp, pc}
647 /* Move 'dirty' blocks to the 'clean' list */
659 .size cc_interrupt, .-cc_interrupt
663 .type do_interrupt, %function
665 ldr r0, [fp, #pcaddr-dynarec_local]
667 ldr r1, [fp, #next_interupt-dynarec_local]
668 ldr r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
669 str r1, [fp, #last_count-dynarec_local]
673 .size do_interrupt, .-do_interrupt
677 .type fp_exception, %function
681 ldr r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
683 str r0, [fp, #reg_cop0+56-dynarec_local] /* EPC */
686 str r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
687 str r2, [fp, #reg_cop0+52-dynarec_local] /* Cause */
691 .size fp_exception, .-fp_exception
693 .global fp_exception_ds
694 .hidden fp_exception_ds
695 .type fp_exception_ds, %function
697 mov r2, #0x90000000 /* Set high bit if delay slot */
699 .size fp_exception_ds, .-fp_exception_ds
703 .type jump_syscall, %function
705 ldr r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
707 str r0, [fp, #reg_cop0+56-dynarec_local] /* EPC */
710 str r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
711 str r2, [fp, #reg_cop0+52-dynarec_local] /* Cause */
715 .size jump_syscall, .-jump_syscall
717 .global indirect_jump_indexed
718 .hidden indirect_jump_indexed
719 .type indirect_jump_indexed, %function
720 indirect_jump_indexed:
721 ldr r0, [r0, r1, lsl #2]
722 .size indirect_jump_indexed, .-indirect_jump_indexed
724 .global indirect_jump
725 .hidden indirect_jump
726 .type indirect_jump, %function
728 ldr r12, [fp, #last_count-dynarec_local]
730 str r2, [fp, #reg_cop0+36-dynarec_local] /* Count */
732 .size indirect_jump, .-indirect_jump
736 .type jump_eret, %function
738 ldr r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
739 ldr r0, [fp, #last_count-dynarec_local]
742 str r1, [fp, #reg_cop0+48-dynarec_local] /* Status */
743 str r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
745 ldr r1, [fp, #next_interupt-dynarec_local]
746 ldr r0, [fp, #reg_cop0+56-dynarec_local] /* EPC */
747 str r1, [fp, #last_count-dynarec_local]
751 add r6, fp, #reg+256-dynarec_local
757 eor r3, r3, r2, asr #31
762 ldr r2, [fp, #hi-dynarec_local]
763 ldr r3, [fp, #hi+4-dynarec_local]
764 eors r3, r3, r2, asr #31
765 ldr r2, [fp, #lo-dynarec_local]
766 ldreq r3, [fp, #lo+4-dynarec_local]
767 eoreq r3, r3, r2, asr #31
773 str r0, [fp, #pcaddr-dynarec_local]
775 ldr r0, [fp, #pcaddr-dynarec_local]
777 .size jump_eret, .-jump_eret
779 .global new_dyna_start
780 .hidden new_dyna_start
781 .type new_dyna_start, %function
786 stmia r12, {r4, r5, r6, r7, r8, r9, sl, fp, lr}
790 bl new_recompile_block
791 ldr r0, [fp, #next_interupt-dynarec_local]
792 ldr r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
793 str r0, [fp, #last_count-dynarec_local]
797 .word dynarec_local+28
800 .size new_dyna_start, .-new_dyna_start
802 .global invalidate_addr_r0
803 .hidden invalidate_addr_r0
804 .type invalidate_addr_r0, %function
806 stmia fp, {r0, r1, r2, r3, r12, lr}
808 b invalidate_addr_call
809 .size invalidate_addr_r0, .-invalidate_addr_r0
811 .global invalidate_addr_r1
812 .hidden invalidate_addr_r1
813 .type invalidate_addr_r1, %function
815 stmia fp, {r0, r1, r2, r3, r12, lr}
817 b invalidate_addr_call
818 .size invalidate_addr_r1, .-invalidate_addr_r1
820 .global invalidate_addr_r2
821 .hidden invalidate_addr_r2
822 .type invalidate_addr_r2, %function
824 stmia fp, {r0, r1, r2, r3, r12, lr}
826 b invalidate_addr_call
827 .size invalidate_addr_r2, .-invalidate_addr_r2
829 .global invalidate_addr_r3
830 .hidden invalidate_addr_r3
831 .type invalidate_addr_r3, %function
833 stmia fp, {r0, r1, r2, r3, r12, lr}
835 b invalidate_addr_call
836 .size invalidate_addr_r3, .-invalidate_addr_r3
838 .global invalidate_addr_r4
839 .hidden invalidate_addr_r4
840 .type invalidate_addr_r4, %function
842 stmia fp, {r0, r1, r2, r3, r12, lr}
844 b invalidate_addr_call
845 .size invalidate_addr_r4, .-invalidate_addr_r4
847 .global invalidate_addr_r5
848 .hidden invalidate_addr_r5
849 .type invalidate_addr_r5, %function
851 stmia fp, {r0, r1, r2, r3, r12, lr}
853 b invalidate_addr_call
854 .size invalidate_addr_r5, .-invalidate_addr_r5
856 .global invalidate_addr_r6
857 .hidden invalidate_addr_r6
858 .type invalidate_addr_r6, %function
860 stmia fp, {r0, r1, r2, r3, r12, lr}
862 b invalidate_addr_call
863 .size invalidate_addr_r6, .-invalidate_addr_r6
865 .global invalidate_addr_r7
866 .hidden invalidate_addr_r7
867 .type invalidate_addr_r7, %function
869 stmia fp, {r0, r1, r2, r3, r12, lr}
871 b invalidate_addr_call
872 .size invalidate_addr_r7, .-invalidate_addr_r7
874 .global invalidate_addr_r8
875 .hidden invalidate_addr_r8
876 .type invalidate_addr_r8, %function
878 stmia fp, {r0, r1, r2, r3, r12, lr}
880 b invalidate_addr_call
881 .size invalidate_addr_r8, .-invalidate_addr_r8
883 .global invalidate_addr_r9
884 .hidden invalidate_addr_r9
885 .type invalidate_addr_r9, %function
887 stmia fp, {r0, r1, r2, r3, r12, lr}
889 b invalidate_addr_call
890 .size invalidate_addr_r9, .-invalidate_addr_r9
892 .global invalidate_addr_r10
893 .hidden invalidate_addr_r10
894 .type invalidate_addr_r10, %function
896 stmia fp, {r0, r1, r2, r3, r12, lr}
898 b invalidate_addr_call
899 .size invalidate_addr_r10, .-invalidate_addr_r10
901 .global invalidate_addr_r12
902 .hidden invalidate_addr_r12
903 .type invalidate_addr_r12, %function
905 stmia fp, {r0, r1, r2, r3, r12, lr}
907 .size invalidate_addr_r12, .-invalidate_addr_r12
909 .type invalidate_addr_call, %function
910 invalidate_addr_call:
912 ldmia fp, {r0, r1, r2, r3, r12, pc}
913 .size invalidate_addr_call, .-invalidate_addr_call
915 .global write_rdram_new
916 .hidden write_rdram_new
917 .type write_rdram_new, %function
919 ldr r3, [fp, #ram_offset-dynarec_local]
920 ldr r2, [fp, #address-dynarec_local]
921 ldr r0, [fp, #word-dynarec_local]
922 str r0, [r2, r3, lsl #2]
924 .size write_rdram_new, .-write_rdram_new
926 .global write_rdramb_new
927 .hidden write_rdramb_new
928 .type write_rdramb_new, %function
930 ldr r3, [fp, #ram_offset-dynarec_local]
931 ldr r2, [fp, #address-dynarec_local]
932 ldrb r0, [fp, #cpu_byte-dynarec_local]
934 strb r0, [r2, r3, lsl #2]
936 .size write_rdramb_new, .-write_rdramb_new
938 .global write_rdramh_new
939 .hidden write_rdramh_new
940 .type write_rdramh_new, %function
942 ldr r3, [fp, #ram_offset-dynarec_local]
943 ldr r2, [fp, #address-dynarec_local]
944 ldrh r0, [fp, #hword-dynarec_local]
949 .size write_rdramh_new, .-write_rdramh_new
951 .global write_rdramd_new
952 .hidden write_rdramd_new
953 .type write_rdramd_new, %function
955 ldr r3, [fp, #ram_offset-dynarec_local]
956 ldr r2, [fp, #address-dynarec_local]
957 /* ldrd r0, [fp, #dword-dynarec_local]*/
958 ldr r0, [fp, #dword-dynarec_local]
959 ldr r1, [fp, #dword+4-dynarec_local]
960 add r3, r2, r3, lsl #2
964 .size write_rdramd_new, .-write_rdramd_new
966 .type do_invalidate, %function
968 ldr r2, [fp, #address-dynarec_local]
970 ldr r1, [fp, #invc_ptr-dynarec_local]
976 .size do_invalidate, .-do_invalidate
978 .global read_nomem_new
979 .hidden read_nomem_new
980 .type read_nomem_new, %function
982 ldr r2, [fp, #address-dynarec_local]
983 add r12, fp, #memory_map-dynarec_local
985 ldr r12, [r12, r0, lsl #2]
989 ldr r0, [r2, r12, lsl #2]
990 str r0, [fp, #readmem_dword-dynarec_local]
992 .size read_nomem_new, .-read_nomem_new
994 .global read_nomemb_new
995 .hidden read_nomemb_new
996 .type read_nomemb_new, %function
998 ldr r2, [fp, #address-dynarec_local]
999 add r12, fp, #memory_map-dynarec_local
1001 ldr r12, [r12, r0, lsl #2]
1006 ldrb r0, [r2, r12, lsl #2]
1007 str r0, [fp, #readmem_dword-dynarec_local]
1009 .size read_nomemb_new, .-read_nomemb_new
1011 .global read_nomemh_new
1012 .hidden read_nomemh_new
1013 .type read_nomemh_new, %function
1015 ldr r2, [fp, #address-dynarec_local]
1016 add r12, fp, #memory_map-dynarec_local
1018 ldr r12, [r12, r0, lsl #2]
1025 str r0, [fp, #readmem_dword-dynarec_local]
1027 .size read_nomemh_new, .-read_nomemh_new
1029 .global read_nomemd_new
1030 .hidden read_nomemd_new
1031 .type read_nomemd_new, %function
1033 ldr r2, [fp, #address-dynarec_local]
1034 add r12, fp, #memory_map-dynarec_local
1036 ldr r12, [r12, r0, lsl #2]
1041 /* ldrd r0, [r2, r12]*/
1045 str r0, [fp, #readmem_dword+4-dynarec_local]
1046 str r1, [fp, #readmem_dword-dynarec_local]
1048 .size read_nomemd_new, .-read_nomemd_new
1050 .global write_nomem_new
1051 .hidden write_nomem_new
1052 .type write_nomem_new, %function
1057 ldr r2, [fp, #address-dynarec_local]
1058 add r12, fp, #memory_map-dynarec_local
1062 ldr r12, [r12, r0, lsl #2]
1064 tst r12, #0x40000000
1066 ldr r0, [fp, #word-dynarec_local]
1067 str r0, [r2, r12, lsl #2]
1069 .size write_nomem_new, .-write_nomem_new
1071 .global write_nomemb_new
1072 .hidden write_nomemb_new
1073 .type write_nomemb_new, %function
1078 ldr r2, [fp, #address-dynarec_local]
1079 add r12, fp, #memory_map-dynarec_local
1083 ldr r12, [r12, r0, lsl #2]
1085 tst r12, #0x40000000
1088 ldrb r0, [fp, #cpu_byte-dynarec_local]
1089 strb r0, [r2, r12, lsl #2]
1091 .size write_nomemb_new, .-write_nomemb_new
1093 .global write_nomemh_new
1094 .hidden write_nomemh_new
1095 .type write_nomemh_new, %function
1100 ldr r2, [fp, #address-dynarec_local]
1101 add r12, fp, #memory_map-dynarec_local
1105 ldr r12, [r12, r0, lsl #2]
1110 ldrh r0, [fp, #hword-dynarec_local]
1113 .size write_nomemh_new, .-write_nomemh_new
1115 .global write_nomemd_new
1116 .hidden write_nomemd_new
1117 .type write_nomemd_new, %function
1122 ldr r2, [fp, #address-dynarec_local]
1123 add r12, fp, #memory_map-dynarec_local
1127 ldr r12, [r12, r0, lsl #2]
1132 ldr r0, [fp, #dword+4-dynarec_local]
1133 ldr r1, [fp, #dword-dynarec_local]
1134 /* strd r0, [r2, r12]*/
1138 .size write_nomemd_new, .-write_nomemd_new
1140 .type tlb_exception, %function
1144 /* r3 = instr addr/flags */
1145 ldr r4, [fp, #reg_cop0+48-dynarec_local] /* Status */
1146 add r5, fp, #memory_map-dynarec_local
1148 orr r1, r1, r3, lsl #31
1150 ldr r7, [r5, r6, lsl #2]
1152 str r4, [fp, #reg_cop0+48-dynarec_local] /* Status */
1154 str r1, [fp, #reg_cop0+52-dynarec_local] /* Cause */
1156 ldr r0, [r8, r7, lsl #2]
1157 add r4, r8, r1, asr #29
1158 add r5, fp, #reg-dynarec_local
1159 str r4, [fp, #reg_cop0+56-dynarec_local] /* EPC */
1161 ldr r8, [fp, #reg_cop0+16-dynarec_local] /* Context */
1164 and r7, r7, r0, lsr #18
1166 sub r2, r2, r1, asr #16
1167 bic r9, r9, #0x0F800000
1174 add r4, r2, r1, asr #16
1175 add r6, fp, #reg+4-dynarec_local
1177 str r4, [fp, #reg_cop0+32-dynarec_local] /* BadVAddr */
1179 and r4, r9, r4, lsr #9
1182 str r8, [fp, #reg_cop0+16-dynarec_local] /* Context */
1184 ldr r1, [fp, #next_interupt-dynarec_local]
1185 ldr r10, [fp, #reg_cop0+36-dynarec_local] /* Count */
1186 str r1, [fp, #last_count-dynarec_local]
1189 .size tlb_exception, .-tlb_exception
1193 .type breakpoint, %function
1195 /* Set breakpoint here for debugging */
1197 .size breakpoint, .-breakpoint
1198 /* The following bug-fix implements __clear_cache (missing in Android) */
1200 .global __clear_cache_bugfix
1201 .hidden __clear_cache_bugfix
1202 .type __clear_cache_bugfix, %function
1203 __clear_cache_bugfix:
1207 add r7, r7, #0xf0000
1210 .size __clear_cache_bugfix, .-__clear_cache_bugfix
1211 /* End of bug-fix */
1212 .section .note.GNU-stack,"",%progbits