chiark / gitweb /
documentation, organisation, and error-handling improvements
authorian <ian>
Sat, 3 Dec 2005 16:56:34 +0000 (16:56 +0000)
committerian <ian>
Sat, 3 Dec 2005 16:56:34 +0000 (16:56 +0000)
detpic/common.inc
detpic/detect.asm
detpic/morse.messages
detpic/variables.asm

index 31262c9cccaaa4d5edf3ff56b15200495d4b2abf..21409b7a7b7bcc672305def2ade0257952a23788 100644 (file)
@@ -16,15 +16,59 @@ clock equ -1
 
 ;----------------------------------------------------------------------
 ; Common conventions for function register notation:
-; NOTE THAT THIS IS WRONG FIXME FIXME
-AND CHECK IT FIXME
+
 ;                      Master                  Slave
+; Registers etc.
 ;   W                  Trashed                 Trashed
 ;   STATUS             Trashed                 Trashed
 ;   BSR                        Not used                Not used
-;   TBLPTR*,TABLAT     Reserved for ISR/init   Not used except init
-;   FSR0               Reserved for ISR/init   Reserved for ISR/init
-;   FSR1, FSR2         Trashed                 Reserved for I2C/init
+;   t                  Low ISR                 Low ISR
+;   TBLPTR*,TABLAT     Low ISR                 Low ISR
+;   FSR0               Low ISR                 Low ISR
+;   FSR1               Low ISR                 High ISR (detect)
+;   FSR2               Low ISR                 High ISR (detect)
+;
+; Trashed      May be trashed by any routine anywhere.  Saved
+;              during every ISR entry/exit.
+;
+; Low ISR      May be used/traashed by any routine run in low-priority
+;              interrupt, or any routine run during initialisation.
+;              May therefore not be used in background loop with
+;              interrupts enabled.  May not be used by high-priority
+;              ISR (unless explicitly saved).
+;
+; High ISR     May be used/trashed by any routine run in high-priority
+;              interrupt, or any routine run during initialisation.
+;              May therefore not be used elsewhere with interrupts
+;              enabled.
+;
+;              Only the routines specially noted as intended to
+;              be called from the High ISR are safe.
+;
+; ... (subsystem)
+;              Register is reserved for use by this subsystem, which
+;              is allowed to expect the value to be preserved.
+;              Anything else which uses it must save and restore (and
+;              may also need to disable interrupts, depending on its
+;              relative status).
+;
+; Not High     May be used by any routine not running in high-priority
+;              interrupt.  Not saved by high-priority interrupt
+;              entry/exit, so any high-priority interrupt routine which
+;              uses this register must save and restore it.
+;
+; A routine which is allowed to trash a register may document that it
+; saves that register for the benefit of its callers.
+;
+; General-purpose hardware allocation:
+;
+;                      Master                  Slave
+;  Timer 0             nmra                    Disabled
+;  Timer 2             -                       -
+;  Timer 1             1ms tick, int. low      1ms tick, int. low
+;  CCP1                        1ms tick, int. low      1ms tick, int. low
+;  Timer 3             -                       -
+;  ECCP                        -                       -
 
 ;----------------------------------------------------------------------
 ; MACROS
index 8709db43ed7690af9ed67d44b2c754ace48b4957..1275fd702080de53448cfac151e685d5fa27d36f 100644 (file)
@@ -9,6 +9,30 @@
 
  include common.inc
 
+; I2C protocol is as follows:
+;
+;  Master periodically polls each slave, addressing it for reading.
+;  The slave replies with the first byte of a self-delimiting message.
+;  The master must then read the whole message before doing anything
+;  else on the bus.
+;
+;  First byte is like this:
+;      MM 05 B2 B1  10 13 16 08        (detectors)
+;      MM zz 01 02  03 00 04 05        (reversers)
+;  where
+;      B1 and B2 indicates that the is more detection data;
+;              each bit corresponding to a subsequent byte:
+;              if the bit is set the byte is present; otherwise
+;              it is skipped and the contents can be presumed
+;              to be the same as last time (initially: 0)
+;      zz      is a zero bit
+;      MM      indicates that there are extra message byte(s)
+;
+;  Following that are the zero, one or two more bytes of
+;  detection data, 
+;      X and Y indicate that further detection bytes exist
+;      M indicates that more 
+
 ;======================================================================
 ; variables and memory organisation
 
