diff options
author | Michael Sevakis <jethead71@rockbox.org> | 2010-05-11 12:37:49 +0000 |
---|---|---|
committer | Michael Sevakis <jethead71@rockbox.org> | 2010-05-11 12:37:49 +0000 |
commit | 565a863dd50b62245e52e18caaf5306955f6b9f5 (patch) | |
tree | 6057b247a6887851d648c018d19ff2d745d94037 /apps | |
parent | 68da06f3dce9ee3418c2541179485a93c3f971b2 (diff) | |
download | rockbox-565a863dd50b62245e52e18caaf5306955f6b9f5.tar.gz rockbox-565a863dd50b62245e52e18caaf5306955f6b9f5.zip |
ARM DSP: Add assembly custom sound channel processing. 13% to 14% faster than currently-used default C code on ARMv4.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@25949 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps')
-rw-r--r-- | apps/dsp_arm.S | 85 | ||||
-rw-r--r-- | apps/dsp_asm.h | 1 |
2 files changed, 77 insertions, 9 deletions
diff --git a/apps/dsp_arm.S b/apps/dsp_arm.S index 2a5647d759..2150ff0631 100644 --- a/apps/dsp_arm.S +++ b/apps/dsp_arm.S | |||
@@ -22,10 +22,6 @@ | |||
22 | 22 | ||
23 | /**************************************************************************** | 23 | /**************************************************************************** |
24 | * void channels_process_sound_chan_mono(int count, int32_t *buf[]) | 24 | * void channels_process_sound_chan_mono(int count, int32_t *buf[]) |
25 | * | ||
26 | * NOTE: The following code processes two samples at once. When count is odd, | ||
27 | * there is an additional obsolete sample processed, which will not be | ||
28 | * used by the calling functions. | ||
29 | */ | 25 | */ |
30 | .section .icode, "ax", %progbits | 26 | .section .icode, "ax", %progbits |
31 | .align 2 | 27 | .align 2 |
@@ -63,13 +59,84 @@ channels_process_sound_chan_mono: | |||
63 | @ | 59 | @ |
64 | ldmfd sp!, { r4, pc } @ | 60 | ldmfd sp!, { r4, pc } @ |
65 | .size channels_process_sound_chan_mono, \ | 61 | .size channels_process_sound_chan_mono, \ |
66 | .-channels_process_sound_chan_mono | 62 | .-channels_process_sound_chan_mono |
67 | 63 | ||
64 | /**************************************************************************** | ||
65 | * void channels_process_sound_chan_custom(int count, int32_t *buf[]) | ||
66 | */ | ||
67 | .section .icode, "ax", %progbits | ||
68 | .align 2 | ||
69 | .global channels_process_sound_chan_custom | ||
70 | .type channels_process_sound_chan_custom, %function | ||
71 | channels_process_sound_chan_custom: | ||
72 | stmfd sp!, { r4-r10, lr } | ||
73 | |||
74 | ldr r3, =dsp_sw_gain | ||
75 | ldr r4, =dsp_sw_cross | ||
76 | |||
77 | ldmia r1, { r1, r2 } @ r1 = buf[0], r2 = buf[1] | ||
78 | ldr r3, [r3] @ r3 = dsp_sw_gain | ||
79 | ldr r4, [r4] @ r4 = dsp_sw_cross | ||
80 | |||
81 | subs r0, r0, #1 | ||
82 | beq .custom_single_sample @ Zero? Only one sample! | ||
83 | |||
84 | .custom_loop: | ||
85 | ldmia r1, { r5, r6 } @ r5 = Li0, r6 = Li1 | ||
86 | ldmia r2, { r7, r8 } @ r7 = Ri0, r8 = Ri1 | ||
87 | |||
88 | subs r0, r0, #2 | ||
89 | |||
90 | smull r9, r10, r5, r3 @ Lc0 = Li0*gain | ||
91 | smull r12, r14, r7, r3 @ Rc0 = Ri0*gain | ||
92 | smlal r9, r10, r7, r4 @ Lc0 += Ri0*cross | ||
93 | smlal r12, r14, r5, r4 @ Rc0 += Li0*cross | ||
94 | |||
95 | mov r9, r9, lsr #31 @ Convert to s0.31 | ||
96 | mov r12, r12, lsr #31 | ||
97 | orr r5, r9, r10, asl #1 | ||
98 | orr r7, r12, r14, asl #1 | ||
99 | |||
100 | smull r9, r10, r6, r3 @ Lc1 = Li1*gain | ||
101 | smull r12, r14, r8, r3 @ Rc1 = Ri1*gain | ||
102 | smlal r9, r10, r8, r4 @ Lc1 += Ri1*cross | ||
103 | smlal r12, r14, r6, r4 @ Rc1 += Li1*cross | ||
104 | |||
105 | mov r9, r9, lsr #31 @ Convert to s0.31 | ||
106 | mov r12, r12, lsr #31 | ||
107 | orr r6, r9, r10, asl #1 | ||
108 | orr r8, r12, r14, asl #1 | ||
109 | |||
110 | stmia r1!, { r5, r6 } @ Store Lc0, Lc1 | ||
111 | stmia r2!, { r7, r8 } @ Store Rc0, Rc1 | ||
112 | |||
113 | bgt .custom_loop | ||
114 | |||
115 | ldmltfd sp!, { r4-r10, pc } @ < 0? even count | ||
116 | |||
117 | .custom_single_sample: | ||
118 | ldr r5, [r1] @ handle odd sample | ||
119 | ldr r7, [r2] | ||
120 | |||
121 | smull r9, r10, r5, r3 @ Lc0 = Li0*gain | ||
122 | smull r12, r14, r7, r3 @ Rc0 = Ri0*gain | ||
123 | smlal r9, r10, r7, r4 @ Lc0 += Ri0*cross | ||
124 | smlal r12, r14, r5, r4 @ Rc0 += Li0*cross | ||
125 | |||
126 | mov r9, r9, lsr #31 @ Convert to s0.31 | ||
127 | mov r12, r12, lsr #31 | ||
128 | orr r5, r9, r10, asl #1 | ||
129 | orr r7, r12, r14, asl #1 | ||
130 | |||
131 | str r5, [r1] @ Store Lc0 | ||
132 | str r7, [r2] @ Store Rc0 | ||
133 | |||
134 | ldmfd sp!, { r4-r10, pc } | ||
135 | .size channels_process_sound_chan_custom, \ | ||
136 | .-channels_process_sound_chan_custom | ||
137 | |||
68 | /**************************************************************************** | 138 | /**************************************************************************** |
69 | * void channels_process_sound_chan_karaoke(int count, int32_t *buf[]) | 139 | * void channels_process_sound_chan_karaoke(int count, int32_t *buf[]) |
70 | * NOTE: The following code processes two samples at once. When count is odd, | ||
71 | * there is an additional obsolete sample processed, which will not be | ||
72 | * used by the calling functions. | ||
73 | */ | 140 | */ |
74 | .section .icode, "ax", %progbits | 141 | .section .icode, "ax", %progbits |
75 | .align 2 | 142 | .align 2 |
diff --git a/apps/dsp_asm.h b/apps/dsp_asm.h index 9204266c53..7bf18370a3 100644 --- a/apps/dsp_asm.h +++ b/apps/dsp_asm.h | |||
@@ -30,6 +30,7 @@ | |||
30 | #define DSP_HAVE_ASM_RESAMPLING | 30 | #define DSP_HAVE_ASM_RESAMPLING |
31 | #define DSP_HAVE_ASM_CROSSFEED | 31 | #define DSP_HAVE_ASM_CROSSFEED |
32 | #define DSP_HAVE_ASM_SOUND_CHAN_MONO | 32 | #define DSP_HAVE_ASM_SOUND_CHAN_MONO |
33 | #define DSP_HAVE_ASM_SOUND_CHAN_CUSTOM | ||
33 | #define DSP_HAVE_ASM_SOUND_CHAN_KARAOKE | 34 | #define DSP_HAVE_ASM_SOUND_CHAN_KARAOKE |
34 | #define DSP_HAVE_ASM_SAMPLE_OUTPUT_MONO | 35 | #define DSP_HAVE_ASM_SAMPLE_OUTPUT_MONO |
35 | #define DSP_HAVE_ASM_SAMPLE_OUTPUT_STEREO | 36 | #define DSP_HAVE_ASM_SAMPLE_OUTPUT_STEREO |