+;ERRORS:
+
+; 1red = high interrupt bit set
+; 2red = low interrupt bit set by something which isn't timer0 or the USART
+
+
+
; pin 21 (per-pic-led, RD2/PSP2/C1IN) states: high H = green, low L = red, float Z = black
include /usr/share/gputils/header/p18f458.inc
org 0
goto initialise
+;*****************************************************************************************
; high priority interrupt
org 000018h
goto interrupt_low
+;*****************************************************************************************
code
initialise
+; interrupt set-up
; globally enable interrupts - p77
bsf RCON,7,0 ; enable priority levels
bsf INTCON,7,0 ; enable high-priority interrupts
bsf INTCON,6,0 ; enable low-priority interrupts
+; interrupt set-up for serial receive
+ bsf PIE1,5,0 ; enable USART receive interrupt (p85)
+ bsf IPR1,5,0 ; set to low-priority interrupt
+
+; interrupt set-up for timer0 interrupt p79/80
+ bsf INTCON,5,0 ; enable timer0 interrupts
+ bcf INTCON2,2,0 ; timer0 overflow low priority
+
+
+;-----------------------------------------------------------------------------------------
+
+
+; serial set-up
+
; initial config - TXSTA register p181
bcf TXSTA,6,0 ; p181, set 8-bit mode
bsf TXSTA,5,0 ; transmit enable
bsf SPBRG,7,0
bsf SPBRG,0,0
-; interrupt set-up for serial receive
- bsf PIE1,5,0 ; enable USART receive interrupt (p85)
- bsf IPR1,5,0 ; set to low-priority interrupt
+;-----------------------------------------------------------------------------------------
+; timer set-up
; LED pin (21) initialisation
bcf TRISE,4,0 ; turn off PSPMODE (Data Sheet p100/101)
-; *** check relevant pin is set as output
-
; timer0 initial config for led flash
- bcf T0CON,6,0 ; p107 Timer0 -> 16bit mode
- bcf T0CON,5,0 ; timer0 use internal clock
- bcf INTCON,5,0 ; clear TMR0IE => mask interrupt
- bcf T0CON,3,0 ; use prescaler
- bcf T0CON,2,0 ; }
- bsf T0CON,1,0 ; } prescale value 1:8 (13ms x 8)
- bcf T0CON,0,0 ; }
+; bcf T0CON,6,0 ; p107 Timer0 -> 16bit mode
+; bcf T0CON,5,0 ; timer0 use internal clock
+; bcf T0CON,3,0 ; use prescaler
+; bcf T0CON,2,0 ; }
+; bsf T0CON,1,0 ; } prescale value 1:8 (13ms x 8)
+; bcf T0CON,0,0 ; }
-; *** timer for nmra bits
+; *** setup for timer0 for nmra bits
+
+;-----------------------------------------------------------------------------------------
-; 00h = data present to read byte
-; 01h = next write location byte
-; 10h-1Fh
-; 20h-2Fh
-; 30h-3Fh
-; 40h-4Fh = 4 rolling registers (check this is in the right buffer range)
+; initialise buffers
-main_loop
-; flash led
- goto main_loop
+ movlw 5
+ movwf FSR0H,0
+ clrf FSR0L,0 ; set next empty buffer to 500h
+ movlw 5
+ movwf FSR1H,0
+ clrf FSR1L,0 ; set current buffer to 500h
+;*****************************************************************************************
+main_loop_led
+ call led_green
+ call waiting
+ call led_black
+ call waiting
+ goto main_loop_led
-timer_interrupt
-;
-; clear interrupt
-; retfie
-
+;*****************************************************************************************
+interrupt_high
+ call led_red
+ call waiting
+ retfie 1
-check_last_byte
-; shift L
-; read C; if 0 then call call nmra_transmit, if 1 then branch to nmra_transmit
-; move to next byte
+;*****************************************************************************************
+interrupt_low
-nmra_transmit
-; shift L
-; read C, transmit (extra timer loop of nmra-0)
-; repeat for bits 5-0
-; clear byte
+; *** check which interrupt. Branch to serial_receive or timer or return
+ btfss PIR1,5,0 ; check whether serial receive interrupt bit set
+ goto serial_receive
+ btfss INTCON,2,0 ; check whether timer0 interrupt set
+ goto timer0_interrupt
+ call led_red
+ call waiting
+ call led_red
+ retfie ; return from interrupt to main if spurious interrupt
+
+;*****************************************************************************************
+
+serial_receive
-interrupt_low
-; *** check which interrupt. Branch to receive_serial or timer or return
- btfss PIR1,5,0 ; check whether serial receive interrupt bit set
- retfie ; return from interrupt to main if spurious interrupt
-receive_serial
-; ***
-; check buffer to write to
-; check byte to write to
-; read from serial to this buffer/byte
-; check top bit. if 0, add 1 to byte. if 1, add 1 to buffer and set byte to 0 and mark buffer full
-; clear interrupt
- retfie ; needs # ?
+;*****************************************************************************************
+timer0_interrupt
+
+ bcf INTCON,2,0 ; clear interrupt-set bit
+ retfie 1
+
+nmra_transmit
+;*****************************************************************************************
waiting
-; *** change to me the right length (58us eventually, slower first)
+; change - timer0 now for NMRA timer; run this off timer0+counter
+
bcf INTCON,2,0 ; clear timer0 interrupt bit (p109)
clrf TMR0H,0 ; p107 set high bit of timer0 to 0 (buffered,
; so only actually set when write to tmr0l occurs)
return
+;*****************************************************************************************
end
+;ERRORS:
+
+; 1red = high interrupt bit set
+; 2red = low interrupt bit set by something which isn't timer0 or the USART
+
+
+
; pin 21 (per-pic-led, RD2/PSP2/C1IN) states: high H = green, low L = red, float Z = black
include /usr/share/gputils/header/p18f458.inc
org 0
goto initialise
+;*****************************************************************************************
; high priority interrupt
org 000018h
goto interrupt_low
+;*****************************************************************************************
code
initialise
+; interrupt set-up
; globally enable interrupts - p77
bsf RCON,7,0 ; enable priority levels
bsf INTCON,7,0 ; enable high-priority interrupts
bsf INTCON,6,0 ; enable low-priority interrupts
+; interrupt set-up for serial receive
+ bsf PIE1,5,0 ; enable USART receive interrupt (p85)
+ bsf IPR1,5,0 ; set to low-priority interrupt
+
+; interrupt set-up for timer0 interrupt p79/80
+ bsf INTCON,5,0 ; enable timer0 interrupts
+ bcf INTCON2,2,0 ; timer0 overflow low priority
+
+
+;-----------------------------------------------------------------------------------------
+
+
+; serial set-up
+
; initial config - TXSTA register p181
bcf TXSTA,6,0 ; p181, set 8-bit mode
bsf TXSTA,5,0 ; transmit enable
bsf SPBRG,7,0
bsf SPBRG,0,0
-; interrupt set-up for serial receive
- bsf PIE1,5,0 ; enable USART receive interrupt (p85)
- bsf IPR1,5,0 ; set to low-priority interrupt
+;-----------------------------------------------------------------------------------------
+; timer set-up
; LED pin (21) initialisation
bcf TRISE,4,0 ; turn off PSPMODE (Data Sheet p100/101)
-; *** check relevant pin is set as output
-
; timer0 initial config for led flash
- bcf T0CON,6,0 ; p107 Timer0 -> 16bit mode
- bcf T0CON,5,0 ; timer0 use internal clock
- bcf INTCON,5,0 ; clear TMR0IE => mask interrupt
- bcf T0CON,3,0 ; use prescaler
- bcf T0CON,2,0 ; }
- bsf T0CON,1,0 ; } prescale value 1:8 (13ms x 8)
- bcf T0CON,0,0 ; }
+; bcf T0CON,6,0 ; p107 Timer0 -> 16bit mode
+; bcf T0CON,5,0 ; timer0 use internal clock
+; bcf T0CON,3,0 ; use prescaler
+; bcf T0CON,2,0 ; }
+; bsf T0CON,1,0 ; } prescale value 1:8 (13ms x 8)
+; bcf T0CON,0,0 ; }
-; *** timer for nmra bits
+; *** setup for timer0 for nmra bits
+
+;-----------------------------------------------------------------------------------------
-; 00h = data present to read byte
-; 01h = next write location byte
-; 10h-1Fh
-; 20h-2Fh
-; 30h-3Fh
-; 40h-4Fh = 4 rolling registers (check this is in the right buffer range)
+; initialise buffers
-main_loop
-; flash led
- goto main_loop
+ movlw 5
+ movwf FSR0H,0
+ clrf FSR0L,0 ; set next empty buffer to 500h
+ movlw 5
+ movwf FSR1H,0
+ clrf FSR1L,0 ; set current buffer to 500h
+;*****************************************************************************************
+main_loop_led
+ call led_green
+ call waiting
+ call led_black
+ call waiting
+ goto main_loop_led
-timer_interrupt
-;
-; clear interrupt
-; retfie
-
+;*****************************************************************************************
+interrupt_high
+ call led_red
+ call waiting
+ retfie 1
-check_last_byte
-; shift L
-; read C; if 0 then call call nmra_transmit, if 1 then branch to nmra_transmit
-; move to next byte
+;*****************************************************************************************
+interrupt_low
-nmra_transmit
-; shift L
-; read C, transmit (extra timer loop of nmra-0)
-; repeat for bits 5-0
-; clear byte
+; *** check which interrupt. Branch to serial_receive or timer or return
+ btfss PIR1,5,0 ; check whether serial receive interrupt bit set
+ goto serial_receive
+ btfss INTCON,2,0 ; check whether timer0 interrupt set
+ goto timer0_interrupt
+ call led_red
+ call waiting
+ call led_red
+ retfie ; return from interrupt to main if spurious interrupt
+
+;*****************************************************************************************
+
+serial_receive
-interrupt_low
-; *** check which interrupt. Branch to receive_serial or timer or return
- btfss PIR1,5,0 ; check whether serial receive interrupt bit set
- retfie ; return from interrupt to main if spurious interrupt
-receive_serial
-; ***
-; check buffer to write to
-; check byte to write to
-; read from serial to this buffer/byte
-; check top bit. if 0, add 1 to byte. if 1, add 1 to buffer and set byte to 0 and mark buffer full
-; clear interrupt
- retfie ; needs # ?
+;*****************************************************************************************
+timer0_interrupt
+
+ bcf INTCON,2,0 ; clear interrupt-set bit
+ retfie 1
+
+nmra_transmit
+;*****************************************************************************************
waiting
-; *** change to me the right length (58us eventually, slower first)
+; change - timer0 now for NMRA timer; run this off timer0+counter
+
bcf INTCON,2,0 ; clear timer0 interrupt bit (p109)
clrf TMR0H,0 ; p107 set high bit of timer0 to 0 (buffered,
; so only actually set when write to tmr0l occurs)
return
+;*****************************************************************************************
end