KHỞI TẠO USB HID STM32F103C8T6 ĐƠN GIẢN BẰNG STM32CUBEMX
1. Hardware
Kit STM32F103C8T6
Schematic kit
2. Khởi tạo STM32CubeMx
STEP 1:
Vào chương trình STM32CubeMX -> Chon Create new project. -> Chọn MCU STM32F103C8Tx( STM32F103C8T6).
STEP 2:
Trong muc Pinout.
Peripherals => USB => Tick vào Device(FS)
Middlewares=> Custom Human Interface Device Class(HID).
Trong mục Pinout.
Peripherals => RCC => High Speed Clock (HSE) =>Chọn => Crytal/Ceramic Resonator.
STEP 4:
Trong mục Clock configuration.
Config Clock USB => 48Mhz.
STEP 6:
Xuất hiện hôp thoại USB Configuration => Tab Parameter settings => Basic parameters => Endpoint 0 Max Packet size => 64 byte. (Maximum gói data endpoint 0 là 64 byte)
STEP 7:
STEP 8:
Xuất hiện hôp thoại USB_DEVICE Configuration => Tab Parameter settings => Class parameters :
- USBD_CUSTOM_HID_REPORT_DESC_SIZE (Total length for Report descriptor (IN ENDPOINT)): 32 (32 byte mô tả report input).
- USBD_CUSTOMHID_OUTREPORT_BUF_SIZE (Maximum report buffer size (OUT ENDPOINT)): 64 ( maximum 64 byte buffer report output ).
STEP 9:
Xuất hiện hôp thoại USB_DEVICE Configuration => Tab Device Descriptor => Device Descriptor FS => PRODUCT_STRING (Product Identifier) =>Đổi Product string USB HID.
3. Config file mô tả USB HID (USB HID Report Descriptor).
- Trong file usbd_custom_hid_if.c
__ALIGN_BEGIN static uint8_t CUSTOM_HID_ReportDesc_FS[USBD_CUSTOM_HID_REPORT_DESC_SIZE] __ALIGN_END =
{
/* USER CODE BEGIN 0 */
0x00,
/* USER CODE END 0 */
0xC0 /* END_COLLECTION */
};
Sửa thành=====>
__ALIGN_BEGIN static uint8_t CUSTOM_HID_ReportDesc_FS[USBD_CUSTOM_HID_REPORT_DESC_SIZE] __ALIGN_END =
{
0x05, 0x01, // USAGE_PAGE (Generic Desktop)
0x09, 0x00, // USAGE (Undefined)
0xa1, 0x01, // COLLECTION (Application)
0x15, 0x00, // LOGICAL_MINIMUM (0)
0x26, 0xff, 0x00, // LOGICAL_MAXIMUM (255)
0x85, 0x01, // REPORT_ID (1) //report id input là 0x01
0x75, 0x08, // REPORT_SIZE (8)
0x95, 0x3F, // REPORT_COUNT (63)//report input gồm có 63 byte data và một byte ID=0x01
0x09, 0x00, // USAGE (Undefined)
0x81, 0x82, // INPUT (Data,Var,Abs,Vol) - to the host
0x85, 0x02, // REPORT_ID (2)//report id output là 0x02
0x75, 0x08, // REPORT_SIZE (8)
0x95, 0x3F, // REPORT_COUNT (63)//report output gồm có 63 byte data và một byte ID=0x02
0x09, 0x00, // USAGE (Undefined)
0x91, 0x82, // OUTPUT (Data,Var,Abs,Vol) - from the host
0xc0 // END_COLLECTION
};
USBD_CUSTOM_HID_REPORT_DESC_SIZE: 32 byte mô tả đã config trên soft STM32CubeMX.
- Trong file usb_customhid.h
#define CUSTOM_HID_EPIN_ADDR 0x81
#define CUSTOM_HID_EPIN_SIZE 0x02
#define CUSTOM_HID_EPOUT_ADDR 0x01
#define CUSTOM_HID_EPOUT_SIZE 0x02
Sửa thành===>
#define CUSTOM_HID_EPIN_ADDR 0x81
#define CUSTOM_HID_EPIN_SIZE 64
#define CUSTOM_HID_EPOUT_ADDR 0x01
#define CUSTOM_HID_EPOUT_SIZE 64
///////////////////////////////
4. Send và Receive data.
- Send data:
uint8_t USBD_CUSTOM_HID_SendReport (USBD_HandleTypeDef *pdev, uint8_t *report, uint16_t len);
VD:
uint8_t data[64];
data[0]=0x01; //report id input là 0x01, byte đầu tiên phải là report id.
USBD_CUSTOM_HID_SendReport(&hUsbDeviceFS,data,64);
Khi config USBD_CUSTOM_HID_REPORT_DESC_SIZE=64 thì gửi gói data luôn có len=64.
Note: Nếu muốn gửi và nhận gói data >64 byte VD 128 byte có thể sửa như sau:
USBD_CUSTOM_HID_REPORT_DESC_SIZE=128
CUSTOM_HID_ReportDesc_FS[USBD_CUSTOM_HID_REPORT_DESC_SIZE] __ALIGN_END =
{
0x05, 0x01, // USAGE_PAGE (Generic Desktop)
0x09, 0x00, // USAGE (Undefined)
0xa1, 0x01, // COLLECTION (Application)
0x15, 0x00, // LOGICAL_MINIMUM (0)
0x26, 0xff, 0x00, // LOGICAL_MAXIMUM (255)
0x85, 0x01, // REPORT_ID (1) //report id input là 0x01
0x75, 0x08, // REPORT_SIZE (8)
0x95, 127, // REPORT_COUNT (127)//report input gồm có 127 byte data và một byte ID=0x01
0x09, 0x00, // USAGE (Undefined)
0x81, 0x82, // INPUT (Data,Var,Abs,Vol) - to the host
0x85, 0x02, // REPORT_ID (2)//report id output là 0x02
0x75, 0x08, // REPORT_SIZE (8)
0x95, 127, // REPORT_COUNT (127)//report output gồm có 127 byte data và một byte ID=0x02
0x09, 0x00, // USAGE (Undefined)
0x91, 0x82, // OUTPUT (Data,Var,Abs,Vol) - from the host
0xc0 // END_COLLECTION
};
uint8_t data[128];
data[0]=0x01; //report id input là 0x01, byte đầu tiên phải là report id.
USBD_CUSTOM_HID_SendReport(&hUsbDeviceFS,data,128);
- Receive data:
uint8_t My_Buffer[USBD_CUSTOMHID_OUTREPORT_BUF_SIZE];
static uint8_t USBD_CUSTOM_HID_DataOut (USBD_HandleTypeDef *pdev,
uint8_t epnum)
{
USBD_CUSTOM_HID_HandleTypeDef *hhid = (USBD_CUSTOM_HID_HandleTypeDef*)pdev->pClassData;
((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->OutEvent(hhid->Report_buf[0], hhid->Report_buf[1]);
///////////////////////////////
for(uint8_t i=0;i<64;i++)
{
My_Buffer[i]=hhid->Report_buf[i]; //gán buffer Report_buf vào My_Buffer để truy xuất data.
}
//////////////////
USBD_LL_PrepareReceive(pdev, CUSTOM_HID_EPOUT_ADDR , hhid->Report_buf,
USBD_CUSTOMHID_OUTREPORT_BUF_SIZE);
return USBD_OK;
}
5. Example code:
- Code nhận data và gửi data đã nhận lên máy tính. Test bằng phần mềm USB HID Demonstrator(v1.02)
/////////////////////////////////////////////////
uint8_t data[64];
data[0]=0x01;
while (1)
{
if(check_usb==1)
{
HAL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin);
for(uint8_t i=1;i<64;i++)
{
data[i]=My_Buffer[i];
}
USBD_CUSTOM_HID_SendReport(&hUsbDeviceFS,data,64);
check_usb=0;
}
}
/////////////////////////////////////////////
Link demo code:
https://drive.google.com/file/d/0B9pHWA4exz3gU3lzZDBlMWExMGM/view?usp=sharing
USB HID Demonstrator(v1.02): https://drive.google.com/file/d/0B9pHWA4exz3gNWNGak9zY1dVakU/view?usp=sharing
Video demo: