1*404b540aSrobert/* libgcc routines for R8C/M16C/M32C 2*404b540aSrobert Copyright (C) 2005 3*404b540aSrobert Free Software Foundation, Inc. 4*404b540aSrobert Contributed by Red Hat. 5*404b540aSrobert 6*404b540aSrobert This file is part of GCC. 7*404b540aSrobert 8*404b540aSrobert GCC is free software; you can redistribute it and/or modify it 9*404b540aSrobert under the terms of the GNU General Public License as published 10*404b540aSrobert by the Free Software Foundation; either version 2, or (at your 11*404b540aSrobert option) any later version. 12*404b540aSrobert 13*404b540aSrobert In addition to the permissions in the GNU General Public License, 14*404b540aSrobert the Free Software Foundation gives you unlimited permission to link 15*404b540aSrobert the compiled version of this file into combinations with other 16*404b540aSrobert programs, and to distribute those combinations without any 17*404b540aSrobert restriction coming from the use of this file. (The General Public 18*404b540aSrobert License restrictions do apply in other respects; for example, they 19*404b540aSrobert cover modification of the file, and distribution when not linked 20*404b540aSrobert into a combine executable.) 21*404b540aSrobert 22*404b540aSrobert GCC is distributed in the hope that it will be useful, but WITHOUT 23*404b540aSrobert ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 24*404b540aSrobert or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 25*404b540aSrobert License for more details. 26*404b540aSrobert 27*404b540aSrobert You should have received a copy of the GNU General Public License 28*404b540aSrobert along with GCC; see the file COPYING. If not, write to the Free 29*404b540aSrobert Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 30*404b540aSrobert 02110-1301, USA. */ 31*404b540aSrobert 32*404b540aSrobert#if defined(__r8c_cpu__) || defined(__m16c_cpu__) 33*404b540aSrobert#define A16 34*404b540aSrobert#define A(n,w) n 35*404b540aSrobert#define W w 36*404b540aSrobert#else 37*404b540aSrobert#define A24 38*404b540aSrobert#define A(n,w) w 39*404b540aSrobert#define W l 40*404b540aSrobert#endif 41*404b540aSrobert 42*404b540aSrobert 43*404b540aSrobert#ifdef L__m32c_memregs 44*404b540aSrobert 45*404b540aSrobert/* Warning: these memory locations are used as a register bank. They 46*404b540aSrobert *must* end up consecutive in any final executable, so you may *not* 47*404b540aSrobert use the otherwise obvious ".comm" directive to allocate space for 48*404b540aSrobert them. */ 49*404b540aSrobert 50*404b540aSrobert .bss 51*404b540aSrobert .global mem0 52*404b540aSrobertmem0: .space 1 53*404b540aSrobert .global mem1 54*404b540aSrobertmem1: .space 1 55*404b540aSrobert .global mem2 56*404b540aSrobertmem2: .space 1 57*404b540aSrobert .global mem3 58*404b540aSrobertmem3: .space 1 59*404b540aSrobert .global mem4 60*404b540aSrobertmem4: .space 1 61*404b540aSrobert .global mem5 62*404b540aSrobertmem5: .space 1 63*404b540aSrobert .global mem6 64*404b540aSrobertmem6: .space 1 65*404b540aSrobert .global mem7 66*404b540aSrobertmem7: .space 1 67*404b540aSrobert .global mem8 68*404b540aSrobertmem8: .space 1 69*404b540aSrobert .global mem9 70*404b540aSrobertmem9: .space 1 71*404b540aSrobert .global mem10 72*404b540aSrobertmem10: .space 1 73*404b540aSrobert .global mem11 74*404b540aSrobertmem11: .space 1 75*404b540aSrobert .global mem12 76*404b540aSrobertmem12: .space 1 77*404b540aSrobert .global mem13 78*404b540aSrobertmem13: .space 1 79*404b540aSrobert .global mem14 80*404b540aSrobertmem14: .space 1 81*404b540aSrobert .global mem15 82*404b540aSrobertmem15: .space 1 83*404b540aSrobert 84*404b540aSrobert#endif 85*404b540aSrobert 86*404b540aSrobert#ifdef L__m32c_eh_return 87*404b540aSrobert .text 88*404b540aSrobert .global __m32c_eh_return 89*404b540aSrobert__m32c_eh_return: 90*404b540aSrobert 91*404b540aSrobert /* At this point, r0 has the stack adjustment, r1r3 has the 92*404b540aSrobert address to return to. The stack looks like this: 93*404b540aSrobert 94*404b540aSrobert old_ra 95*404b540aSrobert old_fp 96*404b540aSrobert <- unwound sp 97*404b540aSrobert ... 98*404b540aSrobert fb 99*404b540aSrobert through 100*404b540aSrobert r0 101*404b540aSrobert <- sp 102*404b540aSrobert 103*404b540aSrobert What we need to do is restore all the registers, update the 104*404b540aSrobert stack, and return to the right place. 105*404b540aSrobert */ 106*404b540aSrobert 107*404b540aSrobert stc sp,a0 108*404b540aSrobert 109*404b540aSrobert add.W A(#16,#24),a0 110*404b540aSrobert /* a0 points to the current stack, just above the register 111*404b540aSrobert save areas */ 112*404b540aSrobert 113*404b540aSrobert mov.w a0,a1 114*404b540aSrobert exts.w r0 115*404b540aSrobert sub.W A(r0,r2r0),a1 116*404b540aSrobert sub.W A(#3,#4),a1 117*404b540aSrobert /* a1 points to the new stack. */ 118*404b540aSrobert 119*404b540aSrobert /* This is for the "rts" below. */ 120*404b540aSrobert mov.w r1,[a1] 121*404b540aSrobert#ifdef A16 122*404b540aSrobert mov.w r2,r1 123*404b540aSrobert mov.b r1l,2[a1] 124*404b540aSrobert#else 125*404b540aSrobert mov.w r2,2[a1] 126*404b540aSrobert#endif 127*404b540aSrobert 128*404b540aSrobert /* This is for the "popc sp" below. */ 129*404b540aSrobert mov.W a1,[a0] 130*404b540aSrobert 131*404b540aSrobert popm r0,r1,r2,r3,a0,a1,sb,fb 132*404b540aSrobert popc sp 133*404b540aSrobert rts 134*404b540aSrobert#endif 135*404b540aSrobert 136*404b540aSrobert/* SImode arguments for SI foo(SI,SI) functions. */ 137*404b540aSrobert#ifdef A16 138*404b540aSrobert#define SAL 5[fb] 139*404b540aSrobert#define SAH 7[fb] 140*404b540aSrobert#define SBL 9[fb] 141*404b540aSrobert#define SBH 11[fb] 142*404b540aSrobert#else 143*404b540aSrobert#define SAL 8[fb] 144*404b540aSrobert#define SAH 10[fb] 145*404b540aSrobert#define SBL 12[fb] 146*404b540aSrobert#define SBH 14[fb] 147*404b540aSrobert#endif 148*404b540aSrobert 149*404b540aSrobert#ifdef L__m32c_mulsi3 150*404b540aSrobert .text 151*404b540aSrobert .global ___mulsi3 152*404b540aSrobert___mulsi3: 153*404b540aSrobert enter #0 154*404b540aSrobert push.w r2 155*404b540aSrobert mov.w SAL,r0 156*404b540aSrobert mulu.w SBL,r0 /* writes to r2r0 */ 157*404b540aSrobert mov.w r0,mem0 158*404b540aSrobert mov.w r2,mem2 159*404b540aSrobert mov.w SAL,r0 160*404b540aSrobert mulu.w SBH,r0 /* writes to r2r0 */ 161*404b540aSrobert add.w r0,mem2 162*404b540aSrobert mov.w SAH,r0 163*404b540aSrobert mulu.w SBL,r0 /* writes to r2r0 */ 164*404b540aSrobert add.w r0,mem2 165*404b540aSrobert pop.w r2 166*404b540aSrobert exitd 167*404b540aSrobert#endif 168*404b540aSrobert 169*404b540aSrobert#ifdef L__m32c_cmpsi2 170*404b540aSrobert .text 171*404b540aSrobert .global ___cmpsi2 172*404b540aSrobert___cmpsi2: 173*404b540aSrobert enter #0 174*404b540aSrobert cmp.w SBH,SAH 175*404b540aSrobert jgt cmpsi_gt 176*404b540aSrobert jlt cmpsi_lt 177*404b540aSrobert cmp.w SBL,SAL 178*404b540aSrobert jgt cmpsi_gt 179*404b540aSrobert jlt cmpsi_lt 180*404b540aSrobert mov.w #1,r0 181*404b540aSrobert exitd 182*404b540aSrobertcmpsi_gt: 183*404b540aSrobert mov.w #2,r0 184*404b540aSrobert exitd 185*404b540aSrobertcmpsi_lt: 186*404b540aSrobert mov.w #0,r0 187*404b540aSrobert exitd 188*404b540aSrobert#endif 189*404b540aSrobert 190*404b540aSrobert#ifdef L__m32c_ucmpsi2 191*404b540aSrobert .text 192*404b540aSrobert .global ___ucmpsi2 193*404b540aSrobert___ucmpsi2: 194*404b540aSrobert enter #0 195*404b540aSrobert cmp.w SBH,SAH 196*404b540aSrobert jgtu cmpsi_gt 197*404b540aSrobert jltu cmpsi_lt 198*404b540aSrobert cmp.w SBL,SAL 199*404b540aSrobert jgtu cmpsi_gt 200*404b540aSrobert jltu cmpsi_lt 201*404b540aSrobert mov.w #1,r0 202*404b540aSrobert exitd 203*404b540aSrobertcmpsi_gt: 204*404b540aSrobert mov.w #2,r0 205*404b540aSrobert exitd 206*404b540aSrobertcmpsi_lt: 207*404b540aSrobert mov.w #0,r0 208*404b540aSrobert exitd 209*404b540aSrobert#endif 210*404b540aSrobert 211*404b540aSrobert#ifdef L__m32c_jsri16 212*404b540aSrobert .data 213*404b540aSrobertm32c_jsri_addr: 214*404b540aSrobert .byte 0, 0, 0 215*404b540aSrobertm32c_jsri_ret: 216*404b540aSrobert .byte 0, 0, 0 217*404b540aSrobert 218*404b540aSrobert .text 219*404b540aSrobert .global m32c_jsri16 220*404b540aSrobertm32c_jsri16: 221*404b540aSrobert pop.w m32c_jsri_ret 222*404b540aSrobert pop.b m32c_jsri_ret+2 223*404b540aSrobert pop.w m32c_jsri_addr 224*404b540aSrobert push.b m32c_jsri_ret+2 225*404b540aSrobert push.w m32c_jsri_ret 226*404b540aSrobert jmpi.a m32c_jsri_addr 227*404b540aSrobert 228*404b540aSrobert#endif 229