Statistics
| Branch: | Tag: | Revision:

root / gnuradio-core / src / lib / filter / short_dotprod_mmx.S @ 2b60291c

History | View | Annotate | Download (2.7 kB)

1 5d69a524 jcorgan
#
2 5d69a524 jcorgan
# Copyright 2002 Free Software Foundation, Inc.
3 5d69a524 jcorgan
# 
4 5d69a524 jcorgan
# This file is part of GNU Radio
5 5d69a524 jcorgan
# 
6 5d69a524 jcorgan
# GNU Radio is free software; you can redistribute it and/or modify
7 5d69a524 jcorgan
# it under the terms of the GNU General Public License as published by
8 937b719d eb
# the Free Software Foundation; either version 3, or (at your option)
9 5d69a524 jcorgan
# any later version.
10 5d69a524 jcorgan
# 
11 5d69a524 jcorgan
# GNU Radio is distributed in the hope that it will be useful,
12 5d69a524 jcorgan
# but WITHOUT ANY WARRANTY; without even the implied warranty of
13 5d69a524 jcorgan
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 5d69a524 jcorgan
# GNU General Public License for more details.
15 5d69a524 jcorgan
# 
16 5d69a524 jcorgan
# You should have received a copy of the GNU General Public License
17 5d69a524 jcorgan
# along with GNU Radio; see the file COPYING.  If not, write to
18 86f5c924 eb
# the Free Software Foundation, Inc., 51 Franklin Street,
19 86f5c924 eb
# Boston, MA 02110-1301, USA.
20 5d69a524 jcorgan
# 
21 5d69a524 jcorgan
22 5d69a524 jcorgan
# SIMD MMX dot product
23 5d69a524 jcorgan
# Equivalent to the following C code:
24 5d69a524 jcorgan
# long dotprod(signed short *a,signed short *b,int cnt)
25 5d69a524 jcorgan
# {
26 5d69a524 jcorgan
#	long sum = 0; 
27 5d69a524 jcorgan
#	cnt *= 4; 
28 5d69a524 jcorgan
#	while(cnt--)
29 5d69a524 jcorgan
#		sum += *a++ + *b++;
30 5d69a524 jcorgan
#	return sum;
31 5d69a524 jcorgan
# }
32 5d69a524 jcorgan
# a and b should also be 64-bit aligned, or speed will suffer greatly
33 5d69a524 jcorgan
# Copyright 1999, Phil Karn KA9Q
34 5d69a524 jcorgan
# May be used under the terms of the GNU public license
35 5d69a524 jcorgan
	
36 5d69a524 jcorgan
#include "assembly.h"
37 5d69a524 jcorgan
38 5d69a524 jcorgan
39 5d69a524 jcorgan
	.file	"short_dotprod_mmx.S"
40 5d69a524 jcorgan
	.version	"01.01"
41 5d69a524 jcorgan
.text
42 5d69a524 jcorgan
	.p2align 3
43 5d69a524 jcorgan
.globl GLOB_SYMB(short_dotprod_mmx)
44 5d69a524 jcorgan
	DEF_FUNC_HEAD(short_dotprod_mmx)
45 5d69a524 jcorgan
GLOB_SYMB(short_dotprod_mmx):
46 5d69a524 jcorgan
	pushl %ebp
47 5d69a524 jcorgan
	movl %esp,%ebp
48 5d69a524 jcorgan
	pushl %esi
49 5d69a524 jcorgan
	pushl %edi
50 5d69a524 jcorgan
	pushl %ecx
51 5d69a524 jcorgan
	pushl %ebx
52 5d69a524 jcorgan
	movl 8(%ebp),%esi	# a
53 5d69a524 jcorgan
	movl 12(%ebp),%edi	# b
54 5d69a524 jcorgan
	movl 16(%ebp),%ecx	# cnt
55 5d69a524 jcorgan
	pxor %mm0,%mm0		# clear running sum (in two 32-bit halves)
56 5d69a524 jcorgan
	
57 5d69a524 jcorgan
# MMX dot product loop unrolled 4 times, crunching 16 terms per loop
58 5d69a524 jcorgan
	.p2align 4
