1 /* OpenCP Module Player
2 * copyright (c) '94-'98 Niklas Beisert <nbeisert@physik.tu-muenchen.de>
3 *
4 * DOS4GFIX initialisation handlers
5 *
6 * revision history: (please note changes here)
7 * -nb980510 Niklas Beisert <nbeisert@physik.tu-muenchen.de>
8 * -first release
9 * -kb98???? Tammo Hinrichs <opencp@gmx.net> (?)
10 * -some bugfix(?)
11 * -fd981205 Felix Domke <tmbinc@gmx.net>
12 * -KB's "bugfix" doesn't work with Watcom106
13 * -ss040613 Stian Skjelstad <stian@nixia.no>
14 * -Redone to use gcc assembler inline and posix libc
15 * -ss040908 Stian Skjelstad <stian@nixia.no>
16 * -Made the assembler inlines optimize-safe
17 */
18
19 #ifndef IMSRTNS__H
20 #define IMSRTNS__H
21
22 /* Assembler optimization per cpu we can wait with.... */
23
24 #define memsetb(dst, what, len) memset(dst, what, len*1) /* let the compiler handle this */
25 #define memcpyb(dst, src, len) memcpy(dst, src, len) /* let the compiler handle this */
26 #define memcpyf(dst, src, len) memcpy(dst, src, len*sizeof(float)) /* let the compiler handle this.. even this one... not even used yet */
27 #define memmovel(dst, src, n) memmove(dst, src, (n)*4)
28
29 #ifdef I386_ASM
30
imuldiv(int32_t a,int32_t b,int32_t c)31 static inline int32_t imuldiv(int32_t a,int32_t b,int32_t c)
32 {
33 #ifdef __PIC__
34 int d0, d1;
35 register int32_t retval;
36 __asm__ __volatile__(
37 "pushl %%ebx\n"
38 "movl %%ecx, %%ebx\n"
39 "imul %%edx\n"
40 "idiv %%ebx\n"
41 "popl %%ebx\n"
42 :"=a"(retval), "=&d"(d0), "=&c"(d1)
43 :"0"(a), "1"(b), "2"(c)
44 );
45 return retval;
46 #else
47 int d0, d1;
48 register int32_t retval;
49 __asm__ __volatile__(
50 "imul %%edx\n"
51 "idiv %%ebx\n"
52 :"=a"(retval), "=&d"(d0), "=&b"(d1)
53 :"0"(a), "1"(b), "2"(c)
54 );
55 return retval;
56 #endif
57 }
58
umuldiv(uint32_t a,uint32_t b,uint32_t c)59 static inline uint32_t umuldiv(uint32_t a,uint32_t b,uint32_t c)
60 {
61 #ifdef __PIC__
62 int d0, d1;
63 register uint32_t retval;
64 __asm__ __volatile__
65 (
66 "pushl %%ebx\n"
67 "movl %%ecx, %%ebx\n"
68 "mul %%edx\n"
69 "div %%ebx\n"
70 "popl %%ebx\n"
71 :"=a"(retval), "=&d"(d0), "=&c"(d1)
72 :"0"(a), "1"(b), "2"(c)
73 );
74 return retval;
75 #else
76 int d0, d1;
77 register uint32_t retval;
78 __asm__ __volatile__
79 (
80 "mul %%edx\n"
81 "div %%ebx\n"
82 :"=a"(retval), "=&d"(d0), "=&b"(d1)
83 :"0"(a), "1"(b), "2"(c)
84 );
85 return retval;
86 #endif
87 }
88
imulshr16(int32_t a,int32_t b)89 static inline int32_t imulshr16(int32_t a,int32_t b)
90 {
91 int d0;
92 register int32_t retval;
93 __asm__ __volatile__
94 (
95 "imul %%edx\n"
96 "shrd $16,%%edx,%%eax\n"
97 :"=a"(retval), "=&d"(d0)
98 :"0"(a), "1"(b)
99 );
100 return retval;
101 }
102
umulshr16(uint32_t a,uint32_t b)103 static inline uint32_t umulshr16(uint32_t a,uint32_t b)
104 {
105 int d0;
106 register uint32_t retval;
107 __asm__ __volatile__
108 (
109 "mul %%edx\n"
110 "shrd $16,%%edx,%%eax\n"
111 :"=a"(retval), "=&d"(d0)
112 :"0"(a), "1"(b)
113 );
114 return retval;
115 }
116
umldivrnd(uint32_t a,uint32_t b,uint32_t c)117 static inline uint32_t umldivrnd(uint32_t a,uint32_t b,uint32_t c)
118 {
119 int d0, d1;
120 register uint32_t retval;
121 __asm__ __volatile__
122 (
123 "mul %%edx\n"
124 "movl %%ecx,%%ebx\n"
125 "shrl $1,%%ebx\n"
126 "addl %%ebx,%%eax\n"
127 "adc $0,%%edx\n"
128 "div %%ecx\n"
129 :"=a"(retval), "=&d"(d0), "=&c"(d1)
130 :"0"(a), "1"(b), "2"(c)
131 :"ebx"
132 );
133 return retval;
134 }
135
memsetd(void * dst,uint32_t what,uint32_t len)136 static inline void memsetd(void *dst, uint32_t what, uint32_t len)
137 {
138 int d0, d1, d2;
139 __asm__ __volatile__
140 (
141 "rep stosl\n"
142 : "=&D"(d0), "=&a"(d1), "=&c"(d2)
143 : "0" (dst), "1" (what), "2" (len)
144 : "memory"
145 );
146 }
147
memsetw(void * dst,uint16_t what,uint32_t len)148 static inline void memsetw(void *dst, uint16_t what, uint32_t len)
149 {
150 short d1;
151 int d0, d2;
152 __asm__ __volatile__
153 (
154 "rep stosw\n"
155 : "=&D"(d0), "=&a"(d1), "=&c"(d2)
156 : "0" (dst), "1" (what), "2" (len)
157 : "memory"
158 );
159 }
160
161 #else
162
imuldiv(int32_t a,int32_t b,int32_t c)163 static inline int32_t imuldiv(int32_t a,int32_t b,int32_t c)
164 {
165 int64_t temp = (int64_t)a*(int64_t)b;
166 return temp/c;
167 }
168
umuldiv(uint32_t a,uint32_t b,uint32_t c)169 static inline uint32_t umuldiv(uint32_t a,uint32_t b,uint32_t c)
170 {
171 uint64_t temp = (uint64_t)a*(uint64_t)b;
172 return temp/c;
173 }
174
imulshr16(int32_t a,int32_t b)175 static inline int32_t imulshr16(int32_t a,int32_t b)
176 {
177 int64_t temp = (int64_t)a*(int64_t)b;
178 return temp>>16;
179 }
180
umulshr16(uint32_t a,uint32_t b)181 static inline uint32_t umulshr16(uint32_t a,uint32_t b)
182 {
183 uint64_t temp = (uint64_t)a*(uint64_t)b;
184 return temp>>16;
185 }
186
187 #define umldivrnd(mul1, mul2, divby) umuldiv(mul1, mul2, divby) /* dirty */
188
189 #define memsetd(dst, what, len) {int i;uint32_t *tmp_dst=(uint32_t *)(dst);for(i=(len);i;i--)*tmp_dst++=(uint32_t)(what);} while(0)
190 #define memsetw(dst, what, len) {int i;uint16_t *tmp_dst=(uint16_t *)(dst);for(i=(len);i;i--)*tmp_dst++=(uint16_t)(what);} while(0)
191
192 #endif
193
194
195 #endif
196