Search

usb 프로토콜 분석

Category
임베디드
Column
2022/01/07 12:51
Tags
study

1. USB란?

usb 사진
USB의 간단한 개념과 주요 특징을 먼저 살펴보자.

특징 1) Universal Serial Bus, wired

USB(Universal Serial Bus)는 범용 직렬 장치라는 사전적 의미를 가지고 있다. 쉽게 말하면 하나의 커넥터로 각종 주변기기를 동일한 규격 하에 접속할 수 있도록 설계된 디바이스를 뜻한다.
장치관리자에 들어가면 범용 직렬 장치 버스 탭에서 현재 컴퓨터에 연결되어 있는 usb들을 확인할 수 있다.

특징 2) Single master, multiple slaves

usb는 기본적으로 하나의 마스터와 여러 개의 슬레이브로 구성되어있다. 따라서 usb 버스안에는 하나의 마스터가 존재하며 마스터 하위에 여러개의 슬레이브가 연결되어 있는 구조를 띈다.
마스터/슬레이브(Master/slave)는 장치나 프로세스(마스터)가 하나 이상의 다른 장치나 프로세스(슬레이브)를 통제하고 통신 허브 역할을 하는 비대칭 통신 및 제어 모델을 의미한다. ex) 휴대폰(마스터), 블루투스 스피커(슬레이브)

특징 3) Plug and Play

간단하고 쉽게 동작시키기 위해 Plug and Play를 지원한다. 그냥 꼽으면 바로 실행된다.

특징 4) Standardized by the USB

usb의 모든 통신 규약은 USB-IF(Implementers Forum)에 의해 표준화가 되어있다. 따라서 어떠한 usb 포트에도 다 꼽아서 사용할 수 있다. usb 표준에 관련된 자세한 정보는 아래 링크에서 확인 가능하다.

2. Host, Device와 Topology

특징 1) Host, Device

usb는 host라는 bus master가 존재한다. 쉽게 생각하면 bus는 usb cable이라고 생각하면 되고 bus를 제어하는 마스터를 host 라고한다. 그리고 bus에 연결되어 있는 여러가지 슬레이브들을 devices라고 부른다.
내가 이해한 바로는 그냥 쉽게 pc에 usb 케이블로 된 키보드를 연결하면, host가 pc가 되고 키보드가 devices 가된다. hostdevice가 연결되면 장치인식(Enumerate)과정을 통해 연결하려는 device와 설정과정을 거치게 된다.
host(pc)는 키보드라는 device를 제어하는 주체가 된다는 의미이다.
또한 device는 크게 2가지로 구분된다.
hub device
해당 디바이스가 포트의 확장 역할을 한다면 이는 hub device라고 부른다. 일반적으로 아래 사진과 같은 hub가 해당 디바이스이다.
function device
만약 해당 디바이스가 키보드나, 마우스처럼 특정 기능을 하면서 통신을 한다면 이를 function device라고 부른다. 따라서 허브가 아닌 특정 기능은 전부 function device이다.

특징 2) Togology

여기까지 Host와 Device에 대해서 간략하게 살펴보았다. 그럼 이제 이 두 개가 어떠한 구성을 가지는지 살펴보자.
host controller를 root hub라고 부른다. 위 사진을 보면 host에 2개의 function device와 하나의 hub device가 연결되어 있다. 허브는 usb 포트확장을 위함이므로 하위에 또 function device가 연결될 수 있다.
현재 host가 존재하는 layer를 1이라고 하면 총 3개의 layer라는 것을 알 수 있다. 이렇게 최대 가질 수 있는 layer는 총 7개의 계층 구조를 가질 수 있고 이러한 구조를 tiered start togology 구조라고 부른다.
또한 layer를 떠나서 총 연결될 수 있는 device는 host(root hub)포함 최대 128개까지이다.

3. Speed and Power

1) Speed

usb 2.0 기준으로는 총 3가지의 device 속도를 가진다.
**참고로 usb 3.0 이상 버전에서는 5Gb/s ~ 10Gb/s 속도까지 지원 가능하다.
Low Speed(LS) : 1.5 Mb/s
Full Speed(FS) : 12 Mb/s
High Speed(HS) : 480 Mb/s
위 속도는 이론상의 최대 속도이고 실제로는 하나의 호스트가 관리하기 때문에 저렇게까지는 나오지 않는다.
그러면 디바이스가 호스트에 연결이 되면 호스트는 디바이스의 속도를 알아야 필요한 설정 정보 등을 알 수 있고 원하는 통신을 할 수 있을 것이다. 따라서 하드웨어적으로 기본적인 속도가 구분되야 한다.
이런 이유 떄문에 usb에는 통신을 위한 선이 두가지가 존재한다. 바로 D+와 D-이다.
LS : pull-up on D-
FS : pull-up on D+
D- 라인인 경우는 LS에 풀업 저항이 걸려있고, D+ 라인인 경우는 FS에 풀업 저항이 걸린다. 따라서 host디바이스가 연결되면 D-,D+ 에 대한 전압을 판단해서 hostLow Speed device가 붙었구나 혹은 Full Speed device가 붙었구나를 판단할 수 있게 된다.

