You are on page 1of 9

// INTRERUPERI

void interrupt ext0()


{
if (INT0IF)
{
// do sum funky shit
INT0IF = 0; // exemplu intrerupere pe RB0/INT0
}
}

// TODO: prioritate cand sunt mai multe intreruperi

// START afisare pe display 7 segemente 7SEG-MPX1-CC

unsigned char numere_7seg[] = {0x3F, 0x06, 0x5B, 0x4F, 0x66, 0x6D, 0x7D, 0x07, 0x7F, 0x6F}; // 0 - 9 pe 7seg display

// display 7 segemente 7SEG-MPX1-CC

#define SPI1_CLK RC3


#define SPI1_SDO RC5

void setDigit(int cifra) // functia care scrie pe display, primeste ca parametru cifre 0 - 9
{
LATD = SPI_read(numere_7seg[cifra]);
}

char SPI_read(unsigned char data)


{
SSPBUF = data;
while (!SSPSTATbits.BF)
;
return data;
}

void SPI_write(unsigned char data)


{
SSPBUF = data;
while (!SSPSTATbits.BF)
;
}

void SPI_init()
{
TRISCbits.SPI1_CLK = 0;
TRISCbits.SPI1_SDO = 0;
}

void SPI_open()
{
//Fosc/64
SSPM3 = 0;
SSPM2 = 0;
SSPM1 = 1;
SSPM0 = 0;

CKE = 1;
CKP = 0;
SMP = 0;
SSPEN = 1; //Serial port enable(0 = porturi sincrone oprite, 1 = pornite)
}

void SPI_close()
{
SSPEN = 0;
}

// END afisare pe display 7 segemente 7SEG-MPX1-CC

// delay de n secunde

void waitSeconds(float n)
{
for (int i = 1; i <= (n * 100); i++)
__delay_ms(10);
}

// OUTPUT PINI

TRISxbits.Rx(0..7) = 0; // setarea unui singur pin ca input


TRISxbits.Rx(0..7) = 1; // setarea unui singur pin ca output
TRISBbits.RB1 = 0; // exemplu

TRISx(x = A, B, C sau D) = 0; // setarea pinilor de pe un port ca OUTPUT


TRISx(x = A, B, C sau D) = 1; // setarea pinilor de pe un port ca INPUT

GIE = 1; // activeaza intreruperile


INT0IE = 1; // pentru intrerupere pe INT0
INT0IF = 0; // seteaza flag-ul intreruperii pe INT0 la val 0
INT1IE = 1; // pentru intrerupere pe INT1
INT1IF = 0; // seteaza flag-ul intreruperii pe INT1 la val 0

IPEN = 1; // Interrupt Priority Enable bit


// 1 = Enable priority levels on interrupts
// 0 = Disable priority levels on interrupts (PIC16CXXX Compatibility mode)

// PORTx, LATx -> folosite pentru setarea valorii de output


// LATxbits.LATxn = 0x01;(x = A-D, n=0-7) // output 1 in loc de Rxn=1 gen RC0=1
// = 0x00; // output 0

// ------------------------------------- configurare timer0 8 biti, prescalor 1:32

TMR0IE = 1; // Enables the TMR0 overflow interrupt


TMR0IF = 0; // TMR0 register did not overflow
T08BIT = 1; // Timer0 is configured as an 8-bit timer/counter
T08BIT = 0; // Timer0 pe 16 biti
T0CS = 0; // Internal instruction cycle clock (CLKO)
PSA = 0; // Timer0 prescaler is assigned. Timer0 clock input comes from prescaler output
T0PS2 = 1; // 100 = 1:32 Prescale value
T0PS1 = 0;
T0PS0 = 0;
/*
111 = 1:256 Prescale value
110 = 1:128 Prescale value
101 = 1:64 Prescale value
100 = 1:32 Prescale value
011 = 1:16 Prescale value
010 = 1:8 Prescale value
001 = 1:4 Prescale value
000 = 1:2 Prescale value
*/

TMR0IP = 1; // TMR0 Overflow Interrupt Priority bit - 1 = High priority


TMR0L = 0; // Valoarea initiala a numaratorului = 0
TMR0ON = 1; // Enables Timer0

// ------------------------------------- configurare timer 1(TMR1)

T1CONbits.RD16 = 0; // 16-Bit Read/Write Mode Enable bit


// 1 = Enables register read/write of Timer1 in one 16-bit operation
// 0 = Enables register read/write of Timer1 in two 8-bit operations

// T1CKPS<1:0>: Timer1 Input Clock Prescale Select bits


T1CKPS1 = 1; // 10 = 1:4 Prescale value
T1CKPS0 = 0;
/*
T1CKPS<1:0>: Timer1 Input Clock Prescale Select bits
11 = 1:8 Prescale value
10 = 1:4 Prescale value
01 = 1:2 Prescale value
00 = 1:1 Prescale value
*/
// T1SYNC: Timer1 External Clock Input Synchronization Select bit
TMR1CS = 0; // 0 = Ceas intern => Fout = Fosc/4
// 1 = Ceas extern de la pinul RC0

