; passage au 18F258 sans lecture ADC ; 17/1/2010 rajout lecture clavier (et affichage) A SUIVRE... ; 18F252_3ANA_rs232_ok_091115.asm revu Bcd_temp routines et tempo variables en bank1 ; SIMUL: attention aux variables commencant par un chiffre ! ; SIMUL: attention aux lignes vides => decalent le pointeur en simulation ASM ; 18F252 avec bootloader: usage de Tinybootloader C:\Mplab8\tinybld195.exe pour charger l' executable Hex ; Connected to \\.\COM2 at 19200 Q=10Mhz ; HEX: 2 min old, INHX32,18Fcode, total=2366 bytes. ; Searching for PIC ... ; Found:18F 252o/452o ; WRITE OK at 19:48, time:2.413 sec ;---------------------------------------------------------------------- ;Release build of project `C:\Mplab8\_Mesprojets\_18Fxx\tst18F252a.mcp' started. ;Language tool versions: MPASMWIN.exe v5.34, mplink.exe v4.34 ;Mon Nov 23 20:56:07 2009 ;---------------------------------------------------------------------- ;Clean: Deleting intermediary and output files. ;Clean: Deleted file "C:\Mplab8\_Mesprojets\_18Fxx\18F252_3ANA_IR_rs232.o". ;Clean: Deleted file "C:\Mplab8\_Mesprojets\_18Fxx\18F252_3ANA_IR_rs232.err". ;Clean: Deleted file "C:\Mplab8\_Mesprojets\_18Fxx\18F252_3ANA_IR_rs232.hex". ;Clean: Deleted file "C:\Mplab8\_Mesprojets\_18Fxx\18F252_3ANA_IR_rs232.lst". ;Clean: Deleted file "C:\MPLAB8\_Mesprojets\18F252_3ANA_IR_rs232.cof". ;Clean: Done. ;Executing: "C:\Program Files\Microchip\MPASM Suite\MPASMWIN.exe" /q /p18F252 ;"18F252_3ANA_IR_rs232.asm" /l"18F252_3ANA_IR_rs232.lst" /e"18F252_3ANA_IR_rs232.err" ;Message[301] C:\MPLAB8\_MESPROJETS\_18FXX\18F252_3ANA_IR_RS232.ASM 1780 : ; MESSAGE: (Delta adresse Msg3 et Msg2: 202) ; MESSAGE: (Delta adresse Msg5 et Msg4: 24) ; MESSAGE: (Fin ;de programme at : 5150) ; MESSAGE: (Max ;programme at : 16128) ; MESSAGE: ;(Percent_use= : 31%) ;Executing: "C:\Program Files\Microchip\MPASM Suite\mplink.exe" /p18F252 /l"C:\Program ;Files\Microchip\MPLAB ASM30 Suite\lib" /k"C:\Mplab8\MPASM Suite" ;"_18Fxx\18F252_3ANA_IR_rs232.o" /z__MPLAB_BUILD=1 /o"18F252_3ANA_IR_rs232.cof" ;/M"18F252_3ANA_IR_rs232.map" /W /x ;MPLINK 4.34, Linker ;Copyright (c) 2009 Microchip Technology Inc. ;Errors : 0 ;Loaded C:\MPLAB8\_Mesprojets\18F252_3ANA_IR_rs232.cof. ;----------------------------- ;Release build of project `C:\Mplab8\_Mesprojets\_18Fxx\tst18F252a.mcp' succeeded. ;Language tool versions: MPASMWIN.exe v5.34, mplink.exe v4.34 ;Mon Nov 23 20:56:11 2009 ;----------------------------- ;BUILD SUCCEEDED ;---------------------------------------------------------------------- ; ATTENTION PB de config ; The new 18F config directive without the double underscore only works if you use it in the .inc file. ; They will not work when inserted directly in your code. ; If you comment out 18F config settings in the default PBP .inc file, then insert them directly in your ; code, you'll have to use the older __config directive. ;----------------------------------------- ; programme de test ; fonction UART … 19200bds 8bits datas ; PIC18F252 en DIP28 narrow ; pin 23 RB2 -- led1 blanche - R 390 -- +5V ; pin 22 RB1 -- led2 blanche - R 390 -- +5V ; pin 21 RB0 -- interrutpt IR sensor ; pin17 RC6 Tx ----vert ---- 3 de DS275 5 -- RS232 --> Ecran ; pin18 RC7 Rx --- blc/vert--- 1 de DS275 7 -- RS232 <-- Clavier ; pin 9 et 10 Quartz Q=20MHz ; pin 8 VSS ;acquisition de 3 mesures ANA ; PORTA,5 (pin 7) <----------- Entree ANALOGIQUE 4 ; PORTA,4 (pin 6) libre I/O ; PORTA,3 (pin 5) ---------> +REF 5.00V => 1023 ; PORTA,2 (pin 4) <--------- -REF 0.00V => 0000 ; PORTA,1 (pin 3) <----------- Entree ANALOGIQUE 1 ; PORTA,0 (pin 2) <----------- Entree ANALOGIQUE 0 ;************************************************* Title "Marantz IRC5 decodage." ; Quartz 10Mhz voir #define FOSC D'10000000' ; bootloader installe en fond de memeoire LIST p = 18F258, r = dec, w = -311, f = inhx32 , n=62 , c=100 #include "../common/P18F258_.inc" RADIX DEC ; CONFIG faite par MPLAB !!! ;30001 22 ;30002 0C ;30003 0E ;30005 01 ;30006 80 ;30008 0F ;30009 C0 ;3000A 0F ;3000B E0 ;3000C 0F ;3000D 40 CONFIG OSC=HS ,OSCS=OFF CONFIG BOR=OFF CONFIG WDT=OFF CONFIG STVR=OFF, LVP=OFF, DEBUG=OFF CONFIG CPB=OFF ; boot protect off CONFIG CP0=OFF,CP1=OFF,CP2=OFF,CP3=OFF CONFIG CPD=OFF ; 8000H -> 32Kb -> 16Kmot -256 mots = 16128 mots -> 3F00 #DEFINE _MAXFLASH 0x3F00 ; -------------------- ; USER RAM DEFINITIONS ; -------------------- ;=========== declarations de variables ========= cblock 0x00 ; en bank0 buff Buffer_Texte :.32 ptr1 : 1 ; pointeur temporaire 1 ptr2 : 1 ; pointeur temporaire 2 octemp : 1 ; sauvegarde temporaire SEC MIN HEURE JourSem Jour Mois Annee CtrlReg conf ; I2C variables ADDR DEV_DS1307 ; adresse DS1307 RTC DEV_1624 ; Adresse DS1624 mesure Tø DEV_PCF8574 ; O_BYTE I_BYTE _N _N0 _N1 _Cpt1 _Cpt2 _RsByte _Temp1 _Temp2 _Diz_IT Nbl ; compteur de ligne caractere addwrite Voie IntervalSec ; w_temp ; Sauvegarde registre W status_temp ; sauvegarde registre STATUS FSR0L_temp ; sauvegarde FSR (si indirect en interrupt) FSR0H_temp ; sauvegarde FSR (si indirect en interrupt) BSR_temp time ; bufinptr ; pointeur sur caractere courant buffer entree bufoutptr ; pointeur sur caractere courant buffer sortie local1 ; variable locale pour interruptions flags ; 8 flags divers ; b0 : parit‚ calculee ; b1 : erreur de parite ; b2 : erreur de frame ; b3 : erreur overflow ; ;------------------ ; IR RC5 variables COUNT0 ; compteur TOGGLE ; The RC5 Toggle bit SYSTEM ; The RC5 System word COMND ; The RC5 Command word MZDATA ; The RC5 extra Data word BIT_COUNT ; Counter for incoming bits BYTE_COUNT ; Counter for buffer bytes TEMP ; Used by PARSE to hold the 2-bit pattern SERIAL_BUF ; Buffer for incoming bitstream SERIAL_2 SERIAL_3 SERIAL_4 SERIAL_5 SERIAL_6 FIELD PARSE_FLAGS ; DECODE returns its data in this MZ_FLAG ; Set if there is an extra data word ;------------ reserve : .32 ; du RAB ICI !!!!! ;----------- ; Drapeaux ; Drapeaux de 8 bits … usage multiple ;7 signe 1=negatif ;6 elligible =1 ;5 si=1 => affichage 00000 … 999999 sinon si =0 affichage XXX.XX ;4 si=1 rajoute Nb de ligne ;3 ;2 ;1 ;0 endc LastBank0 EQU Drapeaux IF ( LastBank0 >= 0x7F ) ERROR "Attention debordement zone RAM bank0" ENDIF ;#DEFINE debuging ;--------------------------------------------- #DEFINE PARITE flags,0 ; parit‚ calculee #DEFINE ER_PAR flags,1 ; erreur de parite #DEFINE ER_FR flags,2 ; erreur de frame #DEFINE ER_OV flags,3 ; erreur d'overflow #define FOSC D'10000000' ; quartz 20MHZ ;#define TIMEOUT D'10' ; <<< uniquement pour TIME - temps = [0.1s] ;---------------------------------------------- ; variables gestion PWM IF FOSC > D'10240000' #define T1PS 8 #define T1SU 0x31 ELSE IF FOSC > D'5120000' #define T1PS 4 #define T1SU 0x21 ELSE IF FOSC > D'2560000' #define T1PS 2 #define T1SU 0x11 ELSE #define T1PS 1 #define T1SU 0x01 ENDIF ENDIF ENDIF TIMER EQU (D'65538'-(FOSC/(D'10'*4*T1PS))) ;*********************** ; VARIABLES BANQUE 1 * ;*********************** ; Zone de 128 bytes CBLOCK 0x100 ; Debut de la zone (0x100 … 0x17F) Cpt10 ; Bcd Mcount btmp btmp1 dixmil mille cent dix uno value ; variables 16 bits SommeTamb :1 ; LSB puis MSB MesAn0 :2 MesAn1 :2 MesAn4 :2 valx :2 val1 :2 ; val1=LOW Val1+1=HIGH val2 :2 val3 :2 reste :2 result :2 count1 ;delay routines count2 ;delay routines count3 ;delay routines endc ;*********************** ; VARIABLES BANQUE 2 * ;*********************** ; Zone de 128 bytes CBLOCK 0x200 ; Debut de la zone (0x200 … 0x27F) bufin : D'96' ; zone de stockage des donnees entrees banque2spare : D'16' ENDC ; Fin de la zone ;*********************** ; VARIABLES BANQUE 3 * ;*********************** ; Zone de 128 bytes ; ---------------- CBLOCK 0x300 ; Debut de la zone (0x300 … 0x37F) banque3spare :D'16' bufout : D'96' ; message … envoyer ENDC ;=========== fin declaration de variables =========== ; telecommande MARANTZ RC5 200SR #define ARRET_ 41 #define LECTURE_ 43 #define TREBSUP_ 24 #define TREBDWN_ 25 #define BASSUP_ 22 #define BASSDOWN_ 23 #define VOLUP_ 16 #define VOLDOWN_ 17 #define MENUON_ 82 #define MENUOFF_ 83 #define MUTE_ 13 #define OSD_ 15 #define TV_ 63 #define UP_ 28 #define DOWN_ 29 #define LEFT_ 44 #define RIGHT_ 43 #define OK_ 87 #define BAUD D'19200' ; <<< vitesse du port serie [bit/sec] #define BAUD_ERROR D'4'; <<< erreur de vitesse [%] #define ProgHI 0x1FFF #define LoaderTop ProgHI-(ICD_DEBUG*0x100) ; adresse haute du bootloader #define DIVIDER (FOSC/(D'16' * BAUD))-1 #define Analog0 PORTA,0 ;pin2 #define RETENUE Drapeaux,7 #define ELLIGIBLE Drapeaux,6 #define I2C_SDA PORTB,7 ;RB7 (pin 28) ---> output-->SDA #define I2C_SCL PORTB,6 ;RB6 (pin 27) <--in/out---> SCL #define LED1 PORTB,1 #define LED2 PORTB,2 #define LED3 PORTA,4 #define IR_Sensor PORTB,0 CONSTANT TABUL =.9 ; caractere ascii tabulation Buffer_MAJ EQU SEC BRGVAL EQU D'12' ; pour un debit de 38400 bauds en mode high-speed ONE EQU B'00000001' ; pour IR RC5 ZERO EQU B'00000010' ; pour IR RC5 ; ;************************************************ ; Reset Vector org 00000h nop ; strap bootloader nop goto start ;********************************** ; Interrupt vector org 00008h goto IntVectorHi ;********************************** ; Interrupt vector org 00018h ; Interrupt vector goto IntVectorLow ;********************************** IntVectorHi ;-------------------------------- ; est-ce une interrupt Haute Priorite sur RB0 ;-------------------------------- ; movwf w_temp ; sauver registre W ; swapf STATUS , w ; swap status avec resultat dans w ; movwf status_temp ; sauver status swapp movf FSR0L , w ,0 ; charger FSR movwf FSR0L_temp,0 ; sauvegarder FSR movf FSR0H , w ,0 ; charger FSR movwf FSR0H_temp,0 ; sauvegarder FSR movf BSR , w,0 ; charger PCLATH movwf BSR_temp,0 ; le sauver BTFSS INTCON,INT0IF goto IsnotRB0 Rb0_int bcf INTCON,INT0IF ; raz flag interrupt Rb0 bcf INTCON,INT0IE ; raz autorise int RB0 call Read_IR ; call MsgFlash5 ; pour debugging IsnotRB0 movf BSR_temp ,w,0 ; recharger pointeur de BANK movwf BSR,0 ; le restaurer movf FSR0H_temp,w,0 ; charger FSR sauv‚ movwf FSR0H,0 ; restaurer FSR movf FSR0L_temp,w,0 ; charger FSR sauv‚ movwf FSR0L ,0 ; restaurer FSR ; swapf status_temp,w ; swap ancien status, r‚sultat ; movwf STATUS ; restaurer status ; swapf w_temp,f ; Inversion L et H de l'ancien sans modifier Z ; swapf w_temp,w ; Reinversion de L et H => W restaure sans modifier le status retfie ; FAST ;*********************************** org 0100h start movlb 0x01 ; bank1 BSF LED1 call delay_1S BCF LED1 clrf Drapeaux clrf valx,1 clrf val1,1 movlw 0 movwf WDTCON ;------------------------------------------ ; Configuration Voie ANALOGIQUE et logiques ;right justified, max.ref = sur RA3 pin4 et min.ref= sur RA2 pin 3 ; voie analogique AN0 pin RA0 sur Pin 2 ; voie analogique AN1 pin RA1 sur Pin 3 ; voie analogique AN4 pin RA5 sur pin 7 ; RA4=Digital sur Pin 6 ;------------------------------------------- movlw b'10001011' ; RA0,RA1,RA2,RA5= ANA, RA3=+Vref, RE0..RE2=digital ,cadre a droite movwf ADCON1 ; 1100 D D D A VREF+ VREF- A A movlw b'00101111' ; RA0,RA1,RA2,RA3,RA5 en entrees car ANA , RA4 en sorie Digit output movwf TRISA ;test 2011 movlw b'00000111' ; no analog movwf ADCON1 movlw b'00000111' ;t movwf TRISA movlw b'11001001' ; RB1,RB2 en sorties ,RB0,RB3 en entree ,RB4,RB5 en sortie Rb6,RB7 en entrees movwf TRISB movlw b'11011000' ; SCL, SDA et Rx Uart en entrees movwf TRISC clrf Voie,0 ;------------------------------------------ ;bit 7-6: ADCS1:ADCS0: A/D Conversion Clock Select bits 10 = FOSC/32 ;bit 5-3: CHS2:CHS0: Analog Channel Select bits 000 = channel 0, (RA2/AN2) RA0,1,2,3,5 ;bit 2: GO/DONE: A/D Conversion Status bit,If ADON = 1 1=in progress 0=Done ;bit 1: Unimplemented: Read as '0' ;bit 0: ADON: A/D On bit 1 = A/D converter module is operating movlw b'10000001' ;clock/32 Channel=0 ADON=1 movwf ADCON0 clrf INTCON clrf INTCON2 bsf INTCON2,7 ;RBPU =1 disable PORTB pull_up bcf INTCON2,6 ;INTEDG =0 int sur front descendant RB0 ;--------------------------------------------------------------------- ;config UART asynchrone ; pin17=RC6=Tx ------vert ---------- 3 de DS275 --- RS232 --> Ecran ; pin18=RC7=Rx ------blznc/vert ---- 1 de DS275 --- RS232 <-- Clavier ;---------------------------------------------------------------------- ; b7=0 ; b6=0=TX9 8 bits datas ; b5=1=TXEN Transmit ENable ; b4=0 SYNC=0 Asynchrone ; b3=0 ; b2=1 BRGH=1 high speed ; b1=x TRMT Status registre TRANSMISIION 1=vide ; b0=0 TX9D 9em bit data movlw 0x24 ;BRGH=1 TXEN=1 movwf TXSTA ;Si BRGH = 1 ;Debit = Fosc / (16 * (SPBRG + 1))soit SPBRG = (Fosc / (D‚bit * 16)) - 1 movlw DIVIDER ; generateur de baud rate 38400bauds soit 12 movwf SPBRG ; =64 bank0 ; b7=1 SPEN serial port ENAble ; b6=0 RX9 8 bits datas ; b5=0 ; b4=1 CREN Continuous enable bit ; b3=0 ADDEN Adress Detect Enable Bit ; b2=0 FERR Frame Error ; b1=0 OERR Over Flow Error ; b0=0 RX9D Receive 9em bit data movlw 0x90 ; SPEN = 1, CREN = 1 movwf RCSTA ; initialiser variables ; --------------------- clrf Nbl clrf flags ; effacer flags movlw LOW bufin ; adresse du buffer de reception movwf bufinptr,0 ; dans pointeur movlw LOW bufout ; adresse basse du buffer d'emission movwf bufoutptr,0 ; dans pointeur ;-------------------------------------------- ;config TIMER1 at 200mS .....voir PIC_calculs.xls Timers ;-------------------------------------------- movlw b'10110000' ;enable in 16bits mode, prescaler=1/8 Internal clock=Fosc/4 , stop timer1 movwf T1CON movlw HIGH (.3035) ;65536-3035=62500 62500*0.4*8=> 200mS movwf TMR1H movlw LOW (.3035) movwf TMR1L movlw .10 ; 10x0,2S=> 2 sec movwf _Diz_IT,0 ; movlw TIMEOUT+1 ; movwf time,0 ;-------------------------------------------- ;config TIMER0 at 448uS ;-------------------------------------------- movlw b'11000011' ; enable=1,8bits mode=1, internal=0,0,prescaler=0,prescaler value=16= 011 movwf T0CON movlw .185 ; 255-185=70 => 0.4*70*16=448µS movwf TMR0L ;**************** ;init interruptions ;******************* CLRF INTCON ; disable all interrupt clrf PIE2 ; disable PERIPHERAL INTERRUPT ENABLE REGISTER 2 clrf IPR1 clrf IPR2 clrf RCON bsf RCON,IPEN ; incompatibilite 16Fxx , valide interrupt High Priority clrf INTCON2 clrf INTCON3 bsf T1CON,TMR1ON ; mettre timer 1 en service bsf PIE1,RCIE ; autoriser interrupt USART receive bsf PIE1,TXIE ; autoriser interrupt USART Transmit ; bsf PIE1,PSPIE ; must be =1 on 18Fxx2 bcf INTCON2,INTEDG0 ;Interrupt on FALLING edge RB0 ; bsf IPR1,PSPIP ; must be=1 on 18F2x2 low priority EXCEPT RB0 interrupt allways HIGH priority clrf PIR1 ; raz flags interrupt clrf PIR2 ; raz flags interrupt bcf INTCON,PEIE ; interruptions peripheriques HORS service ;=============== MAIN ===================== bcf LED1 ; movlw '1' ; call Rs_Putchar CALL Rs_CrLf Presentation clrf _Cpt1 movlw 0 call Msg_Eeprom call delay_1S btg LED1 movlw EE1-EE0 call Msg_Eeprom call delay_1S call MsgFlash1 btg LED1 call delay_1S ; movlw '2' ; call Rs_Putchar ; CALL Rs_CrLf call MsgFlash2 btg LED1 call delay_1S movlw EE2-EE0 call Msg_Eeprom btg LED1 call delay_1S bcf ELLIGIBLE,0 bcf COMND,0 bcf INTCON,INT0IF ; raz drapeau interrupt RB0 bcf INTCON,INT0IE ; interdit interrupt RB0 bsf PIE1,RCIE bsf PIE1,TMR1IE ; autoriser interruptions timer 1; bsf INTCON,PEIE ; autorisation interrupts peripheriques bsf INTCON,GIE ; autorisation globale interrupts Boucle btg LED1 btfss ELLIGIBLE goto CODAGE_TOUCHE call Incr_ligne movlw EE3-EE0 call Msg_Eeprom clrf _Cpt2 movlw TABUL call Rs_Putchar ; movlw 0x81 ;ana0 ; movwf Voie ; call Acquis_Ana ; call delay_10mS ; movlw 0x89 ; ana1 ; movwf Voie ; call Acquis_Ana ; call delay_10mS ; movlw 0xA1 ; ana4 ; movwf Voie ; call Acquis_Ana ; call delay_10mS ; CALL Rs_CrLf bcf ELLIGIBLE movlw LOW bufin subwf bufinptr,w bz Boucle CALL Rs_CrLf movlw .16 movwf COUNT0,0 movlw LOW bufin ;partie haute de l'adresse movwf FSR0L Buf_Suite bank2 movf INDF0, w sublw .13 bz Buf_Fin movf INDF0,W bank0 call Rs_Putchar incf FSR0L,f decf COUNT0,f,0 BNZ Buf_Suite ;BTFSC STATUS,Z ;test si =0 => non trouve donc exit ;goto Buf_suite Buf_Fin bank0 CALL Rs_CrLf movlw LOW bufin ; adresse du buffer de reception movwf bufinptr,0 ; dans pointeur goto Boucle CODAGE_TOUCHE bcf INTCON,INT0IF ; Raz preventive du flag bsf INTCON,INT0IE ; autorise interrupt prioritaire Rb0 call delay_250mS ; fenetre temporelle permettant la capture IR bcf INTCON,INT0IE ; interdit interrupt RB0 movf COMND,w,0 ; si COMND=0 => pas de code! btfsc STATUS,Z goto Boucle call MsgTouche ; affiche message movf COMND,w,0 call hex8 ; valeur code en Hexadecimal CALL Rs_Tab ; decodage de la touche de telecommande IR movlw .17 ; taille table de code movwf COUNT0,0 movlw HIGH (RC5_code_text) ;partie haute de l'adresse movwf TBLPTRH movlw LOW (RC5_code_text) ;partie basse de l'adress movwf TBLPTRL CODAGE_T1 tblrd *+ ;1 lit la table pointee par TBLPTR et incremente le pointeur movf TABLAT,W ;resultat dans W XORWF COMND,W,0 BTFSC STATUS ,Z ;test si =0 egalité CODE et COMND BRA Find_it tblrd *+ ;2 code modulo 8 bytes tblrd *+ ;3 tblrd *+ ;4 tblrd *+ ;5 tblrd *+ ;6 tblrd *+ ;7 tblrd *+ ;8 decf COUNT0,f,0 BTFSC STATUS,Z ;test si =0 => non trouve donc exit goto NO_CODE movf TABLAT,w goto CODAGE_T1 Find_it tblrd *+ ;lit la table pointee par TBLPTR et incremente le pointeur movf TABLAT,W ;resultat dans W .. on parcour les 6 cars du code BTFSC STATUS,Z ;test si W=0 byte … 0= fin de chaine goto NO_CODE call Rs_Putchar goto Find_it NO_CODE CALL Rs_CrLf clrf COMND,0 goto Boucle ;**************** ;Subroutines ;**************** Acquis_Ana ;armemement acquisition Analogique movf Voie,w,0 movwf ADCON0 bsf ADCON0,ADON ; set Analog Converter ON (ADCON0,0=1) call delay_50uS bsf ADCON0,GO_DONE ; set GO on start conversion (ADCON0,2=1) call delay_50uS bcf RETENUE ; Positif not_yet btfsc ADCON0,NOT_DONE ; conversion AD ok ?(ADCON0,2=0 ???) goto not_yet movf ADRESL,w movwf val1,1 movwf val3,1 movf ADRESH,w movwf val1+1,1 movwf val3+1,1 Posit1 bcf Drapeaux,5,0 ; mode XXXXX bcf RETENUE call bcd_temp ; remplit le buffer d'affichage ASCII movlw TABUL call Rs_Putchar return ;---------------- sub16 movlb 0x01 ; = acces bank1 movf val2+1,W,1 ; source subwf val1+1,F,1 ; dest movf val2,W,1 btfss STATUS,C incfsz val2,W,1 subwf val1,F,1 ;dest = dest - source, WITH VALID CARRY return ;--------------------- ; Delays pour Q=10MHz ;#include "../common/Delais_10Mhz_18F.inc" ;------------------ ; uses count1,count2,count3 en bank0 ;delay_10uS ;delay_50uS ;delay_100uS ;delay_1mS ;delay_10mS ;delay_100mS ;delay_250mS ;delay_1S ;delay tronc commun .. ;rev 22/11/2009 ;--------------------- ; Tempos for Q=10MHz ;------------------ delay_10uS movlw .5 movwf count3,1 goto delay delay_50uS movlw .25 movwf count3,1 goto delay delay_100uS movlw .50 movwf count3,1 goto delay delay_1mS movlw .2 movwf count2,1 movlw .244 movwf count3,1 goto delay1 delay_10mS movlw .20 movwf count2,1 movlw .128 movwf count3,1 goto delay1 delay_100mS movlw .196 movwf count2,1 movlw .2 movwf count3,1 goto delay1 delay_250mS movlw .2 movwf count1,1 movlw .232 movwf count2,1 movlw .235 movwf count3,1 goto delay2 delay_1S movlw .8 movwf count1,1 movlw .161 movwf count2,1 movlw .218 movwf count3,1 goto delay2 delay movlw 0x001 movwf count2,1 delay1 movlw 0x001 movwf count1,1 delay2 decfsz count3,f,1 ;2 + 5*(count3-1) + bra delay2 ;2 + (5*255 +2+5) * (count2-1) + decfsz count2,f,1 ;2 + (5*255*256 +2 + 5*255 +2+5) *(count1-1) bra delay2 ; = decfsz count1,f,1 ;5(count3-1)+1282(count2-1)+327684(count1-1)+6 bra delay2 return ;--------------- Rs_Tab movlw .9 call Rs_Putchar return ;--------------- Rs_CrLf movlw .13 call Rs_Putchar movlw .10 call Rs_Putchar return ;--------------- Rs_Putchar clrwdt Rs_P1 btfss PIR1,TXIF ; while(!TXIF) goto Rs_P1 movwf TXREG ; TXREG = octet return ;--------------- getbyte ; clrwdt btfsc ELLIGIBLE goto fin_getbyte gb1 btfss PIR1,RCIF ; while(!RCIF) goto gb1 movf RCREG,w ; RCREG return fin_getbyte bcf ELLIGIBLE movlw '*' return ;----------------- Rs_Getchar clrwdt Rs_G1 btfss PIR1,RCIF ; while(!RCIF) goto Rs_G1 movf RCREG,w ; RCREG return ;--------------- Msg_Eeprom movwf EEADR Msg_eep1 movf EEADR,w call Read_EE ANDLW 0x0FF BTFSC STATUS, Z Return call Rs_Putchar goto Msg_eep1 return MsgFlash1 movlw high( Message1) ;partie haute de l'adresse movwf TBLPTRH movlw low (Message1) ;partie basse de l'adress movwf TBLPTRL bra MsgFlash MsgFlash2 movlw high Message2 ;partie haute de l'adresse movwf TBLPTRH movlw low Message2 ;partie basse de l'adress movwf TBLPTRL bra MsgFlash MsgFlash3 movlw high Message3 ;partie haute de l'adresse movwf TBLPTRH movlw low Message3 ;partie basse de l'adress movwf TBLPTRL bra MsgFlash MsgFlash4 movlw high Message4 ;partie haute de l'adresse movwf TBLPTRH movlw low Message4 ;partie basse de l'adress movwf TBLPTRL bra MsgFlash MsgFlash5 movlw high Message5 ;partie haute de l'adresse movwf TBLPTRH movlw low Message5 ;partie basse de l'adress movwf TBLPTRL bra MsgFlash MsgFlash tblrd *+ ;lit la table pointée par TBLPTR et ;incrémente le pointeur ; tblrd *+ ; avec declaration en DT " texte .." movf TABLAT,W ;resultat dans W BTFSC STATUS,Z ;test si =0 return call Rs_Putchar goto MsgFlash return MsgTouche movlw high MsgRC5 ;partie haute de l'adresse movwf TBLPTRH movlw low MsgRC5 ;partie basse de l'adress movwf TBLPTRL bra MsgFlash ;------- ; subroutine to read EEPROM memory ;(adresse & resultat en w) Read_EE ; 18F252 MOVWF EEADR ;Data Memory Address to read BCF EECON1, EEPGD ;Point to DATA memory BCF EECON1, CFGS ;acces DATA EEPROM Memory BSF EECON1, RD ;EEPROM Read MOVF EEDATA, W ;W = EEDATA incf EEADR,f ; incf EEADR,f ; car PB avec declaration en DT " texte .." => 1 mot par caractere return ;--------------------------- Write_EE ; 18F252 ; la donnee se trouve dans W movwf EEDATA ; placer data dans registre movlw addwrite ; charger adresse d'ecriture movwf EEADR ; placer dans registre bcf EECON1 , EEPGD ; pointer sur memoire data BCF EECON1, CFGS ;acces DATA EEPROM Memory bsf EECON1 , WREN ; autoriser acces ecriture bcf INTCON , GIE ; interdire interruptions movlw 0x55 ; charger 0x55 movwf EECON2 ; envoyer commande movlw 0xAA ; charger 0xAA movwf EECON2 ; envoyer commande bsf EECON1 , WR ; lancer cycle d'‚criture bsf INTCON , GIE ; reautoriser interruptions loop clrwdt ; effacer watchdog btfsc EECON1 , WR ; tester si ‚criture terminee goto loop ; non, attendre bcf EECON1 , WREN ; verrouiller prochaine ‚criture return ;------------------ Incr_ligne incf Nbl,f movf Nbl,w Bcd_3digits movwf btmp ; affichage octet --> decimal 3 digits ( de 0 a 255 ) movlw '0' movwf cent movwf dix bcd31 movlw 100 subwf btmp,w bnc bcd32 movwf btmp incf cent,f goto bcd31 bcd32 movlw 10 subwf btmp,w bnc bcd33 movwf btmp incf dix,f goto bcd32 bcd33 movlw '0' addwf btmp,w movwf uno movf cent,w btfss Drapeaux,4 call Rs_Putchar movf dix,w btfss Drapeaux,4 call Rs_Putchar movf uno,w btfss Drapeaux,4 call Rs_Putchar return ;---------------------- ; affichage octet (W) --> hexadecimal 2 digits ( de 00 a FF )sur LCD hex8 movwf value swapf value,W andlw 0x0f addlw -0x0a btfsc STATUS,C addlw 0x07 addlw 0x3a movwf caractere call Rs_Putchar movf value,W andlw 0x0f addlw -0x0a btfsc STATUS, C addlw 0x07 addlw 0x3a movwf caractere call Rs_Putchar movlw 'h' movwf caractere call Rs_Putchar return ;---------------- Binary (16-bit) to BCD ----------------------- ; 16-bit-Binary -> 4 digits de 8bits ; ( val1:val1+1) -> Dixmil , mille , cent , dix , uno bcd_temp swapf val1+1,W,1 ; HIGH andlw 0x0F addlw 0xF0 movwf mille,1 addwf mille,F,1 addlw 0xE2 movwf cent,1 addlw 0x32 movwf uno,1 movf val1+1,W,1 andlw 0x0F addwf cent,F,1 addwf cent,F,1 addwf uno,F,1 addlw 0xE9 movwf dix,1 addwf dix,F,1 addwf dix,F,1 swapf val1,W,1 ; LOW andlw 0x0F addwf dix,F,1 addwf uno,F,1 rlcf dix,F,1 rlcf uno,F,1 comf uno,F,1 rlcf uno,F,1 movf val1,W,1 andlw 0x0F addwf uno,F,1 rlcf mille,F,1 movlw 0x07 movwf dixmil,1 movlw 0x0A Lb1: decf dix,F,1 addwf uno,F,1 btfss STATUS,C bra Lb1 Lb2: decf cent,F,1 addwf dix,F,1 btfss STATUS,C bra Lb2 Lb3: decf mille,F,1 addwf cent,F,1 btfss STATUS,C bra Lb3 Lb4: decf dixmil,F,1 addwf mille,F ,1 btfss STATUS,C bra Lb4 btfss Drapeaux,5 ; 1 => affichage 00000 a 999999 bra Bcd_5digits ; 0 => affichage + ou - XXX.XX movlw '+' btfsc RETENUE,0 movlw '-' call Rs_Putchar movf mille,w,1 btfss STATUS,Z ; si digit=0 remplace par Blanc bra Lb5 movlw ' ' call Rs_Putchar bra Lb6 Lb5 addlw '0' call Rs_Putchar Lb6 movf cent,w,1 addlw '0' call Rs_Putchar movlw '.' call Rs_Putchar movf dix,w,1 addlw '0' call Rs_Putchar movf uno,w,1 addlw '0' call Rs_Putchar return ;--------------- Bcd_5digits ; movf dixmil,w ; addlw '0' ; call Rs_Putchar ; bank1 movf mille,w,1 addlw '0' call Rs_Putchar movf cent,w,1 addlw '0' call Rs_Putchar movf dix,w,1 addlw '0' call Rs_Putchar movf uno,w,1 addlw '0' call Rs_Putchar movlw ' ' call Rs_Putchar return ;================================================================ Saisie_Caracteres ; 2 caracteres par octet => BCD format 00 a 99 ; preciser la longueur du buffer a remplir dans W <= N-1 caracteres ; Buffer_MAJ = buffer de stockage en page 0 movwf _N1,0 ; Index de rangement 2 car -> 1 emplacement bcf INTCON,TMR0IE ; interdit interrupt timer0 Actualise bsf INTCON,GIE clrf _RsByte,0 bsf INTCON,INT0IE ;Autorise interrupt RB0 ;attente saisi caractere au clavier Actu3 btfss ELLIGIBLE,0 goto Actu3 bcf ELLIGIBLE bcf INTCON,GIE bcf INTCON,INT0IE ;interdit interrupt RB0 movf _RsByte,W ;echo call Rs_Putchar movlw .27 ;esc (abandon) xorwf _RsByte,w btfss STATUS,Z goto Test_Back return Test_Back movlw .8 ;back space (<- correction) xorwf _RsByte,w btfss STATUS,Z goto Test_Tab movlw Buffer_MAJ subwf _N1,w btfsc STATUS,C ; negatif ? goto Actualise incf _N1,f ;incremente indice goto Actualise Test_Tab movlw .9 ;tabulation (-> correction) xorwf _RsByte,w btfss STATUS,Z goto Test_Num decf _N1,w btfsc STATUS,C ; negatif ? goto Test_Num decf _N1,f ;decremente indice goto Actualise Test_Num movlw '0' subwf _RsByte,w btfsc STATUS,C goto SUP_0 goto Actualise SUP_0 movlw '9' subwf _RsByte,w btfsS STATUS,C goto LESS_EQ_9 ; less <9 btfsC STATUS,Z goto LESS_EQ_9 ;or egal =9 goto Actualise LESS_EQ_9 btfsc _N1,0 ;test bit 0 du compteur goto HB goto LB HB MOVLW .48 subWF _RsByte,w movwf _Temp2 ;=x1 bcf STATUS,C rlcf _Temp2,f ;x2 rlcf _Temp2,f ;x4 btfsc Drapeaux,5 ; si drapeau:5=1 *10 , sinon *16 goto HB1 bcf STATUS,C ; <- rajout 31/01/07 rlcf _Temp2,f ;x2 rlcf _Temp2,f ;x4 goto HB2 HB1 addwf _Temp2,w ;x5 movwf _Temp2 rlcf _Temp2,f ;x10 HB2 decf _N1,f goto Actualise LB MOVLW .48 subWF _RsByte,w AndLW 0x0F ; MSB + LSB addwf _Temp2,W movwf _RsByte Rangement ; dans buffer specifique Horodatage clrf FSR0H bcf STATUS,C rrcf _N1,W ; Index/2= deplacement en octet ADDLW Buffer_MAJ ; offset table movwf FSR0L movf _RsByte,w movwf INDF0 ; sauvegarde W -> @FSR() movf _N1,w btfsc STATUS,Z goto OK_Saisie decf _N1,f btfss STATUS,Z goto Actualise OK_Saisie bcf INTCON,GIE movf _RsByte,w return ;-------------------------------------- ; The following routines are low level I2C routines applicable to most ; interfaces with I2C devices. ;------------------------------------------------------ I2C_DELAY goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 goto $+2 nop nop return ;--------------- START: ; bsf STATUS,RP0 bcf I2C_SDA ; bcf STATUS,RP0 bsf I2C_SDA bsf I2C_SCL ;I2C start: change of SDA call I2C_DELAY ;from 1 to 0 while SCL = 1 bcf I2C_SDA call I2C_DELAY bcf I2C_SCL return ;--------------------- STOP: ; bsf STATUS,RP0 bcf I2C_SDA ; bcf STATUS,RP0 bcf I2C_SDA bsf I2C_SCL ;I2C stop: change of SDA call I2C_DELAY ;from 0 to 1 while SCL = 1 bsf I2C_SDA return ;--------------------- M_ACK: ; bsf STATUS,RP0 bcf I2C_SDA ; bcf STATUS,RP0 bcf I2C_SDA ;I2C master acknowledge: call I2C_DELAY ;SDA = 0 bsf I2C_SCL call I2C_DELAY bcf I2C_SCL return ;---------- NACK: ; bsf STATUS,RP0 bcf I2C_SDA ; bcf STATUS,RP0 bsf I2C_SDA ;I2C master non-acknowledge: call I2C_DELAY ;SDA = 1 bsf I2C_SCL call I2C_DELAY bcf I2C_SCL return ;----------- ACK: ; bsf STATUS,RP0 bsf I2C_SDA ; bcf STATUS,RP0 call I2C_DELAY ;I2C device acknowledge: bsf I2C_SCL ;SDA set 1 by master call I2C_DELAY ;SDA = 1 if device doesn't ACK bsf STATUS,Z ;SDA = 0 if devcie acknowledges btfsc I2C_SDA bcf STATUS,Z ;STATUS,Z=1 if device acknowledges bcf I2C_SCL ;STATUS,Z=0 if device doesn't ACK return ;------------ CLOCK_PULSE: ; SCL momentarily to logic one CALL HIGH_SCL call I2C_DELAY CALL LOW_SCL call I2C_DELAY RETURN ;------------ HIGH_SDA: ; high impedance by making SDA an input BSF I2C_SDA ; bank1 nop BSF I2C_SDA ; make SDA pin an input ; bank0 call I2C_DELAY RETURN ;------------ LOW_SDA: ; bank1 BCF I2C_SDA ; make SDA pin an output ; bank0 nop BCF I2C_SDA call I2C_DELAY RETURN ;------------ HIGH_SCL: BSF I2C_SCL ; bank1 nop BSF I2C_SCL ; make SCL pin an input ; bank0 call I2C_DELAY RETURN ;------------ LOW_SCL: ; bank1 BCF I2C_SCL ; make SCL pin an output ; bank0 BCF I2C_SCL call I2C_DELAY RETURN ;--------------------- ; The following routines are low level I2C routines applicable to most ; interfaces with I2C devices. IN_BYTE ; read byte on i2c bus CLRF I_BYTE MOVLW .8 MOVWF _N0 ; set index to 8 CALL HIGH_SDA ; be sure SDA is configured as input IN_BIT CALL HIGH_SCL ; clock high BTFSS I2C_SDA ; test SDA bit GOTO IN_ZERO GOTO IN_ONE IN_ZERO BCF STATUS, C ; clear any carry RLCF I_BYTE, F ; i_byte = i_byte << 1 | 0 GOTO CONT_IN IN_ONE BCF STATUS, C ; clear any carry RLCF I_BYTE, F INCF I_BYTE, F ; i_byte = (i_byte << 1) | 1 GOTO CONT_IN CONT_IN CALL LOW_SCL ; bring clock low DECFSZ _N0, F ; decrement index GOTO IN_BIT RETURN ;------------- OUT_BYTE: ; send o_byte on I2C bus MOVWF O_BYTE MOVLW .8 MOVWF _N0 OUT_BIT: BCF STATUS,C ; clear carry RLCF O_BYTE, F ; left shift, most sig bit is now in carry BTFSS STATUS, C ; if one, send a one GOTO OUT_ZERO GOTO OUT_ONE OUT_ZERO: CALL LOW_SDA ; SDA at zero CALL CLOCK_PULSE CALL HIGH_SDA GOTO OUT_CONT OUT_ONE: CALL HIGH_SDA ; SDA at logic one CALL CLOCK_PULSE GOTO OUT_CONT OUT_CONT: DECFSZ _N0, F ; decrement index GOTO OUT_BIT RETURN ;--------------- Init_RTC CALL STOP call delay_10mS ; was 25mS CALL START MOVLW 0xD0 ; B'11010000'=0xD0 = adresse device CALL OUT_BYTE CALL ACK clrf ADDR MOVF ADDR, W ; addresse registre CALL OUT_BYTE CALL ACK MOVF SEC,W CALL OUT_BYTE CALL ACK ; a ce momment la led connectee sur pin7 doit osciller a 1HZ ! MOVf MIN,W CALL OUT_BYTE CALL ACK Movf HEURE,w CALL OUT_BYTE CALL ACK Movf JourSem,w ;Jour de la semaine=07 CALL OUT_BYTE CALL ACK Movf Jour,w ;Jour du mois=02 CALL OUT_BYTE CALL ACK MOVF Mois,W ;Mois= 12 CALL OUT_BYTE CALL ACK MOVF Annee,W ;ANNEE=07 CALL OUT_BYTE CALL ACK MOVLW B'10010000' ;Registre de controle SQWE=1 RS0=RS1=0 sortie 1Hz CALL OUT_BYTE CALL NACK call STOP call delay_10mS return ;----------------------------- Lecture_DS1307 Call STOP call delay_50uS CALL START MOVLW 0xD0 ; B'11010000' MOVWF DEV_DS1307 ; @D0H adresse device CALL OUT_BYTE CALL ACK clrf ADDR ; adresse 0 MOVF ADDR, W ; send high byte of address CALL OUT_BYTE CALL ACK MOVLW 0xD1 ; B'11010001' MOVWF DEV_DS1307 ;Mode Lecture CALL START ;genere un start bit MOVF DEV_DS1307,W CALL OUT_BYTE CALL NACK ;-------- CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF SEC CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF MIN CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF HEURE CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF JourSem CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF Jour CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF Mois CALL IN_BYTE Call M_ACK MOVF I_BYTE,W MOVWF Annee ; CALL IN_BYTE ; Call M_ACK ; MOVF I_BYTE,W ; MOVWF CtrlReg ; call M_ACK CALL STOP return ;******************************************************** ; interruptions ;****************************************************** org 0x1000 IntVectorLow movwf w_temp,0 ; sauver registre W swapf STATUS , w,0 ; swap status avec resultat dans w movwf status_temp ; sauver status swapp movf FSR0L , w,0 ; charger FSR movwf FSR0L_temp,0 ; sauvegarder FSR movf FSR0H , w,0 ; charger FSR movwf FSR0H_temp,0 ; sauvegarder FSR movf BSR , w ,0 ; charger PCLATH movwf BSR_temp,0 ; le sauver ;-------------------------------- ; Interruption transmission USART ; ------------------------------- Uart_Tx_Int btfss PIE1,TXIE ; tester si interrupt autorisee goto Uart_Rx_Int ; non sauter btfss PIR1,TXIF ; oui, tester si interrupt en cours goto Uart_Rx_Int ; non sauter call inttx ; oui, traiter interrupt bcf PIR1,TXIF ; raz flag ;-------------------------------- ; Interruption reception USART ;------------------------------- Uart_Rx_Int btfss PIE1,RCIE ; tester si interrupt autorisee goto Timer1_int ; non sauter btfss PIR1,RCIF ; oui, tester si interrupt en cours goto Timer1_int ; non sauter call intrc ; oui, traiter interrupt bcf PIR1,RCIF ;-------------------------------- ; Interruption TIMER1 ;------------------------------- Timer1_int btfss PIE1,TMR1IE ; tester si interrupt autorisee goto restorereg ; non sauter btfss PIR1,TMR1IF ; oui, tester si Flag interrupt arme goto restorereg ; non test suivant decf _Diz_IT,f,0 btfss STATUS,Z goto Tim11 bsf ELLIGIBLE,0 ; arme drapeau,6 => ok pour mesure movlw .10 movwf _Diz_IT,0 ; 10 x200mS =2 sec btg LED2 ; led change ; #ifdef debuging ; call MsgFlash4 ; #endif Tim11 ; reinit timer pour 200mS at Q=10MHz movlw LOW (.3035) ; 65535-3035=62500*0.4*16=2000000µS movwf TMR1L movlw HIGH (.3035) movwf TMR1H bcf PIR1,TMR1IF ; RAZ flag interrupt restorereg movf BSR_temp ,w,0 ; recharger pointeur de BANK movwf BSR ; le restaurer movf FSR0H_temp , w,0 movwf FSR0H,0 movf FSR0L_temp , w,0 movwf FSR0L,0 ; restaurer FSR swapf status_temp,w,0 ; swap ancien status, r‚sultat movwf STATUS,0 ; restaurer status swapf w_temp,f,0 ; Inversion L et H de l'ancien sans modifier Z swapf w_temp,w,0 ; Reinversion de L et H => W restaure sans modifier le status retfie ; return from interrupt ;**************************************************** ; INTERRUPTION RECEPTION USART * ;**************************************************** ; Recoit le caractere de l'USART et le place dans le buffer d'entr‚e. ; Si la longueur atteint D'96', on n'encode plus, et on place 0x0D en avant- ; derniere position et 0x0A en derniere position ; Si la reception est terminee (longueur atteinte ou 0x0A recu), on stoppe les ; interruptions de reception et on repositionne le pointeur au d‚but du buffer ; Les erreurs sont detectees et signalees intrc ; tester si erreur de frame clrf FSR0H btfsc RCSTA,FERR ; tester si erreur de frame bsf ER_FR ; oui, signaler erreur de frame ; lire la parite ; bcf PARITE ; par defaut, parite = 0 ; btfsc RCSTA,RX9D ; parite lue = 1? ; bsf PARITE ; oui, le signaler ; lire octet recu movf bufinptr,w ; charger pointeur destination movwf FSR0L ; dans pointeur d'adresse movf RCREG,w ; charger octet recu bank2 movwf INDF0 ; sauver dans buffer bufin en bank2 ; verifier si LF ou CR intrc1 movf INDF0,w ; charger caractere recu xorlw 0x0A ; comparer avec line-feed btfsc STATUS,Z ; identique? goto intrcend ; oui, fin de message ; verifier si buffer plein bank0 incf bufinptr,f ; incr‚menter pointeur de caracteres bank2 movf FSR0L,w ; charger pointeur xorlw .94 ; comparer avec dernier emplacement possible btfss STATUS,Z ; identique? return ; non, fin de reception incf FSR0L,f ; pointeur sur emplacement suivant movlw 0x0D ; mettre carriage-return movwf INDF0 ; en avant-derniere position incf FSR0L,f ; pointer sur derniere position movlw 0x0A ; charger line-feed movwf INDF0 ; en derniere position intrcend ; fin de message bank0 movlw LOW bufin ; oui adresse de depart du buffer d'entree movwf bufinptr ; prochain caractere sera le premier bcf PIR1,RCIF ; RAZ flag return ;***************************************************************** ; INTERRUPTION EMISSION USART * ;**************************************************************** ; envoie le caractere pointe par bufoutptr, puis incremente le pointeur ; Si ce caractere est le "line-feed", alors on arrete l'emission et on pointe de ; nouveau au debut du buffer ;---------------------------------------------------------------- inttx ; Charger octet … envoyer ; movf bufoutptr,w,0 ; charger pointeur d'octets ; movwf FSR0L ; dans pointeur ; movf INDF0,w ; charger octet … envoyer ; bank0 ; movlb 0x00 ; movwf TXREG ; envoyer octet ; incf bufoutptr,f,0 ; pointer sur octet suivant ; tester si fin de message ; xorlw 0x0A ; comparer octet envoy‚ avec Line-feed ; btfss STATUS,Z ; egalite ; return ; non, retour d'interruption ; traiter fin d'emission bcf PIE1,TXIE ; fin des interruptions ‚mission USART ; movlw LOW bufout ; adresse du buffer de sortie ; movwf bufoutptr,0 ; prochain caractere = premier return ; fin d'interruption ;------------------------------------- ;#include "../common/Read_IR_18F.inc" ; version PIC18F2x2 Read_IR #ifdef debuging call MsgFlash3 ; pour debug interruptHighPriority on RB0 btg LED3 return ; debug #endif CLRF COMND Test_Rb0 MOVLW .5 ; 255 - 5 =250*0.4*16 = 1600 uSec MOVWF TMR0L BCF INTCON,TMR0IF ; Raz Timer0 bit overflow Test_Rb1 BTFSC INTCON, TMR0IF ; go out the loop after 1600µS goto Test_Rb0_Over BTFSC IR_Sensor GOTO Test_Rb1 movlw .185 ; 255 - 185 = 70 => 0.4*70*16=448µS movwf TMR0L ; ce qui fait une attente de 1/4 bit BCF INTCON,TMR0IF ; Raz Timer0 bit overflow BCF STATUS,C ; C=0 CALL READ ; Read the data stream BTFSC STATUS,C ; si C=1 => erreur data GOTO Test_Rb0 ; recommence si erreur CALL PARSE ; Decode les donnees BTFSC STATUS,C ; C=1 => erreur GOTO Test_Rb0 ; recommence si erreur btg LED3 ; call delay_100mS return Test_Rb0_Over clrf COMND,0 BSF STATUS,C ; C=1 =error return ;Test ok 7 avril 2003 avec telecommand MARANTZ RC5 only ;READ reads the incoming data stream and saves it into a 6-byte buffer ;RESTART_TMR0 Restart the timer with an 888 uSec delay ; 889 µS = demi duree d'un pulse (bit) 1.778mS/2 ;PARSE Analyse : TOGGLE =repet touche, COMND= code touche ;DECODE Decodage trame IR RC5 PARSE_FLAGS<0> = valide,donnee 0 ou 1 ;Remember again that the IR pickup output is active low ;codage PHILIPS en retour: Carry =1 si ERREUR! sinon C=0 ;-------------------- READ ;Raz buffer de stockage CLRF SERIAL_BUF CLRF SERIAL_BUF+1 CLRF SERIAL_BUF+2 CLRF SERIAL_BUF+3 CLRF SERIAL_BUF+4 CLRF SERIAL_BUF+5 CLRF BIT_COUNT,0 CLRF BYTE_COUNT,0 MOVLW SERIAL_BUF ; Reset the indirect pointer back MOVWF FSR0L,0 ; to the start of the buffer space RD_LOOP2 BTFSS INTCON,TMR0IF ; Wait till timer goes 444 Usec GOTO RD_LOOP2 BCF INTCON, TMR0IF ; Clear the overflow flag MOVLW .117 ; 255 - 117 =138*0.4*16 = 883.2 uSec MOVWF TMR0L BTFSC IR_Sensor ; Check RB0 IR signal (i.e. debounce) GOTO BAD_DATA ; If it's high (logic 0), bail out RD_LOOP3 BTFSS INTCON, TMR0IF ; Wait till timer goes 888 uSec GOTO RD_LOOP3 BCF INTCON, TMR0IF ; Clear the overflow flag MOVLW .117 ; 255 - 117 =138*0.4*16 = 883.2 uSec MOVWF TMR0L INCF BIT_COUNT,f,0 MOVLW .64 ;.43 See if we've done all 42 bits XORWF BIT_COUNT,w,0 BTFSC STATUS,Z GOTO RD_FINISH ; We've done all 42 bits BSF STATUS,C ; Preset the carry bit BTFSS IR_Sensor ; Test RAx IR input signal @@@ BCF STATUS,C ; Input bit is high (logic 0) so change carry ; Now the input bit is in the carry flag RLCF INDF0,f,0 ; Rotate it into the buffer INCF BYTE_COUNT,f,0 ; BTFSC BYTE_COUNT,3,0 ; See if all 8 bits are filled CALL NEXT_BYTE,0 ; Yes, use next buffer byte GOTO RD_LOOP3 ; Loop back & do the rest of the bits RD_FINISH BCF STATUS,C ; RLCF INDF0,f,0 ; The last buffer byte has only 2 RLCF INDF0,f,0 ; bits loaded. RLCF INDF0,f,0 ; So we shift them up to the top RLCF INDF0,f,0 ; the hard way. RLCF INDF0,f,0 RLCF INDF0,f,0 BCF STATUS,C ; Clear carry to show a successful capture RETURN NEXT_BYTE INCF FSR0L,f ,0 ;Increment the FSR and clear the counter CLRF BYTE_COUNT,0 RETURN ;------------------------------------------ ; Restart the timer with an 888 uSec delay ; and refresh the Timer0 overflow flag. ;------------------------------------------ RESTART_TMR0 BCF INTCON, TMR0IF ; Clear the overflow flag MOVLW .117 ; 255 - 117 =138*0.4*16 = 883.2 uSec MOVWF TMR0L RETURN ;------------------------------------------------ ; decodes the saved datastream into the various ; RC5 words and flags. ;------------------------------------------------ PARSE clrf FSR0H MOVLW SERIAL_BUF ; Put buffer start address into MOVWF FSR0L,0 ; the FSR CLRF TEMP,0 ; Initialize variables CLRF BYTE_COUNT,0 ; CLRF MZ_FLAG,0 ; CLRF FIELD,0 ; CLRF TOGGLE,0 ; CLRF SYSTEM,0 ; CLRF COMND,0 ; CLRF MZDATA,0 ; ; First one is the field bit RLCF INDF0,f,0 ; First bit into carry RLCF TEMP,f,0 ; Put it into TEMP for decoding RLCF INDF0,f,0 ; Second bit RLCF TEMP,f,0 ; ditto INCF BYTE_COUNT,f,0 ; Start keeping track of INDF bit position CALL DECODE BTFSC PARSE_FLAGS,2,0 ; Illegal pattern found GOTO BAD_DATA ; Must have found a good bit RRCF PARSE_FLAGS,f,0 ; Put field bit into Carry RLCF FIELD,f,0 ; Move it into FIELD CLRF TEMP,0 ; Next one is the toggle bit RLCF INDF0,f,0 ; First bit into carry RLCF TEMP,f,0 ; Put it into TEMP for decoding RLCF INDF0,f,0 ; Second bit RLCF TEMP,f,0 ; ditto INCF BYTE_COUNT,f,0 ; keep track of INDF bit position CALL DECODE BTFSC PARSE_FLAGS,2,0 ; Illegal pattern found GOTO BAD_DATA ; Must have found a good bit RRCF PARSE_FLAGS,f,0 ; Put toggle bit into Carry RLCF TOGGLE,f,0 ; Move it into TOGGLE MOVLW 0x05 ; Next one is the system byte, 5 bits MOVWF COUNT0,0 SYS_1 CLRF TEMP,0 RLCF INDF0,f,0 ; First bit into carry RLCF TEMP,f,0 ; Put it into TEMP for decoding RLCF INDF0,f,0 ; Second bit RLCF TEMP,f,0 ; ditto INCF BYTE_COUNT,f,0 ; keep track of INDF bit position BTFSC BYTE_COUNT,2,0 ; (there are two rotates per count) CALL NEXT_BYTE ; Go to next buffer byte when count=4 CALL DECODE BTFSC PARSE_FLAGS,2,0 ; Illegal pattern found GOTO BAD_DATA ; Must have found a good bit RRCF PARSE_FLAGS,f,0 ; Put bit into Carry RLCF SYSTEM,f,0 ; Move it into SYSTEM DECFSZ COUNT0,f,0 ; Have we done all 5 bits? GOTO SYS_1 ; No, not yet ; Here we test for the two spaces ; present in the extended data format. ; If they appear, we set a flag ; and skip over them to the command ; word. MOVLW B'11000000' ; Mask for 2nd buffer byte ANDWF SERIAL_2,w,0 ; Are the 2 top bits zero? BTFSS STATUS,Z ; GOTO PHILIPS ; No space found CALL NEXT_BYTE ; Skip over first space RLCF INDF0,f,0 ; Skip over second space RLCF INDF0,f,0 INCF BYTE_COUNT,f,0 MOVLW 0x01 MOVWF MZ_FLAG,0 ; Set the flag PHILIPS MOVLW 0x06 ; Next one is the command byte, 6 bits MOVWF COUNT0,0 CMD_1 CLRF TEMP,0 RLCF INDF0,f,0 ; First bit into carry RLCF TEMP,f,0 ; Put it into TEMP for decoding RLCF INDF0,f,0 ; Second bit RLCF TEMP,f,0 ; ditto INCF BYTE_COUNT,f,0 ; keep track of INDF bit position BTFSC BYTE_COUNT,2,0 ; (there are two rotates per count) CALL NEXT_BYTE ; Go to next buffer byte when count=4 CALL DECODE BTFSC PARSE_FLAGS,2,0 ; Illegal pattern found GOTO BAD_DATA ; Must have found a good bit RRCF PARSE_FLAGS,f,0 ; Put bit into Carry RLCF COMND,f,0 ; Move it into COMND DECFSZ COUNT0,f,0 ; Have we done all 6 bits? GOTO CMD_1 ; No, not yet BTFSS FIELD,0,0 ; If field bit=0 then comnd=comnd+64 BSF COMND,6,0 BTFSC MZ_FLAG,0,0 ; Test for extra data word GOTO MDAT_1 ; Parse extra data word RETURN ; Finish here if Philips format MDAT_1 MOVLW 0x06 ; Next one is the data byte, 6 bits MOVWF COUNT0,0 MDAT_2 CLRF TEMP,0 RLCF INDF0,f,0 ; First bit into carry RLCF TEMP,f,0 ; Put it into TEMP for decoding RLCF INDF0,f,0 ; Second bit RLCF TEMP,f,0 ; ditto INCF BYTE_COUNT,f,0 ; keep track of INDF bit position BTFSC BYTE_COUNT,2,0 ; (there are two rotates per count) CALL NEXT_BYTE ; Go to next buffer byte when count=4 CALL DECODE BTFSC PARSE_FLAGS,2,0 ; Illegal pattern found GOTO BAD_DATA ; Must have found a good bit RRCF PARSE_FLAGS,f,0 ; Put bit into Carry RLCF MZDATA,f,0 ; Move it into MZDATA DECFSZ COUNT0,f,0 ; Have we done all 6 bits? GOTO MDAT_2 ; No, not yet PARSE_DONE RETURN ;------------------------------------------------------- ; DECODE .. enter with two-bit data in TEMP ; return with result code in PARSE_FLAGS, thus ; PARSE_FLAGS<0> = valid data, one or zero ; PARSE_FLAGS<1> = unused ; PARSE_FLAGS<2> = set if data is invalid ;------------------------------------------------------- DECODE CLRF PARSE_FLAGS,0 MOVLW ONE XORWF TEMP,w, 0 ; Compare to bit pattern '01' btfss STATUS,Z,0 goto ONE_EXIT MOVLW ZERO XORWF TEMP,w,0 ; compare to bit pattern '10' btfss STATUS,Z,0 goto ZERO_EXIT BAD_EXIT BSF PARSE_FLAGS,2,0 ; bit pattern neither 01 nor 10 RETURN ONE_EXIT BSF PARSE_FLAGS,0,0 ; Return with valid data in LSB ZERO_EXIT RETURN ; of the PARSE_FLAGS variable ; BAD_DATA .. Exit if Read or Parse doesn't like what it finds. ; The Carry flag is set as an error message. BAD_DATA BSF STATUS,C ; Set the carry flag to show error RETURN ;------------------------------------- ;******************** ; ZONE Messages ;******************** ; 17 codes ; code; 6 ascii; 0 RC5_code_text ; 1 ;123456; 1 DB .13,"MUTE_ ",0 DB .15,"OSD_ ",0 DB .16,"VOL + ",0 DB .17,"VOL - ",0 DB .22,"BassUp",0 DB .23,"BassDw",0 DB .24,"TrebUp",0 DB .25,"TrebDw",0 DB .28,"Haut ",0 DB .29,"Bas ",0 DB .41,"ARRET_",0 DB .44,"Gauche",0 DB .43,"Droite",0 DB .63,"TV_ ",0 DB .87,"OK_ ",0 MsgRC5 ; 12345678901234567890123456789012 DB "TOUCHE = " ,'\t',0 Message1 DB "Message 1 en FLASH MEMORY .... ",'\r' DB "de 64 caracteres sur 2 lignes ",'\r',0 Message2 ; 12345678901234567890123456789012 DB "Message 2 en FLASH MEMORY 32car",'\r' DB "usage de BANK 1 ........",'\r' DB "usage interrupt sur RB0 .......",'\r' DB "usage interrupt sur TMR1 ......",'\r' DB "EEPROM en F00000 0..255 bytes ",'\r',0 Message3 ; 12345678901234567890123456789012 DB "Interrupt on RB0 .",'\r',0 DeltaMsg32=(Message3-Message2) messg Delta adresse Msg3 et Msg2: #v(DeltaMsg32); Message4 ; 12345678901234567890123456789012 DB "Interrupt on TIMER1.",'\r',0 ; IF ( (((Message4 - Message3)/2)mod 2 ) ; ERROR "Attention long Msg NON PAIR" ; ENDIF Message5 ; 12345678901234567890123456789012 DB "Interrupt High Priority......",'\r',0 DeltaMsg54=(Message5-Message4) messg Delta adresse Msg5 et Msg4: #v(DeltaMsg54); if (DeltaMsg54 % 2) >0 ERROR "Attention long Msg NON PAIR" ERROR " Jamais d'erreur car rajoute 00 si impair!" endif ;-------------------------------------------------- ;MPASM a donc complété votre ligne en considérant que vous vouliez ; mettre 2 octets par ligne (ou un multiple de 2), et a complété de ; lui-meme par un « ,0x00 ». Méfiez-vous. ;-------------------------------------------------- ;ATTENTION: Origine Eprom <> des pic16F8XX ! ;ATTENTION si usage de DT "texte" pointage sur MOTS et non sur BYTE! _FinProgr EQU $ ; verification Anti-crash bootloader ; Taille MAX Prog = 8000H bytes soit 32768 bytes -> 16384 mots ; 16384 - 256 mots = messg Fin de programme at : #v(_FinProgr) messg Max programme at : #v(_MAXFLASH) messg Percent_use= : #v(100 * _FinProgr/_MAXFLASH)% IF ( _FinProgr > _MAXFLASH) ERROR "Attention DEPASSEMENT MAXI MEM FLASH..risque pour le bootlader" ENDIF ORG 0xF00000 ; 256 bytes of eeprom EEPROM EQU $ ; 12345678901234567890123456789012 EE0 DB "18F258_IR_RS232 10/10/2011",'\r',0 ; 12345678901234567890123456789012 EE1 DB "AVEC Tiny bootloader 10MHz 19200bds",'\r',0 ; 12345678901234567890123456789012 EE2 DB "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx ",'\r',0 ; 12345678901234567890123456789012 EE3 DB " xxxxxxxxxxxxx ",0 END ;************************************************************ Release build of project `C:\Mplab8\_Mesprojets_ASM\_18Fxx\tst18F252a.mcp' started. Language tool versions: MPASMWIN.exe v5.39, mplink.exe v4.38, mplib.exe v4.38 Mon Oct 10 21:51:11 2011 ------------------------------ Clean: Deleting intermediary and output files. Clean: Done. Executing: "C:\Program Files\Microchip\MPASM Suite\MPASMWIN.exe" /q /p18F258 "18F258_IR_rs232_111010.asm" /l"18F258_IR_rs232_111010.lst" /e"18F258_IR_rs232_111010.err" Message[301] ..... MESSAGE: (Delta adresse Msg3 et Msg2: 168) Message[301]......MESSAGE: (Delta adresse Msg5 et Msg4: 24) Message[301]..... MESSAGE: (Fin de programme at : 5182) Message[301]...... MESSAGE: (Max programme at : 16128) Message[301]. 2010 : MESSAGE: (Percent_use= : 32%) Executing: "C:\Program Files\Microchip\MPASM Suite\mplink.exe" /p18F258 /l" C:\Program Files\Microchip\MPLAB ASM30 Suite\lib" /k"C:\Mplab8\MPASM Suite" ".. \_Mesprojets_ASM\_18Fxx\18F258_IR_rs232_111010.o" /z__MPLAB_BUILD=1 /o"18F258_IR_rs232_111010.cof" /M"18F258_IR_rs232_111010.map" /W /x MPLINK 4.38, Linker Copyright (c) 1998-2010 Microchip Technology Inc. Errors : 0 Loaded C:\MPLAB8\_Mesprojets\18F258_IR_rs232_111010.cof. ----------------- Release build of project `C:\Mplab8\_Mesprojets_ASM\_18Fxx\tst18F252a.mcp' succeeded. Language tool versions: MPASMWIN.exe v5.39, mplink.exe v4.38, mplib.exe v4.38 Mon Oct 10 21:51:14 2011 ------------------ BUILD SUCCEEDED ******************************************************************** Interface to TinyBootLoader, v1.9.5 contact: claudiu.chiculita@ugal.ro http://www.etc.ugal.ro/cchiculita/software/picbootloader.htm ------- Connected to \\.\COM2 at 19200 HEX: 0 min old, INHX32,18Fcode+cfg+eeprom , total=3274 bytes. Searching for PIC ... Found:18F 252o/452o Addr:000h -> 31h Addr:001h -> 38h Addr:002h -> 46h Addr:003h -> 32h Addr:004h -> 35h Addr:005h -> 38h Addr:006h -> 5Fh Addr:007h -> 49h Addr:008h -> 52h Addr:009h -> 5Fh Addr:00Ah -> 52h Addr:00Bh -> 53h Addr:00Ch -> 32h Addr:00Dh -> 33h Addr:00Eh -> 32h Addr:00Fh -> 20h Addr:010h -> 31h Addr:011h -> 30h Addr:012h -> 2Fh Addr:013h -> 31h Addr:014h -> 30h Addr:015h -> 2Fh Addr:016h -> 32h Addr:017h -> 30h Addr:018h -> 31h Addr:019h -> 31h Addr:01Ah -> 0Ch Addr:01Bh -> 0Dh Addr:01Ch -> 00h Addr:01Dh -> 00h Addr:01Eh -> 41h Addr:01Fh -> 56h Addr:020h -> 45h Addr:021h -> 43h Addr:022h -> 20h Addr:023h -> 54h Addr:024h -> 69h Addr:025h -> 6Eh Addr:026h -> 79h Addr:027h -> 20h Addr:028h -> 62h Addr:029h -> 6Fh Addr:02Ah -> 6Fh Addr:02Bh -> 74h Addr:02Ch -> 6Ch Addr:02Dh -> 6Fh Addr:02Eh -> 61h Addr:02Fh -> 64h Addr:030h -> 65h Addr:031h -> 72h Addr:032h -> 20h Addr:033h -> 31h Addr:034h -> 30h Addr:035h -> 4Dh Addr:036h -> 48h Addr:037h -> 7Ah Addr:038h -> 20h Addr:039h -> 31h Addr:03Ah -> 39h Addr:03Bh -> 32h Addr:03Ch -> 30h Addr:03Dh -> 30h Addr:03Eh -> 62h Addr:03Fh -> 64h Addr:040h -> 73h Addr:041h -> 0Ch Addr:042h -> 0Dh Addr:043h -> 00h Addr:044h -> 78h Addr:045h -> 78h Addr:046h -> 78h Addr:047h -> 78h Addr:048h -> 78h Addr:049h -> 78h Addr:04Ah -> 78h Addr:04Bh -> 78h Addr:04Ch -> 78h Addr:04Dh -> 78h Addr:04Eh -> 78h Addr:04Fh -> 78h Addr:050h -> 78h Addr:051h -> 78h Addr:052h -> 78h Addr:053h -> 78h Addr:054h -> 78h Addr:055h -> 78h Addr:056h -> 78h Addr:057h -> 78h Addr:058h -> 78h Addr:059h -> 78h Addr:05Ah -> 78h Addr:05Bh -> 78h Addr:05Ch -> 78h Addr:05Dh -> 78h Addr:05Eh -> 78h Addr:05Fh -> 78h Addr:060h -> 78h Addr:061h -> 78h Addr:062h -> 20h Addr:063h -> 0Ch Addr:064h -> 0Dh Addr:065h -> 00h Addr:066h -> 20h Addr:067h -> 78h Addr:068h -> 78h Addr:069h -> 78h Addr:06Ah -> 78h Addr:06Bh -> 78h Addr:06Ch -> 78h Addr:06Dh -> 78h Addr:06Eh -> 78h Addr:06Fh -> 78h Addr:070h -> 78h Addr:071h -> 78h Addr:072h -> 78h Addr:073h -> 78h Addr:074h -> 20h Addr:075h -> 00h WRITE OK at 21:51, time:4.576 sec ******************************* Resultat sur Terminal VBRAY ******************************* 18F258_IR_RS232 10/10/2011 AVEC Tiny bootloader 10MHz 19200bds Message 1 en FLASH MEMORY .... de 64 caracteres sur 2 lignes Message 2 en FLASH MEMORY 32car usage de BANK 1 ........ usage interrupt sur RB0 ....... usage interrupt sur TMR1 ...... EEPROM en F00000 0..255 bytes xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx <0>TOUCHE = 3Fh TV_ TOUCHE = 2Bh Droite TOUCHE = 1Dh Bas TOUCHE = 2Ch Gauche TOUCHE = 1Fh TOUCHE = 57h OK_ TOUCHE = 10h VOL + TOUCHE = 0Dh MUTE_ TOUCHE = 11h VOL - TOUCHE = 16h BassUp TOUCHE = 17h BassDw TOUCHE = 18h TrebUp TOUCHE = 19h TrebDw TOUCHE = 26h TOUCHE = 3Fh TV_ TOUCHE = 2Eh TOUCHE = 0Fh OSD_ TOUCHE = 10h VOL + TOUCHE = 11h VOL - TOUCHE = 2Bh Droite TOUCHE = 2Ch Gauche TOUCHE = 1Ch Haut TOUCHE = 1Dh Bas