[svn] / trunk / xvidcore / src / quant / x86_asm / quantize_mpeg_mmx.asm Repository:
ViewVC logotype

Diff of /trunk/xvidcore/src/quant/x86_asm/quantize_mpeg_mmx.asm

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1535, Sun Aug 22 11:46:10 2004 UTC revision 1793, Tue Nov 11 20:46:24 2008 UTC
# Line 21  Line 21 
21  ; *  along with this program ; if not, write to the Free Software  ; *  along with this program ; if not, write to the Free Software
22  ; *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA  ; *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
23  ; *  ; *
24  ; * $Id: quantize_mpeg_mmx.asm,v 1.4 2004-08-22 11:46:10 edgomez Exp $  ; * $Id: quantize_mpeg_mmx.asm,v 1.10 2008-11-11 20:46:24 Isibaar Exp $
25  ; *  ; *
26  ; *************************************************************************/  ; *************************************************************************/
27    
# Line 32  Line 32 
32  %macro cglobal 1  %macro cglobal 1
33          %ifdef PREFIX          %ifdef PREFIX
34                  %ifdef MARK_FUNCS                  %ifdef MARK_FUNCS
35                          global _%1:function                          global _%1:function %1.endfunc-%1
36                          %define %1 _%1:function                          %define %1 _%1:function %1.endfunc-%1
37                            %define ENDFUNC .endfunc
38                  %else                  %else
39                          global _%1                          global _%1
40                          %define %1 _%1                          %define %1 _%1
41                            %define ENDFUNC
42                  %endif                  %endif
43          %else          %else
44                  %ifdef MARK_FUNCS                  %ifdef MARK_FUNCS
45                          global %1:function                          global %1:function %1.endfunc-%1
46                            %define ENDFUNC .endfunc
47                  %else                  %else
48                          global %1                          global %1
49                            %define ENDFUNC
50                  %endif                  %endif
51          %endif          %endif
52  %endmacro  %endmacro
# Line 129  Line 133 
133          times 4 dw 0          times 4 dw 0
134    
135  ;=============================================================================  ;=============================================================================
136    ; rounding
137    ;=============================================================================
138    
139    mmx_rounding:
140            dw (1<<13)
141            dw 0
142            dw (1<<13)
143            dw 0
144    
145    ;=============================================================================
146  ; Code  ; Code
147  ;=============================================================================  ;=============================================================================
148    
# Line 139  Line 153 
153  cglobal dequant_mpeg_intra_mmx  cglobal dequant_mpeg_intra_mmx
154  cglobal dequant_mpeg_inter_mmx  cglobal dequant_mpeg_inter_mmx
155    
156    
157    %macro QUANT_MMX        1
158            movq    mm0, [eax + 16*(%1)]                    ; data
159            movq    mm2, [ecx + 16*(%1) + 128]              ; intra_matrix_rec
160            movq    mm4, [eax + 16*(%1) + 8]                ; data
161            movq    mm6, [ecx + 16*(%1) + 128 + 8]  ; intra_matrix_rec
162    
163            movq    mm1, mm0
164            movq    mm5, mm4
165    
166            pmullw  mm0, mm2                                        ; low results
167            pmulhw  mm1, mm2                                        ; high results
168            pmullw  mm4, mm6                                        ; low results
169            pmulhw  mm5, mm6                                        ; high results
170    
171            movq    mm2, mm0
172            movq    mm6, mm4
173    
174            punpckhwd mm0, mm1
175            punpcklwd mm2, mm1
176            punpckhwd mm4, mm5
177            punpcklwd mm6, mm5
178    
179            paddd   mm2, mm7
180            paddd   mm0, mm7
181            paddd   mm6, mm7
182            paddd   mm4, mm7
183    
184            psrad   mm2, 14
185            psrad   mm0, 14
186            psrad   mm6, 14
187            psrad   mm4, 14
188    
189            packssdw mm2, mm0
190            packssdw mm6, mm4
191    
192            movq    [edi + 16*(%1)], mm2
193            movq    [edi + 16*(%1)+8], mm6
194    %endmacro
195    
196  ;-----------------------------------------------------------------------------  ;-----------------------------------------------------------------------------
197  ;  ;
198  ; uint32_t quant_mpeg_intra_mmx(int16_t * coeff,  ; uint32_t quant_mpeg_intra_mmx(int16_t * coeff,
# Line 152  Line 206 
206  ALIGN 16  ALIGN 16
207  quant_mpeg_intra_mmx:  quant_mpeg_intra_mmx:
208    
   push ecx  
   push esi  
209    push edi    push edi
210    push ebx    movq mm7, [mmx_rounding]
211    
212    mov edi, [esp + 16 + 4]       ; coeff    mov eax, [esp + 4 + 8]                ; data
213    mov esi, [esp + 16 + 8]       ; data    mov ecx, [esp + 4 + 20]               ; mpeg_quant_matrices
214    mov eax, [esp + 16 + 12]      ; quant    mov edi, [esp + 4 + 4]                ; coeff
215    mov ebx, [esp + 16 + 20]              ; mpeg_quant_matrices  
216      QUANT_MMX(0)
217    movq mm5, [quantd + eax * 8 - 8] ; quantd -> mm5    QUANT_MMX(1)
218      QUANT_MMX(2)
219    xor ecx, ecx    QUANT_MMX(3)
220    cmp al, 1    QUANT_MMX(4)
221    jz near .q1loop    QUANT_MMX(5)
222      QUANT_MMX(6)
223    cmp al, 2    QUANT_MMX(7)
224    jz near .q2loop  
225      ; calculate DC
226    movq mm7, [mmx_div + eax * 8 - 8] ; multipliers[quant] -> mm7    movsx eax, word [eax]     ; data[0]
227      mov ecx, [esp + 4 + 16]   ; dcscalar
228      mov edx, eax
229      mov edi, ecx
230      shr ecx, 1                ; ecx = dcscalar/2
231      sar edx, 31               ; edx = sign extend of eax (ready for division too)
232      xor ecx, edx              ; adjust ecx according to the sign of data[0]
233      sub ecx, edx
234      add eax, ecx
235    
236      mov ecx, [esp + 4 + 4]        ; coeff again
237      idiv edi                  ; eax = edx:eax / dcscalar
238      mov [ecx], ax             ; coeff[0] = ax
239    
 ALIGN 16  
 .loop  
   movq mm0, [esi + 8*ecx]       ; mm0 = [1st]  
   movq mm3, [esi + 8*ecx + 8]   ;  
   pxor mm1, mm1                 ; mm1 = 0  
   pxor mm4, mm4  
   pcmpgtw mm1, mm0              ; mm1 = (0 > mm0)  
   pcmpgtw mm4, mm3  
   pxor mm0, mm1                 ; mm0 = |mm0|  
   pxor mm3, mm4                 ;  
   psubw mm0, mm1                ; displace  
   psubw mm3, mm4                ;  
   psllw mm0, 4                  ; level << 4  
   psllw mm3, 4  
   movq mm2, [ebx + 8*ecx]  
   psrlw mm2, 1                  ; intra_matrix[i]>>1  
   paddw mm0, mm2  
   movq mm2, [ebx + 256 + ecx*8]  
   pmulhw mm0, mm2                       ; (level<<4 + intra_matrix[i]>>1) / intra_matrix[i]  
   movq mm2, [ebx + 8*ecx + 8]  
   psrlw mm2, 1  
   paddw mm3, mm2  
   movq mm2, [ebx + 256 + ecx*8 + 8]  
   pmulhw mm3, mm2  
   paddw mm0, mm5                ; + quantd  
   paddw mm3, mm5  
   pmulhw mm0, mm7               ; mm0 = (mm0 / 2Q) >> 16  
   pmulhw mm3, mm7               ;  
   psrlw mm0, 1                  ; additional shift by 1 => 16 + 1 = 17  
   psrlw mm3, 1  
   pxor mm0, mm1                 ; mm0 *= sign(mm0)  
   pxor mm3, mm4                 ;  
   psubw mm0, mm1                ; undisplace  
   psubw mm3, mm4                ;  
   
   movq [edi + 8*ecx], mm0  
   movq [edi + 8*ecx + 8], mm3  
   
   add ecx,2  
   cmp ecx,16  
   jnz near .loop  
   
 .done  
   ; caclulate  data[0] // (int32_t)dcscalar)  
   mov ecx, [esp + 16 + 16]  ; dcscalar  
   mov edx, ecx  
   movsx eax, word [esi]     ; data[0]  
   shr edx, 1                ; edx = dcscalar /2  
   cmp eax, 0  
   jg .gtzero  
   
   sub eax, edx  
   jmp short .mul  
 .gtzero  
   add eax, edx  
 .mul  
   cdq                       ; expand eax -> edx:eax  
   idiv ecx                  ; eax = edx:eax / dcscalar  
   
   mov [edi], ax             ; coeff[0] = ax  
   
   pop ebx  
240    pop edi    pop edi
   pop esi  
   pop ecx  
241    
242    xor eax, eax              ; return(0);    xor eax, eax              ; return(0);
243    ret    ret
244    ENDFUNC
 ALIGN 16  
 .q1loop  
   movq mm0, [esi + 8*ecx]       ; mm0 = [1st]  
   movq mm3, [esi + 8*ecx + 8]   ;  
   pxor mm1, mm1                 ; mm1 = 0  
   pxor mm4, mm4                 ;  
   pcmpgtw mm1, mm0              ; mm1 = (0 > mm0)  
   pcmpgtw mm4, mm3              ;  
   pxor mm0, mm1                 ; mm0 = |mm0|  
   pxor mm3, mm4                 ;  
   psubw mm0, mm1                ; displace  
   psubw mm3, mm4                ;  
   psllw mm0, 4  
   psllw mm3, 4  
   movq mm2, [ebx + 8*ecx]  
   psrlw mm2, 1  
   paddw mm0, mm2  
   movq mm2, [ebx + 256 + ecx*8]  
   pmulhw mm0, mm2                       ; (level<<4 + intra_matrix[i]>>1) / intra_matrix[i]  
   movq mm2, [ebx + 8*ecx + 8]  
   psrlw mm2, 1  
   paddw mm3, mm2  
   movq mm2, [ebx + 256 + ecx*8 + 8]  
   pmulhw mm3, mm2  
   paddw mm0, mm5  
   paddw mm3, mm5  
   psrlw mm0, 1              ; mm0 >>= 1   (/2)  
   psrlw mm3, 1              ;  
   pxor mm0, mm1             ; mm0 *= sign(mm0)  
   pxor mm3, mm4             ;  
   psubw mm0, mm1            ; undisplace  
   psubw mm3, mm4            ;  
   movq [edi + 8*ecx], mm0  
   movq [edi + 8*ecx + 8], mm3  
   
   add ecx, 2  
   cmp ecx, 16  
   jnz near .q1loop  
   jmp near .done  
   
   
 ALIGN 16  
 .q2loop  
   movq mm0, [esi + 8*ecx]       ; mm0 = [1st]  
   movq mm3, [esi + 8*ecx + 8]   ;  
   pxor mm1, mm1                 ; mm1 = 0  
   pxor mm4, mm4                 ;  
   pcmpgtw mm1, mm0              ; mm1 = (0 > mm0)  
   pcmpgtw mm4, mm3              ;  
   pxor mm0, mm1                 ; mm0 = |mm0|  
   pxor mm3, mm4                 ;  
   psubw mm0, mm1                ; displace  
   psubw mm3, mm4                ;  
   psllw mm0, 4  
   psllw mm3, 4  
   movq mm2, [ebx + 8*ecx]  
   psrlw mm2, 1  
   paddw mm0, mm2  
   movq mm2, [ebx + 256 + ecx*8]  
   pmulhw mm0, mm2                       ; (level<<4 + intra_matrix[i]>>1) / intra_matrix[i]  
   movq mm2, [ebx + 8*ecx + 8]  
   psrlw mm2, 1  
   paddw mm3, mm2  
   movq mm2, [ebx + 256 + ecx*8 + 8]  
   pmulhw mm3, mm2  
   paddw mm0, mm5  
   paddw mm3, mm5  
   psrlw mm0, 2                  ; mm0 >>= 1   (/4)  
   psrlw mm3, 2                  ;  
   pxor mm0, mm1                 ; mm0 *= sign(mm0)  
   pxor mm3, mm4                 ;  
   psubw mm0, mm1                ; undisplace  
   psubw mm3, mm4            ;  
   movq [edi + 8*ecx], mm0  
   movq [edi + 8*ecx + 8], mm3  
   
   add ecx,2  
   cmp ecx,16  
   jnz near .q2loop  
   jmp near .done  
245    
246    
247  ;-----------------------------------------------------------------------------  ;-----------------------------------------------------------------------------
# Line 359  Line 279 
279    movq mm7, [mmx_div + eax * 8 - 8] ; divider    movq mm7, [mmx_div + eax * 8 - 8] ; divider
280    
281  ALIGN 16  ALIGN 16
282  .loop  .loop:
283    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]
284    movq mm3, [esi + 8*ecx + 8]   ;    movq mm3, [esi + 8*ecx + 8]   ;
285    pxor mm1, mm1                 ; mm1 = 0    pxor mm1, mm1                 ; mm1 = 0
# Line 399  Line 319 
319    cmp ecx, 16    cmp ecx, 16
320    jnz near .loop    jnz near .loop
321    
322  .done  .done:
323    pmaddwd mm5, [mmx_one]    pmaddwd mm5, [mmx_one]
324    movq mm0, mm5    movq mm0, mm5
325    psrlq mm5, 32    psrlq mm5, 32
# Line 414  Line 334 
334    ret    ret
335    
336  ALIGN 16  ALIGN 16
337  .q1loop  .q1loop:
338    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]
339    movq mm3, [esi + 8*ecx+ 8]    movq mm3, [esi + 8*ecx+ 8]
340    pxor mm1, mm1                 ; mm1 = 0    pxor mm1, mm1                 ; mm1 = 0
# Line 454  Line 374 
374    
375    jmp .done    jmp .done
376    
   
