I decided to try and make the assembler less ugly first by using indirect addressing to access the Period[8] array but it is no faster than my laborious method and this one will only run on an 18F4550 due to the use of the helpful POSTINC0 operator representing INDF(0) with a post Increment:
Code:_xPULSIN MOVLW 0xFF MOVWF _pCount MOVLW 0x0F MOVWF _pCount + 1 ;pCount = $FFF = 4095 MOVLW _Mask MOVWF _k ;k = Mask CLRF _sample ;clear sample flag cycleX MOVF _mPort, W ;Sample the Port ANDWF _k, W MOVWF _j ;j = Port AND Mask MOVLW High(_Period) ;Set up FSR to point to Period[0] MOVWF FSR0H MOVLW Low(_Period) MOVWF FSR0L MOVLW 1 MOVWF _i ;Bit Marker = 00000001 CheckJ RRCF _j BTFSS STATUS,C ;Bit i Set GOTO BCLR INCFSZ POSTINC0 ;Yes - Period[i] = Period[i]+1 GOTO NoRoll INFSNZ POSTINC0 ;=Inc and always skip - Period.Hi never Zero NoRoll MOVF POSTINC0,F ;=NOP except inc FSR MOVF _i,W IORWF _sample,F ;Now sampling bit i Nexti RLCF _i ;i = i<<1 BTFSS STATUS,C ;Carry set = 8 rotations? GOTO CheckJ ;No - Loop round MOVF _k,F ;Is Mask = 0? BTFSC STATUS,Z RETURN ;Yes - Finished all samples DecCount DECFSZ _pCount ;No - Update counter GOTO cycleX DECFSZ _pCount + 1 GOTO cycleX RETURN ;Countdown = 0 - Timeout? BCLR MOVF POSTINC0,F ;=NOP except inc FSR MOVF POSTINC0,F ;=NOP except inc FSR MOVF _i,W ANDWF _sample,W ;Pulse low - already sampling? BTFSC STATUS,Z GOTO Nexti ;No - do nothing MOVF _i,W XORWF _k,F ;Yes - Clear Bit in Mask GOTO Nexti ;----------------------------------------------------------------------------- _PeriodZ MOVLW High(_Period) ;Set Period[0 to 7] = 0 MOVWF FSR0H MOVLW Low(_Period) MOVWF FSR0L CLRF _i ; i = 0 (counter) clr CLRF POSTINC0 ;CLRF INDF0 then inc FSR0 INCF _i BTFSS _i,4 ; i.4 set = 16 GOTO clr RETURN




Bookmarks