
;°°°°°°°°°°°°°°°°°°°°°°°°°°°° (C) R.LETOURNEUR °°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°

;°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°
;°°°°°°°°° K°° K°°° III°°° TTTTT°°° 8888°°°°° 0000°°°° 55555°°°°° 11°°°°°°°°°°
;°°°°°°°°° K° K°°°°° I°°°°°° T°°°° 8°°° 8°°° 0°°° 0°°° 5°°°°°°°° 1 1°°°°°°°°°°
;°°°°°°°°° KKK°°°°°° I°°°°°° T°°°°° 8888°°°° 0°°° 0°°° 55555°°°°°° 1°°°°°°°°°°
;°°°°°°°°° K° K°°°°° I°°°°°° T°°°° 8°°° 8°°° 0°°° 0°°°°°°° 5°°°°°° 1°°°°°°°°°°
;°°°°°°°°° K°° K°°° III°°°°° T°°°°° 8888°°°°° 0000°°°° 55555°°°°° 111°°°°°°°°° 
;°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°

;°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°

                                 CHIP  8052
                                 SYMBOLS ON

;*****************************************************************************
;
;          Ce programme permet de telecharger un fichier au format INTEL.HEX 
; en memoire RAM via le port serie ( 9600,N,8,1 ). En fin de telechargement 
; le kit reboot par l'intermediaire du port  P1.0  automatiquement sur la  
; RAM-PROGAMME  et execute ainsi le programme d'application charge en RAM. 
;
;*****************************************************************************

;BANK0:		.REG	00H - 07H	RESERVED

;---------------------------------- PORTS ------------------------------------

REBOOT: REG     P1.0    ; Reboot apres telechargement

;---------------------------------- FLAGS ------------------------------------

FLAG:		.REG    20H   
EOF:		.REG    FLAG.0  ;INDIQUE FIN DE FICHIER 
COLUM:		.REG	FLAG.1	;INDIQUE DEBUT DE LIGNE RECU
CHECK:		.REG	FLAG.2	;VALIDE LA ROUTINE DE CALCUL DE CHECKSUM
FILLING:	.REG	FLAG.3	;BRANCHE SUR LA ROUTINE DE REMPLISSAGE MEMOIRE

;-------------------------------- REGISTRES ----------------------------------
                           
OCTET:  	.REG    08H     ;COMPTEUR DU NOMBRE D'OCTETS RECUS     
SUM:		.REG	09H	;REGISTRE DE CALCUL DE CHECKSUM
LENGTH:		.REG	0AH	;STOCKE LE NOMBRE D'OCTETS A RECEVOIR SUR LA LIGNE
ADHIGH:		.REG	0BH	;REGISTRE D'ADRESSE DE POIDS FORT
ADDLOW:		.REG	0CH	;REGISTRE D'ADRESSE DE POIDS FAIBLE
TYPE:		.REG	0DH	;RECORD TYPE FIELD "01" FOR END OF FILE
RX:     	.REG    0EH     ;POINTEUR IT SERIE DE FIFO DE RECEPTION
PILRX:  	.REG    0FH     ;POINTEUR DE FIFO SERIE
DPILRX: 	.REG    10H     ;POINTEUR DE FIFO SERIE
MEMSUM:		.REG	11H	;REGISTRE DE STOCKAGE DE CHECKSUM
RXFIFO:   	.REG    12H     ;NOMBRE DE CARACTERES STOCKES DANS LA FIFO DE RECEPTION SERIE 30H - 3FH
TXFIFO:   	.REG    13H     ;NOMBRE DE CARACTERES STOCKES DANS LA FIFO DE TRANSMISSION 
RECDAT:   	.REG    13H     ;NOMBRE D'OCTETS DE DATA ENREGISTRES

;------------------------------- CONSTANTES ----------------------------------

LF      EQU     0AH     ;ASCII LINE-FEED 
CR      EQU     0DH     ;ASCII CARRIAGE RETURN
CLS     EQU     0CH     ;ASCII CLEAR SCREEN
ESC     EQU     1BH     ;ASCII ESCAPE CODE
BEL     EQU     07H     ;RING BEL 

;*****************************************************************************
;                 INITIALISATION DES VECTEURS D'INTERRUPTIONS 
;*****************************************************************************


        ORG     0000H   ;VECTEUR DE RESET
	JMP     INIT

        ORG     0003H   ;VECTEUR INT0
        RETI

        ORG     000BH   ;VECTEUR TIMER0
        RETI

        ORG     0013H   ;VECTEUR INT1
        RETI

        ORG     001BH   ;VECTEUR TIMER1
        RETI

        ORG     0023H   ;VECTEUR LIAISON SERIE
        JMP     SERIE

        ORG     002BH
        RETI

