Remove old OTG demo directory with useless TestApp demo. Add new DualRole directory with new Class Driver powered Mouse dual role demonstration application showing a dual role device using the HID host/device Class drivers.

pull/1469/head
Dean Camera 15 years ago
parent e57e08c672
commit fa8d25ef29

@ -37,6 +37,42 @@
#include "Descriptors.h"
/** HID class report descriptor. This is a special descriptor constructed with values from the
* USBIF HID class specification to describe the reports and capabilities of the HID device. This
* descriptor is parsed by the host and its contents used to determine what data (and in what encoding)
* the device will send, and what it may be sent back from the host. Refer to the HID specification for
* more details on HID report descriptors.
*/
USB_Descriptor_HIDReport_Datatype_t PROGMEM MouseReport[] =
{
0x05, 0x01, /* Usage Page (Generic Desktop) */
0x09, 0x02, /* Usage (Mouse) */
0xA1, 0x01, /* Collection (Application) */
0x09, 0x01, /* Usage (Pointer) */
0xA1, 0x00, /* Collection (Application) */
0x95, 0x03, /* Report Count (3) */
0x75, 0x01, /* Report Size (1) */
0x05, 0x09, /* Usage Page (Button) */
0x19, 0x01, /* Usage Minimum (Button 1) */
0x29, 0x03, /* Usage Maximum (Button 3) */
0x15, 0x00, /* Logical Minimum (0) */
0x25, 0x01, /* Logical Maximum (1) */
0x81, 0x02, /* Input (Data, Variable, Absolute) */
0x95, 0x01, /* Report Count (1) */
0x75, 0x05, /* Report Size (5) */
0x81, 0x01, /* Input (Constant) */
0x75, 0x08, /* Report Size (8) */
0x95, 0x02, /* Report Count (2) */
0x05, 0x01, /* Usage Page (Generic Desktop Control) */
0x09, 0x30, /* Usage X */
0x09, 0x31, /* Usage Y */
0x15, 0x81, /* Logical Minimum (-127) */
0x25, 0x7F, /* Logical Maximum (127) */
0x81, 0x06, /* Input (Data, Variable, Relative) */
0xC0, /* End Collection */
0xC0 /* End Collection */
};
/** Device descriptor structure. This descriptor, located in FLASH memory, describes the overall
* device characteristics, including the supported USB version, control endpoint size and the
* number of device configurations. The descriptor is read out by the USB host when the enumeration
@ -51,17 +87,17 @@ USB_Descriptor_Device_t PROGMEM DeviceDescriptor =
.SubClass = 0x00,
.Protocol = 0x00,
.Endpoint0Size = 8,
.Endpoint0Size = FIXED_CONTROL_ENDPOINT_SIZE,
.VendorID = 0x03EB,
.ProductID = 0x2040,
.ProductID = 0x2041,
.ReleaseNumber = 0x0000,
.ManufacturerStrIndex = 0x01,
.ProductStrIndex = 0x02,
.SerialNumStrIndex = NO_DESCRIPTOR,
.NumberOfConfigurations = 1
.NumberOfConfigurations = FIXED_NUM_CONFIGURATIONS
};
/** Configuration descriptor structure. This descriptor, located in FLASH memory, describes the usage
@ -75,9 +111,7 @@ USB_Descriptor_Configuration_t PROGMEM ConfigurationDescriptor =
{
.Header = {.Size = sizeof(USB_Descriptor_Configuration_Header_t), .Type = DTYPE_Configuration},
.TotalConfigurationSize = ( sizeof(USB_Descriptor_Configuration_Header_t)
+ sizeof(USB_Descriptor_Interface_t) ),
.TotalConfigurationSize = sizeof(USB_Descriptor_Configuration_t),
.TotalInterfaces = 1,
.ConfigurationNumber = 1,
@ -92,17 +126,38 @@ USB_Descriptor_Configuration_t PROGMEM ConfigurationDescriptor =
{
.Header = {.Size = sizeof(USB_Descriptor_Interface_t), .Type = DTYPE_Interface},
.InterfaceNumber = 1,
.AlternateSetting = 0,
.InterfaceNumber = 0x00,
.AlternateSetting = 0x00,
.TotalEndpoints = 0,
.TotalEndpoints = 1,
.Class = 0xFF,
.SubClass = 0x00,
.Protocol = 0x00,
.Class = 0x03,
.SubClass = 0x01,
.Protocol = HID_BOOT_MOUSE_PROTOCOL,
.InterfaceStrIndex = NO_DESCRIPTOR
},
.MouseHID =
{
.Header = {.Size = sizeof(USB_HID_Descriptor_t), .Type = DTYPE_HID},
.HIDSpec = VERSION_BCD(01.11),
.CountryCode = 0x00,
.TotalReportDescriptors = 1,
.HIDReportType = DTYPE_Report,
.HIDReportLength = sizeof(MouseReport)
},
.MouseEndpoint =
{
.Header = {.Size = sizeof(USB_Descriptor_Endpoint_t), .Type = DTYPE_Endpoint},
.EndpointAddress = (ENDPOINT_DESCRIPTOR_DIR_IN | MOUSE_EPNUM),
.Attributes = (EP_TYPE_INTERRUPT | ENDPOINT_ATTR_NO_SYNC | ENDPOINT_USAGE_DATA),
.EndpointSize = MOUSE_EPSIZE,
.PollingIntervalMS = 0x0A
}
};
/** Language descriptor structure. This descriptor, located in FLASH memory, is returned when the host requests
@ -133,9 +188,9 @@ USB_Descriptor_String_t PROGMEM ManufacturerString =
*/
USB_Descriptor_String_t PROGMEM ProductString =
{
.Header = {.Size = USB_STRING_LEN(9), .Type = DTYPE_String},
.Header = {.Size = USB_STRING_LEN(15), .Type = DTYPE_String},
.UnicodeString = L"LUFA Demo"
.UnicodeString = L"LUFA Mouse Demo"
};
/** This function is called by the library when in device mode, and must be overridden (see library "USB Descriptors"
@ -179,9 +234,18 @@ uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue, const uint8_t wIndex,
break;
}
break;
case DTYPE_HID:
Address = (void*)&ConfigurationDescriptor.MouseHID;
Size = sizeof(USB_HID_Descriptor_t);
break;
case DTYPE_Report:
Address = (void*)&MouseReport;
Size = sizeof(MouseReport);
break;
}
*DescriptorAddress = Address;
return Size;
}

@ -38,6 +38,7 @@
/* Includes: */
#include <LUFA/Drivers/USB/USB.h>
#include <LUFA/Drivers/USB/Class/HID.h>
#include <avr/pgmspace.h>
@ -48,10 +49,19 @@
*/
typedef struct
{
USB_Descriptor_Configuration_Header_t Config; /**< Configuration descriptor header structure */
USB_Descriptor_Interface_t Interface; /**< Interface descriptor, required for the device to enumerate */
USB_Descriptor_Configuration_Header_t Config;
USB_Descriptor_Interface_t Interface;
USB_HID_Descriptor_t MouseHID;
USB_Descriptor_Endpoint_t MouseEndpoint;
} USB_Descriptor_Configuration_t;
/* Macros: */
/** Endpoint number of the Mouse HID reporting IN endpoint. */
#define MOUSE_EPNUM 1
/** Size in bytes of the Mouse HID reporting IN endpoint. */
#define MOUSE_EPSIZE 8
/* Function Prototypes: */
uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue, const uint8_t wIndex, void** const DescriptorAddress)
ATTR_WARN_UNUSED_RESULT ATTR_NON_NULL_PTR_ARG(3);