2) Power

전원 관련해서 usb device는 크게 두가지로 구분된다.
Bus Powered : 디바이스가 host로부터 전원을 공급 받음
Self Powered : 디바이스가 자체 파워를 가지고 있음
Bus Power 인 경우 host로부터 무작정 전원을 공급 받을 수는 없기 때문에 장치인식시에는 최대 100mA 까지 전원 공급을 받고, 장치인식이 끝나 후에는 최대 500mA까지 전원을 공급 받을 수 있다.
또한 디바이스는 두가지의 전원 관리 상태를 가진다.
Suspended 모드
흔히 말하는 sleep 모드를 뜻한다. 만약 버스에 3ms 이상 어떤 신호가 없을 경우 혹은 host로부터 suspend 신호가 전달될 경우 sleep 모드로 빠질 수 가 있다.
예를 들어 무선 마우스가 3초 정도 사용 안되면 sleep 모드로 빠져서 한번 클릭을 해야 돌아오는 경우를 많이 봤을 것이다. (이를 Remote wake-up 기능이라 함.)

4. 장치인식(Enumeration)

디바이스가 호스트에 연결되었을 때 호스트는 해당 디바이스를 감지하고 장치인식에 관한 일련의 프로세스를 진행한다. 장치인식의 제일 첫 번째 과정은 다음과 같다.
호스트는 디바이스의 요구사항들을 제일 먼저 확인한다. 예를 들면 연결시도를 하는 디바이스는 얼마의 전원 공급을 원하는지 혹은 function 디바이스 중에서 키보드인지, 마우스인지 등과 같은 사항들의 요청을 의미한다.
용어적으로 설명하면 해당 요청사항의 정보를 담고있는 것을 descriptor라고 부른다. 즉 호스트는 제일 처음으로 디바이스로부터 descriptor 를 읽어온 뒤, 해당 디바이스에게 고유한 주소를 할당해준다. (descriptor 에 대한 내용은 뒤에서 좀더 자세히 살펴볼것이다.)
자세하게 말하면 고유한 주소(Address)만 할당해주는 것은 아니고, 통신 타입이라든가, 디바이스 타입, 뒤에서 말할 endpoint 주소를 만드는 과정도 일어난다.
위에서 usb device는 최대 128개 까지 연결이 가능하다고 했으므로 할당해주는 주소의 범위는 0~127 까지이다. (0은 보통 예약된 번호. 아마 usb root hub). 이렇게 할당한 주소를 가지고 디바이스와 통신을 시작하게 된다.
호스트는 디바이스의 요청사항들을 확인하고 정상적인 경우에는 요청을 받아들인다. 하지만 만약 규격 이상의 전압을 요청했다던가, 정해진 bandwith를 벗어난 값을 요청했다거나 등의 경우에는 호스트는 장치인식을 허용하지 않는다.

5. Transfer and Endpoints

1) Transfer - Data 전송 Format

호스트와 디바이스가 통신할 때 transfer 라는 단위를 사용한다. 이는 가장 상위 단계의 용어이며 transfertransactions 으로 구성이되어있다. transactions 은 매 프레임마다 전송된다.
Frame은 1ms 마다 전송되는 Data의 단위를 가리키고, Frame의 내부는 Transaction으로 차있다. Frame의 최소 통신간격은 1ms이다.
transactions 은 최종적으로 패킷으로 구성되어있다. 정리를 하면 다음과 같다.
usb data 구조
호스트와 디바이스 통신에 사용되는 일련의 데이터는 크게 transfer로 구성되어 있으며 transfer는 여러개의 transaction으로 구성되어있다. 또한 transaction 역시 패킷으로 구성되어있다. 패킷 역시 크게 2가지의 타입으로 구성된다.
Packet Types
1.
Token 패킷 : starts the transaction 패킷
IN Token : Host ← Device로 데이터를 받고 싶을 때
Out Token : Host → Device로 데이터를 전송하고 싶을 때
SOF Token : 프레임의 시작시 보내는 토큰
setup Tokn : 장치인식에 사용되는 토큰
2.
Data 패킷 : 실제 데이터의 IN/OUT 패킷
Data0, Data1
Data2, MDATA
3.
Handshake 패킷 : token, data 패킷을 보내고 잘 처리됬는지 확인하는 용도의 패킷
ACK : 데이터를 잘 받았다는 의미
NAK : 들어온 데이터가 없거나 아직 준비되지 않았다는 의미
STALL :
NYET
(CRC에러나 다른 에러의 경우 handshake 패킷이 없을 수도 있음)
위에서 설명한 packet type을 그림으로 살펴보자.
Host → Device로 나가는 패킷인 경우
Out Token 패킷 전송 (H→D)
실제 Data 패킷 전송 (H→D)
디바이스가 잘 받았다는 의미의 Ack 패킷 전송 (D→H)
Host ← Device로 들어오는 패킷인 경우
Input Token 패킷 전송 (H→D)
실제 Data 패킷 전송 (D→H)
호스트가 잘 받았다는 의미의 Ack 패킷 전송 (H→D)

