chiark / gitweb /
hostside: more length for bavarian
[trains.git] / detpic / energy.asm
1 ;======================================================================
2 ; TRACK POWER AND SHORT CIRCUIT
3
4   include common.inc
5
6 settling_timeout        equ      10000 ; us
7
8 stopping_timeout        equ     500000 ; us
9 stopflash_timeout       equ     100000 ; us
10 retriableflash_timeout  equ     500000 ; us
11
12   udata_acs
13 settling        res     1 ; all counters are 0 if stopped
14 stopping_wait   res     1 ;  or otherwise count down
15 ledflash_wait   res     1
16
17 fault_spurious_count    res     1
18
19   code
20
21 ;======================================================================
22 ;
23 ; POLARISING/SETTLING:
24 ;
25 ;               NMRA            flag_p. settling        Booster PWM
26 ;
27 ; Normal        running         0       stopped         mark
28 ; Polarising    paused          1       stopped         space
29 ; Settling      paused          1       running         space
30 ;
31 ; NMRA is paused by disabling timer 0 intr; when we restart,
32 ; we restart the current message.
33 ;
34 ;----------------------------------------------------------------------
35
36 ;--------------------
37 power_polarising_init @
38         clr_f   settling
39         pin_h   p0_booster_pwm
40         return
41
42 ;--------------------
43 power_polarising_begin @
44         pin_vl  p0_booster_pwm
45         bc_f    INTCON, TMR0IE ; disables NMRA interrupt
46         bs_f    flags, flags_polarising
47         clr_f   settling
48         return
49
50 ;--------------------
51 power_polarising_nonetodo @
52 ; idempotent
53         bt_f_if0 flags, flags_polarising
54         return
55         tst_f_ifnz settling
56         return
57         mov_lw  settling_timeout / tick_us
58         mov_wf  settling
59         return
60
61 ;--------------------
62 power_polarising_tick @
63         tst_f_ifnz settling
64         dec_f_ifnz settling ; decrement if not zero
65         return ; return if not dec'd, or if decrement didn't make zero
66         ; settle timeout complete:
67
68         bc_f    flags, flags_polarising
69
70         tst_f_ifnz stopping_wait
71         bra     power_polarising_done_ifstopping
72         pin_vh  p0_booster_pwm
73 power_polarising_done_ifstopping
74
75         call    nmra_restartmessage
76         bs_f    INTCON, TMR0IE ; reenables NMRA interrupt
77         goto    i2c_consider_restartread
78
79 ;======================================================================
80 ;
81 ; FAULTS AND POWER:
82 ;
83 ;
84 ;                 Off     On       Stopping     Retriable       Watchdogged
85 ; Recognise by
86 ;  stopping_wait  0       0        >0           0               0
87 ;  ledflash_wait  0       0        >0           >0              0
88 ;  b._shutdowwn   H       L        H            H               H
89 ;  b._userfault_  H       H        *            *               L
90 ;
91 ; Managed here:
92 ;  shutdown       H       L        H            H               H
93 ;  Fault LED      -       -        50% 1/100ms  50% 1/500ms     on
94 ;  Timeout?       -       -        500ms        -               -
95 ;   next state                      Retriable
96 ;
97 ; Elsewhere:
98 ;  CDU            -       ON       ON           ON              ON
99 ;  booster_pwm    !polar  !polar   OFF          !polar          !polar[1]
100 ;   so power is   -       ON       off!         -               -
101 ;
102 ; Events, results:
103 ;  Fault          -       Stopping -            Stopping[2]     Stopping
104 ;  Watchdog       -       W'dogged -            -               -
105 ;  ON             On      (On)     -            On              On
106 ;  OFF            (Off)   Off      -            Off             Off
107 ;  (- means event ignored)
108 ;
109 ; [1] booster_pwm `!polar' means on if we're not polarising.
110 ; [2] this is not supposed to happen but we don't check for it
111
112 ;--------------------
113 power_fault_init @
114         bs_f    INTCON2, INTEDG1 ; rising edge
115         bc_f    INTCON3, INT1IP
116         bc_f    INTCON3, INT1IF
117         bs_f    INTCON3, INT1IE
118         pin_h   p0_booster_shutdown
119         pin_h   p0_booster_userfault_
120         clr_f   ledflash_wait
121         clr_f   stopping_wait
122         clr_f   fault_spurious_count
123         ; now we are Off
124         return
125
126 command_power_section code 0x2080
127 ;--------------------
128 command_power_on @
129         tst_f_ifnz stopping_wait
130         return  ; that deals with Stopping
131         ; safe to just turn On, even if already On
132
133         pin_vl  p0_booster_shutdown
134         pin_vh  p0_booster_userfault_
135         clr_f   ledflash_wait
136         goto    cdu_on
137
138 ;----------
139 command_power_off @
140         tst_f_ifnz stopping_wait
141         return  ; that deals with Stopping
142         ; safe to just turn Off, even if already Off
143
144         pin_vh  p0_booster_shutdown
145         pin_vh  p0_booster_userfault_
146         clr_f   ledflash_wait
147         goto    cdu_off
148
149 code2 code
150 ;--------------------
151 power_fault_intrl @
152         bt_f_if0 INTCON3, INT1IF
153         return
154         ; we may have a fault:
155
156         bc_f    INTCON3, INT1IF
157
158         call    portb_read
159         pin_inw_ifh p0_booster_overload
160         bra     fault_isactual
161         ; spurious:
162
163         inc_f_ifz fault_spurious_count  ; ++f.s._count == 0x00 ?
164         bs_f    fault_spurious_count, 7 ; f.s._count = 0x80
165
166         intrl_handled_nostack
167
168 ;-----
169 fault_isactual
170         pin_vl  p0_booster_pwm
171         pin_vh  p0_booster_shutdown
172         tst_f_ifnz stopping_wait
173         bra     fault_isactual_ifalreadystopping
174
175         mov_lw  b'00000111'
176         call    serial_addbyte
177
178         mov_lw  stopping_timeout / tickdiv_us
179         mov_wf  stopping_wait
180         pin_vh  p0_booster_userfault_
181         rcall   power_led_start_stoppingflash
182
183 fault_isactual_ifalreadystopping
184         intrl_handled_nostack
185
186 ;--------------------
187 power_fault_tick @
188         tst_f_ifnz ledflash_wait
189         dec_f_ifnz ledflash_wait
190         return
191 ;... ledflash_wait was running but has just reached zero; flash the LED
192
193         pin_vhl p0_booster_userfault_
194
195 power_led_start_retriableflash
196         mov_lw  retriableflash_timeout / 2 / tick_us
197         tst_f_ifnz stopping_wait
198 power_led_start_stoppingflash
199         mov_lw  stopflash_timeout / 2 / tick_us
200         mov_wf  ledflash_wait
201         return
202
203 ;--------------------
204 power_watchdog_timeout @
205         pinlat_ifh p0_booster_shutdown
206         return
207 ;... must be On, so go to Watchdogged
208         pin_vh  p0_booster_shutdown
209         pin_vl  p0_booster_userfault_
210         return
211
212 ;--------------------
213 power_fault_tickdiv @
214         tst_f_ifnz fault_spurious_count
215         bra     fault_spurious_tickdiv
216         ; in any case:
217 fault_tickdiv_rest
218         tst_f_ifnz stopping_wait
219         dec_f_ifnz stopping_wait
220         return
221         ; stopping_wait was running but has just reached zero;
222         ; we were in Stopping, go to Retriable:
223
224         rcall   power_led_start_retriableflash
225
226         bt_f_if0 flags, flags_polarising
227         pin_vh  p0_booster_pwm
228
229         mov_lw  b'00000110'
230         goto    serial_addbyte  
231
232 ;----------
233 fault_spurious_tickdiv
234 ; does not return, instead continues with fault_tickdiv_rest
235         mov_lw  0xc1 ; SPURIOUS
236         call    serial_addbyte
237
238         mov_fw  fault_spurious_count
239         bra_n   fault_spurious_tickdiv_isoverflow
240 fault_spurious_tickdiv_writeamt
241         call    serial_addbyte_another
242         clr_f   fault_spurious_count
243         bra     fault_tickdiv_rest
244
245 ;-----
246 fault_spurious_tickdiv_isoverflow
247         mov_lw  0x7f
248         bra     fault_spurious_tickdiv_writeamt
249
250 ;--------------------
251 power_panichook @
252         pin_vh  p0_booster_shutdown
253         pin_vl  p0_booster_pwm
254         pin_vh  p0_booster_userfault_
255         return
256
257 ;======================================================================
258   include final.inc