;*****************************************************************************
;                         PROGRAMME D'INITIALISATION
;*****************************************************************************

        ORG     0050H

INIT:   MOV     SP,#60H 	; STACK DE 60H A 7FH          

        MOV     R0,#FFH 	; RESET MEMOIRE INTERNE DU MICRO
$0:     MOV     @R0,#00H
        DJNZ    R0,$0

        MOV     PSW,#00H

        CLR     RS0
        CLR     RS1     	;BANK 0 Actif

        MOV     SCON,#01010000B ;INIT PORT SERIE
                                ;B7-B6 = SM0-SM1 = 01 => UART 8 BITS MODE 1
                                ;B5 = SM2 = 0 => MODE SINGLE PROCESSOR
                                ;B4 = REN = 1 => ENABLE SERIAL RECEPTION

                                ;BAUD RATE GENERATOR IN MODE2 FOR 8052 ONLY
        ;MOV     RCAP2H,#FFH 
        ;MOV     RCAP2L,#DCH    ;RCAP2 = FFFF - 11,059MHZ / (32 x 9600 BAUD)

                                ;IN MODE 1 TIMER IS THE BAUD RATE GENERATOR
        MOV     TMOD,#20H       ;8-BIT AUTO-RELOAD TIMER1 SOFTWARE CONTROL

        MOV     TH1,#FDH        ;INITIALISE BAUD RATE GENERATOR ( K = 1 BECAUSE SMOD = 0 )
				;TH1 = 256 - ( K x 11,059MHZ / ( 384 x 9600 BAUD )) = 253

        SETB    TR1             ;TIMER 1 RUN CONTROL

        MOV     P1,#FFH         ;INIT PORT P1 ET P3 
        MOV     P3,#FFH

	MOV	DPTR,#ACCEUIL
        CALL    XSTRING         ;MESSAGE D'ACCEUIL

                                ;IP: INTERRUPT PRIORITY REGISTER
        SETB    PS              ;SERIAL PRIORITY LEVEL ITERRUPT IP.4 = 1

	CLR	TI
                                ;IE: INTERRUPT ENABLE REGISTER
        SETB    EA              ;IE.7 = EA = 1 => ENABLE INTERRUPTS
        SETB    ES              ;IE.4 = 1 => ENABLE SERIAL PORT INTERRUPT

        MOV    RXFIFO,#00H
        MOV    PILRX,#30H       ; INITIALISE LES POINTEURS DE LA FIFO  
        MOV    DPILRX,#30H      ; DE STOCKAGE DE RECEPTION SERIE

        JMP     MAIN

;*****************************************************************************
;             TRANSMITTING SERIAL PORT CHARACTER STRINGS SUBROUTINE
;*****************************************************************************


XSTRING:	CLR     A       	;( ZERO OFFSET ) DPTR LOADED WITH THE BEGININ OF THE STRING
                MOVC    A,@A + DPTR     ;FETCH FIRST CHARACTER OF STRING
		JMP	$2

        $1:     JNB     TI,$    	;WAIT UNTIL TRANSMITTER READY
	$2:	CLR     TI      	;MARK AS NOT READY
                MOV     SBUF,A  	;OUTPUT NEXT CHARACTER
                INC     DPTR    	;BUMP POINTER
                CLR     A		;( ZERO OFFSET )
                MOVC    A,@A + DPTR     ;GET NEXT OUTPUT CHARACTER
                CJNE    A,#ESC,$1       ;LOOP UNTIL ESCAPE READ

		JNB     TI,$    	;WAIT UNTIL TRANSMITTER READY
		RET

;*****************************************************************************
;                  SOUS PROGRAMME DE TELECHARGEMENT INTEL.HEX
;*****************************************************************************


		;A:	LOADED WITH RECEIVED DATA
		;R0:	USED FOR READING CHAR IN FIFO
		;R1:	USED FOR TESTING THE NUMBER OF THE RECEIVED BYTE
		;DPTR:	LOADED WITH EXTERNAL ADDRESS FOR LOADING DATA

LOADING: 	MOV	R0,DPILRX	;VIDANGE FIFO
		CJNE	R0,#3FH,$1	;TEST SI FIN DE FIFO
		MOV	DPILRX,#30H

	$1:	INC	DPILRX		;INCREMENTE LE POINTEUR DE LECTURE
		MOV	A,@R0		;LECTURE DU CARACTERE RECU DANS LA FIFO
		DEC	RXFIFO		;ET DECREMENTE LE POINTEUR DE CONTENU

		INC     OCTET		;COMPTE LES OCTETS RECUS
		
		JB	COLUM,ASC2BIN	;TESTING HEADER ':'

		CJNE	A,#":",NEWLINE	;STRIP LF, CR, ETC... AFTER END OF LINE
		SETB	COLUM		;HEADER OK
		RET