2) Endpoints

transfer가 전송되면 이를 받아들일 버퍼가 필요하다. 이 버퍼를 바로 usb에서는 Endpoints라고 부른다. Endpoints 는 input 버퍼 16개, output 버퍼 16개 총 32개의 버퍼를 가질 수 있다.
IN : 호스트로 들어가는 데이터를 저장하는 Endpoint
OUT : 호스트에서 나가는 데이터를 저장하는 Endpoint
EP0 : 장치인식을 위한 Endpoint
EP0를 제외한 EP1 ~ EP15는 데이터 통신을 위한 버퍼로 사용되기 떄문에 EP1~EP15 endpoint를 interfaces라고 부른다. 따라서 장치인식이 끝난 후에 interface가 형성이 되고 이를 통해서 호스트와 디바이스는 데이터를 주고받는다.
위 사진에서 Endpoint 는 호스트와 디바이스 각 끝단에 존재한다. 호스트쪽 endpoint에 데이터가 디바이스로 전송되거나, 디바이스 쪽의 endpoint에 들어있는 데이터가 host endpoint 쪽으로 전송되는 식으로 통신이 일어난다.

3) Transfer Type - 전송 방식 종류

usb 데이터는 기본적으로 가장 상위 레벨인 transfer 단위로 통신한다고 설명했는데, 이 transfer에는 통신 목적에 따라 여러가지 타입들이 존재한다.
Bulk Type (not available on LS)
속도가 가장 빠른 전송 방식이다. 따라서 외장하드 같이 데이터 전송량이 많은 usb 디바이스들이 연결되면 주로 bulk type을 이용한다. bulk type에서는 FS에서는 64byte, HS에서는 512byte로 endpont의 사이즈가 제한된다.
위에서 설명한 것처럼 Transfertransaction으로 구성된다고 했다. transaction은 또 하위에 여러 패킷들로 구성되어있다. 결국 패킷들을 묶어서 transaction으로 그룹을 짓고, 또 transaction을 묶어서 transfer로 그룹을 짓는다. 결과적으로 하위단을 보면 다 패킷들인 것을 알 수 있다.
위 사진을 보면 transaction id 값, in or out type, addr, endpoint, data size 등이 필드인 것을 알 수 있다.
Interrupt Type
주기적으로 데이터를 보낼 때 딜레이를 가장 최소화하는 디바이스에 가장 많이 사용된다. 인터럽트 방식은 주기적으로 데이터를 주시하여 데이터를 송수신한다. 이 방식은 latency가 보장되지만 bulk type은 보장되지 않는다.
Interrupt 방식의 디바이스에는 키보드, 마우스 등이 있다.
bulk type에서 설명한 그림보다 좀 더 자세히 나와있다. transfer 하위에 transcation과 그 하위에 또 패킷이 존재하며, tranfer 필드를 보면 interrupt 타입인 것을 알 수 있다. interrupt 타입은 LS/FS 일때 최대 64byte의 endpoint 사이즈를 가지며 HS일 때는 최대 1024byte 크기의 endpoint를 가진다.
Isochronous Type (not available on LS)
Isochronous 타입은 latency와 속도를 둘다 잡아야 할 때 사용하는 타입이다. 실시간 usb 오디오 스트리밍, usb 마이크 등 처럼 실시간의 데이터가 나가야 할 때 주로 사용한다.(Real Time transfer)
단점으로는 에러 검출이 불가능하다.(bulk, interrupt 타입은 crc 체킹을 통해 재전송이 가능함). 결국 정확성보다는 속도를 더 중요시 여기는 디바이스에서 사용한다.
Control Type
디바이스 장치인식 과정에서 사용하는 transfer 타입이다.
장치인식 과정에서 디바이스 주소를 할당하거나 설정과정을 처리할 때 사용하는 전송 타입이다. (address를 설정하거나 descriptor를 읽거나 하는 등의 처리과정에 쓰임)

