Mercurial > sdl-ios-xcode
comparison src/cpuinfo/SDL_cpuinfo.c @ 793:c20f08c4f437
Altivec detection on non-MacOS X systems
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Thu, 29 Jan 2004 05:22:23 +0000 |
parents | 07760c8854d1 |
children | 275708f2e838 |
comparison
equal
deleted
inserted
replaced
792:2cbb8eaa2c92 | 793:c20f08c4f437 |
---|---|
24 static char rcsid = | 24 static char rcsid = |
25 "@(#) $Id$"; | 25 "@(#) $Id$"; |
26 #endif | 26 #endif |
27 | 27 |
28 /* CPU feature detection for SDL */ | 28 /* CPU feature detection for SDL */ |
29 | |
30 #ifdef unix /* FIXME: Better setjmp detection? */ | |
31 #define USE_SETJMP | |
32 #include <signal.h> | |
33 #include <setjmp.h> | |
34 #endif | |
29 | 35 |
30 #include "SDL.h" | 36 #include "SDL.h" |
31 #include "SDL_cpuinfo.h" | 37 #include "SDL_cpuinfo.h" |
32 | 38 |
33 #ifdef MACOSX | 39 #ifdef MACOSX |
40 #define CPU_HAS_3DNOW 0x00000010 | 46 #define CPU_HAS_3DNOW 0x00000010 |
41 #define CPU_HAS_3DNOWEXT 0x00000020 | 47 #define CPU_HAS_3DNOWEXT 0x00000020 |
42 #define CPU_HAS_SSE 0x00000040 | 48 #define CPU_HAS_SSE 0x00000040 |
43 #define CPU_HAS_SSE2 0x00000080 | 49 #define CPU_HAS_SSE2 0x00000080 |
44 #define CPU_HAS_ALTIVEC 0x00000100 | 50 #define CPU_HAS_ALTIVEC 0x00000100 |
51 | |
52 #ifdef USE_SETJMP | |
53 /* This is the brute force way of detecting instruction sets... | |
54 the idea is borrowed from the libmpeg2 library - thanks! | |
55 */ | |
56 static jmp_buf jmpbuf; | |
57 static void illegal_instruction(int sig) | |
58 { | |
59 longjmp(jmpbuf, 1); | |
60 } | |
61 #endif // USE_SETJMP | |
45 | 62 |
46 static __inline__ int CPU_haveCPUID() | 63 static __inline__ int CPU_haveCPUID() |
47 { | 64 { |
48 int has_CPUID = 0; | 65 int has_CPUID = 0; |
49 #if defined(__GNUC__) && defined(i386) | 66 #if defined(__GNUC__) && defined(i386) |
209 return 0; | 226 return 0; |
210 } | 227 } |
211 | 228 |
212 static __inline__ int CPU_haveAltiVec() | 229 static __inline__ int CPU_haveAltiVec() |
213 { | 230 { |
231 int altivec = 0; | |
214 #ifdef MACOSX | 232 #ifdef MACOSX |
215 /* TODO: This check works on OS X. It would be nice to detect AltiVec | |
216 properly on for example Linux/PPC, too. But I don't know how that | |
217 is done in Linux (or FreeBSD, or whatever other OS you run PPC :-) | |
218 */ | |
219 int selectors[2] = { CTL_HW, HW_VECTORUNIT }; | 233 int selectors[2] = { CTL_HW, HW_VECTORUNIT }; |
220 int hasVectorUnit = 0; | 234 int hasVectorUnit = 0; |
221 size_t length = sizeof(hasVectorUnit); | 235 size_t length = sizeof(hasVectorUnit); |
222 int error = sysctl(selectors, 2, &hasVectorUnit, &length, NULL, 0); | 236 int error = sysctl(selectors, 2, &hasVectorUnit, &length, NULL, 0); |
223 if( 0 == error ) | 237 if( 0 == error ) |
224 return hasVectorUnit != 0; | 238 altivec = (hasVectorUnit != 0); |
225 #endif | 239 #elseif defined(USE_SETJMP) && defined(__GNUC__) && defined(__powerpc__) |
226 return 0; | 240 void (*handler)(int sig); |
241 handler = signal(SIGILL, illegal_instruction); | |
242 if ( setjmp(jmpbuf) == 0 ) { | |
243 asm volatile ("mtspr 256, %0\n\t" | |
244 "vand %%v0, %%v0, %%v0" | |
245 : | |
246 : "r" (-1)); | |
247 altivec = 1; | |
248 } | |
249 signal(SIGILL, handler); | |
250 #endif | |
251 return altivec; | |
227 } | 252 } |
228 | 253 |
229 static Uint32 SDL_CPUFeatures = 0xFFFFFFFF; | 254 static Uint32 SDL_CPUFeatures = 0xFFFFFFFF; |
230 | 255 |
231 static Uint32 SDL_GetCPUFeatures() | 256 static Uint32 SDL_GetCPUFeatures() |