참고자료

아두이노, 오렌지보드 등의 오픈소스하드웨어를 사용하는데 필요한 것들을 알아봅니다.

통신-SPI

2014-08-11 14:09:36

SPI 통신에 대해서

SPI 통신이란

SPI통신은 I2C통신과 같은 통신방법의 한 종류이지만 통신하는 방법이 다르다. 예를 들자면 어떤사람은 편지를 통해 대화할 수도 있고 누구는 전화나 화상통화를 통해 쉽게 다른사람과 대화할 수 있을것이다. 이처럼 통신방법에는 여러가지가 있는데 쉽게 비유하자면 I2C통신은 한사람이 보낼때는 다른사람을 받고만 있어야하는 무전기와 같은 통신방식이고 SPI는 한사람이 데이터를 보내면서 데이터를 받을 수 있는 전화같은 방식이다. 어느 통신방법을 쓸 것인가에 대하여는 사용자들의 몫이다.

I2C통신에서는 데이터를 전송하는 SDA(Serial Data)선과 클럭을 전송하는 SCL(Serial Clock)선 두개만 필요했다면 SPI통신에서는 송신과 수신을 위한 MOSI(Master Out Slave IN)선과 MISO(Master In Slave Out)선, 클럭(SCK)선, SS(Slave Select)선 이렇게 4개가 필요하다. 
MOSI(Master Out Slave IN)는 이름그대로 마스터에서 나와서 슬레이브에게 가는 데이터를 전송하는 선이고, MISO(Master In Slave Out)는 슬레이브에게 나와서 마스터에게 가는 데이터를 전송하는 선이다. I2C통신이 전이중통신이 안됐다면 SPI는 선이 구분되어 있기 때문에 송수신이 동시에 가능하다.
다만 SPI통신은 Master-Slave관계(주인-종)처럼 Slave는 Master에게 통신은 마음대로 하지 못한다. SPI의 데이터 송수신은 동시에 이루어지기 때문에 데이터 송신이 곧 수신이 된다. 이 데이터 송수신의 타이밍을 결정짓는 것은 Master장치이다. SPI통신은 Master와 여러 Slave간에 1:! 통신이 가능하다. 
SS(Slave Select)선은 마스터인 경우에는 어디에든 꽂아도 상관없지만 슬레이브일 경우에는 UNO기준으로 10번핀, Mega를 기준으로 53핀에 무조건 꽂아줘야한다.
이 선은 Slave과 Master를 구분하기 위한 선이다. SPI통신에서 Master는 무조건 하나지만 Slave는 여러대가 될 수도 있다. 따라서 Slave를 구분하기 위한 방법이 필요한데 SS선은 Slave를 구분하기 위한 방법 중 하나이다. Slave는 SS선을 10번핀에 꽂고 Master는 아무핀에 꽂으면 Master는 이 선을 통해 Slave를 구분할 수 있다.
이외에도 Slave를 구분하기 위해 쓰이는 방법은

1. Slave마다 ID를 구분하여서 그에 맞는 Slave만 사용하는 방법
2. Demultiplexer(분배기)를 사용하여 Slave를 구분하는 방법

도 있지만 SS선을 사용하여 구분하는 방법이 제일 많이 쓰인다.
아두이노가 슬레이브로 동작하기 위해서는 SS핀이 INPUT으로 설정된 상태에서 LOW값이 들어가야 한다. 

아두이노는 자체 라이브러리에서 Master로만 쓰이고 센서들이 Slave로만 쓰이게 해놨기 때문에 아두이노를 Slave로 쓰기 위해서는 별도의 레지스터 조작이 필요하다.

SPI라이브러리

NO
함수명
정보
1 begin() SPI통신 초기화
2 end() SPI통신 종료 
3 setBitOrder(bitOrder) SPI통신을 할때 데이터의 전송순서를 설정한다. LSBFIRST나 MSBFIRST중 선택할 수있다.  
4 setClockDivider(rate) 시스템에서 사용할 클럭의 상대적인 분주비율을 설정한다. AVR기반의 보드에서는 2,4,8,16,32,64,128중 선택할 수 있으며
default값은 SPI_CLOCK_DIV4로 시스템클럭의 1/4속도로 데이터를 전송한다. 
5 setDataMode(mode) 클럭의 phase와 polarity를 조합하여 4가지의 전송모드를 나타낸다. 내용이 어렵기 때문에 자세한 내용은 생략한다.
6 transfer(data)  SPI통신으로 데이터를 보내고 데이터를 수신받는다. 

 


※SPI통신에서의 전송모드

Microchip PIC, ATMEL AVR, ARM-based microcontrollers의 경우

 

 

SPI 모드 클럭 극성 
(CPOL / CKP)
클럭 에지 
(CKE / NCPHA)
0 0 1
1 0 0
2 1 0
3 1 1
 

다른 microcontrollers의 경우

 

 

모드 CPOL CPHA
0 0 0
1 0 1
2 1 0
3 1 1

이부분에 있어서 자세히 설명하면 파형에 대해 나오기 때문에 좀 더 자세한 내용을 원한다면 Wiki의 SPI를 찾아보는 것이 좋다 

링크 -> Wiki SPI찾아보기

 

 

아두이노를 Slave로 사용하기 위해서

아두이노는 SPI.h에서 Master로만 쓰일 수 있게 설정해놨기 때문에 Slave로 쓰기 위해서는 ATmel328의 별도의 레지스터 조작이 필요하다.
AVR에서는 SPI를 다루기 위해 3개의 레지스터를 제공하는데 SPCR/SPSR/SPDR이다.

SPCR : SPI Control Register
SPSR : SPI Status Register
SPDR : SPI Data Register

이중에서 SPCR(SPI Control Register)라는 레지스터를 설정해 준다면 아두이노를 Slave로 사용이 가능하다

SPCR레지스터는 총 8비트로 상위비트부터
SPIE | SPE | DORD | MSTR | CPOL | CPHA | SPR1 | SPR0
이렇게 존재하는데 각각의 레지스터는
SPIE -  SPI모드를 인터럽트 모드로 사용할 때 1로 설정
SPE - SPI통신을 하려면 1로 설정
DORD - 들어오는 데이터 순서가 LSB면 1, MSB면 0
MSTR - 마스터 모드이면 1, 슬레이브 모드이면 0
CPOL - SCK에서 데이터를 읽는 모드 설정(default값이 LOW였다면 읽을때 HIGH가 올때 그 값이 0인지 1인지를 결정)
CPHA - SCK에서 데이터를 읽는 모드 설정
SPR1 - 주파수 설정
SPR0 - 주파수 설정(SPI통신의 속도를 결정 SPI통신은 1/4이하일 때만 올바른 전송을 보장한다. 우노같은 경우 16MHz이므로 SPI통신은 1/4인 4MHz까지 사용이 가능하다)
이렇게 된다.

Slave로 사용하기 위해 중요한것은 MSTR가 0인것과 SPE이 1이 되야 한다는 것이다. 나머지 부분은 사용에 맞게 변경해 주면 된다.
비트 연산자를 통해 해당비트만 1로 변경해 줄수도 있고 통째로 8비트 모두를 SPCR에 넣어서 사용하는 방법도 있다. 결정은 사용자의 몫이다. 
 

 

kocoafabeditor

항상 진취적이고, 새로운 것을 추구하는 코코아팹 에디터입니다!

통신, SPI, 기타