xref: /aosp_15_r20/external/sonivox/arm-wt-22k/lib_src/ARM-E_interpolate_noloop_gnu.s (revision f81fb7c475c4b71ff83bdcc517de2a8c174e4e5c)
1@***********************************************************
2@ Function:    WT_InterpolateNoLoop
3@ Processor:   ARM-E
4@ Description: the main synthesis function when fetching
5@			   wavetable samples.
6@              C-callable.
7@
8@ Usage:
9@	void WT_InterpolateNoLoop(
10@		S_WT_VOICE *pWTVoice,
11@		S_WT_FRAME *pWTFrame);
12@
13@ Copyright Sonic Network Inc. 2004
14@****************************************************************
15@ Revision Control:
16@   $Revision: 496 $
17@   $Date: 2006-12-11 14:33:26 -0800 (Mon, 11 Dec 2006) $
18@****************************************************************
19@
20@   where:
21@	S_WT_VOICE *pWTVoice
22@	PASSED IN: r0
23@
24@	S_WT_FRAME *pWTFrame;
25@	PASSED IN: r1
26@****************************************************************
27
28	#include	"ARM_synth_constants_gnu.inc"
29
30	.arm
31	.text
32
33
34	.global	WT_InterpolateNoLoop
35
36
37@ Register usage
38@ --------------
39pWTVoice	.req	r0
40pWTFrame	.req	r1
41pOutputBuffer	.req	r2
42numSamples	.req	r3
43
44phaseIncrement	.req	r4
45pPhaseAccum	.req	r5
46phaseFrac	.req	r6
47phaseFracMask	.req	r7
48
49tmp0	.req	r1	@ reuse register
50tmp1	.req	r8
51tmp2	.req	r9
52
53
54@SaveRegs	RLIST	{r4-r9,lr}
55@RestoreRegs	RLIST	{r4-r9,pc}
56
57WT_InterpolateNoLoop:
58
59	STMFD	sp!, {r4-r9,lr}
60
61@
62@ Fetch parameters from structures
63@----------------------------------------------------------------
64
65	LDR		pOutputBuffer, [pWTFrame, #m_pAudioBuffer]
66	LDR		numSamples, [pWTFrame, #m_numSamples]
67
68	LDR		phaseIncrement, [pWTFrame, #m_phaseIncrement]
69	LDR		pPhaseAccum, [pWTVoice, #m_pPhaseAccum]
70	LDR		phaseFrac, [pWTVoice, #m_phaseFrac]
71	LDR		phaseFracMask,=PHASE_FRAC_MASK
72
73InterpolationLoop:
74
75	#ifdef	SAMPLES_8_BIT
76	LDRSB	tmp0, [pPhaseAccum]				@ tmp0 = x0
77	LDRSB	tmp1, [pPhaseAccum, #1]			@ tmp1 = x1
78	#elif	SAMPLES_16_BIT
79	LDRSH	tmp0, [pPhaseAccum]				@ tmp0 = x0
80	LDRSH	tmp1, [pPhaseAccum, #2]			@ tmp1 = x1
81	#else
82	#error Must define one of SAMPLES_8_BIT or SAMPLES_16_BIT.
83	#endif
84
85	ADD		tmp2, phaseIncrement, phaseFrac	@ increment pointer here to avoid pipeline stall
86
87	SUB		tmp1, tmp1, tmp0				@ tmp1 = x1 - x0
88	SMULBB	tmp1, phaseFrac, tmp1			@ tmp1 = phaseFrac * tmp2
89
90@ This section performs a gain adjustment of -12dB for 16-bit samples
91@ or +36dB for 8-bit samples. For a high quality synthesizer, the output
92@ can be set to full scale, however if the filter is used, it can overflow
93@ with certain coefficients and signal sources. In this case, either a
94@ saturation operation should take in the filter before scaling back to
95@ 16 bits or the signal path should be increased to 18 bits or more.
96
97	#ifdef	SAMPLES_8_BIT
98	MOV		tmp0, tmp0, LSL #6							@ boost 8-bit signal by 36dB
99	#elif	SAMPLES_16_BIT
100	MOV		tmp0, tmp0, ASR #2							@ reduce 16-bit signal by 12dB
101	#else
102	#error Must define one of SAMPLES_8_BIT or SAMPLES_16_BIT.
103	#endif
104
105	ADD		tmp1, tmp0, tmp1, ASR #(NUM_EG1_FRAC_BITS-6)	@ tmp1 = tmp0 + (tmp1 >> (15-6))
106															@	   = x0 + f * (x1 - x0) == interpolated result
107
108	STRH	tmp1, [pOutputBuffer], #NEXT_OUTPUT_PCM	@ *pOutputBuffer++ = interpolated result
109
110@ carry overflow from fraction to integer portion
111	ADD	pPhaseAccum, pPhaseAccum, tmp2, LSR #(NUM_PHASE_FRAC_BITS - NEXT_INPUT_PCM_SHIFT)
112	AND	phaseFrac, tmp2, phaseFracMask		@ nphaseFrac = frac part
113
114	SUBS	numSamples, numSamples, #1
115	BGT		InterpolationLoop
116
117@ Clean up and store any changes that were caused during the loop
118@----------------------------------------------------------------
119
120	@ update and store phase
121	STR		pPhaseAccum, [pWTVoice, #m_pPhaseAccum]
122	STR		phaseFrac, [pWTVoice, #m_phaseFrac]
123
124@
125@ Return to calling function
126@----------------------------------------------------------------
127
128	LDMFD	sp!,{r4-r9,lr}
129	BX		lr
130
131	.end
132
133