1 1.1 mrg /* libgcc routines for RL78 2 1.1.1.11 mrg Copyright (C) 2011-2024 Free Software Foundation, Inc. 3 1.1 mrg Contributed by Red Hat. 4 1.1 mrg 5 1.1 mrg This file is part of GCC. 6 1.1 mrg 7 1.1 mrg GCC is free software; you can redistribute it and/or modify it 8 1.1 mrg under the terms of the GNU General Public License as published 9 1.1 mrg by the Free Software Foundation; either version 3, or (at your 10 1.1 mrg option) any later version. 11 1.1 mrg 12 1.1 mrg GCC is distributed in the hope that it will be useful, but WITHOUT 13 1.1 mrg ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 1.1 mrg or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 1.1 mrg License for more details. 16 1.1 mrg 17 1.1 mrg Under Section 7 of GPL version 3, you are granted additional 18 1.1 mrg permissions described in the GCC Runtime Library Exception, version 19 1.1 mrg 3.1, as published by the Free Software Foundation. 20 1.1 mrg 21 1.1 mrg You should have received a copy of the GNU General Public License and 22 1.1 mrg a copy of the GCC Runtime Library Exception along with this program; 23 1.1 mrg see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 1.1 mrg <http://www.gnu.org/licenses/>. */ 25 1.1 mrg 26 1.1 mrg /* RL78 Trampoline support 27 1.1 mrg 28 1.1 mrg Since the RL78's RAM is not in the first 64k, we cannot "just" use a 29 1.1 mrg function pointer to point to a trampoline on the stack. So, we 30 1.1 mrg create N fixed trampolines that read from an array, and allocate 31 1.1 mrg them as needed. 32 1.1 mrg 33 1.1 mrg */ 34 1.1 mrg 35 1.1.1.2 mrg #include "vregs.h" 36 1.1 mrg 37 1.1 mrg .data 38 1.1 mrg .p2align 1 39 1.1 mrg trampoline_array: 40 1.1 mrg 41 1.1 mrg .macro stub n 42 1.1 mrg 43 1.1 mrg .text 44 1.1 mrg trampoline_\n: 45 1.1 mrg .type trampoline_\n, @function 46 1.1 mrg movw ax, !trampoline_chain_\n 47 1.1 mrg movw r14, ax 48 1.1 mrg movw ax, !trampoline_addr_\n 49 1.1 mrg br ax 50 1.1 mrg .size trampoline_\n, .-trampoline_\n 51 1.1 mrg 52 1.1 mrg .data 53 1.1 mrg trampoline_frame_\n: 54 1.1 mrg .short 0 55 1.1 mrg trampoline_stub_\n: 56 1.1 mrg .short trampoline_\n 57 1.1 mrg trampoline_chain_\n: 58 1.1 mrg .short 0 59 1.1 mrg trampoline_addr_\n: 60 1.1 mrg .short 0 61 1.1 mrg 62 1.1 mrg #define TO_FRAME 0 63 1.1 mrg #define TO_STUB 2 64 1.1 mrg #define TO_CHAIN 4 65 1.1 mrg #define TO_ADDR 6 66 1.1 mrg #define TO_SIZE 8 67 1.1 mrg 68 1.1 mrg .endm 69 1.1 mrg 70 1.1 mrg stub 0 71 1.1 mrg stub 1 72 1.1 mrg stub 2 73 1.1 mrg stub 3 74 1.1 mrg stub 4 75 1.1 mrg stub 5 76 1.1 mrg 77 1.1 mrg trampoline_array_end: 78 1.1 mrg 79 1.1 mrg /* Given the function pointer in R8 and the static chain 80 1.1 mrg pointer in R10, allocate a trampoline and return its address in 81 1.1 mrg R8. */ 82 1.1 mrg 83 1.1.1.2 mrg START_FUNC ___trampoline_init 84 1.1 mrg movw hl, #trampoline_array 85 1.1.1.2 mrg 86 1.1.1.2 mrg 1: movw ax, [hl + TO_ADDR] 87 1.1 mrg cmpw ax, #0 88 1.1 mrg bz $2f 89 1.1 mrg 90 1.1 mrg movw ax, hl 91 1.1 mrg addw ax, #TO_SIZE 92 1.1 mrg movw hl, ax 93 1.1 mrg cmpw ax, #trampoline_array_end 94 1.1 mrg bnz $1b 95 1.1 mrg brk ; no more slots? 96 1.1 mrg 97 1.1 mrg 2: movw ax, r8 98 1.1 mrg movw [hl + TO_ADDR], ax 99 1.1 mrg movw ax, r10 100 1.1 mrg movw [hl + TO_CHAIN], ax 101 1.1 mrg movw ax, sp 102 1.1 mrg movw [hl + TO_FRAME], ax 103 1.1 mrg 104 1.1 mrg movw ax, [hl + TO_STUB] 105 1.1 mrg movw r8, ax 106 1.1 mrg ret 107 1.1.1.2 mrg END_FUNC ___trampoline_init 108 1.1 mrg 109 1.1.1.2 mrg 110 1.1.1.2 mrg START_FUNC ___trampoline_uninit 111 1.1 mrg movw hl, #trampoline_array 112 1.1 mrg movw ax, sp 113 1.1 mrg movw bc, ax 114 1.1.1.2 mrg 115 1.1.1.2 mrg 1: movw ax, [hl + TO_FRAME] 116 1.1 mrg cmpw ax, bc 117 1.1 mrg bc $2f 118 1.1 mrg 119 1.1 mrg clrw ax 120 1.1 mrg movw [hl + TO_ADDR], ax 121 1.1 mrg 122 1.1.1.2 mrg 2: movw ax, hl 123 1.1 mrg addw ax, #TO_SIZE 124 1.1 mrg movw hl, ax 125 1.1 mrg cmpw ax, #trampoline_array_end 126 1.1 mrg bnz $1b 127 1.1 mrg 128 1.1 mrg ret 129 1.1.1.2 mrg END_FUNC ___trampoline_uninit 130