kit

kit
git clone https://git.ryansepassi.com/git/kit.git
Log | Files | Refs | README

si_div.c (1240B)


      1 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
      2 //
      3 // 32-bit integer division helpers required by compiler-rt routines even on
      4 // LP64 targets where normal C int division is otherwise a single instruction.
      5 
      6 #include "int_lib.h"
      7 
      8 COMPILER_RT_ABI su_int __udivsi3(su_int n, su_int d) {
      9   const unsigned bits = sizeof(su_int) * CHAR_BIT;
     10   su_int q = 0;
     11   su_int r = 0;
     12   for (unsigned i = bits; i > 0; --i) {
     13     r = (su_int)((r << 1) | ((n >> (i - 1u)) & 1u));
     14     if (r >= d) {
     15       r = (su_int)(r - d);
     16       q |= (su_int)1u << (i - 1u);
     17     }
     18   }
     19   return q;
     20 }
     21 
     22 COMPILER_RT_ABI su_int __udivmodsi4(su_int n, su_int d, su_int* rem) {
     23   const unsigned bits = sizeof(su_int) * CHAR_BIT;
     24   su_int q = 0;
     25   su_int r = 0;
     26   for (unsigned i = bits; i > 0; --i) {
     27     r = (su_int)((r << 1) | ((n >> (i - 1u)) & 1u));
     28     if (r >= d) {
     29       r = (su_int)(r - d);
     30       q |= (su_int)1u << (i - 1u);
     31     }
     32   }
     33   if (rem) *rem = r;
     34   return q;
     35 }
     36 
     37 COMPILER_RT_ABI si_int __divsi3(si_int a, si_int b) {
     38   su_int sa = (su_int)(a >> 31);
     39   su_int sb = (su_int)(b >> 31);
     40   su_int ua = ((su_int)a ^ sa) - sa;
     41   su_int ub = ((su_int)b ^ sb) - sb;
     42   su_int sign = sa ^ sb;
     43   su_int q = __udivsi3(ua, ub);
     44   return (si_int)((q ^ sign) - sign);
     45 }