@ -0,0 +1,144 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* Device Mode USB Mouse functionality for the MouseHostDevice demo. This file contains the Device mode
* USB Mouse related code of the demo and is responsible for all the Device mode Mouse functionality.
*/
#include "DeviceFunctions.h"
/** Buffer to hold the previously generated Mouse Device HID report, for comparison purposes inside the HID class driver. */
uint8_t PrevMouseHIDReportBuffer[sizeof(USB_MouseReport_Data_t)];
/** LUFA HID Class driver interface configuration and state information. This structure is
* passed to all HID Class driver functions, so that multiple instances of the same class
* within a device can be differentiated from one another.
*/
USB_ClassInfo_HID_Device_t Mouse_HID_Device_Interface =
{
.Config =
{
.InterfaceNumber = 0,
.ReportINEndpointNumber = MOUSE_EPNUM,
.ReportINEndpointSize = MOUSE_EPSIZE,
.PrevReportINBuffer = PrevMouseHIDReportBuffer,
.PrevReportINBufferSize = sizeof(PrevMouseHIDReportBuffer),
},
};
/** Event handler for the library USB WakeUp event. */
void EVENT_USB_Device_Connect(void)
{
LEDs_SetAllLEDs(LEDMASK_USB_ENUMERATING);
}
/** Event handler for the library USB Suspend event. */
void EVENT_USB_Device_Disconnect(void)
{
LEDs_SetAllLEDs(LEDMASK_USB_NOTREADY);
}
/** Event handler for the library USB Configuration Changed event. */
void EVENT_USB_Device_ConfigurationChanged(void)
{
LEDs_SetAllLEDs(LEDMASK_USB_READY);
if (!(HID_Device_ConfigureEndpoints(&Mouse_HID_Device_Interface)))
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
USB_Device_EnableSOFEvents();
}
/** Event handler for the library USB Unhandled Control Request event. */
void EVENT_USB_Device_UnhandledControlRequest(void)
{
HID_Device_ProcessControlRequest(&Mouse_HID_Device_Interface);
}
/** Event handler for the USB device Start Of Frame event. */
void EVENT_USB_Device_StartOfFrame(void)
{
HID_Device_MillisecondElapsed(&Mouse_HID_Device_Interface);
}
/** HID class driver callback function for the creation of HID reports to the host.
*
* \param[in] HIDInterfaceInfo Pointer to the HID class interface configuration structure being referenced
* \param[in,out] ReportID Report ID requested by the host if non-zero, otherwise callback should set to the generated report ID
* \param[out] ReportData Pointer to a buffer where the created report should be stored
* \param[out] ReportSize Number of bytes written in the report (or zero if no report is to be sent
*
* \return Boolean true to force the sending of the report, false to let the library determine if it needs to be sent
*/
bool CALLBACK_HID_Device_CreateHIDReport(USB_ClassInfo_HID_Device_t* const HIDInterfaceInfo, uint8_t* const ReportID,
void* ReportData, uint16_t* ReportSize)
{
USB_MouseReport_Data_t* MouseReport = (USB_MouseReport_Data_t*)ReportData;
uint8_t JoyStatus_LCL = Joystick_GetStatus();
uint8_t ButtonStatus_LCL = Buttons_GetStatus();
if (JoyStatus_LCL & JOY_UP)
MouseReport->Y = -1;
else if (JoyStatus_LCL & JOY_DOWN)
MouseReport->Y = 1;
if (JoyStatus_LCL & JOY_RIGHT)
MouseReport->X = 1;
else if (JoyStatus_LCL & JOY_LEFT)
MouseReport->X = -1;
if (JoyStatus_LCL & JOY_PRESS)
MouseReport->Button = (1 << 0);
if (ButtonStatus_LCL & BUTTONS_BUTTON1)
MouseReport->Button |= (1 << 1);
*ReportSize = sizeof(USB_MouseReport_Data_t);
return true;
}
/** HID class driver callback function for the processing of HID reports from the host.
*
* \param[in] HIDInterfaceInfo Pointer to the HID class interface configuration structure being referenced
* \param[in] ReportID Report ID of the received report from the host
* \param[in] ReportData Pointer to a buffer where the created report has been stored
* \param[in] ReportSize Size in bytes of the received HID report
*/
void CALLBACK_HID_Device_ProcessHIDReport(USB_ClassInfo_HID_Device_t* const HIDInterfaceInfo, const uint8_t ReportID,
const void* ReportData, const uint16_t ReportSize)
{
// Unused (but mandatory for the HID class driver) in this demo, since there are no Host->Device reports
}

