//! This example application turns the evaluation board into a USB mouse
//! supporting the Human Interface Device class. After loading and running the
//! example simply connect the PC to the controlCARDs microUSB port using a USB
//! cable, and the mouse pointer will move in a square pattern for the duration
//! of the time it is plugged in.
#include "device.h"
#include <gpio.h>
#include <cputimer.h>
#include <usblib.h>
#include <usbhid.h>
#include <device/usbdevice.h> // erforderlich für device/usbhid
#include <device/usbdhid.h> // erforderlich für device/usbhidmouse
#include <device/usbdhidmouse.h>
#include <usb_ids.h>
//******************************************************************************
//
// The languages supported by this device.
//
//******************************************************************************
const uint8_t g_pLangDescriptor[] =
{
4,
USB_DTYPE_STRING,
USBShort(USB_LANG_EN_US)
};
//******************************************************************************
//
// The manufacturer string.
//
//******************************************************************************
const uint8_t g_pManufacturerString[] =
{
(17 + 1) * 2,
USB_DTYPE_STRING,
'T', 0, 'e', 0, 'x', 0, 'a', 0, 's', 0, ' ', 0, 'I', 0, 'n', 0, 's', 0,
't', 0, 'r', 0, 'u', 0, 'm', 0, 'e', 0, 'n', 0, 't', 0, 's', 0,
};
//******************************************************************************
//
// The product string.
//
//******************************************************************************
const uint8_t g_pProductString[] =
{
(13 + 1) * 2,
USB_DTYPE_STRING,
'M', 0, 'o', 0, 'u', 0, 's', 0, 'e', 0, ' ', 0, 'E', 0, 'x', 0, 'a', 0,
'm', 0, 'p', 0, 'l', 0, 'e', 0
};
//******************************************************************************
//
// The serial number string.
//
//******************************************************************************
const uint8_t g_pSerialNumberString[] =
{
(8 + 1) * 2,
USB_DTYPE_STRING,
'1', 0, '2', 0, '3', 0, '4', 0, '5', 0, '6', 0, '7', 0, '8', 0
};
//******************************************************************************
//
// The interface description string.
//
//******************************************************************************
const uint8_t g_pHIDInterfaceString[] =
{
(19 + 1) * 2,
USB_DTYPE_STRING,
'H', 0, 'I', 0, 'D', 0, ' ', 0, 'M', 0, 'o', 0, 'u', 0, 's', 0,
'e', 0, ' ', 0, 'I', 0, 'n', 0, 't', 0, 'e', 0, 'r', 0, 'f', 0,
'a', 0, 'c', 0, 'e', 0
};
//******************************************************************************
//
// The configuration description string.
//
//******************************************************************************
const uint8_t g_pConfigString[] =
{
(23 + 1) * 2,
USB_DTYPE_STRING,
'H', 0, 'I', 0, 'D', 0, ' ', 0, 'M', 0, 'o', 0, 'u', 0, 's', 0,
'e', 0, ' ', 0, 'C', 0, 'o', 0, 'n', 0, 'f', 0, 'i', 0, 'g', 0,
'u', 0, 'r', 0, 'a', 0, 't', 0, 'i', 0, 'o', 0, 'n', 0
};
//******************************************************************************
//
// The descriptor string table.
//
//******************************************************************************
const uint8_t * const g_pStringDescriptors[] =
{
g_pLangDescriptor,
g_pManufacturerString,
g_pProductString,
g_pSerialNumberString,
g_pHIDInterfaceString,
g_pConfigString
};
#define NUM_STRING_DESCRIPTORS (sizeof(g_pStringDescriptors) /\
sizeof(uint8_t *))
//******************************************************************************
//
// The HID mouse device initialization and customization structures.
//
//******************************************************************************
tHIDMouseInstance g_sMouseInstance;
static uint32_t MouseHandler(void *pvCBData, uint32_t ui32Event,
uint32_t ui32MsgData, void *pvMsgData);
tUSBDHIDMouseDevice g_sMouseDevice = {
USB_VID_TI_1CBE,
USB_PID_MOUSE,
500,
USB_CONF_ATTR_SELF_PWR,
MouseHandler,
&g_sMouseDevice,
g_pStringDescriptors,
NUM_STRING_DESCRIPTORS,
};
//******************************************************************************
//
// Defines
//
//******************************************************************************
#define MOUSE_MOVE_INC 1 // The incremental update for the mouse.
#define MOUSE_MOVE_DEC -1
#define TICKS_PER_SECOND 100
#define MS_PER_SYSTICK (1000 / TICKS_PER_SECOND)
#define TICK_EVENT 0
#define MAX_SEND_DELAY 50 // The number of system ticks to wait for
// each USB packet to be sent before
// we assume the host has disconnected.
// The value 50 equates to half a second.
//******************************************************************************
//
// Globals
//
//******************************************************************************
volatile uint32_t g_ui32Commands; // Holds command bits used to signal
// the main loop to perform
// various tasks.
volatile bool g_bConnected; // A flag used to indicate whether or
// not we are currently connected to
// the USB host.
volatile uint32_t g_ui32TickCount; // Global system tick counter holds
// elapsed time since the application
// started expressed in 100ths of a
// second.
//******************************************************************************
//
// This enumeration holds the various states that the mouse can be in during
// normal operation.
//
//******************************************************************************
volatile enum {
MOUSE_STATE_UNCONFIGURED, // Unconfigured.
MOUSE_STATE_IDLE, // No keys to send and not waiting on data.
MOUSE_STATE_SENDING // Waiting on data to be sent out.
}g_eMouseState = MOUSE_STATE_UNCONFIGURED;
//******************************************************************************
//
// MouseHandler - This function handles notification messages from the
// mouse device driver.
//
//******************************************************************************
uint32_t MouseHandler(void *pvCBData, uint32_t ui32Event, uint32_t ui32MsgData,
void *pvMsgData) {
switch(ui32Event)
{
//
// The USB host has connected to and configured the device.
//
case USB_EVENT_CONNECTED:
{
g_eMouseState = MOUSE_STATE_IDLE;
g_bConnected = true;
break;
}
//
// The USB host has disconnected from the device.
//
case USB_EVENT_DISCONNECTED:
{
g_bConnected = false;
g_eMouseState = MOUSE_STATE_UNCONFIGURED;
break;
}
//
// A report was sent to the host. We are not free to send another.
//
case USB_EVENT_TX_COMPLETE:
{
g_eMouseState = MOUSE_STATE_IDLE;
break;
}
//
// Ignore the other events.
//
default:
break;
}
return(0);
}
//******************************************************************************
//
// WaitForSendIdle - Wait for a period of time for the state to become idle.
//
// \param ui32TimeoutTick is the number of system ticks to wait before declaring
// a timeout and returning \b false.
//
// This function polls the current keyboard state for ui32TimeoutTicks system
// ticks waiting for it to become idle. If the state becomes idle, the
// function returns true. If it ui32TimeoutTicks occur prior to the state
// becoming idle, false is returned to indicate a timeout.
//
// \return Returns \b true on success or \b false on timeout.
//
//******************************************************************************
bool WaitForSendIdle(uint32_t ui32TimeoutTicks) {
uint32_t ui32Start;
uint32_t ui32Now;
uint32_t ui32Elapsed;
ui32Start = g_ui32TickCount;
ui32Elapsed = 0;
while(ui32Elapsed < ui32TimeoutTicks)
{
//
// Is the mouse is idle, return immediately.
//
if(g_eMouseState == MOUSE_STATE_IDLE)
{
return(true);
}
//
// Determine how much time has elapsed since we started waiting. This
// should be safe across a wrap of g_ui32TickCount.
//
ui32Now = g_ui32TickCount;
ui32Elapsed = ((ui32Start < ui32Now) ? (ui32Now - ui32Start) :
(((uint32_t)0xFFFFFFFF - ui32Start) + ui32Now + 1));
}
//
// If we get here, we timed out so return a bad return code to let the
// caller know.
//
return(false);
}
//******************************************************************************
//
// MoveHandler - This function provides simulated movements of the mouse.
//
//******************************************************************************
void MoveHandler(void) {
uint32_t ui32Retcode;
char cDeltaX, cDeltaY;
//
// Determine the direction to move the mouse.
//
ui32Retcode = g_ui32TickCount % (4 * TICKS_PER_SECOND);
if(ui32Retcode < TICKS_PER_SECOND)
{
cDeltaX = MOUSE_MOVE_INC;
cDeltaY = 0;
}
else if(ui32Retcode < (2 * TICKS_PER_SECOND))
{
cDeltaX = 0;
cDeltaY = MOUSE_MOVE_INC;
}
else if(ui32Retcode < (3 * TICKS_PER_SECOND))
{
cDeltaX = (char)MOUSE_MOVE_DEC;
cDeltaY = 0;
}
else
{
cDeltaX = 0;
cDeltaY = (char)MOUSE_MOVE_DEC;
}
//
// Tell the HID driver to send this new report.
//
g_eMouseState = MOUSE_STATE_SENDING;
ui32Retcode = USBDHIDMouseStateChange((void *)&g_sMouseDevice, cDeltaX,
cDeltaY, 0);
//
// Did we schedule the report for transmission?
//
if(ui32Retcode == MOUSE_SUCCESS)
{
//
// Wait for the host to acknowledge the transmission if all went well.
//
if(!WaitForSendIdle(MAX_SEND_DELAY))
{
//
// The transmission failed, so assume the host disconnected and go
// back to waiting for a new connection.
//
g_bConnected = false;
}
}
}
//******************************************************************************
//
// CPUTimerIntHandler - This is the interrupt handler for the CPU Timer
// interrupt. It is called periodically and updates a global tick counter then
// sets a flag to tell the main loop to move the mouse.
//
//******************************************************************************
__interrupt void
CPUTimerIntHandler(void)
{
GPIO_writePin(0,1);
g_ui32TickCount++;
HWREG(&g_ui32Commands) |= 1;
GPIO_writePin(0,0);
Interrupt_clearACKGroup(INTERRUPT_ACK_GROUP1);
}
//******************************************************************************
//
// This is the main application entry function.
//
//******************************************************************************
int main(void) {
g_bConnected = false;
// Initialize device clock and peripherals
Device_init();
// Initialize GPIO and configure GPIO pins for USB.
Device_initGPIO();
// Set the clocking to run from the PLL at 60MHz
SysCtl_setAuxClock(DEVICE_AUXSETCLOCK_CFG_USB);
// Initialize PIE and clear PIE registers. Disables CPU interrupts.
Interrupt_initModule();
// Initialize the PIE vector table with pointers to the shell Interrupt
// Service Routines (ISR).
Interrupt_initVectorTable();
EINT; // Enable Global Interrupt (INTM) and realtime interrupt (DBGM)
ERTM;
USBGPIOEnable();
Interrupt_register(INT_USBA, f28x_USB0DeviceIntHandler);
// Initialize the USB stack for device mode.
USBStackModeSet(0, eUSBModeForceDevice, 0);
GPIO_setDirectionMode(0, GPIO_DIR_MODE_OUT);
// Register the interrupt handler, returning an error if an error occurs.
Interrupt_register(INT_TIMER0, &CPUTimerIntHandler);
CPUTimerInit();
CPUTimer_setPeriod(CPUTIMER0_BASE,
(SysCtl_getClock(DEVICE_OSCSRC_FREQ) / TICKS_PER_SECOND));
// Enable the CPU Timer interrupt.
CPUTimer_enableInterrupt(CPUTIMER0_BASE);
Interrupt_enable(INT_TIMER0);
CPUTimer_startTimer(CPUTIMER0_BASE);
// Pass the USB library our device information, initialize the USB
// controller and connect the device to the bus.
USBDHIDMouseInit(0,&g_sMouseDevice);
Interrupt_enableMaster();
// Drop into the main loop.
for(;;) {
while (!g_bConnected);// Wait for USB configuration to complete.
// Now keep processing the mouse as long as the host is connected.
while (g_bConnected) {
// If it is time to move the mouse then do so.
if (HWREG(&g_ui32Commands) & 1) {
HWREG(&g_ui32Commands) &= ~1;
MoveHandler();
}
}
}
}
Detected encoding: UTF-8 | 0
|