Mercurial > public > hwos_code
diff src/sleepmode.asm @ 582:b455b31ce022
work on 2.97 stable
author | heinrichsweikamp |
---|---|
date | Mon, 26 Feb 2018 16:40:28 +0100 |
parents | b7eb98dbd800 |
children | ca4556fb60b9 |
line wrap: on
line diff
--- a/src/sleepmode.asm Sun Feb 25 18:25:38 2018 +0100 +++ b/src/sleepmode.asm Mon Feb 26 16:40:28 2018 +0100 @@ -1,113 +1,129 @@ ;============================================================================= ; -; File sleepmode.asm +; File sleepmode.asm Version 2.98 ; ; Sleepmode ; ; Copyright (c) 2011, JD Gascuel, HeinrichsWeikamp, all right reserved. -;============================================================================= +;============================================================================== ; HISTORY ; 2011-08-12 : [mH] moving from OSTC code -#include "hwos.inc" ; Mandatory header -#include "shared_definitions.h" ; Mailbox from/to p2_deco.c -#include "surfmode.inc" -#include "tft.inc" -#include "isr.inc" -#include "start.inc" -#include "adc_lightsensor.inc" -#include "math.inc" -#include "ms5541.inc" -#include "wait.inc" -#include "eeprom_rs232.inc" -#include "external_flash.inc" -#include "ghostwriter.inc" -#include "i2c.inc" -#include "mcp.inc" +#include "hwos.inc" ; Mandatory header +#include "shared_definitions.h" ; Mailbox from/to p2_deco.c +#include "surfmode.inc" +#include "tft.inc" +#include "isr.inc" +#include "start.inc" +#include "adc_lightsensor.inc" +#include "math.inc" +#include "ms5541.inc" +#include "wait.inc" +#include "eeprom_rs232.inc" +#include "external_flash.inc" +#include "ghostwriter.inc" +#include "i2c.inc" +#include "mcp.inc" - extern vault_decodata_into_eeprom + extern vault_decodata_into_eeprom + + + ;---- Private local variables ------------------------------------------------- -gui CODE + CBLOCK local1 ; max size is 16 Byte !!! + sm_temp1 ; sleepmode temporary 1 + sm_temp2 ; sleepmode temporary 2 + sm_timer1 ; timer for pressure check every 10 seconds + sm_timer2 ; timer for 10 minutes tasks (updating of tissues) + sm_timer3 ; timer for 15 minutes tasks (updating of surface pressure) + ENDC ; used: 5 byte, remaining: 11 byte + + +gui CODE + +;============================================================================== global sleeploop -sleeploop: ; enter sleepmode! - call disable_ir_s8 ; IR/S8 off - call mcp_sleep - bcf LEDg - bcf LEDr - movff menupos3,customview_surfmode; save last customview +sleeploop: ; enter sleepmode! + call disable_ir_s8 ; IR/S8 off + call mcp_sleep + bcf LEDg + bcf LEDr call TFT_Display_FadeOut - call TFT_DisplayOff ; display off - bcf enable_screen_dumps ; =1: Ignore vin_usb, wait for "l" command (Screen dump) - call disable_rs232 ; USB off - call vault_decodata_into_eeprom ; store deco data - call ext_flash_enable_protection ; enable write protection for external flash - call update_battery_registers ; update battery registers into EEPROM - clrf divemins+0 - clrf divemins+1 - clrf apnoe_max_pressure+0 - clrf apnoe_max_pressure+1 + call TFT_DisplayOff ; display off + bcf enable_screen_dumps ; =1: Ignore vin_usb, wait for "l" command (Screen dump) + call disable_rs232 ; USB off + call vault_decodata_into_eeprom ; store deco data + call ext_flash_enable_protection ; enable write protection for external flash + call update_battery_registers ; update battery registers into EEPROM + clrf sm_temp1 + clrf sm_temp2 + clrf sm_timer1 + clrf sm_timer2 + clrf sm_timer3 call speed_normal - bsf no_sensor_int ; No sensor interrupt - clrf ADCON0 ; Power-Down ADC Module + bsf no_sensor_int ; No sensor interrupt + clrf ADCON0 ; Power-Down ADC Module + sleeploop_pre: - bcf deep_sleep ; Normal sleepmode - call I2C_sleep_accelerometer - call I2C_sleep_compass - btfss analog_switches - bra sleeploop_loop ; no analog switches + bcf deep_sleep ; Normal sleepmode + call I2C_sleep_accelerometer + call I2C_sleep_compass + btfss analog_switches + bra sleeploop_loop ; no analog switches - bsf power_sw1 - btfss power_sw1 - bra $-4 - bsf power_sw2 - btfss power_sw2 - bra $-4 - movlw .4 ; Wait for button circuity - movwf apnoe_max_pressure+0 ; Used as temp + bsf power_sw1 + btfss power_sw1 + bra $-4 + bsf power_sw2 + btfss power_sw2 + bra $-4 + movlw .4 ; Wait for button circuity + movwf sm_temp1 ; Used as temp bcf onesecupdate + sleeploop_pre1: rcall sleepmode_sleep - btfss onesecupdate ; Wait 1 second - bra sleeploop_pre1 - bcf onesecupdate - decfsz apnoe_max_pressure+0,F - bra sleeploop_pre1 + btfss onesecupdate ; Wait 1 second + bra sleeploop_pre1 + bcf onesecupdate + decfsz sm_temp1,F + bra sleeploop_pre1 + movlw .32 ; Wait for button circuity + movwf sm_temp1 ; Used as temp - movlw .32 ; Wait for button circuity - movwf apnoe_max_pressure+0 ; Used as temp sleeploop_pre2: call get_analog_switches - decfsz apnoe_max_pressure+0,F - bra sleeploop_pre2 - - bcf PIR1,TMR1IF - bcf INTCON,INT0IF - bcf INTCON3,INT1IF - bcf PIR5,TMR7IF - bcf switch_left - bcf switch_right - bcf analog_sw2_pressed - bcf analog_sw1_pressed - bsf PIE1,0 ; (Re)Start Timer 1 Interrupt - bsf PIE2,1 ; (Re)Start Timer 2 Interrupt - bsf PIE5,3 ; (Re)Start Timer 7 Interrupt - bsf INTCON,4 ; (Re)Start INT0 Interrupt - bsf INTCON3,3 ; (Re)Start INT1 Interrupt + decfsz sm_temp1,F + bra sleeploop_pre2 + + bcf PIR1,TMR1IF + bcf INTCON,INT0IF + bcf INTCON3,INT1IF + bcf PIR5,TMR7IF + bcf switch_left + bcf switch_right + bcf analog_sw2_pressed + bcf analog_sw1_pressed + bsf PIE1,0 ; (Re)Start Timer 1 Interrupt + bsf PIE2,1 ; (Re)Start Timer 2 Interrupt + bsf PIE5,3 ; (Re)Start Timer 7 Interrupt + bsf INTCON,4 ; (Re)Start INT0 Interrupt + bsf INTCON3,3 ; (Re)Start INT1 Interrupt sleeploop_loop: - btfsc onesecupdate ; one second in sleep? - rcall onesec_sleep ; check switches, check pressure sensor, etc. + btfsc onesecupdate ; one second in sleep? + rcall onesec_sleep ; check switches, check pressure sensor, etc. + + btfss sleepmode ; wake up? (This bit will be set in other routines) + goto restart ; yes - btfss sleepmode ; wake up? (This bit will be set in other routines) - goto restart ; yes - - btfsc deep_sleep ; Enter deep sleep? - bra deepsleep ; Yes + btfsc deep_sleep ; Enter deep sleep? + bra deepsleep ; Yes + no_deepsleep: - - rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) + rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) ; Any button pressed in sleep? ; btfsc switch_left @@ -115,207 +131,229 @@ ; btfsc switch_right ; rcall onesec_sleep1a ; -; btfss sleepmode ; wake up? (This bit will be set in other routines) -; goto restart ; yes +; btfss sleepmode ; wake up? (This bit will be set in other routines) +; goto restart ; yes - bra sleeploop_loop ; do loop until someting happens + bra sleeploop_loop ; do loop until something happens deepsleep: - btfss analog_switches - bra no_deepsleep ; no analog switches, no deep sleep required + btfss analog_switches + bra no_deepsleep ; no analog switches, no deep sleep required - bcf PIE1,0 ; Stop Timer 1 Interrupt - bcf PIE2,1 ; Stop Timer 2 Interrupt - bcf PIE5,3 ; Stop Timer 7 Interrupt - bcf INTCON,4 ; Stop INT0 Interrupt - bcf INTCON3,3 ; Stop INT1 Interrupt - bcf power_sw1 - bcf power_sw2 - rcall deepsleep_get_accel ; Read accelerometer into WREG - movwf apnoe_max_pressure+0 ; Store init value - -deepsleep_loop: - btfsc onesecupdate ; one second in sleep? - rcall onesec_deepsleep ; check accelerometer + bcf PIE1,0 ; Stop Timer 1 Interrupt + bcf PIE2,1 ; Stop Timer 2 Interrupt + bcf PIE5,3 ; Stop Timer 7 Interrupt + bcf INTCON,4 ; Stop INT0 Interrupt + bcf INTCON3,3 ; Stop INT1 Interrupt + bcf power_sw1 + bcf power_sw2 + rcall deepsleep_get_accel ; Read accelerometer into WREG + movwf sm_temp1 ; Store init value - btfsc onesecupdate ; one second in sleep? - rcall onesec_sleep ; check switches, check pressure sensor, etc. +deepsleep_loop: + btfsc onesecupdate ; one second in sleep? + rcall onesec_deepsleep ; check accelerometer + + btfsc onesecupdate ; one second in sleep? + rcall onesec_sleep ; check switches, check pressure sensor, etc. rcall sleepmode_sleep - - btfss deep_sleep ; Enter normal sleepmode? - bra sleeploop_pre ; Yes - bra deepsleep_loop ; do loop until someting happens + btfss deep_sleep ; Enter normal sleepmode? + bra sleeploop_pre ; Yes + + bra deepsleep_loop ; do loop until something happens onesec_deepsleep: - rcall deepsleep_get_accel ; Read accelerometer into WREG - subwf apnoe_max_pressure+0,W ; apnoe_max_pressure+0 - accel_DZ+0 -> WREG - btfsc STATUS,N ; Result negative? - negf WREG ; Yes, negate it - movwf apnoe_max_pressure+1 ; change of acceleration in Z-axis - movlw .50 ; Threshold (mg) - cpfslt apnoe_max_pressure+1 ; bigger then the threshold? - bcf deep_sleep ; Yes! + rcall deepsleep_get_accel ; Read accelerometer into WREG + subwf sm_temp1,W ; sm_temp1 - accel_DZ+0 -> WREG + btfsc STATUS,N ; Result negative? + negf WREG ; Yes, negate it + movwf sm_temp2 ; change of acceleration in Z-axis + movlw .50 ; Threshold (mg) + cpfslt sm_temp2 ; bigger then the threshold? + bcf deep_sleep ; Yes! ; extern piezo_config_tx -; movff apnoe_max_pressure+0,WREG +; movff sm_temp1,WREG ; call piezo_config_tx ; movff accel_DZ+0,WREG ; call piezo_config_tx -; movff apnoe_max_pressure+1,WREG +; movff sm_temp2,WREG ; call piezo_config_tx + return - + deepsleep_get_accel: - call I2C_init_compass ; required for compass1 - call I2C_init_accelerometer ; required for compass2 - call I2C_RX_accelerometer ; read Accelerometer - call I2C_sleep_compass ; required for compass1 - call I2C_sleep_accelerometer ; required for compass2 + call I2C_init_compass ; required for compass1 + call I2C_init_accelerometer ; required for compass2 + call I2C_RX_accelerometer ; read Accelerometer + call I2C_sleep_compass ; required for compass1 + call I2C_sleep_accelerometer ; required for compass2 movff accel_DZ+0,WREG return - + onehour_sleep: - call update_battery_registers ; update battery registers into EEPROM - call vault_decodata_into_eeprom ; update deco data - bcf onehourupdate ; all done - return + call update_battery_registers ; update battery registers into EEPROM + call vault_decodata_into_eeprom ; update deco data + bcf onehourupdate ; all done + return onemin_sleep: - btfsc onehourupdate ; one hour in sleep? - rcall onehour_sleep ; Yes + btfsc onehourupdate ; one hour in sleep? + rcall onehour_sleep ; Yes + + btfsc battery_gauge_available + call get_battery_voltage ; Check for charger - btfsc battery_gauge_available - call get_battery_voltage ; Check for charger - - ;---- adjust airpressure compensation any 15 minutes - incf divemins+1,F ; counts to 14... - movlw d'14' - cpfsgt divemins+1 - bra onemin_sleep2 ; 15 minutes not done! - -; Tasks every 15 minutes in sleep - bsf deep_sleep ; enter deep-sleep mode - - clrf divemins+1 ; reset counter - - call deco_calc_CNS_decrease_15min ; compute CNS decay in sleep only + ;---- update tissues and CNS every 10 minutes when gradient factor is 0 (no supersaturation in any tissue any more) + movff int_O_gradient_factor+0,WREG ; get gradient factor, only the lower byte is used for the value + tstfsz WREG ; gradient factor = 0? + bra onemin_sleep1 ; NO - continue with air pressure compensation + incf sm_timer2,F ; count-up... + movlw d'9' ; ...to 9 + cpfsgt sm_timer2 ; 10 minutes over? + bra onemin_sleep1 ; NO - continue with air pressure compensation + clrf sm_timer2 ; reset counter + SAFE_2BYTE_COPY amb_pressure, int_I_pres_respiration ; copy pressure to deco routine + call deco_calc_dive_interval_10min ; calculate 10 minutes under surface conditions banksel common - SAFE_2BYTE_COPY last_surfpressure_15min, last_surfpressure_30min ; save older airpressure - SAFE_2BYTE_COPY amb_pressure, last_surfpressure_15min ; save new airpressure +onemin_sleep1: + ;---- adjust air pressure compensation any 15 minutes + incf sm_timer3,F ; count-up... + movlw d'14' ; ...to 14 + cpfsgt sm_timer3 ; 15 minutes over? + bra onemin_sleep2 ; NO - continue with every-minute-tasks - movlw LOW max_surfpressure - movff WREG,sub_a+0 ; max. "allowed" airpressure in mbar - movlw HIGH max_surfpressure - movff WREG,sub_a+1 ; max. "allowed" airpressure in mbar + ; Tasks every 15 minutes in sleep + bsf deep_sleep ; enter deep-sleep mode + clrf sm_timer3 ; reset counter + + SAFE_2BYTE_COPY last_surfpressure_15min, last_surfpressure_30min ; save older air pressure + SAFE_2BYTE_COPY amb_pressure, last_surfpressure_15min ; save new air pressure + + movlw LOW max_surfpressure + movff WREG,sub_a+0 ; max. "allowed" air pressure in mbar + movlw HIGH max_surfpressure + movff WREG,sub_a+1 ; max. "allowed" air pressure in mbar movff last_surfpressure_15min+0,sub_b+0 movff last_surfpressure_15min+1,sub_b+1 - call subU16 ; sub_c = sub_a - sub_b - btfss neg_flag ; Is 1080mbar < amb_pressure ? - bra onemin_sleep2 ; NO: current airpressure is lower then "allowed" airpressure, ok! + call subU16 ; sub_c = sub_a - sub_b + btfss neg_flag ; Is 1080mbar < amb_pressure ? + bra onemin_sleep2 ; NO: current air pressure is lower then "allowed" air pressure, ok! - ; not ok! Overwrite with max. "allowed" airpressure - movlw LOW max_surfpressure - movff WREG,last_surfpressure_15min+0 ; max. "allowed" airpressure in mbar - movlw HIGH max_surfpressure - movff WREG,last_surfpressure_15min+1 ; max. "allowed" airpressure in mbar + ; not ok! Overwrite with max. "allowed" air pressure + movlw LOW max_surfpressure + movff WREG,last_surfpressure_15min+0 ; max. "allowed" air pressure in mbar + movlw HIGH max_surfpressure + movff WREG,last_surfpressure_15min+1 ; max. "allowed" air pressure in mbar onemin_sleep2: -; Tasks every minute in sleep - SAFE_2BYTE_COPY amb_pressure, int_I_pres_respiration ; LOW copy pressure to deco routine - call deco_calc_wo_deco_step_1_min ; "calc_tissue_sleep" - banksel common + ; Tasks every minute in sleep + + ;---- update tissues and CNS every minute when gradient factor is >0 (supersaturation in at least one tissue) + movff int_O_gradient_factor+0,WREG ; get gradient factor, only the lower byte is used for the value + tstfsz WREG ; gradient factor = 0? + bra onemin_sleep3 ; NO - do tissue update on 1 minute schedule + bra onemin_sleep4 ; YES - tissue update is done on 10 minutes schedule - bcf oneminupdate ; all done +onemin_sleep3: + SAFE_2BYTE_COPY amb_pressure, int_I_pres_respiration ; copy pressure to deco routine + call deco_calc_dive_interval_1min ; calculate 1 minute under surface conditions + banksel common + +onemin_sleep4: + bcf oneminupdate ; all done return onesec_sleep: - btfsc oneminupdate ; one minute in sleep? - rcall onemin_sleep ; do oneminute tasks, e.g. calculate desaturation + btfsc oneminupdate ; one minute in sleep? + rcall onemin_sleep ; do one-minute tasks, e.g. calculate desaturation - btfsc battery_gauge_available - call get_battery_voltage ; Check for charger + btfsc battery_gauge_available + call get_battery_voltage ; Check for charger - incf divemins+0,F ; counts to #test_pressure_in_sleep (10) + incf sm_timer1,F ; counts to #test_pressure_in_sleep (10) movlw d'10' - cpfsgt divemins+0 ; here: temp variable - bra onesec_sleep1 ; #test_pressure_in_sleep not done yet + cpfsgt sm_timer1 ; here: temp variable + bra onesec_sleep1 ; #test_pressure_in_sleep not done yet - clrf divemins+0 ; clear counter - rcall pressuretest_sleep_fast ; Gets pressure without averaging (faster!) - ; compare current ambient pressure with wake_up_from_sleep - movlw LOW wake_up_from_sleep - movwf sub_a+0 ; power on if ambient pressure is greater threshold - movlw HIGH wake_up_from_sleep - movwf sub_a+1 ; power on if ambient pressure is greater threshold + clrf sm_timer1 ; clear counter + rcall pressuretest_sleep_fast ; Gets pressure without averaging (faster!) + ; compare current ambient pressure with wake_up_from_sleep + movlw LOW wake_up_from_sleep + movwf sub_a+0 ; power on if ambient pressure is greater threshold + movlw HIGH wake_up_from_sleep + movwf sub_a+1 ; power on if ambient pressure is greater threshold SAFE_2BYTE_COPY amb_pressure, sub_b - call subU16 ; Is (1160mbar - averaged(amb_pressure)) < 0 ? - btfsc neg_flag ; Wake up from Sleep? - bra onesec_sleep1a ; Yes, skip button checks, wake up! + call subU16 ; Is (1160mbar - averaged(amb_pressure)) < 0 ? + btfsc neg_flag ; Wake up from Sleep? + bra onesec_sleep1a ; Yes, skip button checks, wake up! - btfsc battery_gauge_available - bra onesec_sleep1 ; No wake-up with cR hardware - btfsc vusb_in ; USB plugged in? - bra onesec_sleep1a ; Yes, skip button checks, wake up! + btfsc battery_gauge_available + bra onesec_sleep1 ; No wake-up with cR hardware + btfsc vusb_in ; USB plugged in? + bra onesec_sleep1a ; Yes, skip button checks, wake up! onesec_sleep1: - bcf onesecupdate ; all done. -; Check switches + bcf onesecupdate ; all done. + ; Check switches btfsc switch_left - bra onesec_sleep1a + bra onesec_sleep1a btfsc switch_right - bra onesec_sleep1a + bra onesec_sleep1a + ; No button pressed -; bcf INTCON,INT0IF ; Clear flag -; bcf INTCON3,INT1IF ; Clear flag +; bcf INTCON,INT0IF ; Clear flag +; bcf INTCON3,INT1IF ; Clear flag + return -onesec_sleep1a: ; At least one button pressed or amb_pressure > wake_up_from_sleep -; bcf INTCON,INT0IF ; Clear flag -; bcf INTCON3,INT1IF ; Clear flag - bcf sleepmode ; wake up! +onesec_sleep1a: ; At least one button pressed or amb_pressure > wake_up_from_sleep +; bcf INTCON,INT0IF ; Clear flag +; bcf INTCON3,INT1IF ; Clear flag + bcf sleepmode ; wake up! SAFE_2BYTE_COPY last_surfpressure_30min, amb_pressure ; copy for compatibility movlw .0 - movff WREG,sensor_state_counter ; Reset sensor state counter - bcf no_sensor_int ; normal sensor interrupt mode + movff WREG,sensor_state_counter ; Reset sensor state counter + bcf no_sensor_int ; normal sensor interrupt mode return - -pressuretest_sleep_fast: ; Get pressure without averaging (Faster to save some power in sleep mode) - banksel isr_backup ; Back to Bank0 ISR data - clrf amb_pressure_avg+0 ; pressure average registers - clrf amb_pressure_avg+1 - clrf temperature_avg+0 - clrf temperature_avg+1 - call get_temperature_start ; and start temperature integration (73,5us) - banksel common - rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) - rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) - banksel isr_backup ; Back to Bank0 ISR data - call get_temperature_value ; State 1: Get temperature - call get_pressure_start ; Start pressure integration. - banksel common - rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) - rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) - banksel isr_backup ; Back to Bank0 ISR data - call get_pressure_value ; State2: Get pressure (51us) - call calculate_compensation ; calculate temperature compensated pressure (27us) - banksel common - SAFE_2BYTE_COPY amb_pressure_avg, amb_pressure ; copy for compatibility + +pressuretest_sleep_fast: ; Get pressure without averaging (Faster to save some power in sleep mode) + banksel isr_backup ; Back to Bank0 ISR data + clrf amb_pressure_avg+0 ; pressure average registers + clrf amb_pressure_avg+1 + clrf temperature_avg+0 + clrf temperature_avg+1 + call get_temperature_start ; and start temperature integration (73,5us) + banksel common + rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) + rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) + banksel isr_backup ; Back to Bank0 ISR data + call get_temperature_value ; State 1: Get temperature + call get_pressure_start ; Start pressure integration. + banksel common + rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) + rcall sleepmode_sleep ; Wait at least 35ms (every 62,5ms Timer7 wakeup) + banksel isr_backup ; Back to Bank0 ISR data + call get_pressure_value ; State2: Get pressure (51us) + call calculate_compensation ; calculate temperature compensated pressure (27us) + banksel common + SAFE_2BYTE_COPY amb_pressure_avg, amb_pressure ; copy for compatibility return sleepmode_sleep: - banksel 0xF16 ; Addresses, F16h through F5Fh, are also used by SFRs, but are not part of the Access RAM. - clrf T7GCON ; Reset Timer7 Gate Control register - movlw b'10001101' ; 1:1 Prescaler -> 2seconds@32768Hz, not synced - movwf T7CON + banksel 0xF16 ; Addresses, F16h through F5Fh, are also used by SFRs, but are not part of the Access RAM. + clrf T7GCON ; Reset Timer7 Gate Control register + movlw b'10001101' ; 1:1 Prescaler -> 2seconds@32768Hz, not synced + movwf T7CON sleep sleep - clrf T7GCON ; Reset Timer7 Gate Control register - movlw b'10001001' ; 1:1 Prescaler -> 2seconds@32768Hz, synced - movwf T7CON - banksel common ; Bank1 + clrf T7GCON ; Reset Timer7 Gate Control register + movlw b'10001001' ; 1:1 Prescaler -> 2seconds@32768Hz, synced + movwf T7CON + banksel common ; Bank1 return END \ No newline at end of file