@ -30,33 +30,23 @@
/** \file
*
* Header file for TestApp.c.
* Header file for DeviceFunctions.c.
*/
#ifndef _TESTAPP_H_
#define _TESTAPP_H_
#ifndef _MOUSE_DEVICE_FUNCTIONS_H_
#define _MOUSE_DEVICE_FUNCTIONS_H_
/* Includes: */
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/wdt.h>
#include <avr/power.h>
#include <LUFA/Version.h>
#include <LUFA/Drivers/USB/USB.h>
#include <LUFA/Drivers/Misc/TerminalCodes.h>
#include <LUFA/Drivers/Peripheral/ADC.h>
#include <LUFA/Drivers/Peripheral/SerialStream.h>
#include <LUFA/Drivers/Board/Joystick.h>
#include <LUFA/Drivers/Board/LEDs.h>
#include <LUFA/Drivers/Board/Buttons.h>
#include <LUFA/Drivers/Board/Temperature.h>
#include "MouseHostDevice.h"
/* Function Prototypes: */
void SetupHardware(void);
/* External Variables: */
extern USB_ClassInfo_HID_Device_t Mouse_HID_Device_Interface;
void CheckJoystick(void);
void CheckButton(void);
void CheckTemperature(void);
/* Function Prototypes: */
void EVENT_USB_Device_Connect(void);
void EVENT_USB_Device_Disconnect(void);
void EVENT_USB_Device_ConfigurationChanged(void);
void EVENT_USB_Device_UnhandledControlRequest(void);
void EVENT_USB_Device_StartOfFrame(void);
#endif

@ -25,7 +25,7 @@ DOXYFILE_ENCODING = UTF-8
# The PROJECT_NAME tag is a single word (or a sequence of words surrounded
# by quotes) that should identify the project.
PROJECT_NAME = "LUFA Library - Test Application Demo"
PROJECT_NAME = "LUFA Library - Mouse Host/Device Dual Role Demo"
# The PROJECT_NUMBER tag can be used to enter a project or revision number.
# This could be handy for archiving the generated documentation or

