Hi everyone , i have a mini project with pic 16f877. i want to control the speed and direction of a stepper motor using PWM module in assembly language.i searched in the forum and i found some program but i face a problem : i read a variable resistor via AN0 and based on this value i configure my PWM duty cycle (high level). everything works just fine in Mplab but the CCP1/RC2 pin stay in 0 level...
Any help please :
LIST p=16F877
#include <p16f877.inc>
__CONFIG _CP_OFF & _DEBUG_OFF & _WRT_ENABLE_OFF & _CPD_OFF & _LVP_OFF & _BODEN_OFF & _PWRTE_ON & _WDT_OFF & _HS_OSC
;-----------------------ASSIGNATION--------------------------------
OPTIONVAL EQU B'10000000' ;B'10000111'
INTCONVAL EQU B'01000000'
DIRPORTA EQU B'00000001' ; AN0 =entree, le rest sont des sorties
DIRPORTC EQU B'00000000'
DIRPORTB EQU B'00000000'
PIE1VAL EQU B'01000010'
T2CONVAL EQU B'00000000'
CCP1CONVAL EQU B'00001100'
ADCON0VAL EQU B'10000000'
ADCON1VAL EQU B'00001110'
tempoval EQU D'35'
PR2VAL EQU D'255'
;-----------------------MACRO---------------------------------
BANK0 macro ; passer en banque 0
bcf STATUS,RP0
bcf STATUS,RP1
endm
BANK1 macro ;passer en banque 1
bsf STATUS,RP0
bcf STATUS,RP1
endm
BANK2 macro ;passer en banque 2
bcf STATUS,RP0
bsf STATUS,RP1
endm
BANK3 macro ;passer en banque 3
bsf STATUS,RP0
bsf STATUS,RP1
endm
;-----------------------VARIABLES-------------------
;---------zone de BANK0
CBLOCK 0x20
ENDC
;--------zone commune----------------------------
CBLOCK 0x70
tempo : 1
WAIT1:1
WAIT2:1
WAIT3:1
ENDC
;-----------------------DEMARRAGE DU RESET------------
org 0x000
goto init
;----------------------INTERRUPTIONS------------------
org 0x0004
bsf STATUS,RP0
btfss PIE1,ADIE ;sauter si l'int AD est autorise
goto int_test1 ;no! aller au teste suivant
bcf STATUS,RP0
btfsc PIR1,ADIF ;sauter si le flage est 0
call int_AD ;flag=0! traiter cette interruption
goto int_test1
;-------------interruption timer2-----------
int_test1
bsf STATUS,RP0
btfss PIE1,TMR2IE ;sauter si l'int TMR2 est autorisee
goto restoreg ;no fin d'int
bcf STATUS,RP0 ;banque 0
btfsc PIR1,TMR2IF ;flag positione ! traiter l'int
call int_TMR2
goto restoreg
restoreg
retfie ; return from interrupt
;---------interruption timer2------------
int_TMR2
bcf PIR1,TMR2IF ;effacer le flage de timer2
bsf ADCON0,ADON ;lancer l'aquisition AD
bsf PORTC,5
wait20us ;routine de 20 us
;movf tempo,f
decfsz tempo,f
goto wait20us
movlw tempoval
movwf tempo
bsf ADCON0,GO ;lancer la conversion AD
return
;----------interruption convAD-----------
int_AD
bsf PORTC,5
bcf ADCON0,ADON
bcf PIR1,ADIF
movf ADRESH,w
movwf CCPR1L
bsf STATUS,RP0 ;banque 1
btfss ADRESL,7
goto next_test
bcf STATUS,RP0
bsf CCP1CON,CCP1X
next_test
bsf STATUS,RP0
btfss ADRESL,6
return
bcf STATUS,RP0
bsf CCP1CON,CCP1Y
return
;---------------------INITIALISATION---------------------------
init
BANK0
clrf PORTA ;effacer porta
clrf PORTC ;effacer portc
CLRF PORTB
movlw INTCONVAL ;autorisation de l'int periphirique
movwf INTCON
movlw T2CONVAL ;prediviseur=16,
movwf T2CON
movlw CCP1CONVAL ; en mode PWM
movwf CCP1CON
movlw ADCON0VAL ;frequence de osc =32
movwf ADCON0
clrf ADRESH
bsf STATUS,RP0 ; sélectionner banque1
clrf ADRESL
movlw OPTIONVAL
movwf OPTION_REG
movlw DIRPORTA ;AN0 entree
movwf TRISA
movlw DIRPORTC ;CCP1/RC2 sortie
movwf TRISC
MOVLW DIRPORTB
MOVWF TRISB
movlw ADCON1VAL ;justification a gauche
movwf ADCON1 ;1 entree analogique
movlw PR2VAL ;charger PR2 avec H'FF'
movwf PR2
movlw PIE1VAL ;masque int AD=1,masque int TMR2=1
movwf PIE1
bcf STATUS,RP0 ;banque 0
clrf TMR2 ;effacer timer 2
clrf PIR1 ;effacer flags
bsf INTCON,GIE ;valider interruptions
movlw tempoval ;pour la routine de 20 us
movwf tempo
bsf T2CON,TMR2ON ;demarer timer2
goto start
;*** TEMPO 20MS ***
TEMPO3 ;TEMPO DE 500µS
MOVLW D'165'
MOVWF WAIT1
T1
DECFSZ WAIT1,f
GOTO T1
NOP
RETURN
TEMPO2 ;TEMPO DE 20MS
MOVLW D'250'
MOVWF WAIT2
T2
CALL TEMPO3
DECFSZ WAIT2,f
GOTO T2
NOP
RETURN
TEMPO ;TEMPO DE 20MS
MOVLW D'50'
MOVWF WAIT3
T3
CALL TEMPO2
DECFSZ WAIT3,f
GOTO T3
NOP
RETURN
;=================================== SENS NEGATIF ============================================
NEGATIF
CLRF PORTB
movlw b'00000100' ; position 0
movwf PORTB
call TEMPO
movlw b'00000001' ; position -90
movwf PORTB
call TEMPO
movlw b'00001000' ; position -180
movwf PORTB
call TEMPO
movlw b'00000010' ; position -270
movwf PORTB
call TEMPO
RETURN
;-----------------------program principale----------------------------
start
goto start
END
Any help please :
LIST p=16F877
#include <p16f877.inc>
__CONFIG _CP_OFF & _DEBUG_OFF & _WRT_ENABLE_OFF & _CPD_OFF & _LVP_OFF & _BODEN_OFF & _PWRTE_ON & _WDT_OFF & _HS_OSC
;-----------------------ASSIGNATION--------------------------------
OPTIONVAL EQU B'10000000' ;B'10000111'
INTCONVAL EQU B'01000000'
DIRPORTA EQU B'00000001' ; AN0 =entree, le rest sont des sorties
DIRPORTC EQU B'00000000'
DIRPORTB EQU B'00000000'
PIE1VAL EQU B'01000010'
T2CONVAL EQU B'00000000'
CCP1CONVAL EQU B'00001100'
ADCON0VAL EQU B'10000000'
ADCON1VAL EQU B'00001110'
tempoval EQU D'35'
PR2VAL EQU D'255'
;-----------------------MACRO---------------------------------
BANK0 macro ; passer en banque 0
bcf STATUS,RP0
bcf STATUS,RP1
endm
BANK1 macro ;passer en banque 1
bsf STATUS,RP0
bcf STATUS,RP1
endm
BANK2 macro ;passer en banque 2
bcf STATUS,RP0
bsf STATUS,RP1
endm
BANK3 macro ;passer en banque 3
bsf STATUS,RP0
bsf STATUS,RP1
endm
;-----------------------VARIABLES-------------------
;---------zone de BANK0
CBLOCK 0x20
ENDC
;--------zone commune----------------------------
CBLOCK 0x70
tempo : 1
WAIT1:1
WAIT2:1
WAIT3:1
ENDC
;-----------------------DEMARRAGE DU RESET------------
org 0x000
goto init
;----------------------INTERRUPTIONS------------------
org 0x0004
bsf STATUS,RP0
btfss PIE1,ADIE ;sauter si l'int AD est autorise
goto int_test1 ;no! aller au teste suivant
bcf STATUS,RP0
btfsc PIR1,ADIF ;sauter si le flage est 0
call int_AD ;flag=0! traiter cette interruption
goto int_test1
;-------------interruption timer2-----------
int_test1
bsf STATUS,RP0
btfss PIE1,TMR2IE ;sauter si l'int TMR2 est autorisee
goto restoreg ;no fin d'int
bcf STATUS,RP0 ;banque 0
btfsc PIR1,TMR2IF ;flag positione ! traiter l'int
call int_TMR2
goto restoreg
restoreg
retfie ; return from interrupt
;---------interruption timer2------------
int_TMR2
bcf PIR1,TMR2IF ;effacer le flage de timer2
bsf ADCON0,ADON ;lancer l'aquisition AD
bsf PORTC,5
wait20us ;routine de 20 us
;movf tempo,f
decfsz tempo,f
goto wait20us
movlw tempoval
movwf tempo
bsf ADCON0,GO ;lancer la conversion AD
return
;----------interruption convAD-----------
int_AD
bsf PORTC,5
bcf ADCON0,ADON
bcf PIR1,ADIF
movf ADRESH,w
movwf CCPR1L
bsf STATUS,RP0 ;banque 1
btfss ADRESL,7
goto next_test
bcf STATUS,RP0
bsf CCP1CON,CCP1X
next_test
bsf STATUS,RP0
btfss ADRESL,6
return
bcf STATUS,RP0
bsf CCP1CON,CCP1Y
return
;---------------------INITIALISATION---------------------------
init
BANK0
clrf PORTA ;effacer porta
clrf PORTC ;effacer portc
CLRF PORTB
movlw INTCONVAL ;autorisation de l'int periphirique
movwf INTCON
movlw T2CONVAL ;prediviseur=16,
movwf T2CON
movlw CCP1CONVAL ; en mode PWM
movwf CCP1CON
movlw ADCON0VAL ;frequence de osc =32
movwf ADCON0
clrf ADRESH
bsf STATUS,RP0 ; sélectionner banque1
clrf ADRESL
movlw OPTIONVAL
movwf OPTION_REG
movlw DIRPORTA ;AN0 entree
movwf TRISA
movlw DIRPORTC ;CCP1/RC2 sortie
movwf TRISC
MOVLW DIRPORTB
MOVWF TRISB
movlw ADCON1VAL ;justification a gauche
movwf ADCON1 ;1 entree analogique
movlw PR2VAL ;charger PR2 avec H'FF'
movwf PR2
movlw PIE1VAL ;masque int AD=1,masque int TMR2=1
movwf PIE1
bcf STATUS,RP0 ;banque 0
clrf TMR2 ;effacer timer 2
clrf PIR1 ;effacer flags
bsf INTCON,GIE ;valider interruptions
movlw tempoval ;pour la routine de 20 us
movwf tempo
bsf T2CON,TMR2ON ;demarer timer2
goto start
;*** TEMPO 20MS ***
TEMPO3 ;TEMPO DE 500µS
MOVLW D'165'
MOVWF WAIT1
T1
DECFSZ WAIT1,f
GOTO T1
NOP
RETURN
TEMPO2 ;TEMPO DE 20MS
MOVLW D'250'
MOVWF WAIT2
T2
CALL TEMPO3
DECFSZ WAIT2,f
GOTO T2
NOP
RETURN
TEMPO ;TEMPO DE 20MS
MOVLW D'50'
MOVWF WAIT3
T3
CALL TEMPO2
DECFSZ WAIT3,f
GOTO T3
NOP
RETURN
;=================================== SENS NEGATIF ============================================
NEGATIF
CLRF PORTB
movlw b'00000100' ; position 0
movwf PORTB
call TEMPO
movlw b'00000001' ; position -90
movwf PORTB
call TEMPO
movlw b'00001000' ; position -180
movwf PORTB
call TEMPO
movlw b'00000010' ; position -270
movwf PORTB
call TEMPO
RETURN
;-----------------------program principale----------------------------
start
goto start
END