trampoline.S revision 1.1.1.11 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