@ -0,0 +1,185 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* Host Mode USB Mouse functionality for the MouseHostDevice demo. This file contains the Host mode
* USB Mouse related code of the demo and is responsible for all the Host mode Mouse functionality.
*/
#include "HostFunctions.h"
/** LUFA HID Class driver interface configuration and state information. This structure is
* passed to all HID Class driver functions, so that multiple instances of the same class
* within a device can be differentiated from one another.
*/
USB_ClassInfo_HID_Host_t Mouse_HID_Host_Interface =
{
.Config =
{
.DataINPipeNumber = 1,
.DataOUTPipeNumber = 2,
.HIDInterfaceProtocol = HID_BOOT_MOUSE_PROTOCOL,
},
};
/** Event handler for the USB_DeviceAttached event. This indicates that a device has been attached to the host, and
* starts the library USB task to begin the enumeration and USB management process.
*/
void EVENT_USB_Host_DeviceAttached(void)
{
puts_P(PSTR("Device Attached.\r\n"));
LEDs_SetAllLEDs(LEDMASK_USB_ENUMERATING);
}
/** Event handler for the USB_DeviceUnattached event. This indicates that a device has been removed from the host, and
* stops the library USB task management process.
*/
void EVENT_USB_Host_DeviceUnattached(void)
{
puts_P(PSTR("\r\nDevice Unattached.\r\n"));
LEDs_SetAllLEDs(LEDMASK_USB_NOTREADY);
}
/** Event handler for the USB_DeviceEnumerationComplete event. This indicates that a device has been successfully
* enumerated by the host and is now ready to be used by the application.
*/
void EVENT_USB_Host_DeviceEnumerationComplete(void)
{
LEDs_SetAllLEDs(LEDMASK_USB_READY);
}
/** Event handler for the USB_HostError event. This indicates that a hardware error occurred while in host mode. */
void EVENT_USB_Host_HostError(const uint8_t ErrorCode)
{
USB_ShutDown();
printf_P(PSTR(ESC_FG_RED "Host Mode Error\r\n"
" -- Error Code %d\r\n" ESC_FG_WHITE), ErrorCode);
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
for(;;);
}
/** Event handler for the USB_DeviceEnumerationFailed event. This indicates that a problem occurred while
* enumerating an attached USB device.
*/
void EVENT_USB_Host_DeviceEnumerationFailed(const uint8_t ErrorCode, const uint8_t SubErrorCode)
{
printf_P(PSTR(ESC_FG_RED "Dev Enum Error\r\n"
" -- Error Code %d\r\n"
" -- Sub Error Code %d\r\n"
" -- In State %d\r\n" ESC_FG_WHITE), ErrorCode, SubErrorCode, USB_HostState);
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
}
/** Host state machine task. This task handles the enumeration and control of USB Mice while in USB Host mode,
* setting up the appropriate data pipes and processing reports from the attached device.
*/
void MouseHostTask(void)
{
switch (USB_HostState)
{
case HOST_STATE_Addressed:
LEDs_SetAllLEDs(LEDMASK_USB_ENUMERATING);
uint16_t ConfigDescriptorSize;
uint8_t ConfigDescriptorData[512];
if (USB_GetDeviceConfigDescriptor(1, &ConfigDescriptorSize, ConfigDescriptorData,
sizeof(ConfigDescriptorData)) != HOST_GETCONFIG_Successful)
{
printf("Error Retrieving Configuration Descriptor.\r\n");
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
USB_HostState = HOST_STATE_WaitForDeviceRemoval;
break;
}
if (HID_Host_ConfigurePipes(&Mouse_HID_Host_Interface,
ConfigDescriptorSize, ConfigDescriptorData) != HID_ENUMERROR_NoError)
{
printf("Attached Device Not a Valid Mouse.\r\n");
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
USB_HostState = HOST_STATE_WaitForDeviceRemoval;
break;
}
if (USB_Host_SetDeviceConfiguration(1) != HOST_SENDCONTROL_Successful)
{
printf("Error Setting Device Configuration.\r\n");
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
USB_HostState = HOST_STATE_WaitForDeviceRemoval;
break;
}
if (HID_Host_SetBootProtocol(&Mouse_HID_Host_Interface) != 0)
{
printf("Could not Set Boot Protocol Mode.\r\n");
LEDs_SetAllLEDs(LEDMASK_USB_ERROR);
USB_HostState = HOST_STATE_WaitForDeviceRemoval;
break;
}
printf("Mouse Enumerated.\r\n");
USB_HostState = HOST_STATE_Configured;
break;
case HOST_STATE_Configured:
if (HID_Host_IsReportReceived(&Mouse_HID_Host_Interface))
{
uint8_t LEDMask = LEDS_NO_LEDS;
USB_MouseReport_Data_t MouseReport;
HID_Host_ReceiveReport(&Mouse_HID_Host_Interface, &MouseReport);
printf_P(PSTR("dX:%2d dY:%2d Button:%d\r\n"), MouseReport.X,
MouseReport.Y,
MouseReport.Button);
if (MouseReport.X > 0)
LEDMask |= LEDS_LED1;
else if (MouseReport.X < 0)
LEDMask |= LEDS_LED2;
if (MouseReport.Y > 0)
LEDMask |= LEDS_LED3;
else if (MouseReport.Y < 0)
LEDMask |= LEDS_LED4;
if (MouseReport.Button)
LEDMask = LEDS_ALL_LEDS;
LEDs_SetAllLEDs(LEDMask);
}
break;
}
}

@ -30,43 +30,25 @@
/** \file
*
* Header file for TestEvents.c.
* Header file for HostFunctions.c.
*/
#ifndef _TESTEVENTS_H_
#define _TESTEVENTS_H_
#ifndef _MOUSE_HOST_FUNCTIONS_H_
#define _MOUSE_HOST_FUNCTIONS_H_
/* Includes: */
#include <avr/io.h>
#include "MouseHostDevice.h"
#include <LUFA/Common/Common.h>
#include <LUFA/Drivers/USB/USB.h>
#include <LUFA/Drivers/Board/LEDs.h>
#include <LUFA/Drivers/Peripheral/SerialStream.h>
#include <LUFA/Drivers/Misc/TerminalCodes.h>
/* Macros: */
/** Prefix sent through the USART when an even fires before the actual event message. */
#define EVENT_PREFIX ESC_INVERSE_ON "EVENT:" ESC_INVERSE_OFF " "
/* External Variables: */
extern USB_ClassInfo_HID_Host_t Mouse_HID_Host_Interface;
/* Function Prototypes: */
#if defined(INCLUDE_FROM_TESTEVENTS_C) || defined(__DOXYGEN__)
static void Abort_Program(void) ATTR_NO_RETURN;
#endif
void MouseHostTask(void);
void EVENT_USB_InitFailure(const uint8_t ErrorCode);
void EVENT_USB_UIDChange(void);
void EVENT_USB_Host_HostError(const uint8_t ErrorCode);
void EVENT_USB_Host_DeviceAttached(void);
void EVENT_USB_Host_DeviceUnattached(void);
void EVENT_USB_Host_DeviceEnumerationFailed(const uint8_t ErrorCode, const uint8_t SubErrorCode);
void EVENT_USB_Host_DeviceEnumerationComplete(void);
void EVENT_USB_Device_Connect(void);
void EVENT_USB_Device_Disconnect(void);
void EVENT_USB_Device_ConfigurationChanged(void);
void EVENT_USB_Device_ConfigurationChanged(void);
void EVENT_USB_Device_Suspend(void);
void EVENT_USB_Device_WakeUp(void);
void EVENT_USB_Device_Reset(void);
#endif