377  ALIGN 16  ALIGN 16
378  .q2loop  .q2loop:
379    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]    movq mm0, [esi + 8*ecx]       ; mm0 = [1st]
380    movq mm3, [esi + 8*ecx+ 8]    movq mm3, [esi + 8*ecx+ 8]
381    pxor mm1, mm1                 ; mm1 = 0    pxor mm1, mm1                 ; mm1 = 0
# Line 495  Line 414 
414    jnz near .q2loop    jnz near .q2loop
415    
416    jmp .done    jmp .done
417    ENDFUNC
418    
419    
420  ;-----------------------------------------------------------------------------  ;-----------------------------------------------------------------------------
# Line 562  Line 482 
482    pxor mm6, mm6     ; this is a NOP    pxor mm6, mm6     ; this is a NOP
483    
484  ALIGN 16  ALIGN 16
485  .loop  .loop:
486    movq mm0, [ecx+8*eax + 8*16]   ; mm0 = c  = coeff[i]    movq mm0, [ecx+8*eax + 8*16]   ; mm0 = c  = coeff[i]
487    movq mm3, [ecx+8*eax + 8*16 +8]; mm3 = c' = coeff[i+1]    movq mm3, [ecx+8*eax + 8*16 +8]; mm3 = c' = coeff[i+1]
488    pxor mm1, mm1    pxor mm1, mm1
# Line 634  Line 554 
554    pop ebx    pop ebx
555    
556    ret    ret
557    ENDFUNC
558    
559  ;-----------------------------------------------------------------------------  ;-----------------------------------------------------------------------------
560  ;  ;
# Line 665  Line 586 
586    pxor mm6, mm6     ; mismatch sum    pxor mm6, mm6     ; mismatch sum
587    
588  ALIGN 16  ALIGN 16
589  .loop  .loop:
590    movq mm0, [ecx+8*eax + 8*16   ]   ; mm0 = coeff[i]    movq mm0, [ecx+8*eax + 8*16   ]   ; mm0 = coeff[i]
591    movq mm2, [ecx+8*eax + 8*16 +8]   ; mm2 = coeff[i+1]    movq mm2, [ecx+8*eax + 8*16 +8]   ; mm2 = coeff[i+1]
592    add eax, 2    add eax, 2
# Line 747  Line 668 
668    pop ebx    pop ebx
669    
670    ret    ret
671    ENDFUNC
672    
673    
674    %ifidn __OUTPUT_FORMAT__,elf
675    section ".note.GNU-stack" noalloc noexec nowrite progbits
676    %endif
677    

Legend:
Removed from v.1535  
changed lines
  Added in v.1793

No admin address has been configured
ViewVC Help
Powered by ViewVC 1.0.4