xref: /netbsd-src/external/gpl3/gcc.old/dist/libgcc/config/m32c/lib2funcs.c (revision 8feb0f0b7eaff0608f8350bbfa3098827b4bb91b)
136ac495dSmrg /* libgcc routines for R8C/M16C/M32C
2*8feb0f0bSmrg    Copyright (C) 2005-2020 Free Software Foundation, Inc.
336ac495dSmrg    Contributed by Red Hat.
436ac495dSmrg 
536ac495dSmrg    This file is part of GCC.
636ac495dSmrg 
736ac495dSmrg    GCC is free software; you can redistribute it and/or modify it
836ac495dSmrg    under the terms of the GNU General Public License as published
936ac495dSmrg    by the Free Software Foundation; either version 3, or (at your
1036ac495dSmrg    option) any later version.
1136ac495dSmrg 
1236ac495dSmrg    GCC is distributed in the hope that it will be useful, but WITHOUT
1336ac495dSmrg    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
1436ac495dSmrg    or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
1536ac495dSmrg    License for more details.
1636ac495dSmrg 
1736ac495dSmrg    Under Section 7 of GPL version 3, you are granted additional
1836ac495dSmrg    permissions described in the GCC Runtime Library Exception, version
1936ac495dSmrg    3.1, as published by the Free Software Foundation.
2036ac495dSmrg 
2136ac495dSmrg    You should have received a copy of the GNU General Public License and
2236ac495dSmrg    a copy of the GCC Runtime Library Exception along with this program;
2336ac495dSmrg    see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
2436ac495dSmrg    <http://www.gnu.org/licenses/>.  */
2536ac495dSmrg 
2636ac495dSmrg typedef          int  sint32_type   __attribute__ ((mode (SI)));
2736ac495dSmrg typedef unsigned int  uint32_type   __attribute__ ((mode (SI)));
2836ac495dSmrg typedef int           word_type     __attribute__ ((mode (__word__)));
2936ac495dSmrg 
3036ac495dSmrg uint32_type udivmodsi4 (uint32_type, uint32_type, word_type);
3136ac495dSmrg sint32_type __divsi3   (sint32_type, sint32_type);
3236ac495dSmrg sint32_type __modsi3   (sint32_type, sint32_type);
3336ac495dSmrg 
3436ac495dSmrg uint32_type
udivmodsi4(uint32_type num,uint32_type den,word_type modwanted)3536ac495dSmrg udivmodsi4 (uint32_type num, uint32_type den, word_type modwanted)
3636ac495dSmrg {
3736ac495dSmrg   uint32_type bit = 1;
3836ac495dSmrg   uint32_type res = 0;
3936ac495dSmrg 
4036ac495dSmrg   while (den < num && bit && !(den & (1L << 31)))
4136ac495dSmrg     {
4236ac495dSmrg       den <<= 1;
4336ac495dSmrg       bit <<= 1;
4436ac495dSmrg     }
4536ac495dSmrg   while (bit)
4636ac495dSmrg     {
4736ac495dSmrg       if (num >= den)
4836ac495dSmrg 	{
4936ac495dSmrg 	  num -= den;
5036ac495dSmrg 	  res |= bit;
5136ac495dSmrg 	}
5236ac495dSmrg       bit >>= 1;
5336ac495dSmrg       den >>= 1;
5436ac495dSmrg     }
5536ac495dSmrg   if (modwanted)
5636ac495dSmrg     return num;
5736ac495dSmrg   return res;
5836ac495dSmrg }
5936ac495dSmrg 
6036ac495dSmrg sint32_type
__divsi3(sint32_type a,sint32_type b)6136ac495dSmrg __divsi3 (sint32_type a, sint32_type b)
6236ac495dSmrg {
6336ac495dSmrg   word_type neg = 0;
6436ac495dSmrg   sint32_type res;
6536ac495dSmrg 
6636ac495dSmrg   if (a < 0)
6736ac495dSmrg     {
6836ac495dSmrg       a = -a;
6936ac495dSmrg       neg = !neg;
7036ac495dSmrg     }
7136ac495dSmrg 
7236ac495dSmrg   if (b < 0)
7336ac495dSmrg     {
7436ac495dSmrg       b = -b;
7536ac495dSmrg       neg = !neg;
7636ac495dSmrg     }
7736ac495dSmrg 
7836ac495dSmrg   res = udivmodsi4 (a, b, 0);
7936ac495dSmrg 
8036ac495dSmrg   if (neg)
8136ac495dSmrg     res = -res;
8236ac495dSmrg 
8336ac495dSmrg   return res;
8436ac495dSmrg }
8536ac495dSmrg 
8636ac495dSmrg sint32_type
__modsi3(sint32_type a,sint32_type b)8736ac495dSmrg __modsi3 (sint32_type a, sint32_type b)
8836ac495dSmrg {
8936ac495dSmrg   word_type neg = 0;
9036ac495dSmrg   sint32_type res;
9136ac495dSmrg 
9236ac495dSmrg   if (a < 0)
9336ac495dSmrg     {
9436ac495dSmrg       a = -a;
9536ac495dSmrg       neg = 1;
9636ac495dSmrg     }
9736ac495dSmrg 
9836ac495dSmrg   if (b < 0)
9936ac495dSmrg     b = -b;
10036ac495dSmrg 
10136ac495dSmrg   res = udivmodsi4 (a, b, 1);
10236ac495dSmrg 
10336ac495dSmrg   if (neg)
10436ac495dSmrg     res = -res;
10536ac495dSmrg 
10636ac495dSmrg   return res;
10736ac495dSmrg }
10836ac495dSmrg 
10936ac495dSmrg /* See the comment by the definition of LIBGCC2_UNITS_PER_WORD in
11036ac495dSmrg    m32c.h for why we are creating extra versions of some of the
11136ac495dSmrg    functions defined in libgcc2.c.  */
11236ac495dSmrg 
11336ac495dSmrg #define LIBGCC2_UNITS_PER_WORD 2
11436ac495dSmrg 
11536ac495dSmrg #define L_clzsi2
11636ac495dSmrg #define L_ctzsi2
11736ac495dSmrg #define L_ffssi2
11836ac495dSmrg #define L_paritysi2
11936ac495dSmrg #define L_popcountsi2
12036ac495dSmrg 
12136ac495dSmrg #include "libgcc2.c"
12236ac495dSmrg 
12336ac495dSmrg uint32_type
__udivsi3(uint32_type a,uint32_type b)12436ac495dSmrg __udivsi3 (uint32_type a, uint32_type b)
12536ac495dSmrg {
12636ac495dSmrg   return udivmodsi4 (a, b, 0);
12736ac495dSmrg }
12836ac495dSmrg 
12936ac495dSmrg uint32_type
__umoddi3(uint32_type a,uint32_type b)13036ac495dSmrg __umoddi3 (uint32_type a, uint32_type b)
13136ac495dSmrg {
13236ac495dSmrg   return udivmodsi4 (a, b, 1);
13336ac495dSmrg }
13436ac495dSmrg 
13536ac495dSmrg /* Returns the number of leading redundant sign bits in X.
13636ac495dSmrg    I.e. the number of bits following the most significant bit which are
13736ac495dSmrg    identical to it.  There are no special cases for 0 or other values.  */
13836ac495dSmrg 
13936ac495dSmrg int
__clrsbhi2(word_type x)14036ac495dSmrg __clrsbhi2 (word_type x)
14136ac495dSmrg {
14236ac495dSmrg   if (x < 0)
14336ac495dSmrg     x = ~x;
14436ac495dSmrg   if (x == 0)
14536ac495dSmrg     return 15;
14636ac495dSmrg   return __builtin_clz (x) - 1;
14736ac495dSmrg }
148