@ -0,0 +1,83 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* Main source file for the MouseHostDevice demo. This file contains the main tasks of
* the demo and is responsible for the overall control flow of the demo.
*/
#include "MouseHostDevice.h"
/** Main program entry point. This routine configures the hardware required by the application, then
* starts the scheduler to run the application tasks.
*/
int main(void)
{
SetupHardware();
puts_P(PSTR(ESC_FG_CYAN "Mouse Host/Device Demo running.\r\n" ESC_FG_WHITE));
LEDs_SetAllLEDs(LEDMASK_USB_NOTREADY);
for (;;)
{
/* Determine which USB mode we are currently in */
if (USB_CurrentMode == USB_MODE_HOST)
{
MouseHostTask();
HID_Host_USBTask(&Mouse_HID_Host_Interface);
}
else
{
HID_Device_USBTask(&Mouse_HID_Device_Interface);
}
USB_USBTask();
}
}
/** Configures the board hardware and chip peripherals for the demo's functionality. */
void SetupHardware(void)
{
/* Disable watchdog if enabled by bootloader/fuses */
MCUSR &= ~(1 << WDRF);
wdt_disable();
/* Disable clock division */
clock_prescale_set(clock_div_1);
/* Hardware Initialization */
SerialStream_Init(9600, false);
LEDs_Init();
Joystick_Init();
Buttons_Init();
USB_Init(USB_MODE_UID);
}

@ -0,0 +1,75 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* Header file for MouseHost.c.
*/
#ifndef _MOUSE_HOST_DEVICE_H_
#define _MOUSE_HOST_DEVICE_H_
/* Includes: */
#include <avr/io.h>
#include <avr/wdt.h>
#include <avr/pgmspace.h>
#include <avr/power.h>
#include <stdio.h>
#include <LUFA/Version.h>
#include <LUFA/Drivers/Misc/TerminalCodes.h>
#include <LUFA/Drivers/Peripheral/SerialStream.h>
#include <LUFA/Drivers/Board/LEDs.h>
#include <LUFA/Drivers/Board/Joystick.h>
#include <LUFA/Drivers/Board/Buttons.h>
#include <LUFA/Drivers/USB/USB.h>
#include <LUFA/Drivers/USB/Class/HID.h>
#include "Descriptors.h"
#include "DeviceFunctions.h"
#include "HostFunctions.h"
/* Macros: */
/** LED mask for the library LED driver, to indicate that the USB interface is not ready. */
#define LEDMASK_USB_NOTREADY LEDS_LED1
/** LED mask for the library LED driver, to indicate that the USB interface is enumerating. */
#define LEDMASK_USB_ENUMERATING (LEDS_LED2 | LEDS_LED3)
/** LED mask for the library LED driver, to indicate that the USB interface is ready. */
#define LEDMASK_USB_READY (LEDS_LED2 | LEDS_LED4)
/** LED mask for the library LED driver, to indicate that an error has occurred in the USB interface. */
#define LEDMASK_USB_ERROR (LEDS_LED1 | LEDS_LED3)
/* Function Prototypes: */
void SetupHardware(void);
#endif

@ -0,0 +1,80 @@
/** \file
*
* This file contains special DoxyGen information for the generation of the main page and other special
* documentation pages. It is not a project source file.
*/
/** \mainpage Mouse Host/Device Dual Role Demo
*
* \section SSec_Compat Demo Compatibility:
*
* The following table indicates what microcontrollers are compatible with this demo.
*
* - AT90USB1287
* - AT90USB647
*
* \section SSec_Info USB Information:
*
* The following table gives a rundown of the USB utilization of this demo.
*
* <table>
* <tr>
* <td><b>USB Mode:</b></td>
* <td>Host/Device</td>
* </tr>
* <tr>
* <td><b>USB Class:</b></td>
* <td>Human Interface Device (HID)</td>
* </tr>
* <tr>
* <td><b>USB Subclass:</b></td>
* <td>N/A</td>
* </tr>
* <tr>
* <td><b>Relevant Standards:</b></td>
* <td>USBIF HID Specification, USBIF HID Usage Tables</td>
* </tr>
* <tr>
* <td><b>Usable Speeds:</b></td>
* <td>Low Speed Mode, Full Speed Mode</td>
* </tr>
* </table>
*
* \section SSec_Description Project Description:
*
* Mouse host/device dual role demonstration application. This gives a simple
* reference application for implementing a dual role USB Mouse, for USB mice
* using the standard mouse boot protocol HID profile.
*
* <b>When in host mode:</b>
* Mouse movement and button presses are displayed on the board LEDs,
* as well as printed out the serial terminal as formatted dY, dY and
* button status information.
*
* This uses a naive method where the mouse is set to Boot Protocol mode, so
* that the report structure is fixed and known. A better implementation
* uses the HID report parser for correct report data processing across
* all compatible mice with advanced characteristics, as shown in the
* MouseHostWithParser Host demo application.
*
* Currently only single interface mice are supported.
*
* <b>When in device mode:</b>
* Upon enumeration the system will automatically enumerate and function
* as a mouse when the USB connection to a host is present. To use
* the mouse, move the joystick to move the pointer, and push the
* joystick inwards to simulate a left-button click. The HWB serves as
* the right mouse button.
*
* \section SSec_Options Project Options
*
* The following defines can be found in this demo, which can control the demo behaviour when defined, or changed in value.
*
* <table>
* <tr>
* <td>
* None
* </td>
* </tr>
* </table>
*/

