1*dfc6aa5cSAndroid Build Coastguard Worker; 2*dfc6aa5cSAndroid Build Coastguard Worker; jsimdcpu.asm - SIMD instruction support check 3*dfc6aa5cSAndroid Build Coastguard Worker; 4*dfc6aa5cSAndroid Build Coastguard Worker; Copyright 2009 Pierre Ossman <ossman@cendio.se> for Cendio AB 5*dfc6aa5cSAndroid Build Coastguard Worker; Copyright (C) 2016, D. R. Commander. 6*dfc6aa5cSAndroid Build Coastguard Worker; 7*dfc6aa5cSAndroid Build Coastguard Worker; Based on the x86 SIMD extension for IJG JPEG library 8*dfc6aa5cSAndroid Build Coastguard Worker; Copyright (C) 1999-2006, MIYASAKA Masaru. 9*dfc6aa5cSAndroid Build Coastguard Worker; For conditions of distribution and use, see copyright notice in jsimdext.inc 10*dfc6aa5cSAndroid Build Coastguard Worker; 11*dfc6aa5cSAndroid Build Coastguard Worker; This file should be assembled with NASM (Netwide Assembler), 12*dfc6aa5cSAndroid Build Coastguard Worker; can *not* be assembled with Microsoft's MASM or any compatible 13*dfc6aa5cSAndroid Build Coastguard Worker; assembler (including Borland's Turbo Assembler). 14*dfc6aa5cSAndroid Build Coastguard Worker; NASM is available from http://nasm.sourceforge.net/ or 15*dfc6aa5cSAndroid Build Coastguard Worker; http://sourceforge.net/project/showfiles.php?group_id=6208 16*dfc6aa5cSAndroid Build Coastguard Worker 17*dfc6aa5cSAndroid Build Coastguard Worker%include "jsimdext.inc" 18*dfc6aa5cSAndroid Build Coastguard Worker 19*dfc6aa5cSAndroid Build Coastguard Worker; -------------------------------------------------------------------------- 20*dfc6aa5cSAndroid Build Coastguard Worker SECTION SEG_TEXT 21*dfc6aa5cSAndroid Build Coastguard Worker BITS 32 22*dfc6aa5cSAndroid Build Coastguard Worker; 23*dfc6aa5cSAndroid Build Coastguard Worker; Check if the CPU supports SIMD instructions 24*dfc6aa5cSAndroid Build Coastguard Worker; 25*dfc6aa5cSAndroid Build Coastguard Worker; GLOBAL(unsigned int) 26*dfc6aa5cSAndroid Build Coastguard Worker; jpeg_simd_cpu_support(void) 27*dfc6aa5cSAndroid Build Coastguard Worker; 28*dfc6aa5cSAndroid Build Coastguard Worker 29*dfc6aa5cSAndroid Build Coastguard Worker align 32 30*dfc6aa5cSAndroid Build Coastguard Worker GLOBAL_FUNCTION(jpeg_simd_cpu_support) 31*dfc6aa5cSAndroid Build Coastguard Worker 32*dfc6aa5cSAndroid Build Coastguard WorkerEXTN(jpeg_simd_cpu_support): 33*dfc6aa5cSAndroid Build Coastguard Worker push ebx 34*dfc6aa5cSAndroid Build Coastguard Worker; push ecx ; need not be preserved 35*dfc6aa5cSAndroid Build Coastguard Worker; push edx ; need not be preserved 36*dfc6aa5cSAndroid Build Coastguard Worker; push esi ; unused 37*dfc6aa5cSAndroid Build Coastguard Worker push edi 38*dfc6aa5cSAndroid Build Coastguard Worker 39*dfc6aa5cSAndroid Build Coastguard Worker xor edi, edi ; simd support flag 40*dfc6aa5cSAndroid Build Coastguard Worker 41*dfc6aa5cSAndroid Build Coastguard Worker pushfd 42*dfc6aa5cSAndroid Build Coastguard Worker pop eax 43*dfc6aa5cSAndroid Build Coastguard Worker mov edx, eax 44*dfc6aa5cSAndroid Build Coastguard Worker xor eax, 1<<21 ; flip ID bit in EFLAGS 45*dfc6aa5cSAndroid Build Coastguard Worker push eax 46*dfc6aa5cSAndroid Build Coastguard Worker popfd 47*dfc6aa5cSAndroid Build Coastguard Worker pushfd 48*dfc6aa5cSAndroid Build Coastguard Worker pop eax 49*dfc6aa5cSAndroid Build Coastguard Worker xor eax, edx 50*dfc6aa5cSAndroid Build Coastguard Worker jz near .return ; CPUID is not supported 51*dfc6aa5cSAndroid Build Coastguard Worker 52*dfc6aa5cSAndroid Build Coastguard Worker ; Check whether CPUID leaf 07H is supported 53*dfc6aa5cSAndroid Build Coastguard Worker ; (leaf 07H is used to check for AVX2 instruction support) 54*dfc6aa5cSAndroid Build Coastguard Worker xor eax, eax 55*dfc6aa5cSAndroid Build Coastguard Worker cpuid 56*dfc6aa5cSAndroid Build Coastguard Worker test eax, eax 57*dfc6aa5cSAndroid Build Coastguard Worker jz near .return 58*dfc6aa5cSAndroid Build Coastguard Worker cmp eax, 7 59*dfc6aa5cSAndroid Build Coastguard Worker jl short .no_avx2 ; Maximum leaf < 07H 60*dfc6aa5cSAndroid Build Coastguard Worker 61*dfc6aa5cSAndroid Build Coastguard Worker ; Check for AVX2 instruction support 62*dfc6aa5cSAndroid Build Coastguard Worker mov eax, 7 63*dfc6aa5cSAndroid Build Coastguard Worker xor ecx, ecx 64*dfc6aa5cSAndroid Build Coastguard Worker cpuid 65*dfc6aa5cSAndroid Build Coastguard Worker mov eax, ebx 66*dfc6aa5cSAndroid Build Coastguard Worker test eax, 1<<5 ; bit5:AVX2 67*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_avx2 68*dfc6aa5cSAndroid Build Coastguard Worker 69*dfc6aa5cSAndroid Build Coastguard Worker ; Check for AVX2 O/S support 70*dfc6aa5cSAndroid Build Coastguard Worker mov eax, 1 71*dfc6aa5cSAndroid Build Coastguard Worker xor ecx, ecx 72*dfc6aa5cSAndroid Build Coastguard Worker cpuid 73*dfc6aa5cSAndroid Build Coastguard Worker test ecx, 1<<27 74*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_avx2 ; O/S does not support XSAVE 75*dfc6aa5cSAndroid Build Coastguard Worker test ecx, 1<<28 76*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_avx2 ; CPU does not support AVX2 77*dfc6aa5cSAndroid Build Coastguard Worker 78*dfc6aa5cSAndroid Build Coastguard Worker xor ecx, ecx 79*dfc6aa5cSAndroid Build Coastguard Worker xgetbv 80*dfc6aa5cSAndroid Build Coastguard Worker and eax, 6 81*dfc6aa5cSAndroid Build Coastguard Worker cmp eax, 6 ; O/S does not manage XMM/YMM state 82*dfc6aa5cSAndroid Build Coastguard Worker ; using XSAVE 83*dfc6aa5cSAndroid Build Coastguard Worker jnz short .no_avx2 84*dfc6aa5cSAndroid Build Coastguard Worker 85*dfc6aa5cSAndroid Build Coastguard Worker or edi, JSIMD_AVX2 86*dfc6aa5cSAndroid Build Coastguard Worker.no_avx2: 87*dfc6aa5cSAndroid Build Coastguard Worker 88*dfc6aa5cSAndroid Build Coastguard Worker ; Check CPUID leaf 01H for MMX, SSE, and SSE2 support 89*dfc6aa5cSAndroid Build Coastguard Worker xor eax, eax 90*dfc6aa5cSAndroid Build Coastguard Worker inc eax 91*dfc6aa5cSAndroid Build Coastguard Worker cpuid 92*dfc6aa5cSAndroid Build Coastguard Worker mov eax, edx ; eax = Standard feature flags 93*dfc6aa5cSAndroid Build Coastguard Worker 94*dfc6aa5cSAndroid Build Coastguard Worker ; Check for MMX instruction support 95*dfc6aa5cSAndroid Build Coastguard Worker test eax, 1<<23 ; bit23:MMX 96*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_mmx 97*dfc6aa5cSAndroid Build Coastguard Worker or edi, byte JSIMD_MMX 98*dfc6aa5cSAndroid Build Coastguard Worker.no_mmx: 99*dfc6aa5cSAndroid Build Coastguard Worker test eax, 1<<25 ; bit25:SSE 100*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_sse 101*dfc6aa5cSAndroid Build Coastguard Worker or edi, byte JSIMD_SSE 102*dfc6aa5cSAndroid Build Coastguard Worker.no_sse: 103*dfc6aa5cSAndroid Build Coastguard Worker test eax, 1<<26 ; bit26:SSE2 104*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_sse2 105*dfc6aa5cSAndroid Build Coastguard Worker or edi, byte JSIMD_SSE2 106*dfc6aa5cSAndroid Build Coastguard Worker.no_sse2: 107*dfc6aa5cSAndroid Build Coastguard Worker 108*dfc6aa5cSAndroid Build Coastguard Worker ; Check for 3DNow! instruction support 109*dfc6aa5cSAndroid Build Coastguard Worker mov eax, 0x80000000 110*dfc6aa5cSAndroid Build Coastguard Worker cpuid 111*dfc6aa5cSAndroid Build Coastguard Worker cmp eax, 0x80000000 112*dfc6aa5cSAndroid Build Coastguard Worker jbe short .return 113*dfc6aa5cSAndroid Build Coastguard Worker 114*dfc6aa5cSAndroid Build Coastguard Worker mov eax, 0x80000001 115*dfc6aa5cSAndroid Build Coastguard Worker cpuid 116*dfc6aa5cSAndroid Build Coastguard Worker mov eax, edx ; eax = Extended feature flags 117*dfc6aa5cSAndroid Build Coastguard Worker 118*dfc6aa5cSAndroid Build Coastguard Worker test eax, 1<<31 ; bit31:3DNow!(vendor independent) 119*dfc6aa5cSAndroid Build Coastguard Worker jz short .no_3dnow 120*dfc6aa5cSAndroid Build Coastguard Worker or edi, byte JSIMD_3DNOW 121*dfc6aa5cSAndroid Build Coastguard Worker.no_3dnow: 122*dfc6aa5cSAndroid Build Coastguard Worker 123*dfc6aa5cSAndroid Build Coastguard Worker.return: 124*dfc6aa5cSAndroid Build Coastguard Worker mov eax, edi 125*dfc6aa5cSAndroid Build Coastguard Worker 126*dfc6aa5cSAndroid Build Coastguard Worker pop edi 127*dfc6aa5cSAndroid Build Coastguard Worker; pop esi ; unused 128*dfc6aa5cSAndroid Build Coastguard Worker; pop edx ; need not be preserved 129*dfc6aa5cSAndroid Build Coastguard Worker; pop ecx ; need not be preserved 130*dfc6aa5cSAndroid Build Coastguard Worker pop ebx 131*dfc6aa5cSAndroid Build Coastguard Worker ret 132*dfc6aa5cSAndroid Build Coastguard Worker 133*dfc6aa5cSAndroid Build Coastguard Worker; For some reason, the OS X linker does not honor the request to align the 134*dfc6aa5cSAndroid Build Coastguard Worker; segment unless we do this. 135*dfc6aa5cSAndroid Build Coastguard Worker align 32 136