NEWLINE:	CLR	CHECK
		CLR	COLUM
		CLR	FILLING
		MOV	OCTET,#00H
		MOV	RECDAT,#00H
		MOV	SUM,#00H
                RET


ASC2BIN:	PUSH	A		;CONVERT ASCII VALUE IN BINARY 
		ANL	A,#30H
		CJNE	A,#30H,ALPHA	;TESTING NUMERIC/ALPHA VALUE 

		POP	A
		CLR	C     		
		SUBB	A,#30H		;NUMERIC VALUE 0 - 9
		JMP	OCTET1

	ALPHA:	POP	A
		CLR	C
		SUBB	A,#37H		;ALPHA   VALUE  A - F

	
	OCTET1:	JB	CHECK,CHECKSUM	;TESTING CHECKSUM BYTE

		JNB	FILLING,OCTET2
		CALL	FILL		;FILL EXTERNAL MEMORY WITH DATA CODE
		RET

	OCTET2:	MOV	R1,OCTET
		CJNE	R1,#2,OCTET3	
		RL	A		;RECORD LENGTH FIELD HIGH DIGIT
		RL	A
		RL	A
		RL	A
		MOV	LENGTH,A
		RET

	OCTET3:	CJNE	R1,#3,OCTET4	
		ORL	A,LENGTH
		MOV	SUM,A
		MOV	LENGTH,A	;RECORD LENGTH FIELD LOW DIGIT
		RET

	OCTET4:	CJNE	R1,#4,OCTET5
		RL	A		;RECORD HIGH DIGIT OF HIGH ADDRESS
		RL	A
		RL	A
		RL	A
		MOV	ADHIGH,A
		RET

	OCTET5:	CJNE	R1,#5,OCTET6	
		ORL	A,ADHIGH
		MOV	ADHIGH,A	;RECORD LOW DIGIT OF HIGH ADDRESS
		ADD	A,SUM
                MOV     SUM,A
		RET

	OCTET6:	CJNE	R1,#6,OCTET7	
		RL	A		;RECORD HIGH DIGIT OF LOW ADDRESS
		RL	A
		RL	A
		RL	A
		MOV	ADDLOW,A
		MOV	DPH,ADHIGH	;DPTR INITIALISED WITH HIGH DIGIT ADDRESS
		RET

	OCTET7:	CJNE	R1,#7,OCTET8	
		ORL	A,ADDLOW
		MOV	ADDLOW,A	;RECORD LOW DIGIT OF LOW ADDRESS
		ADD	A,SUM
                MOV     SUM,A
		MOV	DPL,ADDLOW	;DPTR INITIALISED WITH LOW DIGIT ADDRESS
		RET

	OCTET8:	CJNE	R1,#8,OCTET9	
		RL	A		;RECORD HIGH DIGIT OF TYPE FIELD
		RL	A
		RL	A
		RL	A
		MOV	TYPE,A
		RET

	OCTET9:	CJNE	R1,#9,OCTET10
		ORL	A,TYPE
		MOV	TYPE,A		;RECORD LOW DIGIT OF RECORD TYPE

		CJNE	A,#01H,TYPE0
		SETB	CHECK		;FOR CALCULATE THE CHEKSUM OF THE LINE BEFORE REBOOT
		SETB	EOF		;END OF FILE => TYPE = 01
		
	TYPE0:	ADD	A,SUM
                MOV     SUM,A

		SETB	FILLING		;FOR BRANCH ON FILL DATA SUBROUTINE
		RET

OCTET10:	JMP	NEWLINE


;-------------------------------- CHECKSUM -----------------------------------

CHECKSUM:	MOV	R1,OCTET
		ANL	R1,#01H		;A COMPLETE LINE IS ODD	=> OCTET = ODD
		CJNE	R1,#01H,SUMHI	;TESTING IF LAST DIGIT OF THE LINE
	      	
		ORL	A,MEMSUM	;EXTRACT LOW DIGIT OF THE CHECKSUM
		MOV	MEMSUM,A

		CLR	C
		MOV	A,#FFH		;CHECKSUM OPERATING
		SUBB	A,SUM
		INC	A
		CJNE	A,MEMSUM,SUMERR	;TESTING CHECKSUM ERROR
		JMP	NEWLINE

	SUMERR:	CLR	ES		;DISABLE SERIAL INTERRUPT
		MOV	DPTR,#CHKERROR	
		CALL	XSTRING
		RET

	SUMHI:	RL	A		;EXTRACT HIGH DIGIT OF THE CHECKSUM
		RL	A
		RL	A
		RL	A
		MOV	MEMSUM,A
		RET

		

