bonjour,
j'ai essayé de programmer un pic 16f84 en mode 4-bit pour qu'il affiche un message s sur l'ecran mais en vain. Quand je branche il y a une ligne de carrés noirs. Le code se compile bien mais quand je fais une simulation avec Mplab sim me donne l'erreur suivante :
CORE-E0002: Stack under flow error occurred from instruction at 0x00000b
Voici mon code :
;**************************************************
;*
;* LCD PIC 2x16 caractères en mode 4-bit
;* HDD 44780 et PIC 16F84a
;* Par Dan, 17 février 2005
;*
;**************************************************
LIST p=16F84; Défintition du processeur
#include <P16F84a.inc>; Variables du processeur
;**************************************************
;*
;* Configuration
;*
;* CP OFF, lecture du pic autorisée
;* WDT OFF, pas de Watch Dog
;* PWRTE_ON, Timer reset sur power on en service
;* HS_OSC, Oscillateur High Speed à 4 Mhz
;*
;**************************************************
__CONFIG _CP_OFF & _WDT_OFF & _PWRTE_ON & _HS_OSC
;**************************************************
;*
;* Définitions
;*
;**************************************************
#DEFINE LCD_RS PORTA,0; On met RS sur A0
#DEFINE LCD_EN PORTA,1; On met Enable sur A1
;**************************************************
;*
;* Déclaration des variables
;*
;**************************************************
CBLOCK 0x00C; Début de la zone de variables
cmpt1 : 1; Variable boucle 1 de temporisation
cmpt2 : 1; Variable boucle 2 de temporisation
writetmp : 1; Variable temporaire d'écriture
ENDC; Fin de la zone de variables
;**************************************************
;*
;* Programme
;*
;**************************************************
call initpic
call initlcd
call ecrire
;**************************************************
;*
;* Initialisation du PIC 16F84a
;*
;**************************************************
initpic
bsf STATUS, RP0; On passe en bank 1
movlw 0x00; On met 0
movwf TRISB; Donc tout le portA est en sortie
movlw 0x00; On met 0
movwf TRISA; tout le portB est en sortie
movlw 0x00;
movwf OPTION_REG
bcf STATUS, RP0; On passe en bank 0
RETURN
;**************************************************
;*
;* Initialisation du LCD HD 44780
;*
;**************************************************
initlcd
movlw D'200'; On mutliplie par 200
call tempo ; pour avoir 20mS
movlw B'00110000'
; Il y a 8 bit ici mais les 4 premiers seront ignorés
; car ils ne sont pas connectés
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw D'41'; On mutliplie par 5
call tempo ; pour avoir 5mS
movlw B'00110000'; Donnée d'initialisation
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw D'2'; On mutliplie par 2
call tempo ; pour avoir 200uS
movlw B'00110000'; Donnée d'initialisation
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'00100000'; Mode 4-bit
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'00100000'; Mode 4-bit (deuxiéme coup)
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'10000000'; Matrice caractéres 5x8
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'00000000'; Ecran OFF/On
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'00010000'; ClearScreen
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'00000000';
movlw PORTB; On écrit sur le port B
call checklcd; On valide
movlw B'01000000';
movlw PORTB; On écrit sur le port B
call checklcd; On valide
RETURN
;**************************************************
;*
;* Temporisation de 101uS
;*
;**************************************************
tempo
;movwf cmpt2
; Ceci est l'argument. On peut multiplier
; par un entier pour obtenir le temps voulu
boucle2
;movlw 0x20; On place 32 ( 0x20 ) dans w
;movwf cmpt1; On met w dans cmpt1
boucle1
;decfsz cmpt1, f; 31 + 2 cycles (saut 2 cycles)
;goto boucle1; 32x2 cycles
;decfsz cmpt2, f; On decrémente de 1 cmpt2
;goto boucle2; Fin des 101uS on boucle2
RETURN; 2 cycles
;**************************************************
;*
;* Validation des données sur le LCD HD 44780
;*
;**************************************************
checklcd; On cherche à se faire valider auprés du LCD
movlw D'1'; On mutliplie par 1
call tempo ; pour avoir 100uS
bsf LCD_EN; On valide en mettant 1 sur E (Pin Enable)
nop
nop
nop; 450ns délai à respecter
bcf LCD_EN; On valide en mettant 0 sur E (Pin Enable)
movlw D'1'; On mutliplie par 1
call tempo ; pour avoir 100uS
RETURN
;**************************************************
;*
;* Ecrire sur le LCD HD 44780
;*
;**************************************************
write
movwf writetmp; On copie le caractère dans writetmp
andlw 0xF0
andlw D'1'
movwf PORTB
swapf writetmp, w
andlw 0xF0
andlw D'1'
movwf PORTB
RETURN
;**************************************************
;*
;* Ecrire
;*
;**************************************************
ecrire
movlw 0x54
bsf LCD_RS
call write
RETURN
END