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