6. USB Classess

USB는 여러 종류의 장치를 지원한다. 이 다양한 디바이스를 기능별로 분류하여 Class라 부르고, Class 별로 표준 프로토콜을 정의하였다. 각 디바이스는 표준 프로토콜을 준수해서 동작한다.
usb software stack

1) Human Interface Device

HID(Human Interface Device)가 대표적인 예이다.
Human Interface Device란 컴퓨터 주변 기기 중 사용자 인터페이스를 담당하는 것을 뜻한다. 대부분은 인간으로부터 입력을 받으며, 일부는 출력 기능을 갖추기도 한다. 한편 HID라는 용어는 대개 USB의 장치 규격 중 하나인 USB 인간 인터페이스 장치 유형을 가리킨다. - 출처 : wikipedia
HID는 위에서 설명한 다양한 Transfer type 중 Interrupt Transfer 타입을 사용한다. HID Class의 장점은 표준 OS에서 대부분 HID를 지원하기 때문에 별도의 USB 드라이버를 개발할 필요가 없다. 키보드, 마우스, 조이스틱, 터치패널 등이 HID로 구성된다.

2) Mass Storage Device

HID이외의 USB Class에는 Mass Storage Device인 MSD(외장하드, sd카드 등)가 있으며 MSD는 Bulk Transfer 타입을 사용한다.

3) Communication Device Class(CDC)

USB to Serial, USb to ethrenet 등 usb 포트에 연결하여 통신하는 디바이스들이 주로 사용하는 class이다. CDC는 통신 방법에 따라 ACM, ECM, EEM, NCM, OBEX 등의 다양한 subclass를 사용한다.
ACM(Abstract Control Model Class)
USB to Serial에 주로 사용되는 subclass
ECM(Ethernet Networking Control Model)
Usb to ethernet의 subclass. 주 목적은 ethernet packet을 전송하기 위한 class이다.

4) Vendor Device Class

비표준의 USB Class로 표준 usb class가 아닌 커스텀한 class를 사용하고 싶을 때 사용한다. 해당 class의 단점은 표준이 아니기 때문에 usb 드라이버를 직접 개발해야한다.
이렇게 다양한 USB 표준 class들이 존재하는데 usb host class 들은 usb 통신에서 아래그림과 같은 layer에 위치한다.
실제 USB 디바이스에서 전송되는 데이터는
1.
USB Host 컨트롤러 드라이버
2.
USB host core (Hub Driver)
3.
USB Host Class
를 거쳐 각 목적에 따른 작업을 수행한다.
만약 Host(PC)와 Device(Embedded Device)가 usb로 연결되어 통신을 하게 된다면, 하드웨어-소프트웨어 구성을 다음과 같다.

6. Descriptor

4장에서 설명한 Descriptor 에 대한 내용을 좀더 자세하게 살펴보자. descriptor에는 usb의 모든 설정 정보가 담겨져 있으며, Host가 이 descriptor 를 읽고 장치인식 및 설정을 진행한다.
standard descriptor - 필수
모든 디바이스는 standard descriptor를 가지고 있다. standard descriptor가 없거나 문제가 생기면 장치인식이 되지않는다.
Class descriptor - 추가
class descriptor란 예를 들어 HID class 인 경우 HID에 필요한 정보만을 담고 있는 descriptor를 뜻한다.
standard descriptor는 다음과 같은 구성으로 되어있다.
Device - 각 디바이스마다 하나씩 존재 (VID, PID 등)
Configuration - 각 디바이스마다 적어도 하나 이상
Interface - 각 configuration마다 적어도 하나 이상
Endpoint - 각 interface마다 적어도 하나 이상
위에서 설명한 Descriptor에 대한 내용을 그림으로 다시 살펴보자
Device Descriptor
디바이스와 관계된 descriptor는 딱 한개만 존재하다고 했다. VID, PID 정보와 몇개의 configuration descriptor를 가지고 있는지에 대한 정보가 들어있다.
Configuration Descriptor
뜻 그대로 설정에 관련된 정보가 들어있다. 파워는 몇이며, suspend모드시 언제 wake-up을 진행할 것이지, 그리고 몇개의 interface descriptor 정보가 들어있는지의 정보가 들어있다.
Interface
Interface 는 Configuration 하위에 들어있는 정보로 어떠한 USB Class인지의 정보와 몇개의 endpoint가 존재하는지의 정보가 들어있다
Endpoint
Endpoint 역시 Configuration 하위에 들어있는 정보로 IN or Out buffer인지, 어떠한 Transfer 타입인지, 버퍼의 사이즈가 몇인지 등인지에 대한 정보가 들어있다.