;*****************************************************************************
;                      FILL EXTERNAL MEMORY SUBROUTINE
;*****************************************************************************


		;A:	LOADED WITH RECEIVED DATA
		;B:	USED FOR STORING DATA CODE BYTE
		;R1:	USED FOR TESTING THE NUMBER OF THE RECEIVED BYTE
		;DPTR:	LOADED WITH EXTERNAL ADDRESS FOR LOADING DATA


FILL:		MOV	R1,OCTET
		ANL	R1,#01H			;TEST IF HIGH DATA DIGIT
 		CJNE	R1,#01H,FILLHIGH	;IF ODD DIGIT => DIGITHIGH

		ORL	A,B
		
		MOVX	@DPTR,A			;LOAD DATA CODE IN EXTERNAL MEMORY
		INC	DPTR			;FOR LOADING NEXT DATA
		INC	RECDAT

		ADD	A,SUM
		MOV	SUM,A

		MOV	A,RECDAT
		CJNE	A,LENGTH,RETFILL	;TEST IF LAST DATA LINE

		SETB	CHECK			;NEXT DATA IS CHECKSUM VALUE
		CLR	FILLING
		RET

FILLHIGH:	RL	A
		RL	A
		RL	A
		RL	A
		MOV	B,A			;STORE HIGH DATA DIGIT

RETFILL:	RET


;*****************************************************************************
;                           PROGRAMME PRINCIPAL
;*****************************************************************************


MAIN:		MOV     A,RXFIFO  
        	JZ      MAIN            ;TESTE SI FIFO DE RECEPTION VIDE
        	CALL    LOADING		;FIFO PLEINE ON TRAITE LA DATA

        	JNB     EOF,MAIN        ;FIN DE FICHIER => REBOOT SUR P1.0
		JB	CHECK,MAIN	;TEST DE CHECKSUM AVANT	RESET

	        CLR     REBOOT          ;POSITIONNE P1.0 POUR REBOOTER  

LOOP:   	JMP     LOOP		;WAITING FOR HARD RESET

;*****************************************************************************
;                        INITERRUPTION LIAISON SERIE
;*****************************************************************************


SERIE:  	PUSH    PSW
        	PUSH    A

        	JB      RI,RECEIVE      ;TESTING RECEIVE  INTERRUPT
        	JB      TI,TRANSMIT     ;TESTING TRANSMIT INTERRUPT
        	JMP     RAZSER

TRANSMIT:       CLR     TI      	;CLEAR FLAG FOR NEW INTERRUPT
	        MOV     SBUF,A          ;LOAD DATA TO TRANSMIT
        	JMP     FSERIE

RECEIVE:        CLR     RI		;CLEAR FLAG FOR NEW INTERRUPT
		MOV     A,SBUF          ;READ RECEIVED BYTE IN BUFFER

		MOV	R0,PILRX
		CJNE	R0,#3FH,$1	;TESTING END OF FIFO	
		MOV	PILRX,#30H

	$1:	MOV	@R0,A		;STORE BYTE IN FIFO	

        	INC     PILRX		
        	INC     RXFIFO		
		MOV	A,RXFIFO
		CJNE	A,#0FH,FSERIE	;TESTING FULL FIFO
		
		CLR	ES		;DISABLE SERIAL INTERRUPT
		MOV	DPTR,#OVERFLOW
		CALL	XSTRING
        	JMP     FSERIE

RAZSER: 	MOV    RXFIFO,#00H	; ERREUR TX - RX INIT FIFO	
        	MOV    PILRX,#30H       ; INITIALISE LES POINTEURS DE LA FIFO  
        	MOV    DPILRX,#30H      ; DE STOCKAGE DE RECEPTION SERIE 


FSERIE: 	POP    A
        	POP    PSW
        	RETI          

;*****************************************************************************
;				MESSAGES ASCII
;*****************************************************************************


ACCEUIL:	DB      CLS
        	DB      'KIT8051 (C) R.LETOURNEUR'
        	DB      CR
        	DB      LF
        	DB      'LOADER INTEL.HEX'
        	DB      CR
        	DB      LF
        	DB      'READY FOR LOADING...'
        	DB      ESC

CHKERROR:	DB	'CHECKSUM ERROR!!!'
        	DB      CR
        	DB      LF
		DB	'LOADING PROGRAMM ABORTED.'
        	DB      ESC

OVERFLOW:	DB	'ERROR: FULL RXFIFO!!!'
		DB      CR
        	DB      LF
		DB	'LOADING PROGRAMM ABORTED.'
        	DB      ESC

;----------------------------------------------------------------------------
                                    END                                        
