void RTCC_Init(void) { __builtin_disi(0x3FFF); //disable interrupts // Set the RTCWREN bit __builtin_write_RTCWEN(); RCFGCALbits.RTCEN = 0; //disable RTCC // set date Mon Jun 29 17:18:47 MST 2015 RCFGCALbits.RTCPTR = 3; // start the sequence RTCVAL = 0x15; // YEAR RTCVAL = 0x629; // MONTH-1/DAY-1 RTCVAL = 0x117; // WEEKDAY/HOURS RTCVAL = 0x1847; // MINUTES/SECONDS // set alarm Mon Jan 01 23:59:00 MST 2001 ALCFGRPTbits.ALRMPTR = 2; //sart write sequence ALRMVAL = 0x101; ALRMVAL = 0x123; ALRMVAL = 0x5900; ALCFGRPTbits.ALRMEN = 1; //enable alarm and chime for every second ALCFGRPTbits.ARPT = 0xFF; ALCFGRPTbits.CHIME = 1; ALCFGRPTbits.AMASK = 0x2; // PWCPOL disabled; PWCEN disabled; RTCLK LPRC; PWCPRE disabled; RTCOUT alarm pulse; PWSPRE disabled; RTCPWCbits.RTCLK = 0b01; //clear RTCWREN RCFGCALbits.RTCWREN = 0; __builtin_disi(0); //enable interrupts }
void _ISR_PSV _U2TXInterrupt(void) { //InterruptTest5++; _U2TXIF = 0; // interrupt flag reset unsigned char debugTX; IFS1bits.U2TXIF = 0; // clear TX interrupt flag __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles ClrWdt(); // [1] if(TxNByte_UART2) { debugTX = *TxPointer_UART2++; // Trasmette il carattere del buffer puntato da TxPointer U2TXREG = debugTX; TxNByte_UART2 = TxNByte_UART2 - 1; // TxNByte_UART2--; non pare funzionare } else { TxComplete[PORT_COM2] = TRUE; IEC1bits.U2TXIE = 0; // Disable Transmit Interrupts } DISICNT = 0; //re-enable interrupts //InterruptTest5--; }
void _ISR_PSV _U2RXInterrupt(void) { // UART2 RX [6zb] //InterruptTest6++; __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles _U2RXIF = 0; // interrupt flag reset ClrWdt(); // [1] unsigned char DatoRx; DatoRx = ReadUART2(); if(StatoSeriale[PORT_COM2] == WAIT_MESSAGE) { // time-out dei dati in ricezione non sia scaduto, altrimenti if (!TimerOutRxModbus[PORT_COM2]) { FreeRxBuffer(PORT_COM2); } TimerOutRxModbus[PORT_COM2] = TIME_OUT_MODBUS; *RxPointer[PORT_COM2] = DatoRx; // Salva nel buffer il dato ricevuto RxPointer[PORT_COM2]++; RxNByte[PORT_COM2]++; if (RxNByte[PORT_COM2] >= MODBUS_N_BYTE_RX) // se ricevuti più caratteri della lunghezza del buffer { RxPointer[PORT_COM2] = ModbusRxBuff[PORT_COM2]; // azzera il puntatore di ricezione RxNByte[PORT_COM2] = 0; // e il numero di byte ricevuti } } DISICNT = 0; //re-enable interrupts //InterruptTest6--; }
void __attribute__ ((interrupt, no_auto_psv)) _U2ErrInterrupt(void) { //InterruptTest8++; __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles IFS4bits.U2EIF = 0; // Clear the UART2 Error Interrupt Flag DISICNT = 0; //re-enable interrupts //InterruptTest8--; }
void __attribute__ ((interrupt, no_auto_psv)) _U1ErrInterrupt(void) { __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles InterruptTest9++; IFS4bits.U1EIF = 0; // Clear the UART1 Error Interrupt Flag InterruptTest9--; DISICNT = 0; //re-enable interrupts }
void __attribute__((interrupt, auto_psv, shadow)) _IC2Interrupt(void) { InterruptTest0++; long int tmp = 0; unsigned int ActualIC2BUF; __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles IFS0bits.IC2IF = 0; ActualIC2BUF = IC2BUF; if (Motore2.UC_First_IC_Interrupt_Done == 0) { Motore2.UI_Old_Capture = ActualIC2BUF; // 1st interrupt, acquire start time Motore2.UC_OverFlowCounter = 0; // reset overflow Motore2.UC_First_IC_Interrupt_Done = 1; // next interrupt valid acquire } else { // 2nd interrupt tmp = TMR2_VALUE; tmp *= Motore2.UC_OverFlowCounter; // overflow offset tmp += ActualIC2BUF; // capture tmp -= Motore2.UI_Old_Capture; // click period Motore2.UI_Period = (unsigned int) ((long) Motore2.L_RpmConversion / tmp); // Valore istantaneo di periodo. Motore2.I_MotorAxelSpeed = Motore2.UI_Period; // Motore2.UI_MediaIC[Motore2.UC_IC_idx] = Motore2.UI_Period; // Motore2.UC_IC_idx++; // if(Motore2.UC_IC_idx > 7) Motore2.UC_IC_idx = 0; // // // media mobile // tmp = 0; // for (i=0;i<8;i++) tmp += Motore2.UI_MediaIC[i]; // Sommatoria degli 8 campioni // // Motore2.I_MotorAxelSpeed = __builtin_divud(tmp,8); // CCW or CW if (!QEI2CONbits.UPDN) { Motore2.I_MotorAxelSpeed *= -1; } Motore2.UC_First_IC_Interrupt_Done = 0; IC2CONbits.ICM = 0; // Disable Input Capture 1 module, // re-enabled after PID computation on 1mSec Interrupt Timer } DISICNT = 0; //re-enable interrupts Motore1.UC_OverFlowCounter = 0; // reset overflow InterruptTest0--; }
void __attribute__((interrupt, auto_psv, shadow)) _T3Interrupt(void) { __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles InterruptTest2++; IFS0bits.T3IF = 0; Motore2.UC_OverFlowCounter++; //reset Vel M2 if (Motore2.UC_OverFlowCounter > 4) { Motore2.UC_OverFlowCounter = 4; Motore2.I_MotorAxelSpeed = 0; // for (i=0;i<8;i++) // { Motore2.UI_MediaIC[i] = 0; // } } DISICNT = 0; //re-enable interrupts //return; InterruptTest2--; }
void __attribute__((interrupt, auto_psv, shadow)) _T2Interrupt(void) { InterruptTest3++; // unsigned char i; __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles IFS0bits.T2IF = 0; Motore1.UC_OverFlowCounter++; // reset Vel M1 if (Motore1.UC_OverFlowCounter > 4) { Motore1.UC_OverFlowCounter = 4; Motore1.I_MotorAxelSpeed = 0; // for (i=0;i<8;i++) // { Motore1.UI_MediaIC[i] = 0; // } } InterruptTest3--; DISICNT = 0; //re-enable interrupts return; }
void _ISR_PSV _T1Interrupt(void) { InterruptTest4++; // Timer 1 1ms __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles IFS0bits.T1IF = 0; // interrupt flag reset /* * Gestione del calcolo del PID, due strade percorribili: * Setto dei FLAG PID1_CALC_FLAG e PID2_CALC_FLAG che poi * nel main intercetto. * * Eseguo direttamente il calcolo nell'interrupt a 1mSec * richiamando le funzioni Pid1() e Pid2(). */ PID1_CALC_FLAG = 1; // PID1 and speed calculation enabled PID2_CALC_FLAG = 1; // PID2 and speed calculation enabled // Pid1(); // Ogni 1mSec ricalcola il prescaler, avvia un ciclo // Pid2(); // di lettura dell'IC e esegue il PID sul dato prec. /* **************************** TIMER SOFTWARE ******************************/ GestioneTimerSW(&Timer1mSec); GestioneTimerSW(&Timer10mSec); /* **************************************************************************/ /* ******************************** MODBUS **********************************/ if (TimerRitardoModbus[0]) TimerRitardoModbus[0]--; if (TimerOutRxModbus[0]) TimerOutRxModbus[0]--; //time-out dei dati in ricezione if (TimerRitardoModbus[1]) TimerRitardoModbus[1]--; if (TimerOutRxModbus[1]) TimerOutRxModbus[1]--; //time-out dei dati in ricezione /* ************************************************************************* */ DISICNT = 0; //re-enable interrupts InterruptTest4--; }
void panic() { // restart the system using the brown-out __builtin_disi(0x3FFF); /* disable interrupts */ asm volatile("RESET"); }
/* Initialize this PIC */ void PIC_Init(void) { unsigned int ClockSwitchTimeout; /* ** Disable all interrupt sources */ __builtin_disi(0x3FFF); /* disable interrupts for 16383 cycles */ IEC0 = 0; IEC1 = 0; IEC4 = 0; __builtin_disi(0x0000); /* enable interrupts */ /* * At Power On Reset the configuration words set the system clock * to use the FRC oscillator. At this point we need to enable the * PLL to get the system clock running at 32MHz. * * Clock switching on the dsPIC33FJ family with the PLL can be a bit tricky. * * First we need to check if the configuration words enabled clock * switching at all, then turn off the PLL, then setup the PLL and * finally enable it. Sounds simple, I know. Make sure you verify this * clock setup on the real hardware. */ if(!OSCCONbits.CLKLOCK) /* if primary oscillator switching is unlocked */ { /* Select primary oscillator as FRC */ __builtin_write_OSCCONH(0b000); /* Request switch primary to new selection */ __builtin_write_OSCCONL(OSCCON | (1 << _OSCCON_OSWEN_POSITION)); /* wait, with timeout, for clock switch to complete */ for(ClockSwitchTimeout=60000; --ClockSwitchTimeout && OSCCONbits.OSWEN;); /* setup PLL to run the system clock at the configured frequency */ CLKDIV = 0x0000; /* Set DOZE 1:1, DOZE disabled, FRCDIV 1:1, PLLPRE 1:2, PLLPOST 1:2 */ /* Configure PLL prescaler, PLL postscaler, PLL divisor */ PLLFBD = PLL_M-2; #if PLL_N2==2 CLKDIVbits.PLLPOST=0; /* N2=2 */ #elif PLL_N2==4 CLKDIVbits.PLLPOST=1; /* N2=4 */ #elif PLL_N2==8 CLKDIVbits.PLLPOST=3; /* N2=8 */ #else #error invalid PLL_N2 paramenter #endif CLKDIVbits.PLLPRE=PLL_N1-2; /* Select primary oscillator as FRCPLL */ __builtin_write_OSCCONH(0b001); /* Request switch primary to new selection */ __builtin_write_OSCCONL(OSCCON | (1 << _OSCCON_OSWEN_POSITION)); /* wait, with timeout, for clock switch to complete */ for(ClockSwitchTimeout=60000; --ClockSwitchTimeout && OSCCONbits.OSWEN;); /* wait, with timeout, for the PLL to lock */ for(ClockSwitchTimeout=60000; --ClockSwitchTimeout && !OSCCONbits.LOCK;); /* at this point the system oscillator should be 78.6432 MHz */ } /* Disable analog mode for all GPIOs */ AD1PCFGL = 0xFFFF; _NSTDIS = 1; /* disable interrupt nesting */ /* set all GPIOs as inputs */ TRISA = 0xFFFF; TRISB = 0xFFFF; TRISC = 0xFFFF; }
void hal_cpu_enable_irqs_and_sleep() { __builtin_disi(0x0000); /* enable interrupts */ mPWRMGNT_GotoIdleMode(); }
void hal_cpu_enable_irqs() { __builtin_disi(0x0000); /* enable interrupts */ }
void hal_cpu_disable_irqs() { __builtin_disi(0x3FFF); /* disable interrupts */ }
/* *************************************************************************** * *************************************************************************** * *************************************************************************** */ void __attribute__((interrupt, auto_psv, shadow)) _IC1Interrupt(void) { InterruptTest1++; long int tmp = 0; unsigned int ActualIC1BUF; __builtin_disi(0x3FFF); //disable interrupts up to priority 6 for n cycles IFS0bits.IC1IF = 0; ActualIC1BUF = IC1BUF; if (Motore1.UC_First_IC_Interrupt_Done == 0) { Motore1.UI_Old_Capture = ActualIC1BUF; // 1st interrupt, acquire start time Motore1.UC_OverFlowCounter = 0; // reset overflow Motore1.UC_First_IC_Interrupt_Done = 1; // next interrupt valid acquire Motore1.UC_OverFlowCounter = 0; // reset overflow } else { // 2nd interrupt tmp = TMR2_VALUE; tmp *= Motore1.UC_OverFlowCounter; // overflow offset tmp += ActualIC1BUF; // capture tmp -= Motore1.UI_Old_Capture; // click period // // /* // * FILTRO MISURE ERRATE : Inizio // */ // // /* FILTRO MISURE ERRATE PER ERRORI LEGATI A SOVRAPPOSIZIONE DI INTERRUPT // * Nel caso l'evento del timerOverflow avvenga nello stesso istante // * in cui vi è il fronte di salita del segnale da misurare ( ENCODER ) // * può essere conteggiato in modo errato il numero di Overflow. // * // * Provvisoriamente introduciamo un filtro che di fatto intercetta // * se la nuova misura discosta dalla precedente per una quantità // * prossima 0xFFFF. // * Non possiamo usare oxFFFF perchè tra due misure consecutive, a causa // * dell'accelerazione o decelerazione del motore, vi sarà comunque una // * certa differenza il cui risultato è sommato al valore errato di Overflow. // * // * Se per 3 misure consecutive il dato misurato discosta dal primo dato // * campionato aggiorno il filtro al nuovo dato. // * Serve nella malaugurata ipotesi che andassimo a campionare come primo // * dato un dato errato :) // * */ // // // /* Mantengo aggiornato uno storico degli ultimi mille campioni per analisi // * -> TestInputCapture1.Anomalie è l'indice // * -> TestInputCapture1.LogginArea[x][0] : Valore della misura letta // * -> TestInputCapture1.LogginArea[x][1] : Valore restituito dal filtro nello stesso istante // */ // // if(TestInputCapture1.Anomalie > (LOGSIZE - 1) ) TestInputCapture1.Anomalie = 0; // else TestInputCapture1.Anomalie++ ; // TestInputCapture1.LogginArea[TestInputCapture1.Anomalie][0] = tmp; // Registro dato calcolato // // // // /* FILTRO: // * se una misura è molto diversa da quella precedente il filtro ritorna quella precedente per // * un massimo di 3 cicli. // * Se la nuova misura "Errata" rimane stabile per 3 cicli allora il filtro si aggiorna, // * restituisce la nuova misura e prende questo valore come riferimento. // */ // if( ((tmp > InputCapture1.OldMeasure+60000) || (tmp < InputCapture1.OldMeasure-60000)) && // (InputCapture1.ErrorCounter < 3) ) // { // Conto quanti errori avvengono consecutivamente // // oltre 3 errori consecutivi significa che la misura è stabile e aggiorno // // il filtro al nuovo valore // InputCapture1.ErrorCounter++; // // /* Per il momento tengo buona la misura precedente. */ // tmp = InputCapture1.OldMeasure; // // //PIN_CN_IC2_5 ^= PIN_ON; // DEBUG // // } // else // { // InputCapture1.OldMeasure = tmp; // InputCapture1.ErrorCounter = 0; // } // // /* -> TestInputCapture1.LogginArea[x][1] : Valore restituito dal filtro nello stesso istante */ // TestInputCapture1.LogginArea[TestInputCapture1.Anomalie][1] = tmp; // Registro dato restituito dal filtro // // /* In TestInputCapture1.LogginArea mi trovo le ultime lille musure e i relativi valori filtrati restituiti dal // * filtro in ogni istante. // */ // /* // * FILTRO MISURE ERRATE : Fine // */ Motore1.UI_Period = (unsigned int) ((long) Motore1.L_RpmConversion / tmp); Motore1.I_MotorAxelSpeed = Motore1.UI_Period; // Motore1.UI_MediaIC[Motore1.UC_IC_idx] = Motore1.UI_Period; // Motore1.UC_IC_idx++; // if(Motore1.UC_IC_idx > 7) Motore1.UC_IC_idx = 0; // // // media mobile // tmp = 0; // for (i=0;i<8;i++) tmp += Motore1.UI_MediaIC[i]; // Sommatoria degli 8 campioni // // Motore1.I_MotorAxelSpeed = __builtin_divud(tmp,8); // CCW or CW if (!QEI1CONbits.UPDN) { Motore1.I_MotorAxelSpeed *= -1; } Motore1.UC_First_IC_Interrupt_Done = 0; IC1CONbits.ICM = 0; // Disable Input Capture 1 module, // re-enabled after PID computation on 1mSec Interrupt Timer } DISICNT = 0; //re-enable interrupts Motore1.UC_OverFlowCounter = 0; // reset overflow InterruptTest1--; }