⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 2nd_order_iir.s90

📁 硬件设计资料,刚上网查找资料,是个新手,望大家提携了,
💻 S90
字号:
;*****************************************************
;* File: 2nd_order_IIR.s90
;*
;*	Version: 1.0 
;*	Date:	01.06.15 [yy.mm.dd]
;*	Author: jllassen
;*
;*  Last modified 02.02.20, by jllassen
;*    Changes: ported the code from the AVR assembler to IAR assembler/compiler
;*
;* Target device: AVRs with HW multiplier
;*
;* Compiler:
;*    IAR EWAVR 2.26C
;*
;* Describtion: 
;*	  2nd order IIR filter. 
;*	  10-bit signed data. 
;*    12-bit signed filter coefficients.
;*
;* Usage:
;*	  Implemented so that the filter can be called from IAR EWAVR C compiler.
;*    Address to the filter nodes and filter coefficients should be provided
;*    as first calling argument (will thus be placed in R16:R17) and the new 
;*    input sample to the filter should be provided as the second calling
;*    argument (placed in R18:R19).
;*      
;*    int FIR_filter(*myFilter, newDataSample);
;*
;*    The structure for the filter nodes and filter coefficients should be
;*    as follows:
;*      
;*    struct IIR_filter{
;*	    int filterNodesX[FILTER_ORDER];			    //memory nodes required to store x(n-1), x(n-2)
;*	    int filterNodesY[FILTER_ORDER];			    //memory nodes required to store y(n-1), y(n-2)
;*	    int filterCoefficientsB[(FILTER_ORDER)+1];  //filter coefficients B0, B1, B2
;*	    int filterCoefficientsA[FILTER_ORDER];      //filter coefficients A1, A2
;*	    } myFilter = {0, 0, 0, 0, B0, B1, B2, A1, A2}; 
;*
;*    The filter nodes should be initialized prior to the first call of the 
;*    filter function and the filter coefficients should be scaled to use
;*    signed 12-bit resolution (max)
;*      
;* Registers usage:
;*	  r0-4, r16-23, Z (all scratch/volatile registers)
;*
;* Memory usage for variables and constants:
;*	  8 bytes SRAM for filter nodes (filter memory)
;*    10 bytes SRAM for filter coefficients
;*
;* Stats:
;*	  INIT:  Depending on compiler settings (223 cycles)
;*	  FILTER:   92 instructions;  116 cycles (excl. ret)
;*****************************************************
	NAME	assembly(16)
	PUBLIC	IIR2
	RSEG	CODE

;ZERO register (used to add carry flag)
#define ZERO	r2

;Accumulator - 24bit
#define AC0	r3		
#define AC1	r16
#define AC2	r17

;New data sample
#define NDATAL r18
#define NDATAH r19

;Data sample multiply registers (used in multiplication)
#define DATAL	r20
#define DATAH	r21

;Filter coefficient (used in multiplication)
#define COEFL	r22
#define COEFH	r23

; Filter nodes offset (relatively to the filter struct)
#define X1	0*2
#define X2	1*2
#define Y1	2*2
#define Y2	3*2

;Filter coefficients offset (relatively to the filter struct)
#define B0	4*2
#define B1	5*2
#define B2	6*2
#define A1	7*2
#define A2	8*2

;**************************************************
;* MACROS
;**************************************************
LOAD_NODE MACRO
	ldd	  DATAL,Z+\1		; Load low byte of node 
	ldd	  DATAH,Z+\1+1		; Load high byte of node
    ENDM

UPDATE_NODE MACRO
	std	  Z+\1, DATAL		; Update low byte of node to prepare next filter run
	std	  Z+\1+1, DATAH		; Update high byte of node to prepare next filter run
    ENDM

LOAD_COEF MACRO
	ldd	  COEFL,Z+\1		; Load low byte of node 
	ldd	  COEFH,Z+\1+1		; Load high byte of node
    ENDM

MUL_MOV_24 MACRO
	muls  COEFH, DATAH		; Signed multiply, coefficient high byte and data high byte
	mov	  AC2, r0			; Copy low byte into accumulator byte 2 (sign bit automatically correct)

	mul	  COEFL, DATAL		; Unsigned multiply, coefficient low byte and data low byte
	mov	  AC0, r0			; Mover result into accumulator byte 0:1
	mov	  AC1, r1
	
	mulsu COEFH, DATAL		; Signed-unsigned multiply, coefficient high byte and data low byte
	add	  AC1, r0			; Add low byte of result to accumulator byte 1
	adc	  AC2, r1			; Add with carry high byte of result to accumulator byte 2

	mulsu DATAH, COEFL		; Signed-unsigned multiply, data high byte and coefficient low byte
	add	  AC1, r0			; Add low byte of result to accumulator byte 1
	adc	  AC2, r1			; Add with carry high byte of result to accumulator byte 2
    ENDM

SMAC24 MACRO
	muls  COEFH, DATAH		; Signed multiply, coefficient high byte and data high byte
	add	  AC2, r0			; Copy low byte into accumulator byte 2

	mul	  COEFL, DATAL		; Unsigned multiply, coefficient low byte and data low byte
	add	  AC0, r0			; Add low byte of result to accumulator byte 0
	adc	  AC1, r1			; Add with carry high byte of result to accumulator byte 1
	adc	  AC2, ZERO			; Add carry to accumulator byte 2

	mulsu COEFH, DATAL		; Signed-unsigned multiply, coefficient high byte and data low byte
	add	  AC1, r0			; Add low byte of result to accumulator byte 1
	adc	  AC2, r1			; Add with carry high byte of result to accumulator byte 2

	mulsu DATAH, COEFL		; Signed-unsigned multiply, data high byte and coefficient low byte 
	add	  AC1, r0			; Add low byte of result to accumulator byte 1
	adc	  AC2, r1			; Add with carry high byte of result to accumulator byte 2
    ENDM

;*****************************************************
; IIR FILTER function
;*****************************************************
IIR2:
	clr	ZERO				; Clear ZERO register 
	movw	ZL, r16			; Move Struct pointer to the Z-pointer (r30:r31)
	
;B2*x[n-2]
	LOAD_COEF B2
	LOAD_NODE X2
	MUL_MOV_24

;B1*x[n-1]
	LOAD_COEF B1
	LOAD_NODE X1
	UPDATE_NODE X2
	SMAC24
	
;B0*x[n]
	LOAD_COEF B0
	movw	DATAL, NDATAL		; Load new sample into data multiply register
	UPDATE_NODE X1
	SMAC24

;A2*y[n-2]
	LOAD_COEF A2
	LOAD_NODE Y2
	SMAC24
	
;A1*y[n-1]
	LOAD_COEF A1
	LOAD_NODE Y1
	UPDATE_NODE Y2
	SMAC24

;Due to coefficient scaling (gain factor 2^11) the output requires "unscaling"
	asr AC2			; Scaling to gain factor 2^10
	ror	AC1			; --

	asr AC2			; Scaling to gain factor 2^9
	ror	AC1			; --

	asr AC2			; Scaling to gain factor 2^8
	ror	AC1			; --
	
;Updating y[n-1] node
;(By copying result from AC1:2 instead of AC0:1 the gain factor becomes 1 (2^0))
	std	Z+Y1, AC1	; Update low byte of y[n-1] node to prepare next filter run 
	std	Z+Y1+1, AC2	; Update high byte of y[n-1] node to prepare next filter run 
	
;Return value stored in accumulator AC2 and AC1
	ret
	END

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -