~ubuntu-branches/ubuntu/quantal/libjpeg-turbo/quantal-security

« back to all changes in this revision

Viewing changes to simd/jdmrgmmx.asm

  • Committer: Package Import Robot
  • Author(s): Tom Gall
  • Date: 2011-09-13 03:53:56 UTC
  • Revision ID: package-import@ubuntu.com-20110913035356-1jybp1r6on1l3son
Tags: upstream-1.1.90+svn702
ImportĀ upstreamĀ versionĀ 1.1.90+svn702

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
;
 
2
; jdmrgmmx.asm - merged upsampling/color conversion (MMX)
 
3
;
 
4
; Copyright 2009 Pierre Ossman <ossman@cendio.se> for Cendio AB
 
5
;
 
6
; Based on
 
7
; x86 SIMD extension for IJG JPEG library
 
8
; Copyright (C) 1999-2006, MIYASAKA Masaru.
 
9
; For conditions of distribution and use, see copyright notice in jsimdext.inc
 
10
;
 
11
; This file should be assembled with NASM (Netwide Assembler),
 
12
; can *not* be assembled with Microsoft's MASM or any compatible
 
13
; assembler (including Borland's Turbo Assembler).
 
14
; NASM is available from http://nasm.sourceforge.net/ or
 
15
; http://sourceforge.net/project/showfiles.php?group_id=6208
 
16
;
 
17
; [TAB8]
 
18
 
 
19
%include "jcolsamp.inc"
 
20
 
 
21
; --------------------------------------------------------------------------
 
22
;
 
23
; Upsample and color convert for the case of 2:1 horizontal and 1:1 vertical.
 
24
;
 
25
; GLOBAL(void)
 
26
; jsimd_h2v1_merged_upsample_mmx (JDIMENSION output_width,
 
27
;                                 JSAMPIMAGE input_buf,
 
28
;                                 JDIMENSION in_row_group_ctr,
 
29
;                                 JSAMPARRAY output_buf);
 
30
;
 
31
 
 
32
%define output_width(b) (b)+8                   ; JDIMENSION output_width
 
33
%define input_buf(b)            (b)+12          ; JSAMPIMAGE input_buf
 
34
%define in_row_group_ctr(b)     (b)+16          ; JDIMENSION in_row_group_ctr
 
35
%define output_buf(b)           (b)+20          ; JSAMPARRAY output_buf
 
36
 
 
37
%define original_ebp    ebp+0
 
38
%define wk(i)           ebp-(WK_NUM-(i))*SIZEOF_MMWORD  ; mmword wk[WK_NUM]
 
39
%define WK_NUM          3
 
40
%define gotptr          wk(0)-SIZEOF_POINTER    ; void * gotptr
 
41
 
 
42
        align   16
 
43
        global  EXTN(jsimd_h2v1_merged_upsample_mmx)
 
44
 
 
45
EXTN(jsimd_h2v1_merged_upsample_mmx):
 
46
        push    ebp
 
47
        mov     eax,esp                         ; eax = original ebp
 
48
        sub     esp, byte 4
 
49
        and     esp, byte (-SIZEOF_MMWORD)      ; align to 64 bits
 
50
        mov     [esp],eax
 
51
        mov     ebp,esp                         ; ebp = aligned ebp
 
52
        lea     esp, [wk(0)]
 
53
        pushpic eax             ; make a room for GOT address
 
54
        push    ebx
 
55
;       push    ecx             ; need not be preserved
 
56
;       push    edx             ; need not be preserved
 
57
        push    esi
 
58
        push    edi
 
59
 
 
60
        get_GOT ebx                     ; get GOT address
 
61
        movpic  POINTER [gotptr], ebx   ; save GOT address
 
62
 
 
63
        mov     ecx, JDIMENSION [output_width(eax)]     ; col
 
64
        test    ecx,ecx
 
65
        jz      near .return
 
66
 
 
67
        push    ecx
 
68
 
 
69
        mov     edi, JSAMPIMAGE [input_buf(eax)]
 
70
        mov     ecx, JDIMENSION [in_row_group_ctr(eax)]
 
71
        mov     esi, JSAMPARRAY [edi+0*SIZEOF_JSAMPARRAY]
 
72
        mov     ebx, JSAMPARRAY [edi+1*SIZEOF_JSAMPARRAY]
 
73
        mov     edx, JSAMPARRAY [edi+2*SIZEOF_JSAMPARRAY]
 
74
        mov     edi, JSAMPARRAY [output_buf(eax)]
 
75
        mov     esi, JSAMPROW [esi+ecx*SIZEOF_JSAMPROW]         ; inptr0
 
76
        mov     ebx, JSAMPROW [ebx+ecx*SIZEOF_JSAMPROW]         ; inptr1
 
77
        mov     edx, JSAMPROW [edx+ecx*SIZEOF_JSAMPROW]         ; inptr2
 
78
        mov     edi, JSAMPROW [edi]                             ; outptr
 
79
 
 
80
        pop     ecx                     ; col
 
81
 
 
82
        alignx  16,7
 
83
.columnloop:
 
84
        movpic  eax, POINTER [gotptr]   ; load GOT address (eax)
 
85
 
 
86
        movq      mm6, MMWORD [ebx]     ; mm6=Cb(01234567)
 
87
        movq      mm7, MMWORD [edx]     ; mm7=Cr(01234567)
 
88
 
 
89
        pxor      mm1,mm1               ; mm1=(all 0's)
 
90
        pcmpeqw   mm3,mm3
 
91
        psllw     mm3,7                 ; mm3={0xFF80 0xFF80 0xFF80 0xFF80}
 
92
 
 
93
        movq      mm4,mm6
 
94
        punpckhbw mm6,mm1               ; mm6=Cb(4567)=CbH
 
95
        punpcklbw mm4,mm1               ; mm4=Cb(0123)=CbL
 
96
        movq      mm0,mm7
 
97
        punpckhbw mm7,mm1               ; mm7=Cr(4567)=CrH
 
98
        punpcklbw mm0,mm1               ; mm0=Cr(0123)=CrL
 
99
 
 
100
        paddw     mm6,mm3
 
101
        paddw     mm4,mm3
 
102
        paddw     mm7,mm3
 
103
        paddw     mm0,mm3
 
104
 
 
105
        ; (Original)
 
106
        ; R = Y                + 1.40200 * Cr
 
107
        ; G = Y - 0.34414 * Cb - 0.71414 * Cr
 
108
        ; B = Y + 1.77200 * Cb
 
109
        ;
 
110
        ; (This implementation)
 
111
        ; R = Y                + 0.40200 * Cr + Cr
 
112
        ; G = Y - 0.34414 * Cb + 0.28586 * Cr - Cr
 
113
        ; B = Y - 0.22800 * Cb + Cb + Cb
 
114
 
 
115
        movq    mm5,mm6                 ; mm5=CbH
 
116
        movq    mm2,mm4                 ; mm2=CbL
 
117
        paddw   mm6,mm6                 ; mm6=2*CbH
 
118
        paddw   mm4,mm4                 ; mm4=2*CbL
 
119
        movq    mm1,mm7                 ; mm1=CrH
 
120
        movq    mm3,mm0                 ; mm3=CrL
 
121
        paddw   mm7,mm7                 ; mm7=2*CrH
 
122
        paddw   mm0,mm0                 ; mm0=2*CrL
 
123
 
 
124
        pmulhw  mm6,[GOTOFF(eax,PW_MF0228)]     ; mm6=(2*CbH * -FIX(0.22800))
 
125
        pmulhw  mm4,[GOTOFF(eax,PW_MF0228)]     ; mm4=(2*CbL * -FIX(0.22800))
 
126
        pmulhw  mm7,[GOTOFF(eax,PW_F0402)]      ; mm7=(2*CrH * FIX(0.40200))
 
127
        pmulhw  mm0,[GOTOFF(eax,PW_F0402)]      ; mm0=(2*CrL * FIX(0.40200))
 
128
 
 
129
        paddw   mm6,[GOTOFF(eax,PW_ONE)]
 
130
        paddw   mm4,[GOTOFF(eax,PW_ONE)]
 
131
        psraw   mm6,1                   ; mm6=(CbH * -FIX(0.22800))
 
132
        psraw   mm4,1                   ; mm4=(CbL * -FIX(0.22800))
 
133
        paddw   mm7,[GOTOFF(eax,PW_ONE)]
 
134
        paddw   mm0,[GOTOFF(eax,PW_ONE)]
 
135
        psraw   mm7,1                   ; mm7=(CrH * FIX(0.40200))
 
136
        psraw   mm0,1                   ; mm0=(CrL * FIX(0.40200))
 
137
 
 
138
        paddw   mm6,mm5
 
139
        paddw   mm4,mm2
 
140
        paddw   mm6,mm5                 ; mm6=(CbH * FIX(1.77200))=(B-Y)H
 
141
        paddw   mm4,mm2                 ; mm4=(CbL * FIX(1.77200))=(B-Y)L
 
142
        paddw   mm7,mm1                 ; mm7=(CrH * FIX(1.40200))=(R-Y)H
 
143
        paddw   mm0,mm3                 ; mm0=(CrL * FIX(1.40200))=(R-Y)L
 
144
 
 
145
        movq    MMWORD [wk(0)], mm6     ; wk(0)=(B-Y)H
 
146
        movq    MMWORD [wk(1)], mm7     ; wk(1)=(R-Y)H
 
147
 
 
148
        movq      mm6,mm5
 
149
        movq      mm7,mm2
 
150
        punpcklwd mm5,mm1
 
151
        punpckhwd mm6,mm1
 
152
        pmaddwd   mm5,[GOTOFF(eax,PW_MF0344_F0285)]
 
153
        pmaddwd   mm6,[GOTOFF(eax,PW_MF0344_F0285)]
 
154
        punpcklwd mm2,mm3
 
155
        punpckhwd mm7,mm3
 
156
        pmaddwd   mm2,[GOTOFF(eax,PW_MF0344_F0285)]
 
157
        pmaddwd   mm7,[GOTOFF(eax,PW_MF0344_F0285)]
 
158
 
 
159
        paddd     mm5,[GOTOFF(eax,PD_ONEHALF)]
 
160
        paddd     mm6,[GOTOFF(eax,PD_ONEHALF)]
 
161
        psrad     mm5,SCALEBITS
 
162
        psrad     mm6,SCALEBITS
 
163
        paddd     mm2,[GOTOFF(eax,PD_ONEHALF)]
 
164
        paddd     mm7,[GOTOFF(eax,PD_ONEHALF)]
 
165
        psrad     mm2,SCALEBITS
 
166
        psrad     mm7,SCALEBITS
 
167
 
 
168
        packssdw  mm5,mm6       ; mm5=CbH*-FIX(0.344)+CrH*FIX(0.285)
 
169
        packssdw  mm2,mm7       ; mm2=CbL*-FIX(0.344)+CrL*FIX(0.285)
 
170
        psubw     mm5,mm1       ; mm5=CbH*-FIX(0.344)+CrH*-FIX(0.714)=(G-Y)H
 
171
        psubw     mm2,mm3       ; mm2=CbL*-FIX(0.344)+CrL*-FIX(0.714)=(G-Y)L
 
172
 
 
173
        movq    MMWORD [wk(2)], mm5     ; wk(2)=(G-Y)H
 
174
 
 
175
        mov     al,2                    ; Yctr
 
176
        jmp     short .Yloop_1st
 
177
        alignx  16,7
 
178
 
 
179
.Yloop_2nd:
 
180
        movq    mm0, MMWORD [wk(1)]     ; mm0=(R-Y)H
 
181
        movq    mm2, MMWORD [wk(2)]     ; mm2=(G-Y)H
 
182
        movq    mm4, MMWORD [wk(0)]     ; mm4=(B-Y)H
 
183
        alignx  16,7
 
184
 
 
185
.Yloop_1st:
 
186
        movq    mm7, MMWORD [esi]       ; mm7=Y(01234567)
 
187
 
 
188
        pcmpeqw mm6,mm6
 
189
        psrlw   mm6,BYTE_BIT            ; mm6={0xFF 0x00 0xFF 0x00 ..}
 
190
        pand    mm6,mm7                 ; mm6=Y(0246)=YE
 
191
        psrlw   mm7,BYTE_BIT            ; mm7=Y(1357)=YO
 
192
 
 
193
        movq    mm1,mm0                 ; mm1=mm0=(R-Y)(L/H)
 
194
        movq    mm3,mm2                 ; mm3=mm2=(G-Y)(L/H)
 
195
        movq    mm5,mm4                 ; mm5=mm4=(B-Y)(L/H)
 
196
 
 
197
        paddw     mm0,mm6               ; mm0=((R-Y)+YE)=RE=(R0 R2 R4 R6)
 
198
        paddw     mm1,mm7               ; mm1=((R-Y)+YO)=RO=(R1 R3 R5 R7)
 
199
        packuswb  mm0,mm0               ; mm0=(R0 R2 R4 R6 ** ** ** **)
 
200
        packuswb  mm1,mm1               ; mm1=(R1 R3 R5 R7 ** ** ** **)
 
201
 
 
202
        paddw     mm2,mm6               ; mm2=((G-Y)+YE)=GE=(G0 G2 G4 G6)
 
203
        paddw     mm3,mm7               ; mm3=((G-Y)+YO)=GO=(G1 G3 G5 G7)
 
204
        packuswb  mm2,mm2               ; mm2=(G0 G2 G4 G6 ** ** ** **)
 
205
        packuswb  mm3,mm3               ; mm3=(G1 G3 G5 G7 ** ** ** **)
 
206
 
 
207
        paddw     mm4,mm6               ; mm4=((B-Y)+YE)=BE=(B0 B2 B4 B6)
 
208
        paddw     mm5,mm7               ; mm5=((B-Y)+YO)=BO=(B1 B3 B5 B7)
 
209
        packuswb  mm4,mm4               ; mm4=(B0 B2 B4 B6 ** ** ** **)
 
210
        packuswb  mm5,mm5               ; mm5=(B1 B3 B5 B7 ** ** ** **)
 
211
 
 
212
%if RGB_PIXELSIZE == 3 ; ---------------
 
213
 
 
214
        ; mmA=(00 02 04 06 ** ** ** **), mmB=(01 03 05 07 ** ** ** **)
 
215
        ; mmC=(10 12 14 16 ** ** ** **), mmD=(11 13 15 17 ** ** ** **)
 
216
        ; mmE=(20 22 24 26 ** ** ** **), mmF=(21 23 25 27 ** ** ** **)
 
217
        ; mmG=(** ** ** ** ** ** ** **), mmH=(** ** ** ** ** ** ** **)
 
218
 
 
219
        punpcklbw mmA,mmC               ; mmA=(00 10 02 12 04 14 06 16)
 
220
        punpcklbw mmE,mmB               ; mmE=(20 01 22 03 24 05 26 07)
 
221
        punpcklbw mmD,mmF               ; mmD=(11 21 13 23 15 25 17 27)
 
222
 
 
223
        movq      mmG,mmA
 
224
        movq      mmH,mmA
 
225
        punpcklwd mmA,mmE               ; mmA=(00 10 20 01 02 12 22 03)
 
226
        punpckhwd mmG,mmE               ; mmG=(04 14 24 05 06 16 26 07)
 
227
 
 
228
        psrlq     mmH,2*BYTE_BIT        ; mmH=(02 12 04 14 06 16 -- --)
 
229
        psrlq     mmE,2*BYTE_BIT        ; mmE=(22 03 24 05 26 07 -- --)
 
230
 
 
231
        movq      mmC,mmD
 
232
        movq      mmB,mmD
 
233
        punpcklwd mmD,mmH               ; mmD=(11 21 02 12 13 23 04 14)
 
234
        punpckhwd mmC,mmH               ; mmC=(15 25 06 16 17 27 -- --)
 
235
 
 
236
        psrlq     mmB,2*BYTE_BIT        ; mmB=(13 23 15 25 17 27 -- --)
 
237
 
 
238
        movq      mmF,mmE
 
239
        punpcklwd mmE,mmB               ; mmE=(22 03 13 23 24 05 15 25)
 
240
        punpckhwd mmF,mmB               ; mmF=(26 07 17 27 -- -- -- --)
 
241
 
 
242
        punpckldq mmA,mmD               ; mmA=(00 10 20 01 11 21 02 12)
 
243
        punpckldq mmE,mmG               ; mmE=(22 03 13 23 04 14 24 05)
 
244
        punpckldq mmC,mmF               ; mmC=(15 25 06 16 26 07 17 27)
 
245
 
 
246
        cmp     ecx, byte SIZEOF_MMWORD
 
247
        jb      short .column_st16
 
248
 
 
249
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
250
        movq    MMWORD [edi+1*SIZEOF_MMWORD], mmE
 
251
        movq    MMWORD [edi+2*SIZEOF_MMWORD], mmC
 
252
 
 
253
        sub     ecx, byte SIZEOF_MMWORD
 
254
        jz      near .endcolumn
 
255
 
 
256
        add     edi, byte RGB_PIXELSIZE*SIZEOF_MMWORD   ; outptr
 
257
        add     esi, byte SIZEOF_MMWORD                 ; inptr0
 
258
        dec     al                      ; Yctr
 
259
        jnz     near .Yloop_2nd
 
260
 
 
261
        add     ebx, byte SIZEOF_MMWORD                 ; inptr1
 
262
        add     edx, byte SIZEOF_MMWORD                 ; inptr2
 
263
        jmp     near .columnloop
 
264
        alignx  16,7
 
265
 
 
266
.column_st16:
 
267
        lea     ecx, [ecx+ecx*2]        ; imul ecx, RGB_PIXELSIZE
 
268
        cmp     ecx, byte 2*SIZEOF_MMWORD
 
269
        jb      short .column_st8
 
270
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
271
        movq    MMWORD [edi+1*SIZEOF_MMWORD], mmE
 
272
        movq    mmA,mmC
 
273
        sub     ecx, byte 2*SIZEOF_MMWORD
 
274
        add     edi, byte 2*SIZEOF_MMWORD
 
275
        jmp     short .column_st4
 
276
.column_st8:
 
277
        cmp     ecx, byte SIZEOF_MMWORD
 
278
        jb      short .column_st4
 
279
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
280
        movq    mmA,mmE
 
281
        sub     ecx, byte SIZEOF_MMWORD
 
282
        add     edi, byte SIZEOF_MMWORD
 
283
.column_st4:
 
284
        movd    eax,mmA
 
285
        cmp     ecx, byte SIZEOF_DWORD
 
286
        jb      short .column_st2
 
287
        mov     DWORD [edi+0*SIZEOF_DWORD], eax
 
288
        psrlq   mmA,DWORD_BIT
 
289
        movd    eax,mmA
 
290
        sub     ecx, byte SIZEOF_DWORD
 
291
        add     edi, byte SIZEOF_DWORD
 
292
.column_st2:
 
293
        cmp     ecx, byte SIZEOF_WORD
 
294
        jb      short .column_st1
 
295
        mov     WORD [edi+0*SIZEOF_WORD], ax
 
296
        shr     eax,WORD_BIT
 
297
        sub     ecx, byte SIZEOF_WORD
 
298
        add     edi, byte SIZEOF_WORD
 
299
.column_st1:
 
300
        cmp     ecx, byte SIZEOF_BYTE
 
301
        jb      short .endcolumn
 
302
        mov     BYTE [edi+0*SIZEOF_BYTE], al
 
303
 
 
304
%else ; RGB_PIXELSIZE == 4 ; -----------
 
305
 
 
306
%ifdef RGBX_FILLER_0XFF
 
307
        pcmpeqb   mm6,mm6               ; mm6=(X0 X2 X4 X6 ** ** ** **)
 
308
        pcmpeqb   mm7,mm7               ; mm7=(X1 X3 X5 X7 ** ** ** **)
 
309
%else
 
310
        pxor      mm6,mm6               ; mm6=(X0 X2 X4 X6 ** ** ** **)
 
311
        pxor      mm7,mm7               ; mm7=(X1 X3 X5 X7 ** ** ** **)
 
312
%endif
 
313
        ; mmA=(00 02 04 06 ** ** ** **), mmB=(01 03 05 07 ** ** ** **)
 
314
        ; mmC=(10 12 14 16 ** ** ** **), mmD=(11 13 15 17 ** ** ** **)
 
315
        ; mmE=(20 22 24 26 ** ** ** **), mmF=(21 23 25 27 ** ** ** **)
 
316
        ; mmG=(30 32 34 36 ** ** ** **), mmH=(31 33 35 37 ** ** ** **)
 
317
 
 
318
        punpcklbw mmA,mmC               ; mmA=(00 10 02 12 04 14 06 16)
 
319
        punpcklbw mmE,mmG               ; mmE=(20 30 22 32 24 34 26 36)
 
320
        punpcklbw mmB,mmD               ; mmB=(01 11 03 13 05 15 07 17)
 
321
        punpcklbw mmF,mmH               ; mmF=(21 31 23 33 25 35 27 37)
 
322
 
 
323
        movq      mmC,mmA
 
324
        punpcklwd mmA,mmE               ; mmA=(00 10 20 30 02 12 22 32)
 
325
        punpckhwd mmC,mmE               ; mmC=(04 14 24 34 06 16 26 36)
 
326
        movq      mmG,mmB
 
327
        punpcklwd mmB,mmF               ; mmB=(01 11 21 31 03 13 23 33)
 
328
        punpckhwd mmG,mmF               ; mmG=(05 15 25 35 07 17 27 37)
 
329
 
 
330
        movq      mmD,mmA
 
331
        punpckldq mmA,mmB               ; mmA=(00 10 20 30 01 11 21 31)
 
332
        punpckhdq mmD,mmB               ; mmD=(02 12 22 32 03 13 23 33)
 
333
        movq      mmH,mmC
 
334
        punpckldq mmC,mmG               ; mmC=(04 14 24 34 05 15 25 35)
 
335
        punpckhdq mmH,mmG               ; mmH=(06 16 26 36 07 17 27 37)
 
336
 
 
337
        cmp     ecx, byte SIZEOF_MMWORD
 
338
        jb      short .column_st16
 
339
 
 
340
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
341
        movq    MMWORD [edi+1*SIZEOF_MMWORD], mmD
 
342
        movq    MMWORD [edi+2*SIZEOF_MMWORD], mmC
 
343
        movq    MMWORD [edi+3*SIZEOF_MMWORD], mmH
 
344
 
 
345
        sub     ecx, byte SIZEOF_MMWORD
 
346
        jz      short .endcolumn
 
347
 
 
348
        add     edi, byte RGB_PIXELSIZE*SIZEOF_MMWORD   ; outptr
 
349
        add     esi, byte SIZEOF_MMWORD                 ; inptr0
 
350
        dec     al                      ; Yctr
 
351
        jnz     near .Yloop_2nd
 
352
 
 
353
        add     ebx, byte SIZEOF_MMWORD                 ; inptr1
 
354
        add     edx, byte SIZEOF_MMWORD                 ; inptr2
 
355
        jmp     near .columnloop
 
356
        alignx  16,7
 
357
 
 
358
.column_st16:
 
359
        cmp     ecx, byte SIZEOF_MMWORD/2
 
360
        jb      short .column_st8
 
361
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
362
        movq    MMWORD [edi+1*SIZEOF_MMWORD], mmD
 
363
        movq    mmA,mmC
 
364
        movq    mmD,mmH
 
365
        sub     ecx, byte SIZEOF_MMWORD/2
 
366
        add     edi, byte 2*SIZEOF_MMWORD
 
367
.column_st8:
 
368
        cmp     ecx, byte SIZEOF_MMWORD/4
 
369
        jb      short .column_st4
 
370
        movq    MMWORD [edi+0*SIZEOF_MMWORD], mmA
 
371
        movq    mmA,mmD
 
372
        sub     ecx, byte SIZEOF_MMWORD/4
 
373
        add     edi, byte 1*SIZEOF_MMWORD
 
374
.column_st4:
 
375
        cmp     ecx, byte SIZEOF_MMWORD/8
 
376
        jb      short .endcolumn
 
377
        movd    DWORD [edi+0*SIZEOF_DWORD], mmA
 
378
 
 
379
%endif ; RGB_PIXELSIZE ; ---------------
 
380
 
 
381
.endcolumn:
 
382
        emms            ; empty MMX state
 
383
 
 
384
.return:
 
385
        pop     edi
 
386
        pop     esi
 
387
;       pop     edx             ; need not be preserved
 
388
;       pop     ecx             ; need not be preserved
 
389
        pop     ebx
 
390
        mov     esp,ebp         ; esp <- aligned ebp
 
391
        pop     esp             ; esp <- original ebp
 
392
        pop     ebp
 
393
        ret
 
394
 
 
395
; --------------------------------------------------------------------------
 
396
;
 
397
; Upsample and color convert for the case of 2:1 horizontal and 2:1 vertical.
 
398
;
 
399
; GLOBAL(void)
 
400
; jsimd_h2v2_merged_upsample_mmx (JDIMENSION output_width,
 
401
;                                 JSAMPIMAGE input_buf,
 
402
;                                 JDIMENSION in_row_group_ctr,
 
403
;                                 JSAMPARRAY output_buf);
 
404
;
 
405
 
 
406
%define output_width(b) (b)+8                   ; JDIMENSION output_width
 
407
%define input_buf(b)            (b)+12          ; JSAMPIMAGE input_buf
 
408
%define in_row_group_ctr(b)     (b)+16          ; JDIMENSION in_row_group_ctr
 
409
%define output_buf(b)           (b)+20          ; JSAMPARRAY output_buf
 
410
 
 
411
        align   16
 
412
        global  EXTN(jsimd_h2v2_merged_upsample_mmx)
 
413
 
 
414
EXTN(jsimd_h2v2_merged_upsample_mmx):
 
415
        push    ebp
 
416
        mov     ebp,esp
 
417
        push    ebx
 
418
;       push    ecx             ; need not be preserved
 
419
;       push    edx             ; need not be preserved
 
420
        push    esi
 
421
        push    edi
 
422
 
 
423
        mov     eax, JDIMENSION [output_width(ebp)]
 
424
 
 
425
        mov     edi, JSAMPIMAGE [input_buf(ebp)]
 
426
        mov     ecx, JDIMENSION [in_row_group_ctr(ebp)]
 
427
        mov     esi, JSAMPARRAY [edi+0*SIZEOF_JSAMPARRAY]
 
428
        mov     ebx, JSAMPARRAY [edi+1*SIZEOF_JSAMPARRAY]
 
429
        mov     edx, JSAMPARRAY [edi+2*SIZEOF_JSAMPARRAY]
 
430
        mov     edi, JSAMPARRAY [output_buf(ebp)]
 
431
        lea     esi, [esi+ecx*SIZEOF_JSAMPROW]
 
432
 
 
433
        push    edx                     ; inptr2
 
434
        push    ebx                     ; inptr1
 
435
        push    esi                     ; inptr00
 
436
        mov     ebx,esp
 
437
 
 
438
        push    edi                     ; output_buf (outptr0)
 
439
        push    ecx                     ; in_row_group_ctr
 
440
        push    ebx                     ; input_buf
 
441
        push    eax                     ; output_width
 
442
 
 
443
        call    near EXTN(jsimd_h2v1_merged_upsample_mmx)
 
444
 
 
445
        add     esi, byte SIZEOF_JSAMPROW       ; inptr01
 
446
        add     edi, byte SIZEOF_JSAMPROW       ; outptr1
 
447
        mov     POINTER [ebx+0*SIZEOF_POINTER], esi
 
448
        mov     POINTER [ebx-1*SIZEOF_POINTER], edi
 
449
 
 
450
        call    near EXTN(jsimd_h2v1_merged_upsample_mmx)
 
451
 
 
452
        add     esp, byte 7*SIZEOF_DWORD
 
453
 
 
454
        pop     edi
 
455
        pop     esi
 
456
;       pop     edx             ; need not be preserved
 
457
;       pop     ecx             ; need not be preserved
 
458
        pop     ebx
 
459
        pop     ebp
 
460
        ret
 
461
 
 
462
; For some reason, the OS X linker does not honor the request to align the
 
463
; segment unless we do this.
 
464
        align   16