/
spi.c
109 lines (95 loc) · 2.01 KB
/
spi.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
#include <avr/io.h>
#include "spi.h"
#include "util.h"
#include "avr.h"
// init SPI bus, spifreq is in KHz
void SPI_init(int spifreq)
{
// Enable SPI, Master, set clock rate
SPI_adjustSpeed(spifreq);
}
void SPI_deselect()
{
SetPin(PORTB, MEM_SEL);
SetPin(PORTD, VS_XCS);
SetPin(PORTD, VS_XDCS);
}
void SPI_select(int dev)
{
SPI_deselect();
switch(dev) {
case MEMCS:
ClearPin(PORTB, MEM_SEL);
break;
case VSXCS:
ClearPin(PORTD, VS_XCS);
break;
case VSXDCS:
ClearPin(PORTD, VS_XDCS);
break;
}
}
// this routine sets the SPI bus clock freq
// CPU_FREQ is defined in avr.h
// spifreq is in KHz
int SPI_adjustSpeed(int spifreq)
{
int clkdiv;
clkdiv = (int)((long)CPU_FREQ / ((long)spifreq*1000));
switch(clkdiv) {
case 2:
SPCR = (1<<SPE) | (1<<MSTR) | (0 << SPR1) | (0 << SPR0);
SPSR = 1;
break;
case 4:
SPCR = (1<<SPE) | (1<<MSTR) | (0 << SPR1) | (0 << SPR0);
SPSR = 0;
break;
case 8:
SPCR = (1<<SPE) | (1<<MSTR) | (0 << SPR1) | (1 << SPR0);
SPSR = 1;
break;
case 16:
SPCR = (1<<SPE) | (1<<MSTR) | (0 << SPR1) | (1 << SPR0);
SPSR = 0;
break;
case 32:
SPCR = (1<<SPE) | (1<<MSTR) | (1 << SPR1) | (0 << SPR0);
SPSR = 1;
break;
case 64:
SPCR = (1<<SPE) | (1<<MSTR) | (1 << SPR1) | (0 << SPR0);
SPSR = 0;
break;
case 128:
SPCR = (1<<SPE) | (1<<MSTR) | (1 << SPR1) | (1 << SPR0);
SPSR = 0;
break;
default:
blinkLED(10);
SPCR = (1<<SPE) | (1<<MSTR) | (0 << SPR1) | (1 << SPR0);
SPSR = 0;
break;
}
return(clkdiv);
}
// send a byte
unsigned char SPI_send(unsigned char data)
{
/* Start transmission */
SPDR = data;
/* Wait for transmission complete */
while(!(SPSR & (1<<SPIF))) {
}
data = SPDR;
return(data);
}
// receive a byte
unsigned char SPI_receive(unsigned char d)
{
unsigned char data;
SPDR = d;
while(!(SPSR & (1<<SPIF)));
data = SPDR;
return(data);
}