-
Notifications
You must be signed in to change notification settings - Fork 0
/
spi.c
92 lines (81 loc) · 3.66 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
/**
* Written by Tim Johns.
*
* The function bodies in this file are specific to MSP430F5310.
*/
#ifndef _SPILIB_C
#define _SPILIB_C
#include <msp430f5310.h>
#include <stdint.h>
#include "spi.h"
/*----------------------------------------------------------------------------*/
/* Set up SPI for master (MCU) and slaves */
/*----------------------------------------------------------------------------*/
void spi_config(void) {
/* Set up ports for SPI. Remember to change the values for a new circuit
design. */
P4SEL |= 0x31; // P4.0,4,5 USCI_A1 SPI option select
P4DIR |= BIT4; // P4.4 output direction (UCA1SIMO)
P4DIR &= ~BIT5; // P4.5 input direction (UCA1SOMI)
P4SEL |= 0x0E; // P4.1-3 USCI_B1 SPI option select
P4DIR |= BIT1; // P4.1 output direction (UCB1SIMO)
P4DIR &= ~BIT2; // P4.2 input direction (UCB1SOMI)
P4DIR |= BIT7; // P4.7 output direction (SD Card CS)
P1DIR |= BIT4; // P1.4 output direction (LIS3LV02DL CS)
P1OUT |= BIT4; // P1.4 high (LIS3LV02DL CS)
P1DIR |= BIT6; // P1.6 output direction (L3G4200D CS)
P1OUT |= BIT6; // P1.6 high (L3G4200D CS)
/* Set up USCI_A1 SPI (currently used for SD card) */
// Clock polarity high, MSB first, master, 3-pin SPI, synchronous
UCA1CTL0 = UCCKPL | UCMSB | UCMST | UCMODE_0 | UCSYNC;
// Clock source SMCLK, set reset bit high
UCA1CTL1 = UCSSEL__SMCLK | UCSWRST;
UCA1BR1 = 0; // Upper byte of divider word
UCA1BR0 = 3; // Clock = SMCLK / 3
UCA1CTL1 &= ~UCSWRST; // Release from reset
/* Set up USCI_B1 SPI (currently used for accelerometer and gyroscope) */
// Clock polarity high, MSB first, master, 3-pin SPI, synchronous
UCB1CTL0 = UCCKPL | UCMSB | UCMST | UCMODE_0 | UCSYNC;
// Clock source SMCLK, set reset bit high
UCB1CTL1 = UCSSEL__SMCLK | UCSWRST;
UCB1BR1 = 0; // Upper byte of divider word
UCB1BR0 = 3; // Clock = SMCLK / 3
UCB1CTL1 &= ~UCSWRST; // Release from reset
}
/*----------------------------------------------------------------------------*/
/* Transmit byte to USCI_A1 SPI slave and return received byte */
/*----------------------------------------------------------------------------*/
uint8_t spia_send(const uint8_t b) {
while ((UCA1IFG & UCTXIFG) == 0); // Wait while not ready
UCA1TXBUF = b; // Transmit
while ((UCA1IFG & UCRXIFG) == 0); // Wait for RX buffer (full)
return (UCA1RXBUF);
}
/*----------------------------------------------------------------------------*/
/* Receive and return byte from USCI_A1 SPI slave */
/*----------------------------------------------------------------------------*/
uint8_t spia_rec(void) {
while ((UCA1IFG & UCTXIFG) == 0); // Wait while not ready
UCA1TXBUF = 0xFF; // Dummy byte to start SPI
while ((UCA1IFG & UCRXIFG) == 0); // Wait for RX buffer (full)
return (UCA1RXBUF);
}
/*----------------------------------------------------------------------------*/
/* Transmit byte to USCI_B1 SPI slave and return received byte */
/*----------------------------------------------------------------------------*/
uint8_t spib_send(const uint8_t b) {
while ((UCB1IFG & UCTXIFG) == 0); // Wait while not ready
UCB1TXBUF = b; // Transmit
while ((UCB1IFG & UCRXIFG) == 0); // Wait for RX buffer (full)
return (UCB1RXBUF);
}
/*----------------------------------------------------------------------------*/
/* Receive and return byte from USCI_B1 SPI slave */
/*----------------------------------------------------------------------------*/
uint8_t spib_rec(void) {
while ((UCB1IFG & UCTXIFG) == 0); // Wait while not ready
UCB1TXBUF = 0xFF; // Dummy byte to start SPI
while ((UCB1IFG & UCRXIFG) == 0); // Wait for RX buffer (full)
return (UCB1RXBUF);
}
#endif