@ -102,7 +102,7 @@ FORMAT = ihex
# Target file name (without extension).
TARGET = TestApp
TARGET = MouseHostDevice
# Object files directory
@ -112,18 +112,21 @@ OBJDIR = .
# Path to the LUFA library
LUFA_PATH = ../../..
LUFA_PATH = ../../../..
# LUFA library compile-time options
LUFA_OPTS = -D USE_FLASH_DESCRIPTORS
LUFA_OPTS += -D FIXED_CONTROL_ENDPOINT_SIZE=8
LUFA_OPTS += -D FIXED_NUM_CONFIGURATIONS=1
LUFA_OPTS += -D USE_FLASH_DESCRIPTORS
LUFA_OPTS += -D USE_STATIC_OPTIONS="(USB_DEVICE_OPT_FULLSPEED | USB_OPT_REG_ENABLED | USB_OPT_AUTO_PLL)"
# List C source files here. (C dependencies are automatically generated.)
SRC = $(TARGET).c \
TestEvents.c \
Descriptors.c \
$(LUFA_PATH)/LUFA/Drivers/Board/Temperature.c \
DeviceFunctions.c \
HostFunctions.c \
$(LUFA_PATH)/LUFA/Drivers/Peripheral/SerialStream.c \
$(LUFA_PATH)/LUFA/Drivers/Peripheral/Serial.c \
$(LUFA_PATH)/LUFA/Drivers/USB/LowLevel/DevChapter9.c \
@ -136,6 +139,9 @@ SRC = $(TARGET).c \
$(LUFA_PATH)/LUFA/Drivers/USB/HighLevel/USBInterrupt.c \
$(LUFA_PATH)/LUFA/Drivers/USB/HighLevel/USBTask.c \
$(LUFA_PATH)/LUFA/Drivers/USB/HighLevel/ConfigDescriptor.c \
$(LUFA_PATH)/LUFA/Drivers/USB/Class/Device/HID.c \
$(LUFA_PATH)/LUFA/Drivers/USB/Class/Host/HID.c \
$(LUFA_PATH)/LUFA/Drivers/USB/Class/Host/HIDParser.c \
# List C++ source files here. (C dependencies are automatically generated.)
@ -208,11 +214,11 @@ CFLAGS += -O$(OPT)
CFLAGS += -funsigned-char
CFLAGS += -funsigned-bitfields
CFLAGS += -ffunction-sections
CFLAGS += -fno-inline-small-functions
CFLAGS += -fpack-struct
CFLAGS += -fshort-enums
CFLAGS += -Wall
CFLAGS += -Wstrict-prototypes
#CFLAGS += -mshort-calls
CFLAGS += -Wundef
#CFLAGS += -fno-unit-at-a-time
#CFLAGS += -Wunreachable-code

@ -0,0 +1,21 @@
#
# LUFA Library
# Copyright (C) Dean Camera, 2009.
#
# dean [at] fourwalledcubicle [dot] com
# www.fourwalledcubicle.com
#
# Makefile to build all the LUFA Dual Role Demos. Call with "make all" to
# rebuild all Dual Role demos.
# Projects are pre-cleaned before each one is built, to ensure any
# custom LUFA library build options are reflected in the compiled
# code.
all:
make -C MouseHostDevice clean
make -C MouseHostDevice all
%:
make -C MouseHostDevice $@

@ -6,16 +6,12 @@
# www.fourwalledcubicle.com
#
# Makefile to build all the LUFA OTG Demos. Call with "make all" to
# rebuild all OTG demos.
# Makefile to build all the LUFA Class Driver and Low Level Demos. Call with
# "make all" to rebuild all demos of both types.
# Projects are pre-cleaned before each one is built, to ensure any
# custom LUFA library build options are reflected in the compiled
# code.
all:
make -C TestApp clean
make -C TestApp all
%:
make -C TestApp $@
make -C ClassDriver/ $@

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -60,7 +60,7 @@
# MCU name
MCU = at90usb647
MCU = at90usb1287
# Target board (see library "Board Types" documentation, USER or blank for projects not requiring

