Icons for Radium and Shellplayer.
[AROS-Contrib.git] / MultiMedia / radium / common / PEQ_calc_64bit.c
blob4b9854645a4be078169dfef03c9d1ac47537c94a
1 /* Copyright 2000 Kjetil S. Matheussen
3 This program is free software; you can redistribute it and/or
4 modify it under the terms of the GNU General Public License
5 as published by the Free Software Foundation; either version 2
6 of the License, or (at your option) any later version.
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
13 You should have received a copy of the GNU General Public License
14 along with this program; if not, write to the Free Software
15 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
22 #ifdef AMIGA
23 # include <proto/utility.h>
24 # ifdef __AMIGAOS__
25 # include <dos.h>
26 # else
27 # include <dos/dos.h>
28 # endif
29 #endif
31 #include <stdio.h>
32 #include <stdlib.h>
34 #include "PEQ_calc_64bit_proc.h"
37 /**************************************
38 FUNCTION
39 Returns a*b/c. a*b may be bigger
40 than a 32 bit variable can hold.
42 NOTE
43 The 68020 and higher versions is
44 defined in the 64bit.a file.
45 (a bit smaller, that one. :)
46 Probably noone that is ever going
47 to use this routine (very unlikely
48 that anyone wants to use the
49 program on an 000), but I wrote
50 this before I knew there was an asm
51 routines that does this directly.
53 NOTE2
54 This function is VERY hard and
55 heavy on an 000.
57 NOTE3
58 68060 version allso uses this function.
59 muls and divs is emulated on an
60 060, so this function is twice
61 as fast as the other one.
62 **************************************/
64 int Mul32Div64_000(const int a,const int b,const int c){
66 #ifdef __AMIGAOS__
67 unsigned long l32=UMult64((unsigned long)abs(a),(unsigned long)abs(b));
68 unsigned long m32=getreg(REG_D1);
69 #else
70 unsigned long l32=(unsigned long)abs(a)/(unsigned long)abs(b);
71 unsigned long m32=(unsigned long)abs(a)%(unsigned long)abs(b);
72 #endif
74 unsigned long result;
75 unsigned long modulo;
76 unsigned long uc;
78 if( m32==0 && ( (1<<31 & l32)==0 ) ){
79 return (a<0)^(b<0) ? -(int)(l32)/c : (int)(l32)/c;
81 // printf("storre\n");
83 uc=(unsigned long)abs(c);
85 #ifdef __AMIGAOS__
86 result=UDivMod32(1<<31,uc);
87 modulo=getreg(REG_D1);
88 #else
89 result=(1<<31)/uc;
90 modulo=(1<<31)%uc;
91 #endif
93 modulo*=2;
94 result*=2;
96 if(modulo>=uc){
97 modulo-=uc;
98 result=(result+1)*m32;
99 }else{
100 result*=m32;
103 #ifdef __AMIGAOS__
104 m32=UDivMod32(m32*modulo,uc);
105 modulo=getreg(REG_D1);
107 l32=UDivMod32(l32,uc);
108 modulo+=getreg(REG_D1);
109 #else
110 m32=(m32*modulo)/uc;
111 modulo=(m32*modulo)&uc;
113 l32=l32/uc;
114 modulo+=132%uc;
115 #endif
117 return (int)(
118 (a<0)^(b<0)^(c<0) ?
119 -(long)(
120 result + m32 + l32 + (modulo>=uc)
122 result + m32 + l32 + (modulo>=uc)
131 int main(){
132 int a,b,c,d=0;
134 for(a=25000;a<25010;a++){
135 printf("a: %d\n",a);
136 for(b=184000;b<185000;b++){
137 for(c=200000;c<200100;c++){
138 d+=Mul32Div64_000(a,b,c);
142 printf("d: %d\n",d);
143 d=0;
145 for(a=25000;a<25010;a++){
146 printf("b: %d\n",a);
147 for(b=184000;b<185000;b++){
148 for(c=200000;c<200100;c++){
149 d+=Mul32Div64_020(a,b,c);
153 printf("d: %d\n",d);
155 // printf("d: %d, %x\n",16383*-20569/185620,Mul32Div64(a,b,c));
157 return 0;