만져보는 임베디드 시스템/아두이노 소프트웨어

아두이노 소프트웨어-xxi. I2C를 위한 WIRE 라이브러리

hanjinee 2021. 1. 5. 13:39
728x90
반응형

안녕하세요 제타지니입니다. 오늘은 Wire Library가 주제입니다.

일전에 포스트에 올렸던 대로 아두이노는 Serial 통신 이외의 두 가지 통신 I2C 통신과 SPI 통신을 지원한다고 하였습니다.

이해를 돕기 위해서 I2C 통신과 SPI 통신에 대한 개념을 다시한 번 여기에서 보고 와주시길 바랍니다. 

 

Wire 라이브러리 I2C 장치들 사이의 통신 기능을 구현해 놓은 아두이노의 기본 라이브러리들 중 하나입니다. I2C 통신의 경우 1:1 통신을 하는 Serial 통신과는 다르게 1:n 통신을 하고 있습니다. 즉, 이 방식은 Wire 라이브러리 내의 함수에도 동일하게 적용이됩니다. 

Wire 라이브러리의 실제 클래스 이름은 TwoWire이며, TwoWire 클래스의 전역 객체는 Wire로, 실제로는 Wire를 통해 통신이 수행됩니다. 시작하기 전에는 #include <Wire.h> 로 Wire 라이브러리를 포함시켜 주셔야 합니다. 이제, Wire 라이브러리의 함수를 알아보겠습니다.

 

 

이름

함수

설명(매개변수와 반환값)

예제

begin

void begin(void)

void begin(uint8_t address)

address: I2C 주소

반환값: 없음

*Wire 라이브러리를 초기화하고, I2C 버스에 마스터나 슬레이브로 참여

*주소가 주어지지 않으면(아무것도 쓰지 않으면) 마스터로 참여

*7비트 주소가 주어지는 경우(address) I2C 버스에 슬레이브로 참여하는 것을 나타냄 

Wire.begin(); //wire 라이브러리 초기화 및 마스터로 I2C 통신 시작

requestFrom

uint8_t requestFrom(uint8_t address, uint8_t quantity) 

uint8_t requestFrom(uint8_t address, uint8_t quantity, uint8_t sendStop)

address: 슬레이브 주소

quantity: 요청하는 바이트 수

sendStop: 오쳥 완료 후 정지 메시지 전송 여부

반환값: 슬레이브 장치로 부터 전송된 바이트 수

*마스터 장치가 슬레이브 장치에 지정한 양(quantity)의 데이터를 요청하는 함수

*sendStop에는 true 나 false의 boolean값 자료형 입력

 -true 입력: 요청 완료 후 정지 메시지를 보냄

 -false입력: 요청 완료후 연결을 유지 (=다른 마스터 장치가 데이터를 요구할 수 없도록 함)

*sendStop을 쓰지 않으면, default 값은 true임. 

Wire.requestFrom(1, 6); //슬레이브 2번에 6 바이트를 요청

beginTransmission

void beginTransmission(uint8_t address)

address: 슬레이브 주소

반환값: 없음

*지정한 주소의 슬레이브 장치로 데이터 전송을 시작

*실제 전송은 write 함수에 의해 버퍼에 기록된 후 endTransmission 함수가 호출될 때 까지 일어남

#define SLAVE_ADDRESS 0x29 //슬레이브의 I2C 주소

 

Wire.beginTransmission(SLAVE_ADDRESS); //슬레이브 주소로 데이터 전송 시작

endTransmission

void endTransmission(void)

void endTransmission(uint8_t snedStop)

sendStop: 요청 완료 후 정지 메시지 전송 여부

반환값: 전송 상태 메시지

*beginTransmission 함수에 의해 시작된 슬레이브 장치에 대한 전송을 종료.

*sendStop에는 true 나 false의 boolean값 자료형 입력

 -true 입력: 요청 완료 후 정지 메시지를 보냄

 -false입력: 요청 완료후 연결을 유지 (=다른 마스터 장치가 데이터를 요구할 수 없도록 함)