@@ -19,14 +43,14 @@ max_messages equ 4
 unattended     res     1       ; counts down once for each det loop
                                ; and if it reaches 0, led is set to red
 
-scana  res     1 ; see bit-twiddling below
-scanb  res     1
-scanc  res     1
-scand  res     1
-scane  res     1
+scana          res     1 ; see bit-twiddling below
+scanb          res     1
+scanc          res     1
+scand          res     1
+scane          res     1
 
-last1  res     1
-last2  res     1
+last1          res     1
+last2          res     1
 
 buf0_startval          res     1 ; reversers start with some det bits
 buf0                   res     1
@@ -34,7 +58,8 @@ message_buffer                res     max_messages
 message_buffer_end
 
 ;----------------------------------------------------------------------
-; buf0, message_buffer, and FSR1 look like this:
+; buf0, message_buffer, and FSR1 are used mainly for recording
+; non-detection messages.  They look like this:
 ;
 ;  +--------+--------+--------+--------+--------+
 ;  |  buf0  | message_buffer...                 |
@@ -46,16 +71,27 @@ message_buffer_end
 ;            ^
 ;  |1d0d0000|1aaaaaaa 0bbbbbbb ???????? ????????|   two extra bytes
 ;
-; etc.    (bits labelled `d' are detection data on reversers boards
+; etc.    Bits labelled `d' are detection data on reversers boards
 ;          0 on detectors boards; `a' and `b' are extra message data;
-;          `^' indicates the byte pointed to by FSR1)
+;          `^' indicates the byte pointed to by FSR1
+;
+;----------------------------------------------------------------------
+;
+; outbuf and FSR2 are used (on slaves) for the message we are
+; transmitting.  FSR2 points to the next byte to transmit (ie, which
+; will be read).  outmsg_end points to the first byte after the
+; message, and is used for read overrun detection.
+;
+; During i2csu_read_start (High ISR), the actual first byte of the
+; message to be sent is calculated from buf0, and transmitted; the
+; extra detection bytes (if any) are stored in outbuf, and any extra
+; messages (from message_buffer) are also appended to outbuf.
 ;
-
 ;======================================================================
        code
 
 ;----------
-det_common_setup
+det_common_init
        mov_lw  0b111   ; turn off comparator, or we can't use pins
        mov_wf  CMCON   ;   RD0-RD4 as digital inputs
        mov_lw  0b0110  ; turn off A/D except perhaps for pin
@@ -63,8 +99,8 @@ det_common_setup
        return
 
 ;----------
-det_slave_setup
-       bsr     det_common_setup
+det_slave_init
+       bsr     det_common_init
        set_f   scana
        set_f   scanb
        set_f   scanc
@@ -78,6 +114,9 @@ det_slave_setup
 
        mov_wf  buf0_startval
 
+       mov_lfsr outbuf, 2
+       clr_f   outmsg_end
+
        goto    reset_message_buffer
 
 ;----------
@@ -92,25 +131,28 @@ slave_add_short_message
 
 ;----------
 i2csu_read_begin
+; called from High ISR, see i2clib.inc
        bt_f_if1 idloc1,idloc1_boarddet
        bra     det_slave_read_start_detectors
        bra     det_slave_read_start_reversers
 
 ;----------
 i2csu_read_another
+; called from High ISR, see i2clib.inc
        mov_fw  POSTINC2
        call    i2cs_read_data
-       bt_f_if0 FSR2L, outbuf_szln2
+       mov_fw  outmsg_end
+       cmp_fw_ifle FSR2L
        return
        ; oops
        panic   morse_DR
 
 ;----------
-det_scanloop_again macro det_scanloop_whatever
+backgroundloop_again macro backgroundloop_whatever
        dec_f_ifnz unattended
-       bra     det_scanloop_whatever
+       bra     backgroundloop_whatever
        call    led_red
-       bra     det_scanloop_whatever
+       bra     backgroundloop_whatever
        endm
 
 ;======================================================================
@@ -130,15 +172,31 @@ det_scanloop_again macro det_scanloop_whatever
 
                        ; buf0  MM zz B2 B1  zz zz zz zz
 
+               ; scheme for bit shuffling:
+               ;
                ; 1:    ; _<A   19 09 12 15  18 xx xx xx
-                       ; >>B   xx xx xx xx  xx 04 20 17
-
+               ;       ; >>B   xx xx xx xx  xx 04 20 17
+               ;
                ; 2:    ; _>E   06 xx xx xx xx  xx 03 00
-                       ; [*D   xx 01 07 02  11 14 xx ??  C=08
-               
+               ;       ; [*D   xx 01 07 02  11 14 xx ??        C=08
+               ;
                ; 0:    ; [_C   xx 05 xx xx  10 13 16 08
+               ;
+;              ; where _ means do nothing
+               ;       *       swap nybbles
+               ;       <       rotate left
+               ;       >       rotate right
+               ;       [       rotate left through carry (NB
+               ;                that the carry bit propagates to
+               ;                the subsequent [ or ] *in the
+               ;                same column*).
+               ; and the operation done first (in backgroundloop)
+               ; is on the right next to the port letter and the one
+               ; done second (in i2csu_read_begin_...) is shown
+               ; on the left, above.
 
-det_scanloop_detectors
+;----------
+backgroundloop_detectors
        rr_fw   PORTB   ; W     xx xx xx xx  04 20 17 xx (now)
        and_wff scanb   ; b     xx xx xx xx  04 20 17 xx (cumulative)
        rl_fw   PORTA   ; W     19 09 12 15  18 xx xx xx (now)
@@ -152,10 +210,10 @@ det_scanloop_detectors
        mov_fw  PORTC   ; W     xx xx 05 xx  xx 10 13 16 (now)
        and_wff scanc   ; c     xx xx 05 xx  xx 10 13 16 (cumulative)
 
-       det_scanloop_again det_scanloop_detectors
+       backgroundloop_again backgroundloop_detectors
 
 ;----------            ; buf0  MM zz zz zz  zz zz zz zz
-det_slave_read_start_detectors
+i2csu_read_begin_detectors
  ; detection byte 1
        mov_lw  0xf8    ; W     yy yy yy yy  yy zz zz zz
        and_wff scana   ; scana 19 09 12 15  18 zz zz zz
@@ -187,7 +245,7 @@ det_slave_read_start_detectors
 
        call    i2cs_read_data
 
-       mov_lfsr outbuf, 2
+       rcall   new_i2c_outmsg
 
        mov_fw  scana
        bt_f_if1 buf0,5
@@ -207,7 +265,7 @@ det_slave_read_start_detectors
 ;----------------------------------------------------------------------
 ; both detectors and reversers
 ;
-both_startread_tail
+i2csu_read_start_either_tail
        set_f   scana
        set_f   scand
 
@@ -220,21 +278,36 @@ msg_copy_loop
        mov_wf  POSTINC2
        bra_n   msg_copy_loop
 
+       mov_ff  FSR2L, outmsg_lastbyte
+
 reset_message_buffer
 ;  FSR1/buf0/message_buffer    any             set to empty
+;  may be called from High ISR or during init
        mov_lfsr message_buffer, 1
        mov_ff  buf0_startval, buf0
        clr_f   INDF1
        return
 
+;----------
+new_i2c_outmsg
+; Called from i2csu_read_start ISR to check that the whole of
+; the previous message was read, and to reset the FSR2 pointer
+; to point to the start of outbuf so that we can fill the outbuf.
+       mov_fw  FSR2L           ; W -> byte after the one we last sent
+       mov_lfsr outbuf, 2      ; FSR2 -> outbuf
+       cmp_fw_ifle outmsg_end  ; transmitted the last byte ?
+       return
+       ; no, oops:
+       panic   morse_DQ
+
 ;----------------------------------------------------------------------
 ; reversers
                        ; A     xx 01 xx 03  xx xx xx xx
                        ; B     xx xx xx xx  xx xx xx xx
                        ; C     xx xx xx xx  xx 00 xx xx
                        ; D     xx xx xx xx  xx xx 04 05
-                       ; E     xx xx xx xx  xx 02 xx xx
-det_scanloop_reversers
+;----------            ; E     xx xx xx xx  xx 02 xx xx
+backgroundloop_reversers
        rr_fw   PORTA   ; W     xx xx 01 xx  03 xx xx xx (now)
        and_wff scana   ; a     xx xx 01 xx  03 xx xx xx (cumulative)
        mov_fw  PORTD   ; D     xx xx xx xx  xx xx 04 05 (now)
@@ -243,10 +316,10 @@ det_scanloop_reversers
        bc_f    buf0,2  ; buf0  MM zz zz ss  zz 00 zz zz (cumulative)
        bt_f_if0 PORTE,2 ;                      02       (now)
        bc_f    buf0,4  ; buf0  MM zz zz 02  zz ss zz zz (cumulative)
-       det_scanloop_again det_scanloop_reversers
+       backgroundloop_again backgroundloop_reversers
 
 ;----------            ; buf0  MM zz zz 02  zz 00 zz zz
-det_slave_read_start_reversers
+i2csu_read_begin_reversers
        mov_fw  scana   ; W     xx xx 01 xx  03 xx xx xx
        and_lw  0x28    ; W     zz zz 01 zz  03 zz zz zz
        ior_wff buf0    ; buf0  MM zz 01 02  03 00 zz zz
@@ -257,7 +330,7 @@ det_slave_read_start_reversers
 
        call    i2cs_read_data
 
-       mov_lfsr outbuf, 2
+       rcall   new_i2c_outmsg
 
        bra     both_startread_tail
 
@@ -298,7 +371,7 @@ det_slave_read_start_reversers
 
 ; ask sub-pic s for data
 ; (i.e. send i2c request - will need to work out how to differentiate this
-; from requests fior other data from subpics, or make a general routine to 
+; from requests fior other data from subpics, or make a general routine to
 ; handle all sorts of data a subpic might send back)
 
 ; if no change, advance subpic # and return
@@ -330,7 +403,7 @@ det_slave_read_start_reversers
 ; main loop of slave program
 
 ; Reads from detection legs as defined by bitmasks Ma-e applied to ports a-e.
-; Writes the result into registers Pa-e. On i2c interrupt, checks that there 
+; Writes the result into registers Pa-e. On i2c interrupt, checks that there
 ; is new data to send to the master pic and if so sends it. Current state of
 ; master's knowledge is stored in Ca-e for comparison with Pa-e.
 ;
index 3b207a5158e63fd204c94ebe5f712ec225002fa4..9219297e56d5eee4a7a5d63173abcf035cfb92de 100644 (file)
@@ -44,6 +44,7 @@ SR    i2clib:st                       ; improper i2cm_read_start
 SA     i2clib:st                       ; improper i2cm_read_another
 SD     i2clib:st                       ; impr. i2cm_read_done/i2cs_read_data
 
-# Messages for slave/detection
+# Messages for slave detection/i2c
 DW                                     ; slave write (nyi)
-DR                                     ; slave read overrun
+DQ     FSR2L,outmsg_end                ; previous slave read incomplete
+DR     FSR2L,outmsg_end                ; slave read overrun
index 9e4728dccf4d65ceb5bc5aee667cdfb00fdf4342..9f76900c6ef6ec941981cb8514b95f54968563ce 100644 (file)
@@ -6,6 +6,7 @@ idloc1          res     1       ; from 2nd idlocs byte; bit 7 is master:
 idloc1_master  equ     7
 idloc1_boarddet        equ     6
 t              res     1       ; general temporary
+outmsg_end     res     1       ; first empty byte in outbuf
 
  udata 0x200
 outbuf_szln2   equ     7