@ -1,166 +0,0 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* Main source file for the TestApp demo. This file contains the main tasks of the demo and
* is responsible for the initial application hardware configuration.
*/
#include "TestApp.h"
/** Main program entry point. This routine configures the hardware required by the application, then
* starts the scheduler to run the application tasks.
*/
int main(void)
{
SetupHardware();
puts_P(PSTR(ESC_FG_CYAN "LUFA Demo running.\r\n" ESC_FG_WHITE));
for (;;)
{
CheckJoystick();
CheckButton();
CheckTemperature();
/* Clear millisecond timer's Output Compare flag (logic 1 clears the flag) */
TIFR0 |= (1 << OCF0A);
USB_USBTask();
}
}
void SetupHardware(void)
{
/* Disable watchdog if enabled by bootloader/fuses */
MCUSR &= ~(1 << WDRF);
wdt_disable();
/* Disable clock division */
clock_prescale_set(clock_div_1);
/* Hardware initialization */
SerialStream_Init(9600, false);
ADC_Init(ADC_SINGLE_CONVERSION | ADC_PRESCALE_64);
Temperature_Init();
Joystick_Init();
LEDs_Init();
Buttons_Init();
/* Millisecond timer initialization */
OCR0A = 0x7D;
TCCR0A = (1 << WGM01);
TCCR0B = ((1 << CS01) | (1 << CS00));
}
/** Task responsible for checking the joystick position, and displaying the joystick position onto the
* board LEDs.
*/
void CheckJoystick(void)
{
uint8_t JoyStatus_LCL = Joystick_GetStatus();
uint8_t LEDMask = LEDS_NO_LEDS;
if (JoyStatus_LCL & JOY_UP)
LEDMask |= LEDS_LED1;
if (JoyStatus_LCL & JOY_DOWN)
LEDMask |= LEDS_LED2;
if (JoyStatus_LCL & JOY_LEFT)
LEDMask |= LEDS_LED3;
if (JoyStatus_LCL & JOY_RIGHT)
LEDMask |= LEDS_LED4;
if (JoyStatus_LCL & JOY_PRESS)
LEDMask = LEDS_ALL_LEDS;
LEDs_SetAllLEDs(LEDMask);
}
/** Task responsible for checking the current temperature via the temperature sensor mounted on the
* board, and displaying it through the serial USART.
*/
void CheckTemperature(void)
{
static uint16_t MSElapsed = 0;
/* Timer 0's compare flag is set every millisecond */
if (TIFR0 & (1 << OCF0A))
MSElapsed++;
/* Task runs every 10000 ticks, 10 seconds for this demo */
if (MSElapsed == 10000)
{
printf_P(PSTR("Current temperature: %d Degrees Celcius\r\n\r\n"),
(int8_t)Temperature_GetTemperature());
MSElapsed = 0;
}
}
/** Task responsible for checking the board's first button' position, and start-stopping other tasks and the USB
* interface in response to user joystick movements.
*/
void CheckButton(void)
{
static uint16_t DebounceMSElapsed = 0;
static bool IsPressed;
/* Timer 0's compare flag is set every millisecond */
if (TIFR0 & (1 << OCF0A))
DebounceMSElapsed++;
if (Buttons_GetStatus() & BUTTONS_BUTTON1)
{
if (!(IsPressed) && (DebounceMSElapsed == 100))
{
IsPressed = true;
if (USB_IsInitialized == true)
{
USB_ShutDown();
puts_P(PSTR(ESC_FG_YELLOW "USB Power Off.\r\n" ESC_FG_WHITE));
}
else
{
puts_P(PSTR(ESC_FG_YELLOW "USB Power On.\r\n" ESC_FG_WHITE));
USB_Init(USB_MODE_UID, USB_DEVICE_OPT_FULLSPEED | USB_OPT_REG_ENABLED | USB_OPT_AUTO_PLL);
}
}
}
else
{
DebounceMSElapsed = 0;
IsPressed = false;
}
}

@ -1,63 +0,0 @@
/** \file
*
* This file contains special DoxyGen information for the generation of the main page and other special
* documentation pages. It is not a project source file.
*/
/** \mainpage Test Application for the LUFA library
*
* \section SSec_Info USB Information:
*
* The following table gives a rundown of the USB utilization of this demo.
*
* <table>
* <tr>
* <td><b>USB Mode:</b></td>
* <td>Host/Device (Dual Role)</td>
* </tr>
* <tr>
* <td><b>USB Class:</b></td>
* <td>N/A</td>
* </tr>
* <tr>
* <td><b>USB Subclass:</b></td>
* <td>N/A</td>
* </tr>
* <tr>
* <td><b>Relevant Standards:</b></td>
* <td>N/A</td>
* </tr>
* <tr>
* <td><b>Usable Speeds:</b></td>
* <td>Low Speed Mode, Full Speed Mode</td>
* </tr>
* </table>
*
* \section SSec_Description Project Description:
*
* Test application. Demonstrates several aspects of the LUFA
* Library. On start-up the current temperature will be printed
* through the USART every 10 seconds, and the current joystick
* position will be indicated via the LEDs on the selected board.
* Pressing the HWB will initiate the USB subsystem, enumerating
* the device (which has <b>no actual functionality beyond
* enumeration as a device or as a host in this demo</b>, and serves
* only to demonstrate the USB portion of the library).
*
* Pressing the HWB a second time will turn off the USB system.
*
* When activated, the USB events will be printed through the
* serial USART.
*
* \section SSec_Options Project Options
*
* The following defines can be found in this demo, which can control the demo behaviour when defined, or changed in value.
*
* <table>
* <tr>
* <td>
* None
* </td>
* </tr>
* </table>
*/

