/** Displays single 2 digit blink code * \param bc blink code 0...99 (in Hex!) */ void disp_code(uint8_t bc) { uint8_t i = 0; //Hi. digit i = bc >> 4; do { ce_set_state(CE_STATE_ON); delay_hom(2); ce_set_state(CE_STATE_OFF); delay_hom(2); }while(--i); delay_hom(10); //Lo. digit i = bc & 0xF; do { ce_set_state(CE_STATE_ON); delay_hom(2); ce_set_state(CE_STATE_OFF); delay_hom(2); }while(--i); }
/** Displays start marker (4 long flashes) */ void disp_start(void) { uint8_t i = 4; do { ce_set_state(CE_STATE_ON); delay_hom(8); ce_set_state(CE_STATE_OFF); delay_hom(3); }while(--i); }
void starter_control(struct ecudata_t* d) { #ifndef VPSEM //control of starter's blocking (starter is blocked after reaching the specified RPM, but will not turn back!) //управление блокировкой стартера (стартер блокируетс¤ после достижени¤ указанных оборотов, но обратно не включаетс¤!) if (d->sens.frequen4 > d->param.starter_off) SET_STARTER_BLOCKING_STATE(1); #else //control of starter's blocking (starter is blocked at speeds greater than the threshold) //and status indication of idle economizer valve (output of starter's blocking is used) //(управление блокировкой стартера (стартер блокируетс¤ при оборотах больше пороговых) //и индикаци¤ состо¤ни¤ клапана Ёѕ’’ (используетс¤ выход блокировки стартера)) SET_STARTER_BLOCKING_STATE( (d->sens.frequen4 > d->param.starter_off)&&(d->ie_valve) ? 1 : 0); //if air flow is maximum - turn on CE and start timer //(если расход воздуха максимальный - зажигаем —≈ и запускаем таймер) if (d->airflow > 15) { s_timer_set(ce_control_time_counter, CE_CONTROL_STATE_TIME_VALUE); ce_set_state(1); } #endif if (d->sens.frequen4 < 30) SET_STARTER_BLOCKING_STATE(0); //unblock starter (снимаем блокировку стартера) }
void bc_indication_mode(struct ecudata_t *d) { uint8_t i = 5; if (!IOCFG_CHECK(IOP_BC_INPUT)) return; //normal program execution //Check 5 times do { if (IOCFG_GET(IOP_BC_INPUT)) return; //normal program execution }while(--i); //We are entered to the blink codes indication mode _DISABLE_INTERRUPT(); ce_set_state(CE_STATE_OFF); vent_turnoff(d); //turn off ventilator starter_set_blocking_state(1); //block starter IOCFG_INIT(IOP_FL_PUMP, 0); //turn off fuel pump IOCFG_INIT(IOP_IE, 0); //turn off IE valve solenoid IOCFG_INIT(IOP_FE, 0); //turn off power valve solenoid wdt_reset_timer(); //delay 2 sec. delay_hom(20); //main loop for(;;) { uint16_t errors = 0; disp_start(); delay_hom(7); //read errors eeprom_read(&errors, EEPROM_ECUERRORS_START, sizeof(uint16_t)); for(i = 0; i < 16; ++i) { if (0 == PGM_GET_BYTE(&blink_codes[i])) continue; if (errors & (1 << i)) { disp_code(PGM_GET_BYTE(&blink_codes[i])); delay_hom(20); } } delay_hom(20); wdt_reset_timer(); } }
//If any error occurs, the CE is light up for a fixed time. If the problem persists (eg corrupted the program code), //then the CE will be turned on continuously. At the start of program CE lights up for 0.5 seconds. for indicating //of the operability. void ce_check_engine(struct ecudata_t* d, volatile s_timer8_t* ce_control_time_counter) { uint16_t temp_errors; check(d); //If the timer counted the time, then turn off the CE if (s_timer_is_action(*ce_control_time_counter)) { ce_set_state(CE_STATE_OFF); d->ce_state = 0; //<--doubling } //If at least one error is present - turn on CE and start timer if (ce_state.ecuerrors!=0) { s_timer_set(*ce_control_time_counter, CE_CONTROL_STATE_TIME_VALUE); ce_set_state(CE_STATE_ON); d->ce_state = 1; //<--doubling } temp_errors = (ce_state.merged_errors | ce_state.ecuerrors); //check for error which is still not in merged_errors if (temp_errors!=ce_state.merged_errors) { //Because at the time of appearing of a new error, EEPROM can be busy (for example, saving options), //then it is necessary to run deffered operation, which will be automatically executed as soon as the EEPROM //will be released. sop_set_operation(SOP_SAVE_CE_MERGED_ERRORS); } ce_state.merged_errors = temp_errors; //copy error's bits into the cache for transferring d->ecuerrors_for_transfer|= ce_state.ecuerrors; }