#include stdio.h
#include stdlib.h
#include unistd.h
#include string.h
#include strings.h
#include signal.h
#include errno.h
#include fcntl.h
#include pthread.h
#include sys/types.h
#include sys/wait.h
#include sys/stat.h
#include sys/ipc.h
#include sys/sem.h
#include sys/shm.h
#include sys/msg.h
#include sys/socket.h
#include arpa/inet.h
#include <linux/hiddev.h>
#include <sys/ioctl.h>
#include <time.h>
typedef uint8_t u8;
typedef int8_t s8;
typedef uint16_t u16;
typedef int16_t s16;
typedef uint32_t u32;
typedef int32_t s32;
int termflag=1;
/* path es del tipo "/dev/usb/hiddevN" */
int hidOpen(char * path)
{
return open(path, O_RDWR);
}
int hidClose(int fd)
{
return close(fd);
}
int hidGetVendorProduct(int fd, u16 * vid, u16 * pid)
{
struct hiddev_devinfo hidinfo;
if(ioctl(fd, HIDIOCGDEVINFO, &hidinfo)<0)
{
perror("hid-ioctl-devinfo");
return -1;
}
*vid = hidinfo.vendor;
*pid = hidinfo.product;
return 0;
}
int hidGetStringDesc(int fd, int index, char * s)
{
struct hiddev_string_descriptor devstr;
devstr.index = index;
if(ioctl(fd, HIDIOCGSTRING, &devstr)<0)
{
perror("hid-ioctl-string");
return -1;
}
strncpy(s, devstr.value, HID_STRING_SIZE);
return 0;
}
int hidGetInReport(int fd, uint8_t * data, int len)
{
struct hiddev_report_info rinfo;
struct hiddev_field_info finfo;
struct hiddev_usage_ref uref;
int i,j,ret;
rinfo.report_type = HID_REPORT_TYPE_INPUT;
rinfo.report_id = HID_REPORT_ID_FIRST;
ret = ioctl(fd, HIDIOCGREPORTINFO, &rinfo);
if(ret<0)
{
perror("hid-ioctl-inrepinfo");
return -1;
}
// Get Fields
for (i = 0; i < rinfo.num_fields; i++)
{
finfo.report_type = rinfo.report_type;
finfo.report_id = rinfo.report_id;
finfo.field_index = i;
ioctl(fd, HIDIOCGFIELDINFO, &finfo);
// Get usages
printf("(IN Max Usage: %d) ", finfo.maxusage);
//si len es menor que finfo.maxusage, leer solamente len bytes
if(len < finfo.maxusage) finfo.maxusage = len;
for (j = 0; j < finfo.maxusage; j++)
{
uref.report_type = finfo.report_type;
uref.report_id = finfo.report_id;
uref.field_index = i;
uref.usage_index = j;
ioctl(fd, HIDIOCGUCODE, &uref);
ioctl(fd, HIDIOCGUSAGE, &uref);
data[j] = uref.value;
}
}
return finfo.maxusage;
}
int hidSetOutReport(int fd, uint8_t * data, int len)
{
struct hiddev_usage_ref uref;
struct hiddev_report_info rinfo;
struct hiddev_field_info finfo;
int i,j,ret;
rinfo.report_type = HID_REPORT_TYPE_OUTPUT;
rinfo.report_id = HID_REPORT_ID_FIRST;
ret = ioctl(fd, HIDIOCGREPORTINFO, &rinfo);
if(ret<0)
{
perror("hid-ioctl-outrepinfo");
return -1;
}
// Get Fields
for (i = 0; i < rinfo.num_fields; i++)
{
finfo.report_type = rinfo.report_type;
finfo.report_id = rinfo.report_id;
finfo.field_index = i;
ioctl(fd, HIDIOCGFIELDINFO, &finfo);
// Get usages
printf("(OUT Max Usage: %d) ", finfo.maxusage);
// si len es menor a finfo.maxusage, mando len bytes y completo con ceros
if(len < finfo.maxusage) finfo.maxusage = len;
for (j = 0; j < finfo.maxusage; j++)
{
uref.report_type = finfo.report_type;
uref.report_id = finfo.report_id;
uref.field_index = i;
uref.usage_index = j;
uref.value = data[j];
ioctl(fd,HIDIOCSUSAGE, &uref);
}
//send report
ret = ioctl(fd,HIDIOCSREPORT,&rinfo);
if(ret<0)
{
perror("ioctl-setout");
return -1;
}
}
return finfo.maxusage;
}
void sigint_handler(int s)
{
termflag=0;
}
//pasar el argumento tipo /dev/usb/hiddev0
int main (int argc, char **argv)
{
int fd = -1;
if ((fd = hidOpen("/dev/usb/hiddev0")) < 0)
{
perror("hidopen");
exit(1);
}
u16 vid, pid;
hidGetVendorProduct(fd, &vid, &pid);
printf("VID:%04X PID:%04X\n", vid, pid);
char str[HID_STRING_SIZE]= "";
hidGetStringDesc(fd, 0x01, str);
printf("Manuf:%s\n", str);
hidGetStringDesc(fd, 0x02, str);
printf("Prod:%s\n", str);
uint8_t data[100] = {1,2,3,4,5,6,7,8};
int i, ret;
ret = hidGetInReport(fd, data, 8);
printf("IN: ");
for(i=0; i<100; i++) printf("0x%02X ", data);
printf("\n");
*data = 1;
hidSetOutReport(fd, data, 1);
sleep(1);
*data = 0;
hidSetOutReport(fd, data, 1);
printf("Fin.\n");
hidClose(fd);
return 0;
}
|
/*
* @brief HID generic example
*
* @note
* Copyright(C) NXP Semiconductors, 2013
* All rights reserved.
*
* @par
* Software that is described herein is for illustrative purposes only
* which provides customers with programming information regarding the
* LPC products. This software is supplied "AS IS" without any warranties of
* any kind, and NXP Semiconductors and its licensor disclaim any and
* all warranties, express or implied, including all implied warranties of
* merchantability, fitness for a particular purpose and non-infringement of
* intellectual property rights. NXP Semiconductors assumes no responsibility
* or liability for the use of the software, conveys no license or rights under any
* patent, copyright, mask work right, or any other intellectual property rights in
* or to any products. NXP Semiconductors reserves the right to make changes
* in the software without notification. NXP Semiconductors also makes no
* representation or warranty that such application will be suitable for the
* specified use without further testing or modification.
*
* @par
* Permission to use, copy, modify, and distribute this software and its
* documentation is hereby granted, under NXP Semiconductors' and its
* licensor's relevant copyrights in the software, without fee, provided that it
* is used in conjunction with NXP Semiconductors microcontrollers. This
* copyright, permission, and disclaimer notice must appear in all copies of
* this code.
*/
#include "board.h"
#include <stdio.h>
#include <string.h>
#include "app_usbd_cfg.h"
#include "hid_generic.h"
/*****************************************************************************
* Private types/enumerations/variables
****************************************************************************/
/*****************************************************************************
* Public types/enumerations/variables
****************************************************************************/
static USBD_HANDLE_T g_hUsb;
extern const USBD_HW_API_T hw_api;
extern const USBD_CORE_API_T core_api;
extern const USBD_HID_API_T hid_api;
/* Since this example only uses HID class link functions for that class only */
static const USBD_API_T g_usbApi = {
&hw_api,
&core_api,
0,
0,
&hid_api,
0,
0,
0x02221101,
};
const USBD_API_T *g_pUsbApi = &g_usbApi;
/*****************************************************************************
* Private functions
****************************************************************************/
/* Initialize pin and clocks for USB port */
static void usb_pin_clk_init(void)
{
/* enable USB PLL and clocks */
Chip_USB_Init();
/* enable USB 1 port on the board */
Board_USBD_Init(1);
}
/*****************************************************************************
* Public functions
****************************************************************************/
/**
* @briefHandle interrupt from USB
* @returnNothing
*/
void USB_IRQHandler(void)
{
USBD_API->hw->ISR(g_hUsb);
}
/* Find the address of interface descriptor for given class type. */
USB_INTERFACE_DESCRIPTOR *find_IntfDesc(const uint8_t *pDesc, uint32_t intfClass)
{
USB_COMMON_DESCRIPTOR *pD;
USB_INTERFACE_DESCRIPTOR *pIntfDesc = 0;
uint32_t next_desc_adr;
pD = (USB_COMMON_DESCRIPTOR *) pDesc;
next_desc_adr = (uint32_t) pDesc;
while (pD->bLength) {
/* is it interface descriptor */
if (pD->bDescriptorType == USB_INTERFACE_DESCRIPTOR_TYPE) {
pIntfDesc = (USB_INTERFACE_DESCRIPTOR *) pD;
/* did we find the right interface descriptor */
if (pIntfDesc->bInterfaceClass == intfClass) {
break;
}
}
pIntfDesc = 0;
next_desc_adr = (uint32_t) pD + pD->bLength;
pD = (USB_COMMON_DESCRIPTOR *) next_desc_adr;
}
return pIntfDesc;
}
/**
* @briefmain routine for blinky example
* @returnFunction should not exit.
*/
int main(void)
{
USBD_API_INIT_PARAM_T usb_param;
USB_CORE_DESCS_T desc;
ErrorCode_t ret = LPC_OK;
/* Initialize board and chip */
SystemCoreClockUpdate();
Board_Init();
/* enable clocks and pinmux */
usb_pin_clk_init();
/* initialize call back structures */
memset((void *) &usb_param, 0, sizeof(USBD_API_INIT_PARAM_T));
usb_param.usb_reg_base = LPC_USB_BASE + 0x200;
usb_param.max_num_ep = 2;
usb_param.mem_base = USB_STACK_MEM_BASE;
usb_param.mem_size = USB_STACK_MEM_SIZE;
/* Set the USB descriptors */
desc.device_desc = (uint8_t *) USB_DeviceDescriptor;
desc.string_desc = (uint8_t *) USB_StringDescriptor;
/* Note, to pass USBCV test full-speed only devices should have both
* descriptor arrays point to same location and device_qualifier set
* to 0.
*/
desc.high_speed_desc = USB_FsConfigDescriptor;
desc.full_speed_desc = USB_FsConfigDescriptor;
desc.device_qualifier = 0;
/* USB Initialization */
ret = USBD_API->hw->Init(&g_hUsb, &desc, &usb_param);
if (ret == LPC_OK) {
ret = usb_hid_init(g_hUsb,
(USB_INTERFACE_DESCRIPTOR *) &USB_FsConfigDescriptor[sizeof(USB_CONFIGURATION_DESCRIPTOR)],
&usb_param.mem_base, &usb_param.mem_size);
if (ret == LPC_OK) {
/* enable USB interrupts */
NVIC_EnableIRQ(USB_IRQn);
/* now connect */
USBD_API->hw->Connect(g_hUsb, 1);
}
}
while (1) {
__WFI();
}
}
|
/*
* @brief HID example USB descriptors
*
* @note
* Copyright(C) NXP Semiconductors, 2013
* All rights reserved.
*
* @par
* Software that is described herein is for illustrative purposes only
* which provides customers with programming information regarding the
* LPC products. This software is supplied "AS IS" without any warranties of
* any kind, and NXP Semiconductors and its licensor disclaim any and
* all warranties, express or implied, including all implied warranties of
* merchantability, fitness for a particular purpose and non-infringement of
* intellectual property rights. NXP Semiconductors assumes no responsibility
* or liability for the use of the software, conveys no license or rights under any
* patent, copyright, mask work right, or any other intellectual property rights in
* or to any products. NXP Semiconductors reserves the right to make changes
* in the software without notification. NXP Semiconductors also makes no
* representation or warranty that such application will be suitable for the
* specified use without further testing or modification.
*
* @par
* Permission to use, copy, modify, and distribute this software and its
* documentation is hereby granted, under NXP Semiconductors' and its
* licensor's relevant copyrights in the software, without fee, provided that it
* is used in conjunction with NXP Semiconductors microcontrollers. This
* copyright, permission, and disclaimer notice must appear in all copies of
* this code.
*/
#include "app_usbd_cfg.h"
/*****************************************************************************
* Private types/enumerations/variables
****************************************************************************/
/*****************************************************************************
* Public types/enumerations/variables
****************************************************************************/
#define HID_INPUT_REPORT_BYTES 1/* size of report in Bytes */
#define HID_OUTPUT_REPORT_BYTES 1/* size of report in Bytes */
#define HID_FEATURE_REPORT_BYTES 1/* size of report in Bytes */
/**
* HID Report Descriptor
*/
const uint8_t HID_ReportDescriptor[] = {
HID_UsagePageVendor(0x00),
HID_Usage(0x01),
HID_Collection(HID_Application),
HID_LogicalMin(0),/* value range: 0 - 0xFF */
HID_LogicalMaxS(0xFF),
HID_ReportSize(8),/* 8 bits */
HID_ReportCount(HID_INPUT_REPORT_BYTES),
HID_Usage(0x01),
HID_Input(HID_Data | HID_Variable | HID_Absolute),
HID_ReportCount(HID_OUTPUT_REPORT_BYTES),
HID_Usage(0x01),
HID_Output(HID_Data | HID_Variable | HID_Absolute),
HID_ReportCount(HID_FEATURE_REPORT_BYTES),
HID_Usage(0x01),
HID_Feature(HID_Data | HID_Variable | HID_Absolute),
HID_EndCollection,
};
const uint16_t HID_ReportDescSize = sizeof(HID_ReportDescriptor);
/**
* USB Standard Device Descriptor
*/
ALIGNED(4) const uint8_t USB_DeviceDescriptor[] = {
USB_DEVICE_DESC_SIZE,/* bLength */
USB_DEVICE_DESCRIPTOR_TYPE,/* bDescriptorType */
WBVAL(0x0200),/* bcdUSB 2.0 */
0x00,/* bDeviceClass */
0x00,/* bDeviceSubClass */
0x00,/* bDeviceProtocol */
USB_MAX_PACKET0,/* bMaxPacketSize0 */
WBVAL(0x1FC9),/* idVendor */
WBVAL(0x0081),/* idProduct */
WBVAL(0x0100),/* bcdDevice */
0x01,/* iManufacturer */
0x02,/* iProduct */
0x03,/* iSerialNumber */
0x01/* bNumConfigurations */
};
/**
* USB FSConfiguration Descriptor
* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor)
*/
ALIGNED(4) uint8_t USB_FsConfigDescriptor[] = {
/* Configuration 1 */
USB_CONFIGURATION_DESC_SIZE,/* bLength */
USB_CONFIGURATION_DESCRIPTOR_TYPE,/* bDescriptorType */
WBVAL(/* wTotalLength */
USB_CONFIGURATION_DESC_SIZE +
USB_INTERFACE_DESC_SIZE +
HID_DESC_SIZE +
USB_ENDPOINT_DESC_SIZE +
USB_ENDPOINT_DESC_SIZE
),
0x01,/* bNumInterfaces */
0x01,/* bConfigurationValue */
0x00,/* iConfiguration */
USB_CONFIG_SELF_POWERED,/* bmAttributes */
USB_CONFIG_POWER_MA(100),/* bMaxPower */
/* Interface 0, Alternate Setting 0, HID Class */
USB_INTERFACE_DESC_SIZE,/* bLength */
USB_INTERFACE_DESCRIPTOR_TYPE,/* bDescriptorType */
0x00,/* bInterfaceNumber */
0x00,/* bAlternateSetting */
0x02,/* bNumEndpoints */
USB_DEVICE_CLASS_HUMAN_INTERFACE,/* bInterfaceClass */
HID_SUBCLASS_NONE,/* bInterfaceSubClass */
HID_PROTOCOL_NONE,/* bInterfaceProtocol */
0x04,/* iInterface */
/* HID Class Descriptor */
/* HID_DESC_OFFSET = 0x0012 */
HID_DESC_SIZE,/* bLength */
HID_HID_DESCRIPTOR_TYPE,/* bDescriptorType */
WBVAL(0x0111),/* bcdHID : 1.11*/
0x00,/* bCountryCode */
0x01,/* bNumDescriptors */
HID_REPORT_DESCRIPTOR_TYPE,/* bDescriptorType */
WBVAL(sizeof(HID_ReportDescriptor)),/* wDescriptorLength */
/* Endpoint, HID Interrupt In */
USB_ENDPOINT_DESC_SIZE,/* bLength */
USB_ENDPOINT_DESCRIPTOR_TYPE,/* bDescriptorType */
HID_EP_IN,/* bEndpointAddress */
USB_ENDPOINT_TYPE_INTERRUPT,/* bmAttributes */
WBVAL(0x0004),/* wMaxPacketSize */
0x20,/* 16ms */ /* bInterval */
/* Endpoint, HID Interrupt Out */
USB_ENDPOINT_DESC_SIZE,/* bLength */
USB_ENDPOINT_DESCRIPTOR_TYPE,/* bDescriptorType */
HID_EP_OUT,/* bEndpointAddress */
USB_ENDPOINT_TYPE_INTERRUPT,/* bmAttributes */
WBVAL(0x0004),/* wMaxPacketSize */
0x20,/* bInterval: 16ms */
/* Terminator */
0/* bLength */
};
/**
* USB String Descriptor (optional)
*/
const uint8_t USB_StringDescriptor[] = {
/* Index 0x00: LANGID Codes */
0x04,/* bLength */
USB_STRING_DESCRIPTOR_TYPE,/* bDescriptorType */
WBVAL(0x0409),/* wLANGID : US English*/
/* Index 0x01: Manufacturer */
(18 * 2 + 2),/* bLength (13 Char + Type + lenght) */
USB_STRING_DESCRIPTOR_TYPE,/* bDescriptorType */
'N', 0,
'X', 0,
'P', 0,
' ', 0,
'S', 0,
'e', 0,
'm', 0,
'i', 0,
'c', 0,
'o', 0,
'n', 0,
'd', 0,
'u', 0,
'c', 0,
't', 0,
'o', 0,
'r', 0,
's', 0,
/* Index 0x02: Product */
(12 * 2 + 2),/* bLength (12 Char + Type + lenght) */
USB_STRING_DESCRIPTOR_TYPE,/* bDescriptorType */
'L', 0,
'P', 0,
'C', 0,
'1', 0,
'1', 0,
'U', 0,
'x', 0,
' ', 0,
'H', 0,
'I', 0,
'D', 0,
' ', 0,
/* Index 0x03: Serial Number */
(13 * 2 + 2),/* bLength (13 Char + Type + lenght) */
USB_STRING_DESCRIPTOR_TYPE,/* bDescriptorType */
'A', 0,
'B', 0,
'C', 0,
'D', 0,
'1', 0,
'2', 0,
'3', 0,
'4', 0,
'5', 0,
'6', 0,
'7', 0,
'8', 0,
'9', 0,
/* Index 0x04: Interface 0, Alternate Setting 0 */
(3 * 2 + 2),/* bLength (3 Char + Type + lenght) */
USB_STRING_DESCRIPTOR_TYPE,/* bDescriptorType */
'H', 0,
'I', 0,
'D', 0,
};
|
/*
* @brief HID generic example's callabck routines
*
* @note
* Copyright(C) NXP Semiconductors, 2013
* All rights reserved.
*
* @par
* Software that is described herein is for illustrative purposes only
* which provides customers with programming information regarding the
* LPC products. This software is supplied "AS IS" without any warranties of
* any kind, and NXP Semiconductors and its licensor disclaim any and
* all warranties, express or implied, including all implied warranties of
* merchantability, fitness for a particular purpose and non-infringement of
* intellectual property rights. NXP Semiconductors assumes no responsibility
* or liability for the use of the software, conveys no license or rights under any
* patent, copyright, mask work right, or any other intellectual property rights in
* or to any products. NXP Semiconductors reserves the right to make changes
* in the software without notification. NXP Semiconductors also makes no
* representation or warranty that such application will be suitable for the
* specified use without further testing or modification.
*
* @par
* Permission to use, copy, modify, and distribute this software and its
* documentation is hereby granted, under NXP Semiconductors' and its
* licensor's relevant copyrights in the software, without fee, provided that it
* is used in conjunction with NXP Semiconductors microcontrollers. This
* copyright, permission, and disclaimer notice must appear in all copies of
* this code.
*/
#include "board.h"
#include <stdint.h>
#include <string.h>
#include "usbd_rom_api.h"
/*****************************************************************************
* Private types/enumerations/variables
****************************************************************************/
static uint8_t *loopback_report;
/*****************************************************************************
* Public types/enumerations/variables
****************************************************************************/
extern const uint8_t HID_ReportDescriptor[];
extern const uint16_t HID_ReportDescSize;
/*****************************************************************************
* Private functions
****************************************************************************/
/* HID get report callback function. */
static ErrorCode_t HID_GetReport(USBD_HANDLE_T hHid, USB_SETUP_PACKET *pSetup, uint8_t * *pBuffer, uint16_t *plength)
{
/* ReportID = SetupPacket.wValue.WB.L; */
switch (pSetup->wValue.WB.H) {
case HID_REPORT_INPUT:
*pBuffer[0] = *loopback_report;
*plength = 1;
break;
case HID_REPORT_OUTPUT:
return ERR_USBD_STALL;/* Not Supported */
case HID_REPORT_FEATURE:
return ERR_USBD_STALL;/* Not Supported */
}
return LPC_OK;
}
/* HID set report callback function. */
static ErrorCode_t HID_SetReport(USBD_HANDLE_T hHid, USB_SETUP_PACKET *pSetup, uint8_t * *pBuffer, uint16_t length)
{
/* we will reuse standard EP0Buf */
if (length == 0) {
return LPC_OK;
}
/* ReportID = SetupPacket.wValue.WB.L; */
switch (pSetup->wValue.WB.H) {
case HID_REPORT_INPUT:
return ERR_USBD_STALL;/* Not Supported */
case HID_REPORT_OUTPUT:
*loopback_report = **pBuffer;
break;
case HID_REPORT_FEATURE:
return ERR_USBD_STALL;/* Not Supported */
}
return LPC_OK;
}
/* HID Interrupt endpoint event handler. */
static ErrorCode_t HID_Ep_Hdlr(USBD_HANDLE_T hUsb, void *data, uint32_t event)
{
USB_HID_CTRL_T *pHidCtrl = (USB_HID_CTRL_T *) data;
switch (event) {
case USB_EVT_IN:
/* last report is successfully sent. Do something... */
break;
case USB_EVT_OUT:
/* Read the new report received. */
USBD_API->hw->ReadEP(hUsb, pHidCtrl->epout_adr, loopback_report);
/* loopback the report received. */
USBD_API->hw->WriteEP(hUsb, pHidCtrl->epin_adr, loopback_report, 1);
break;
}
return LPC_OK;
}
/*****************************************************************************
* Public functions
****************************************************************************/
/* HID init routine */
ErrorCode_t usb_hid_init(USBD_HANDLE_T hUsb,
USB_INTERFACE_DESCRIPTOR *pIntfDesc,
uint32_t *mem_base,
uint32_t *mem_size)
{
USBD_HID_INIT_PARAM_T hid_param;
USB_HID_REPORT_T reports_data[1];
ErrorCode_t ret = LPC_OK;
memset((void *) &hid_param, 0, sizeof(USBD_HID_INIT_PARAM_T));
/* HID paramas */
hid_param.max_reports = 1;
/* Init reports_data */
reports_data[0].len = HID_ReportDescSize;
reports_data[0].idle_time = 0;
reports_data[0].desc = (uint8_t *) &HID_ReportDescriptor[0];
if ((pIntfDesc == 0) || (pIntfDesc->bInterfaceClass != USB_DEVICE_CLASS_HUMAN_INTERFACE)) {
return ERR_FAILED;
}
hid_param.mem_base = *mem_base;
hid_param.mem_size = *mem_size;
hid_param.intf_desc = (uint8_t *) pIntfDesc;
/* user defined functions */
hid_param.HID_GetReport = HID_GetReport;
hid_param.HID_SetReport = HID_SetReport;
hid_param.HID_EpIn_Hdlr = HID_Ep_Hdlr;
hid_param.HID_EpOut_Hdlr = HID_Ep_Hdlr;
hid_param.report_data = reports_data;
ret = USBD_API->hid->init(hUsb, &hid_param);
/* allocate USB accessable memory space for report data */
loopback_report = (uint8_t *) hid_param.mem_base;
hid_param.mem_base += 4;
hid_param.mem_size += 4;
/* update memory variables */
*mem_base = hid_param.mem_base;
*mem_size = hid_param.mem_size;
return ret;
}
|
(Not included, just wanted to point out the name of the file, I think is too long, and wont help seeing its code) |
#define HID_INPUT_REPORT_BYTES 1/* size of report in Bytes */ #define HID_OUTPUT_REPORT_BYTES 1/* size of report in Bytes */ #define HID_FEATURE_REPORT_BYTES 1/* size of report in Bytes */ |