Hash :
a2e6a9dd
Author :
Date :
2006-02-04T00:00:00
IJG R6b with x86SIMD V1.02 Independent JPEG Group's JPEG software release 6b with x86 SIMD extension for IJG JPEG library version 1.02
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130
;
; jsimddjg.asm - SIMD instruction support check (for DJGPP V.2)
;
; x86 SIMD extension for IJG JPEG library
; Copyright (C) 1999-2006, MIYASAKA Masaru.
; For conditions of distribution and use, see copyright notice in jsimdext.inc
;
; This file should be assembled with NASM (Netwide Assembler),
; can *not* be assembled with Microsoft's MASM or any compatible
; assembler (including Borland's Turbo Assembler).
; NASM is available from http://nasm.sourceforge.net/ or
; http://sourceforge.net/project/showfiles.php?group_id=6208
;
; Last Modified : September 26, 2004
;
; [TAB8]
%include "jsimdext.inc"
; --------------------------------------------------------------------------
SECTION SEG_TEXT
BITS 32
;
; Check if the OS supports SIMD instructions (DJGPP V.2)
;
; GLOBAL(unsigned int)
; jpeg_simd_os_support (unsigned int simd)
;
%define EXCEPTION_ILLEGAL_INSTRUCTION 6 ; vector number of #UD
%define simd ebp+8 ; unsigned int simd
%define mxcsr ebp-4 ; unsigned int mxcsr = 0x1F80
align 16
global EXTN(jpeg_simd_os_support)
EXTN(jpeg_simd_os_support):
push ebp
mov ebp,esp
push dword 0x1F80 ; default value of MXCSR register
push ebx
push DWORD [simd] ; simd_flags - modified from exception_handler
mov bl, EXCEPTION_ILLEGAL_INSTRUCTION
mov ax, 0x0202 ; Get Processor Exception Handler Vector
int 0x31 ; DPMI function call
push ecx ; selector of old exception handler
push edx ; offset of old exception handler
mov ecx,cs
mov edx, exception_handler
mov bl, EXCEPTION_ILLEGAL_INSTRUCTION
mov ax, 0x0203 ; Set Processor Exception Handler Vector
int 0x31 ; DPMI function call
mov eax, DWORD [simd]
; If floating point emulation is enabled (CR0.EM = 1),
; executing an MMX/3DNow! instruction generates invalid
; opcode exception (#UD).
push byte (.mmx_1 - .mmx_0) ; inst_bytes
push byte (JSIMD_MMX | JSIMD_3DNOW) ; test_flags
test eax, DWORD [esp]
jz short .mmx_1
.mmx_0: emms ; executing MMX instruction
.mmx_1: add esp, byte 8
push byte (.sse_1 - .sse_0)
push byte (JSIMD_SSE | JSIMD_SSE2)
test eax, DWORD [esp]
jz short .sse_1
.sse_0: ldmxcsr DWORD [mxcsr] ; executing SSE instruction
.sse_1: add esp, byte 8
pop edx ; offset of old exception handler
pop ecx ; selector of old exception handler
mov bl, EXCEPTION_ILLEGAL_INSTRUCTION
mov ax, 0x0203 ; Set Processor Exception Handler Vector
int 0x31 ; DPMI function call
pop eax ; return simd_flags
and eax, byte JSIMD_ALL
pop ebx
mov esp,ebp
pop ebp
ret
; --------------------------------------------------------------------------
;
; LOCAL(void) far
; exception_handler (unsigned long error_code,
; void * context_eip, unsigned short context_cs,
; unsigned long context_eflags,
; void * context_esp, unsigned short context_ss);
;
%define error_code esp+12+8 ; unsigned long error_code
%define context_eip esp+12+12 ; void * context_eip
%define context_cs esp+12+16 ; unsigned short context_cs
%define context_eflags esp+12+20 ; unsigned long context_eflags
%define context_esp esp+12+24 ; void * context_esp
%define context_ss esp+12+28 ; unsigned short context_ss
%define test_flags(b) (b)+0
%define inst_bytes(b) (b)+4
%define simd_flags(b) (b)+16
align 16
exception_handler:
push eax
push ecx
push edx
mov eax, POINTER [context_esp]
mov ecx, DWORD [test_flags(eax)]
mov edx, DWORD [inst_bytes(eax)]
not ecx
add POINTER [context_eip], edx ; next instruction
and DWORD [simd_flags(eax)], ecx ; turn off flag
pop edx
pop ecx
pop eax
retf