TMR1IE = 1; // TMR1 Overflow Interrupt Enable bit; 1 = Enables the TMR1 overflow interrupt
TMR1IF = 0; // 0 = TMR1 register did not overflow
TMR1IP = 0; // TMR1 Overflow Interrupt Priority bit; 0 = Low priority | 1 = High priority
TMR1H = 0; // TMR1H Timer1 Register High Byte
TMR1L = 0; // TMR1L Timer1 Register Low Byte
TMR1ON = 1; // Timer1 can be enabled or disabled by setting or clearing control bit, TMR1ON (T1CON<0>).

// ------------------------------------- configurare timer 2(TMR2)

// T1CKPS<1:0>: Timer2 Input Clock Prescale Select bits


T2CKPS1 = 1; // 1x = Prescaler is 16
T2CKPS0 = 0;
/*
00 = Prescaler is 1
01 = Prescaler is 4
1x = Prescaler is 16
*/

TMR2IE = 1; // TMR2 to PR2 Match Interrupt Enable bit; 1 = Enables the TMR2 to PR2 match interrupt
TMR2IF = 0; // TMR2 to PR2 Match Interrupt Flag bit; 0 = No TMR2 to PR2 match occurred
TMR2IP = 1; // TMR2 to PR2 Match Interrupt Priority bit; 1 = High priority

PR2 = 255; // PR2 Timer2 Period Register


/*
The PWM period is specified by writing to the PR2
(PR4) register. The PWM period can be calculated
using the following formula:

PWM Period = [(PR2) + 1] • 4 • TOSC • (TMR2 Prescale Value)


PWM frequency is defined as 1/[PWM period].

When TMR2 (TMR4) is equal to PR2 (PR4), the following three events occur on the next increment cycle:
• TMR2 (TMR4) is cleared
• The CCPx pin is set (exception: if PWM duty cycle = 0%, the CCPx pin will not be set)
• The PWM duty cycle is latched from CCPRxL into CCPRxH
*/

TMR2ON = 1; // Timer2 On/Off Control bit

// ------------------------------------- START ADC


void init_ADC(char in)
{
//Intrare RA0 - AN0
ADCON0 = ADCON0 | in; // OR logic intre ADCON0 si in (ch0)

//Vref = 5V - vezi pagina 274


VCFG1 = 0;
VCFG0 = 0;

//Intrarea RA0 analogica - vezi pagina 274


PCFG3 = 1;
PCFG2 = 1;
PCFG1 = 1;
PCFG0 = 0;

//Aliniere la dreapta
ADFM = 1;
// ADFM: A/D Result Format Select bit
// 1 = Right justified
// 0 = Left justified

//Tacq = 12*Tad (12*1.2us)


ACQT2 = 1;
ACQT1 = 0;
ACQT0 = 1;
/*
ACQT<2:0>: A/D Acquisition Time Select bits
111 = 20 TAD
110 = 16 TAD
101 = 12 TAD
100 = 8 TAD
011 = 6 TAD
010 = 4 TAD
001 = 2 TAD
000 = 0 TAD
*/

// F = Fosc/32
// TADC = 8us
ADCS2 = 0;
ADCS1 = 1;
ADCS0 = 0;
/*
ADCS<2:0>: A/D Conversion Clock Select bits
111 = FRC (clock derived from A/D RC oscillator)(1)
110 = FOSC/64
101 = FOSC/16
100 = FOSC/4
011 = FRC (clock derived from A/D RC oscillator)(1)
010 = FOSC/32
001 = FOSC/8
000 = FOSC/2
*/

ADRESH = 0;
ADRESL = 0;
__delay_ms(1);
ADON = 1;
}

unsigned int ADC_start()


{
unsigned int ch = 0;
//pornire conversie
GO = 1;
//terminare conversie
while (DONE)
;
ch = ((ADRESH << 8) | ADRESL);
return (ch);
}
// ------------------------------------- END ADC

// ------------------------------------- START PWM


void PWM_init()
{
PR2 = (_XTAL_FREQ / (PWM_freq * 4 * TMR2_pre)) - 1;
CCP1CON = 0b00001100; // ultimii 4 biti 1100 - mod pwm - vezi CCPxCON -> CCPxM<3:0>
CCPR1L = 0x0; // With a 4:1 prescalar, it represents the number of four-cycle count increments
T2CON = T2CON | TMR2_factor | TMR2_ON;
TRISCbits.RC2 = 0; // RC2 ca output pentru ca are ECCP1 pentru PWM
TMR2 = 0x0; // se va numara aici pana se egaleaza PR2
TMR2IF = 0; // fanionul
}

void PWM_duty(unsigned int duty)


{
//0 - 0V -> 1023 - 5V
duty = ((float)duty / 1023) * (_XTAL_FREQ / (PWM_freq * TMR2_pre)); // rezultat pe 10 biti
CCPR1L = (duty >> 2); // scapam de cei mai putin semnificativi 2 biti si ii bagam in
CCP1CON
duty = (duty << 8); // pastram doar cei mai putin semnificativi 2 biti si ii bagam
in duty
CCP1CON = CCP1CON | (duty << 4); // ii mutam cu 4 ca sa ajunga pe pozitiile 5-4 din CCP1CON
while (!PIR1bits.TMR2IF) // verific fanionul atasat timer2; sa vad daca s-a generat
intreruperea
;
}
// ------------------------------------- END PWM

You might also like