*sendStop을 쓰지 않으면, default 값은 true임. 

*반환값은 전송 결과를 나타내는 값으로 0이 아닌 값은 전송 과정에서 오류가 나타났음을 나타냄

*반환값 

 -0: 전송 성공

 -1: 전송 데이터가 버퍼 용량 초과

 -2: 주소 전송 후 NACK(Negative Acknowledge) 수신

 -3: 데이터 전송 후 NACK(Negative Acknowledge) 수신 

 -4: 기타 TWI 오류

#define SLAVE_ADDRESS 0x29 //슬레이브의 I2C 주소

 

Wire.endTransmission(SLAVE_ADDRESS); //슬레이브 주소로 데이터 전송

write

size_t write(uint8_t data)

size_t write(const uint8_t *data, size_t quantity

data: 전송할 단일 바이트

*data: 전송할 바이트 배열에 대한 포인터

quantity: 전송할 바이트 수

반환값: 전송된 바이트 수

*마스터 장치의 요청에 따라 슬레이브 장치가 데이터를 전송하거나, 마스터 장치에서 슬레이브 장치로의 데이터 전송을 위해 큐에 데이터를 기록하는 데 사용

*사용시 beginTransmission, endTransmission 함수와 사용

*데이터 전송은 beginTransmission 함수로 시작, write함수에서 큐에 데이터를 기록 후, endTransmmission 함수 호출로 실제 데이터 전송 일어남. 

 

byte value = 12;

Wire.write(value); // 슬레이브로 보낼 데이터 기록

available

int available(void)

매개변수: 없음

반환값: 유효 바이트 수

*read 함수로 읽어들일 수 있는 유효한 바이트 수를 반환

*마스터 장치에서 requestForm 함수를 통해 슬레이브 장치로 부터 데이터를 요청한 이후, 실제 도착한 데이터를 검사하기 위해 사용

*혹은 슬레이브 장치의 onReceive 함수 내에서 사용됨 

while(Wire.available()){  }; //슬레이브에서 수신된 데이터 확인

int bytes = Wire.available(); //마스터에서 read함수로 읽어들일 수 있는 유효 바이트 수를 반환

read

int read(void)

매개변수: 없음

반환값: 수신 버퍼의 한 바이트를 읽어서 반환

*requestFrom 함수 호출에 의해 슬레이브 장치가 전송한 데이터 한 바이트를 읽어서 반환

*마스터 장치가 전송한 데이터를 슬레이브 장치에서 읽어 들이기 위해서도 사용 가능 

char c = Wire.read(); // 슬레이브에서 수신된 데이터 읽음

onReceive

void onReceieve(void (*)(int)) 

매개변수: 없음

반환값: 없음

*슬레이브 장치가 마스터 장치로 부터 데이터를 수신했을 때 호출되는 핸들러(handler)함수를 등록

*핸들러 함수는 반환값이 없으며, 수신한 데이터의 바이트 수를 나타내는 int 형식의 매개변수를 가짐 

void receiveEvent(){

// 데이터 송신 요구 처리

}

 

Wire.onReceive(receiveEvent);

//송신 요청에 대한 핸들러 함수 등록

onRequest

void onRequest(void (*)(void))

매개변수: 없음

반환값: 없음

*슬레이브 장치가 마스터 장치로 부터 데이터를 요청 받았을 때 호출되는 핸들러(handler)함수를 등록

*마스터에서 전송된 데이터 크기는 available 함수를 통해 알아낼 수 있음

void requestEvent(){

// 데이터 수신 요구 처리

}

 

Wire.onRequest(requestEvent); // 수신 데이터에 대한 핸들러 함수 등록

 

 

밑의 예제를 통해서 한번 알아보지요. 요고는 제 또다른 블로그에서 복사 붙여넣기 한 캡쳐입니다.

 

 

 

 

 

 

다음 포스트에서는 SPI 라이브러리에 대해서 알아보겠습니다. 감사합니다. 

728x90
반응형