@ -1,181 +0,0 @@
/*
LUFA Library
Copyright (C) Dean Camera, 2009.
dean [at] fourwalledcubicle [dot] com
www.fourwalledcubicle.com
*/
/*
Copyright 2009 Dean Camera (dean [at] fourwalledcubicle [dot] com)
Permission to use, copy, modify, and distribute this software
and its documentation for any purpose and without fee is hereby
granted, provided that the above copyright notice appear in all
copies and that both that the copyright notice and this
permission notice and warranty disclaimer appear in supporting
documentation, and that the name of the author not be used in
advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
The author disclaim all warranties with regard to this
software, including all implied warranties of merchantability
and fitness. In no event shall the author be liable for any
special, indirect or consequential damages or any damages
whatsoever resulting from loss of use, data or profits, whether
in an action of contract, negligence or other tortious action,
arising out of or in connection with the use or performance of
this software.
*/
/** \file
*
* This file contains dummy handlers for all the possible USB events passed to the
* application by the library (see library documentation for more details on USB events).
*
* Each event is caught and printed to the USART so that they may be monitored.
*/
#define INCLUDE_FROM_TESTEVENTS_C
#include "TestEvents.h"
/** Simple routine which aborts the program execution when a fatal error occurs, and is passed to the
* application via an event. When run, this function shuts down the USB interface, indicates an error
* via the board LEDs, prints an error message to the USART and then enters an infinite loop, preventing
* any more application code (other than interrupts) from executing.
*/
static void Abort_Program(void)
{
USB_ShutDown();
LEDs_SetAllLEDs(LEDS_LED1 | LEDS_LED3);
puts_P(PSTR(ESC_FG_RED ESC_INVERSE_ON "\r\n**PROGRAM ABORT**" ESC_FG_WHITE));
for (;;);
}
/** Event handler for the USB_UIDChange event. When fired, the event is logged to the USART. */
void EVENT_USB_UIDChange(void)
{
char* ModeStrPtr;
puts_P(PSTR(ESC_FG_RED EVENT_PREFIX "UID Change\r\n"));
if (USB_CurrentMode == USB_MODE_DEVICE)
ModeStrPtr = PSTR("DEVICE");
else if (USB_CurrentMode == USB_MODE_HOST)
ModeStrPtr = PSTR("HOST");
else
ModeStrPtr = PSTR("N/A");
printf_P(PSTR(" -- New Mode %S\r\n" ESC_FG_WHITE), ModeStrPtr);
}
/**
* Event handler for the USB_InitFailure event. When fired, the event is logged to the USART and the program
* execution aborted.
*/
void EVENT_USB_InitFailure(const uint8_t ErrorCode)
{
char* ModeStrPtr;
puts_P(PSTR(ESC_FG_RED EVENT_PREFIX "Power On Fail\r\n"));
if (USB_CurrentMode == USB_MODE_DEVICE)
ModeStrPtr = PSTR("DEVICE");
else if (USB_CurrentMode == USB_MODE_HOST)
ModeStrPtr = PSTR("HOST");
else
ModeStrPtr = PSTR("N/A");
printf_P(PSTR(" -- Mode %S\r\n"
" -- Error Code %d\r\n" ESC_FG_WHITE), ModeStrPtr, ErrorCode);
Abort_Program();
}
/** Event handler for the USB_Device_Connect event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_Connect(void)
{
puts_P(PSTR(ESC_FG_GREEN EVENT_PREFIX "USB Connect\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Device_Disconnect event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_Disconnect(void)
{
puts_P(PSTR(ESC_FG_GREEN EVENT_PREFIX "USB Disconnect\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Device_Suspend event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_Suspend(void)
{
puts_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "USB Sleep\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Device_WakeUp event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_WakeUp(void)
{
puts_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "USB Wakeup\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Device_Reset event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_Reset(void)
{
puts_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "USB Reset\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Device_UnhandledControlRequest event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_UnhandledControlRequest(void)
{
printf_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "Ctrl Request\r\n"
" -- Req Data %d\r\n"
" -- Req Type %d\r\n"
" -- Req Length %d\r\n" ESC_FG_WHITE), USB_ControlRequest.bRequest,
USB_ControlRequest.bmRequestType,
USB_ControlRequest.wLength);
}
/** Event handler for the USB_Device_ConfigurationChanged event. When fired, the event is logged to the USART. */
void EVENT_USB_Device_ConfigurationChanged(void)
{
puts_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "Configuration Number Changed\r\n" ESC_FG_WHITE));
}
/**
* Event handler for the USB_Host_HostError event. When fired, the event is logged to the USART and the program
* execution aborted.
*/
void EVENT_USB_Host_HostError(const uint8_t ErrorCode)
{
printf_P(PSTR(ESC_FG_RED EVENT_PREFIX "Host Mode Error\r\n"
" -- Error Code %d\r\n" ESC_FG_WHITE), ErrorCode);
Abort_Program();
}
/** Event handler for the USB_Host_DeviceEnumerationFailed event. When fired, the event is logged to the USART. */
void EVENT_USB_Host_DeviceEnumerationFailed(const uint8_t ErrorCode, const uint8_t SubErrorCode)
{
printf_P(PSTR(ESC_FG_RED EVENT_PREFIX "Dev Enum Error\r\n"
" -- Error Code %d\r\n"
" -- Sub Error Code %d\r\n"
" -- In State %d\r\n" ESC_FG_WHITE), ErrorCode, SubErrorCode, USB_HostState);
}
/** Event handler for the USB_Host_DeviceEnumerationComplete event. When fired, the event is logged to the USART. */
void EVENT_USB_Host_DeviceEnumerationComplete(void)
{
puts_P(PSTR(ESC_FG_YELLOW EVENT_PREFIX "Device Enumeration Complete\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Host_DeviceAttached event. When fired, the event is logged to the USART. */
void EVENT_USB_Host_DeviceAttached(void)
{
puts_P(PSTR(ESC_FG_GREEN EVENT_PREFIX "Device Attached\r\n" ESC_FG_WHITE));
}
/** Event handler for the USB_Host_DeviceUnattached event. When fired, the event is logged to the USART. */
void EVENT_USB_Host_DeviceUnattached(void)
{
puts_P(PSTR(ESC_FG_GREEN EVENT_PREFIX "Device Unattached\r\n" ESC_FG_WHITE));
}

@ -16,4 +16,4 @@
%:
make -C Device/ $@
make -C Host/ $@
make -C OTG/ $@
make -C DualRole/ $@

Loading…
Cancel
Save