59 5d69a524 jcorgan
.Loop1mmx:	subl $4,%ecx
60 5d69a524 jcorgan
	jl   .Loop1Done
61 5d69a524 jcorgan
	
62 5d69a524 jcorgan
	movq (%esi),%mm1	# mm1 = a[3],a[2],a[1],a[0]
63 5d69a524 jcorgan
 	pmaddwd (%edi),%mm1	# mm1 = b[3]*a[3]+b[2]*a[2],b[1]*a[1]+b[0]*a[0]
64 5d69a524 jcorgan
	paddd %mm1,%mm0
65 5d69a524 jcorgan
	
66 5d69a524 jcorgan
	movq 8(%esi),%mm1
67 5d69a524 jcorgan
	pmaddwd 8(%edi),%mm1
68 5d69a524 jcorgan
	paddd %mm1,%mm0
69 5d69a524 jcorgan
70 5d69a524 jcorgan
	movq 16(%esi),%mm1
71 5d69a524 jcorgan
	pmaddwd 16(%edi),%mm1
72 5d69a524 jcorgan
	paddd %mm1,%mm0
73 5d69a524 jcorgan
74 5d69a524 jcorgan
	movq 24(%esi),%mm1
75 5d69a524 jcorgan
	addl $32,%esi	
76 5d69a524 jcorgan
	pmaddwd 24(%edi),%mm1
77 5d69a524 jcorgan
	addl $32,%edi	
78 5d69a524 jcorgan
	paddd %mm1,%mm0
79 5d69a524 jcorgan
80 5d69a524 jcorgan
	jmp .Loop1mmx
81 5d69a524 jcorgan
.Loop1Done:
82 5d69a524 jcorgan
	
83 5d69a524 jcorgan
	addl $4,%ecx	
84 5d69a524 jcorgan
	
85 5d69a524 jcorgan
# MMX dot product loop, not unrolled, crunching 4 terms per loop
86 5d69a524 jcorgan
# This could be redone as Duff's Device on the unrolled loop above
87 5d69a524 jcorgan
.Loop2:	subl $1,%ecx
88 5d69a524 jcorgan
	jl   .Loop2Done
89 5d69a524 jcorgan
	
90 5d69a524 jcorgan
	movq (%esi),%mm1
91 5d69a524 jcorgan
	addl $8,%esi
92 5d69a524 jcorgan
	pmaddwd (%edi),%mm1
93 5d69a524 jcorgan
	addl $8,%edi
94 5d69a524 jcorgan
	paddd %mm1,%mm0
95 5d69a524 jcorgan
	jmp .Loop2
96 5d69a524 jcorgan
.Loop2Done:
97 5d69a524 jcorgan
	
98 5d69a524 jcorgan
	movd %mm0,%ebx		# right-hand word to ebx
99 5d69a524 jcorgan
	punpckhdq %mm0,%mm0	# left-hand word to right side of %mm0
100 5d69a524 jcorgan
	movd %mm0,%eax
101 5d69a524 jcorgan
	addl %ebx,%eax		# running sum now in %eax
102 5d69a524 jcorgan
	emms			# done with MMX
103 5d69a524 jcorgan
	
104 5d69a524 jcorgan
	popl %ebx
105 5d69a524 jcorgan
	popl %ecx
106 5d69a524 jcorgan
	popl %edi
107 5d69a524 jcorgan
	popl %esi
108 5d69a524 jcorgan
	movl %ebp,%esp
109 5d69a524 jcorgan
	popl	%ebp
110 5d69a524 jcorgan
	ret
111 5d69a524 jcorgan
112 5d69a524 jcorgan
FUNC_TAIL(short_dotprod_mmx)
113 5d69a524 jcorgan
	.ident	"Hand coded x86 MMX assembly"
114 0d4c6442 eb
115 0d4c6442 eb
#if defined(__linux__) && defined(__ELF__)
116 0d4c6442 eb
.section .note.GNU-stack,"",%progbits
117 0d4c6442 eb
#endif