00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00037 #include <multiplication.h>
00038 #include <stdint.h>
00039
00041 #ifndef SOFTINT_CHECK_OF
00042 #define SOFTINT_CHECK_OF 0
00043 #endif
00044
00050 static unsigned long long mul(unsigned int a, unsigned int b) {
00051 unsigned int a1 = a >> 16;
00052 unsigned int a2 = a & UINT16_MAX;
00053 unsigned int b1 = b >> 16;
00054 unsigned int b2 = b & UINT16_MAX;
00055
00056 unsigned long long t1 = a1 * b1;
00057 unsigned long long t2 = a1 * b2;
00058 t2 += a2 * b1;
00059 unsigned long long t3 = a2 * b2;
00060
00061 t3 = (((t1 << 16) + t2) << 16) + t3;
00062
00063 return t3;
00064 }
00065
00069 long long __muldi3 (long long a, long long b)
00070 {
00071 char neg = 0;
00072
00073 if (a < 0) {
00074 neg = !neg;
00075 a = -a;
00076 }
00077
00078 if (b < 0) {
00079 neg = !neg;
00080 b = -b;
00081 }
00082
00083 unsigned long long a1 = a >> 32;
00084 unsigned long long b1 = b >> 32;
00085
00086 unsigned long long a2 = a & (UINT32_MAX);
00087 unsigned long long b2 = b & (UINT32_MAX);
00088
00089 if (SOFTINT_CHECK_OF && (a1 != 0) && (b1 != 0)) {
00090
00091 return (neg ? INT64_MIN : INT64_MAX);
00092 }
00093
00094
00095
00096
00097 unsigned long long t1 = mul(a1, b2) + mul(b1, a2);
00098
00099 if ((SOFTINT_CHECK_OF) && (t1 > UINT32_MAX)) {
00100
00101 return (neg ? INT64_MIN : INT64_MAX);
00102 }
00103
00104 t1 = t1 << 32;
00105 unsigned long long t2 = mul(a2, b2);
00106 t2 += t1;
00107
00108
00109
00110 if (SOFTINT_CHECK_OF && ((t2 < t1) || (t2 & (1ull << 63)))) {
00111
00112 return (neg ? INT64_MIN : INT64_MAX);
00113 }
00114
00115 long long result = t2;
00116 if (neg)
00117 result = -result;
00118
00119 return result;
00120 }
00121