Initial commit

This commit is contained in:
jasonsanctuary 2017-09-17 14:12:49 -07:00
commit 96acb2268b
35 changed files with 11426 additions and 0 deletions

108
Makefile Normal file
View File

@ -0,0 +1,108 @@
#
# There exist several targets which are by default empty and which can be
# used for execution of your targets. These targets are usually executed
# before and after some main targets. They are:
#
# .build-pre: called before 'build' target
# .build-post: called after 'build' target
# .clean-pre: called before 'clean' target
# .clean-post: called after 'clean' target
# .clobber-pre: called before 'clobber' target
# .clobber-post: called after 'clobber' target
# .all-pre: called before 'all' target
# .all-post: called after 'all' target
# .help-pre: called before 'help' target
# .help-post: called after 'help' target
#
# Targets beginning with '.' are not intended to be called on their own.
#
# Main targets can be executed directly, and they are:
#
# build build a specific configuration
# clean remove built files from a configuration
# clobber remove all built files
# all build all configurations
# help print help mesage
#
# Targets .build-impl, .clean-impl, .clobber-impl, .all-impl, and
# .help-impl are implemented in nbproject/makefile-impl.mk.
#
# Available make variables:
#
# CND_BASEDIR base directory for relative paths
# CND_DISTDIR default top distribution directory (build artifacts)
# CND_BUILDDIR default top build directory (object files, ...)
# CONF name of current configuration
# CND_ARTIFACT_DIR_${CONF} directory of build artifact (current configuration)
# CND_ARTIFACT_NAME_${CONF} name of build artifact (current configuration)
# CND_ARTIFACT_PATH_${CONF} path to build artifact (current configuration)
# CND_PACKAGE_DIR_${CONF} directory of package (current configuration)
# CND_PACKAGE_NAME_${CONF} name of package (current configuration)
# CND_PACKAGE_PATH_${CONF} path to package (current configuration)
#
# NOCDDL
# Environment
MKDIR=mkdir
CP=cp
CCADMIN=CCadmin
RANLIB=ranlib
# build
build: .build-post
.build-pre:
# Add your pre 'build' code here...
.build-post: .build-impl
# Add your post 'build' code here...
# clean
clean: .clean-post
.clean-pre:
# Add your pre 'clean' code here...
.clean-post: .clean-impl
# Add your post 'clean' code here...
# clobber
clobber: .clobber-post
.clobber-pre:
# Add your pre 'clobber' code here...
.clobber-post: .clobber-impl
# Add your post 'clobber' code here...
# all
all: .all-post
.all-pre:
# Add your pre 'all' code here...
.all-post: .all-impl
# Add your post 'all' code here...
# help
help: .help-post
.help-pre:
# Add your pre 'help' code here...
.help-post: .help-impl
# Add your post 'help' code here...
# include project implementation makefile
include nbproject/Makefile-impl.mk
# include project make variables
include nbproject/Makefile-variables.mk

48
funclist Normal file
View File

@ -0,0 +1,48 @@
_SYS_InterruptHigh: CODE, 8 0 114
_configDescriptor1: SMALLCONST, 877 0 34
_USB_CD_Ptr: SMALLCONST, 774 0 2
_sd001: SMALLCONST, 776 0 52
_APP_DeviceJoystickInitialize: CODE, 7568 0 36
_USBCtrlTrfInHandler: CODE, 3704 0 260
_USBTransferOnePacket: CODE, 3440 0 264
_sd002: SMALLCONST, 911 0 28
_USBStdGetDscHandler: CODE, 3138 0 302
_memset: CODE, 7442 0 44
_main: CODE, 7486 0 42
_USER_USB_CALLBACK_EVENT_HANDLER: CODE, 6612 0 138
_LED_Off: CODE, 7338 0 52
_USBCtrlEPAllowDataStage: CODE, 6132 0 164
_USBStdFeatureReqHandler: CODE, 962 0 932
_BUTTON_IsPressed: CODE, 7180 0 54
_BUTTON_Enable: CODE, 7604 0 36
_USBCtrlEPAllowStatusStage: CODE, 5396 0 198
_USBCtrlTrfSetupHandler: CODE, 5594 0 192
_USBCtrlTrfOutHandler: CODE, 6750 0 98
_USBCtrlEPServiceComplete: CODE, 3964 0 254
_USBSuspend: CODE, 7234 0 52
_memcpy: CODE, 7000 0 64
__initialization: CODE, 7640 0 24
_USBStdSetCfgHandler: CODE, 4722 0 248
_USBStdGetStatusHandler: CODE, 5190 0 206
_USBWakeFromSuspend: CODE, 7064 0 58
_device_dsc: SMALLCONST, 939 0 18
_USBCtrlTrfRxService: CODE, 2794 0 344
_USBCtrlTrfTxService: CODE, 4970 0 220
_USBEnableEndpoint: CODE, 6848 0 82
_SYSTEM_Initialize: CODE, 7122 0 58
_APP_LEDUpdateUSBStatus: CODE, 6456 0 156
_USBConfigureEndpoint: CODE, 6296 0 160
_USBDeviceInit: CODE, 2366 0 428
_USBIncrement1msInternalTimers: CODE, 7528 0 40
_USB_SD_Ptr: SMALLCONST, 768 0 6
_hid_rpt01: SMALLCONST, 828 0 49
_LED_On: CODE, 7390 0 52
_sd000: SMALLCONST, 957 0 4
_APP_DeviceJoystickTasks: CODE, 5786 0 178
_LED_Enable: CODE, 7286 0 52
_USBCtrlEPService: CODE, 5964 0 168
_USBStallHandler: CODE, 6930 0 70
_USBDeviceTasks: CODE, 1894 0 472
_USBCheckHIDRequest: CODE, 4470 0 252
_USBCheckStdRequest: CODE, 4218 0 252
Total: 7009

113
inc/drivers/adc.h Normal file
View File

@ -0,0 +1,113 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#ifndef ADC_H
#define ADC_H
#include <stdint.h>
#include <stdbool.h>
/*** ADC Channel Definitions *****************************************/
//#define ADC_CHANNEL_POTENTIOMETER ADC_CHANNEL_10
typedef enum {
ADC_CHANNEL_8 = 8,
ADC_CHANNEL_9 = 9
} ADC_CHANNEL;
typedef enum {
ADC_CONFIGURATION_DEFAULT
} ADC_CONFIGURATION;
/*********************************************************************
* Function: ADC_ReadPercentage(ADC_CHANNEL channel);
*
* Overview: Reads the requested ADC channel and returns the percentage
* of that conversions result (0-100%).
*
* PreCondition: channel is enabled via ADC_Enable()
*
* Input: ADC_CHANNEL channel - enumeration of the ADC channels
* available in this demo. They should be meaningful names and
* not the names of the ADC pins on the device (as the demo code
* may be ported to other boards).
* i.e. ADC_ReadPercentage(ADC_CHANNEL_POTENTIOMETER);
*
* Output: uint8_t indicating the percentage of the result 0-100% or
* 0xFF for an error
*
********************************************************************/
uint8_t ADC_ReadPercentage(ADC_CHANNEL channel);
/*********************************************************************
* Function: ADC_Read10bit(ADC_CHANNEL channel);
*
* Overview: Reads the requested ADC channel and returns the 10-bit
* representation of this data.
*
* PreCondition: channel is enabled via ADC_Enable()
*
* Input: ADC_CHANNEL channel - enumeration of the ADC channels
* available in this demo. They should be meaningful names and
* not the names of the ADC pins on the device (as the demo code
* may be ported to other boards).
* i.e. - ADCReadPercentage(ADC_CHANNEL_POTENTIOMETER);
*
* Output: uint16_t the right adjusted 10-bit representation of the ADC
* channel conversion or 0xFFFF for an error.
*
********************************************************************/
uint16_t ADC_Read10bit(ADC_CHANNEL channel);
uint8_t ADC_Read8bit(ADC_CHANNEL channel);
/*********************************************************************
* Function: bool ADC_Enable(ADC_CHANNEL channel, ADC_CONFIGURATION configuration);
*
* Overview: Enables specified channel
*
* PreCondition: none
*
* Input: ADC_CHANNEL channel - the channel to enable
*
* Output: bool - true if successfully configured. false otherwise.
*
********************************************************************/
bool ADC_Enable(ADC_CHANNEL channel);
/*********************************************************************
* Function: bool ADC_SetConfiguration(ADC_CONFIGURATION configuration)
*
* Overview: Configures the ADC module to specified setting
*
* PreCondition: none
*
* Input: ADC_CONFIGURATION configuration - the mode in which to run the ADC
*
* Output: bool - true if successfully configured. false otherwise.
*
********************************************************************/
bool ADC_SetConfiguration(ADC_CONFIGURATION configuration);
#endif //ADC_H

View File

@ -0,0 +1,37 @@
/*******************************************************************************
Copyright 2016 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
/*********************************************************************
* Function: void APP_LEDUpdateUSBStatus(void);
*
* Overview: Uses one LED to indicate the status of the device on the USB bus.
* A fast blink indicates successfully connected. A slow pulse
* indicates that it is still in the process of connecting. Off
* indicates thta it is not attached to the bus or the bus is suspended.
* This should be called on every start of frame packet reception and
* if a suspend/resume event occurs.
*
* PreCondition: LEDs are enabled.
*
* Input: None
*
* Output: None
*
********************************************************************/
void APP_LEDUpdateUSBStatus(void);

72
inc/drivers/buttons.h Normal file
View File

@ -0,0 +1,72 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#include <stdbool.h>
#ifndef BUTTONS_H
#define BUTTONS_H
/*** Button Definitions *********************************************/
typedef enum
{
BUTTON_NONE,
BUTTON_S1,
BUTTON_S2
} BUTTON;
/*********************************************************************
* Function: bool BUTTON_IsPressed(BUTTON button);
*
* Overview: Returns the current state of the requested button
*
* PreCondition: button configured via BUTTON_SetConfiguration()
*
* Input: BUTTON button - enumeration of the buttons available in
* this demo. They should be meaningful names and not the names
* of the buttons on the silkscreen on the board (as the demo
* code may be ported to other boards).
* i.e. - ButtonIsPressed(BUTTON_SEND_MESSAGE);
*
* Output: TRUE if pressed; FALSE if not pressed.
*
********************************************************************/
bool BUTTON_IsPressed(BUTTON button);
/*********************************************************************
* Function: void BUTTON_Enable(BUTTON button);
*
* Overview: Returns the current state of the requested button
*
* PreCondition: button configured via BUTTON_SetConfiguration()
*
* Input: BUTTON button - enumeration of the buttons available in
* this demo. They should be meaningful names and not the names
* of the buttons on the silkscreen on the board (as the demo
* code may be ported to other boards).
* i.e. - ButtonIsPressed(BUTTON_SEND_MESSAGE);
*
* Output: None
*
********************************************************************/
void BUTTON_Enable(BUTTON button);
#endif //BUTTONS_H

38
inc/drivers/eeprom.h Normal file
View File

@ -0,0 +1,38 @@
/*
* EEPROM routines
* www.flitey.com
*/
#ifndef EEPROM_H
#define EEPROM_H
/**
* Gets the value in EEPROM at the specified address.
* @param byteAddress the address of the byte
* @return the value
*/
unsigned char EepromReadByte(uint8_t byteAddress);
/**
* Sets the value in EEPROM with the specified value at the specified address.
* @param byteAddress the address location where the value will be stored
* @param byteData the value to store
*/
void EepromWriteByte(uint8_t byteAddress, uint8_t byteData);
/**
* Gets two bytes from EEPROM starting at the specified address.
* @param startAddress the starting address location
* @return the two byte value
*/
uint16_t EepromReadTwoBytes(uint8_t startAddress);
/**
* Sets the value in EEPROM with the specified value at the specified address
* @param startAddress the starting address location where the value will be stored
* @param value the value to store
*/
void EepromWriteTwoBytes(uint8_t startAddress, uint16_t value);
#endif /* EEPROM_H */

35
inc/drivers/joystick.h Normal file
View File

@ -0,0 +1,35 @@
/**
* Joystick functions
* www.flitey.com
*/
#ifndef USBJOYSTICK_H
#define USBJOYSTICK_H
/**
* Initializes the joystick endpoint
*/
void JoystickInitialize();
/**
* Runs the calibration for the joystick potentiometers
*/
void JoystickRunCalibration();
/**
* Sets the calibration values to the specified values
* @param x_min the min value for the X axis
* @param x_mid the mid value for the X axis
* @param x_max the max value for the X axis
* @param y_min the min value for the Y axis
* @param y_mid the mid value for the Y axis
* @param y_max the max value for the Y axis
*/
void JoystickUseSavedCalibration(uint16_t x_min, uint16_t x_mid, uint16_t x_max, uint16_t y_min, uint16_t y_mid, uint16_t y_max);
/**
* Perform the joystick tasks which includes getting the values from the joystick
* and then sending them to the computer.
*/
void JoystickTasks();
#endif /* USBJOYSTICK_H */

129
inc/drivers/leds.h Normal file
View File

@ -0,0 +1,129 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#ifndef LEDS_H
#define LEDS_H
#include <stdbool.h>
/** Type defintions *********************************/
typedef enum
{
LED_NONE,
LED_D1,
LED_D2,
LED_D3,
LED_D4
} LED;
#define LED_COUNT 4
/*********************************************************************
* Function: void LED_On(LED led);
*
* Overview: Turns requested LED on
*
* PreCondition: LED configured via LED_Configure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_On(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_On(LED led);
/*********************************************************************
* Function: void LED_Off(LED led);
*
* Overview: Turns requested LED off
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Off(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_Off(LED led);
/*********************************************************************
* Function: void LED_Toggle(LED led);
*
* Overview: Toggles the state of the requested LED
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Toggle(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_Toggle(LED led);
/*********************************************************************
* Function: bool LED_Get(LED led);
*
* Overview: Returns the current state of the requested LED
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Get(LED_CONNECTION_DETECTED);
*
* Output: true if on, false if off
*
********************************************************************/
bool LED_Get(LED led);
/*********************************************************************
* Function: bool LED_Enable(LED led);
*
* Overview: Configures the LED for use by the other LED API
*
* PreCondition: none
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
*
* Output: none
*
********************************************************************/
void LED_Enable(LED led);
#endif //LEDS_H

View File

@ -0,0 +1,28 @@
/*******************************************************************************
Copyright 2016 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
#ifndef FIXED_MEMORY_ADDRESS_H
#define FIXED_MEMORY_ADDRESS_H
#define FIXED_ADDRESS_MEMORY
#define JOYSTICK_DATA_ADDRESS 0x260
#define HID_CUSTOM_IN_DATA_BUFFER_ADDRESS 0x2A0
#endif //FIXED_MEMORY_ADDRESS

29
inc/io_mapping.h Normal file
View File

@ -0,0 +1,29 @@
/**
* Mapping of IO
*/
#include "system.h"
#define GAME_SWITCH_0 BUTTON_S1
#define GAME_SWITCH_1 BUTTON_S2
#define PDL0 ADC_CHANNEL_8
#define PDL1 ADC_CHANNEL_9
#define LED_USB_DEVICE_STATE LED_D1
#define X_AXIS_MIN_EEPROM_ADDRESS 0x00
#define X_AXIS_MID_EEPROM_ADDRESS 0x02
#define X_AXIS_MAX_EEPROM_ADDRESS 0x04
#define Y_AXIS_MIN_EEPROM_ADDRESS 0x06
#define Y_AXIS_MID_EEPROM_ADDRESS 0x08
#define Y_AXIS_MAX_EEPROM_ADDRESS 0x0A
#define JOYSTICK_10_BIT_MAX 1023
#define JOYSTICK_10_BIT_MID 511
#define JOYSTICK_10_BIT_MIN 0
#define JOYSTICK_8_BIT_MAX_OUTPUT 255
#define JOYSTICK_8_BIT_MID_OUTPUT 127
#define JOYSTICK_8_BIT_MIN_OUTPUT 0

27
inc/system.h Normal file
View File

@ -0,0 +1,27 @@
/**
* System definitions and functions
*/
#ifndef SYSTEM_H
#define SYSTEM_H
#include <xc.h>
#include <stdbool.h>
#include "buttons.h"
#include "leds.h"
#include "adc.h"
#include "io_mapping.h"
#include "fixed_address_memory.h"
/*** System States **************************************************/
typedef enum {
SYSTEM_STATE_USB_START,
SYSTEM_STATE_USB_SUSPEND,
SYSTEM_STATE_USB_RESUME
} SYSTEM_STATE;
void SYSTEM_Initialize(SYSTEM_STATE state);
#endif

70
inc/usb/usb.h Normal file
View File

@ -0,0 +1,70 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
/*******************************************************************************
Module for Microchip USB Library
Company:
Microchip Technology Inc.
File Name:
usb.h
Summary:
This header file exposes the core library APIs and definitions for the USB
library.
Description:
This header file exposes the core library APIs and definitions for the USB
library. The user is responsible for also including the header file for
the specific driver they will be using.
*******************************************************************************/
#ifndef _USB_H_
#define _USB_H_
#include "usb_config.h"
#include "usb_common.h" // Common USB library definitions
#include "usb_ch9.h" // USB device framework definitions
#if defined( USB_SUPPORT_DEVICE )
#include "usb_device.h" // USB Device abstraction layer interface
#endif
#if defined( USB_SUPPORT_HOST )
#include "usb_host.h" // USB Host abstraction layer interface
#endif
#include "usb_hal.h" // Hardware Abstraction Layer interface
/* USB Library version number. This can be used to verify in an application
specific version of the library is being used.
*/
#define USB_MAJOR_VER 2 // Firmware version, major release number.
#define USB_MINOR_VER 13 // Firmware version, minor release number.
#define USB_DOT_VER 0 // Firmware version, dot release number.
#endif // _USB_H_

596
inc/usb/usb_ch9.h Normal file
View File

@ -0,0 +1,596 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
/*******************************************************************************
Module for Microchip USB Library
Company:
Microchip Technology Inc.
File Name:
usb_ch9.h
Summary:
Defines types associated with chapter 9 of the USB specification.
Description:
Defines types associated with chapter 9 of the USB specification.
*******************************************************************************/
#ifndef _USB_CH9_H_
#define _USB_CH9_H_
#include <stdint.h>
#if defined(__XC8)
#define __attribute__(a)
#endif
// *****************************************************************************
// *****************************************************************************
// Section: USB Descriptors
// *****************************************************************************
// *****************************************************************************
#define USB_DESCRIPTOR_DEVICE 0x01 // bDescriptorType for a Device Descriptor.
#define USB_DESCRIPTOR_CONFIGURATION 0x02 // bDescriptorType for a Configuration Descriptor.
#define USB_DESCRIPTOR_STRING 0x03 // bDescriptorType for a String Descriptor.
#define USB_DESCRIPTOR_INTERFACE 0x04 // bDescriptorType for an Interface Descriptor.
#define USB_DESCRIPTOR_ENDPOINT 0x05 // bDescriptorType for an Endpoint Descriptor.
#define USB_DESCRIPTOR_DEVICE_QUALIFIER 0x06 // bDescriptorType for a Device Qualifier.
#define USB_DESCRIPTOR_OTHER_SPEED 0x07 // bDescriptorType for a Other Speed Configuration.
#define USB_DESCRIPTOR_INTERFACE_POWER 0x08 // bDescriptorType for Interface Power.
#define USB_DESCRIPTOR_OTG 0x09 // bDescriptorType for an OTG Descriptor.
// *****************************************************************************
/* USB Device Descriptor Structure
This struct defines the structure of a USB Device Descriptor.
*/
typedef struct __attribute__ ((packed)) _USB_DEVICE_DESCRIPTOR
{
uint8_t bLength; // Length of this descriptor.
uint8_t bDescriptorType; // DEVICE descriptor type (USB_DESCRIPTOR_DEVICE).
uint16_t bcdUSB; // USB Spec Release Number (BCD).
uint8_t bDeviceClass; // Class code (assigned by the USB-IF). 0xFF-Vendor specific.
uint8_t bDeviceSubClass; // Subclass code (assigned by the USB-IF).
uint8_t bDeviceProtocol; // Protocol code (assigned by the USB-IF). 0xFF-Vendor specific.
uint8_t bMaxPacketSize0; // Maximum packet size for endpoint 0.
uint16_t idVendor; // Vendor ID (assigned by the USB-IF).
uint16_t idProduct; // Product ID (assigned by the manufacturer).
uint16_t bcdDevice; // Device release number (BCD).
uint8_t iManufacturer; // Index of String Descriptor describing the manufacturer.
uint8_t iProduct; // Index of String Descriptor describing the product.
uint8_t iSerialNumber; // Index of String Descriptor with the device's serial number.
uint8_t bNumConfigurations; // Number of possible configurations.
} USB_DEVICE_DESCRIPTOR;
// *****************************************************************************
/* USB Configuration Descriptor Structure
This struct defines the structure of a USB Configuration Descriptor.
*/
typedef struct __attribute__ ((packed)) _USB_CONFIGURATION_DESCRIPTOR
{
uint8_t bLength; // Length of this descriptor.
uint8_t bDescriptorType; // CONFIGURATION descriptor type (USB_DESCRIPTOR_CONFIGURATION).
uint16_t wTotalLength; // Total length of all descriptors for this configuration.
uint8_t bNumInterfaces; // Number of interfaces in this configuration.
uint8_t bConfigurationValue; // Value of this configuration (1 based).
uint8_t iConfiguration; // Index of String Descriptor describing the configuration.
uint8_t bmAttributes; // Configuration characteristics.
uint8_t bMaxPower; // Maximum power consumed by this configuration.
} USB_CONFIGURATION_DESCRIPTOR;
// Attributes bits
#define USB_CFG_DSC_REQUIRED 0x80 // Required attribute
#define USB_CFG_DSC_SELF_PWR (0x40|USB_CFG_DSC_REQUIRED) // Device is self powered.
#define USB_CFG_DSC_REM_WAKE (0x20|USB_CFG_DSC_REQUIRED) // Device can request remote wakup
// *****************************************************************************
/* USB Interface Descriptor Structure
This struct defines the structure of a USB Interface Descriptor.
*/
typedef struct __attribute__ ((packed)) _USB_INTERFACE_DESCRIPTOR
{
uint8_t bLength; // Length of this descriptor.
uint8_t bDescriptorType; // INTERFACE descriptor type (USB_DESCRIPTOR_INTERFACE).
uint8_t bInterfaceNumber; // Number of this interface (0 based).
uint8_t bAlternateSetting; // Value of this alternate interface setting.
uint8_t bNumEndpoints; // Number of endpoints in this interface.
uint8_t bInterfaceClass; // Class code (assigned by the USB-IF). 0xFF-Vendor specific.
uint8_t bInterfaceSubClass; // Subclass code (assigned by the USB-IF).
uint8_t bInterfaceProtocol; // Protocol code (assigned by the USB-IF). 0xFF-Vendor specific.
uint8_t iInterface; // Index of String Descriptor describing the interface.
} USB_INTERFACE_DESCRIPTOR;
// *****************************************************************************
/* USB Endpoint Descriptor Structure
This struct defines the structure of a USB Endpoint Descriptor.
*/
typedef struct __attribute__ ((packed)) _USB_ENDPOINT_DESCRIPTOR
{
uint8_t bLength; // Length of this descriptor.
uint8_t bDescriptorType; // ENDPOINT descriptor type (USB_DESCRIPTOR_ENDPOINT).
uint8_t bEndpointAddress; // Endpoint address. Bit 7 indicates direction (0=OUT, 1=IN).
uint8_t bmAttributes; // Endpoint transfer type.
uint16_t wMaxPacketSize; // Maximum packet size.
uint8_t bInterval; // Polling interval in frames.
} USB_ENDPOINT_DESCRIPTOR;
// Endpoint Direction
#define EP_DIR_IN 0x80 // Data flows from device to host
#define EP_DIR_OUT 0x00 // Data flows from host to device
// ******************************************************************
// USB Endpoint Attributes
// ******************************************************************
// Section: Transfer Types
#define EP_ATTR_CONTROL (0<<0) // Endoint used for control transfers
#define EP_ATTR_ISOCH (1<<0) // Endpoint used for isochronous transfers
#define EP_ATTR_BULK (2<<0) // Endpoint used for bulk transfers
#define EP_ATTR_INTR (3<<0) // Endpoint used for interrupt transfers
// Section: Synchronization Types (for isochronous endpoints)
#define EP_ATTR_NO_SYNC (0<<2) // No Synchronization
#define EP_ATTR_ASYNC (1<<2) // Asynchronous
#define EP_ATTR_ADAPT (2<<2) // Adaptive synchronization
#define EP_ATTR_SYNC (3<<2) // Synchronous
// Section: Usage Types (for isochronous endpoints)
#define EP_ATTR_DATA (0<<4) // Data Endpoint
#define EP_ATTR_FEEDBACK (1<<4) // Feedback endpoint
#define EP_ATTR_IMP_FB (2<<4) // Implicit Feedback data EP
// Section: Max Packet Sizes
#define EP_MAX_PKT_INTR_LS 8 // Max low-speed interrupt packet
#define EP_MAX_PKT_INTR_FS 64 // Max full-speed interrupt packet
#define EP_MAX_PKT_ISOCH_FS 1023 // Max full-speed isochronous packet
#define EP_MAX_PKT_BULK_FS 64 // Max full-speed bulk packet
#define EP_LG_PKT_BULK_FS 32 // Large full-speed bulk packet
#define EP_MED_PKT_BULK_FS 16 // Medium full-speed bulk packet
#define EP_SM_PKT_BULK_FS 8 // Small full-speed bulk packet
/* Descriptor IDs
The descriptor ID type defines the information required by the HOST during a
GET_DESCRIPTOR request
*/
typedef struct
{
uint8_t index;
uint8_t type;
uint16_t language_id;
} DESCRIPTOR_ID;
// *****************************************************************************
/* USB OTG Descriptor Structure
This struct defines the structure of a USB OTG Descriptor. Note that this
structure may need to be packed, or even accessed as uint8_ts, to properly access
the correct fields when used on some device architectures.
*/
typedef struct __attribute__ ((packed)) _USB_OTG_DESCRIPTOR
{
uint8_t bLength; // Length of this descriptor.
uint8_t bDescriptorType; // OTG descriptor type (USB_DESCRIPTOR_OTG).
uint8_t bmAttributes; // OTG attributes.
} USB_OTG_DESCRIPTOR;
// ******************************************************************
// Section: USB String Descriptor Structure
// ******************************************************************
// This structure describes the USB string descriptor. The string
// descriptor provides user-readable information about various aspects of
// the device. The first string descriptor (string descriptor zero (0)),
// provides a list of the number of languages supported by the set of
// string descriptors for this device instead of an actual string.
//
// Note: The strings are in 2-uint8_t-per-character unicode, not ASCII.
//
// Note: This structure only describes the "header" of the string
// descriptor. The actual data (either the language ID array or the
// array of unicode characters making up the string, must be allocated
// immediately following this header with no padding between them.
typedef struct __attribute__ ((packed)) _USB_STRING_DSC
{
uint8_t bLength; // Size of this descriptor
uint8_t bDescriptorType; // Type, USB_DSC_STRING
} USB_STRING_DESCRIPTOR;
// ******************************************************************
// Section: USB Device Qualifier Descriptor Structure
// ******************************************************************
// This structure describes the device qualifier descriptor. The device
// qualifier descriptor provides overall device information if the device
// supports "other" speeds.
//
// Note: A high-speed device may support "other" speeds (ie. full or low).
// If so, it may need to implement the the device qualifier and other
// speed descriptors.
typedef struct __attribute__ ((packed)) _USB_DEVICE_QUALIFIER_DESCRIPTOR
{
uint8_t bLength; // Size of this descriptor
uint8_t bType; // Type, always USB_DESCRIPTOR_DEVICE_QUALIFIER
uint16_t bcdUSB; // USB spec version, in BCD
uint8_t bDeviceClass; // Device class code
uint8_t bDeviceSubClass; // Device sub-class code
uint8_t bDeviceProtocol; // Device protocol
uint8_t bMaxPacketSize0; // EP0, max packet size
uint8_t bNumConfigurations; // Number of "other-speed" configurations
uint8_t bReserved; // Always zero (0)
} USB_DEVICE_QUALIFIER_DESCRIPTOR;
// ******************************************************************
// Section: USB Setup Packet Structure
// ******************************************************************
// This structure describes the data contained in a USB standard device
// request setup packet. It is the data packet sent from the host to
// the device to control and configure the device.
//
// Note: Refer to the USB 2.0 specification for additional details on the
// usage of the setup packet and standard device requests.
typedef union __attribute__ ((packed))
{
/** Standard Device Requests ***********************************/
struct __attribute__ ((packed))
{
uint8_t bmRequestType; //from table 9-2 of USB2.0 spec
uint8_t bRequest; //from table 9-2 of USB2.0 spec
uint16_t wValue; //from table 9-2 of USB2.0 spec
uint16_t wIndex; //from table 9-2 of USB2.0 spec
uint16_t wLength; //from table 9-2 of USB2.0 spec
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
union
{
uint16_t Val;
uint8_t v[2];
struct
{
uint8_t LB;
uint8_t HB;
} byte;
} W_Value;
union
{
uint16_t Val;
uint8_t v[2];
struct
{
uint8_t LB;
uint8_t HB;
} byte;
} W_Index;
union
{
uint16_t Val;
uint8_t v[2];
struct
{
uint8_t LB;
uint8_t HB;
} byte;
} W_Length;
};
struct __attribute__ ((packed))
{
unsigned Recipient:5; //Device,Interface,Endpoint,Other
unsigned RequestType:2; //Standard,Class,Vendor,Reserved
unsigned DataDir:1; //Host-to-device,Device-to-host
unsigned :8;
uint8_t bFeature; //DEVICE_REMOTE_WAKEUP,ENDPOINT_HALT
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
union // offset description
{ // ------ ------------------------
uint8_t bmRequestType; // 0 Bit-map of request type
struct
{
uint8_t recipient: 5; // Recipient of the request
uint8_t type: 2; // Type of request
uint8_t direction: 1; // Direction of data X-fer
};
}requestInfo;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
uint8_t bDscIndex; //For Configuration and String DSC Only
uint8_t bDescriptorType; //Device,Configuration,String
uint16_t wLangID; //Language ID
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
uint8_t bDevADR; //Device Address 0-127
uint8_t bDevADRH; //Must equal zero
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
uint8_t bConfigurationValue; //Configuration Value 0-255
uint8_t bCfgRSD; //Must equal zero (Reserved)
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
uint8_t bAltID; //Alternate Setting Value 0-255
uint8_t bAltID_H; //Must equal zero
uint8_t bIntfID; //Interface Number Value 0-255
uint8_t bIntfID_H; //Must equal zero
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
uint8_t bEPID; //Endpoint ID (Number & Direction)
uint8_t bEPID_H; //Must equal zero
unsigned :8;
unsigned :8;
};
struct __attribute__ ((packed))
{
unsigned :8;
unsigned :8;
unsigned :8;
unsigned :8;
unsigned EPNum:4; //Endpoint Number 0-15
unsigned :3;
unsigned EPDir:1; //Endpoint Direction: 0-OUT, 1-IN
unsigned :8;
unsigned :8;
unsigned :8;
};
/** End: Standard Device Requests ******************************/
} CTRL_TRF_SETUP, SETUP_PKT, *PSETUP_PKT;
// ******************************************************************
// ******************************************************************
// Section: USB Specification Constants
// ******************************************************************
// ******************************************************************
// Section: Valid PID Values
//DOM-IGNORE-BEGIN
#define PID_OUT 0x1 // PID for an OUT token
#define PID_ACK 0x2 // PID for an ACK handshake
#define PID_DATA0 0x3 // PID for DATA0 data
#define PID_PING 0x4 // Special PID PING
#define PID_SOF 0x5 // PID for a SOF token
#define PID_NYET 0x6 // PID for a NYET handshake
#define PID_DATA2 0x7 // PID for DATA2 data
#define PID_SPLIT 0x8 // Special PID SPLIT
#define PID_IN 0x9 // PID for a IN token
#define PID_NAK 0xA // PID for a NAK handshake
#define PID_DATA1 0xB // PID for DATA1 data
#define PID_PRE 0xC // Special PID PRE (Same as PID_ERR)
#define PID_ERR 0xC // Special PID ERR (Same as PID_PRE)
#define PID_SETUP 0xD // PID for a SETUP token
#define PID_STALL 0xE // PID for a STALL handshake
#define PID_MDATA 0xF // PID for MDATA data
#define PID_MASK_DATA 0x03 // Data PID mask
#define PID_MASK_DATA_SHIFTED (PID_MASK_DATA << 2) // Data PID shift to proper position
//DOM-IGNORE-END
// Section: USB Token Types
//DOM-IGNORE-BEGIN
#define USB_TOKEN_OUT 0x01 // U1TOK - OUT token
#define USB_TOKEN_IN 0x09 // U1TOK - IN token
#define USB_TOKEN_SETUP 0x0D // U1TOK - SETUP token
//DOM-IGNORE-END
// Section: OTG Descriptor Constants
#define OTG_HNP_SUPPORT 0x02 // OTG Descriptor bmAttributes - HNP support flag
#define OTG_SRP_SUPPORT 0x01 // OTG Descriptor bmAttributes - SRP support flag
// Section: Endpoint Directions
#define USB_IN_EP 0x80 // IN endpoint mask
#define USB_OUT_EP 0x00 // OUT endpoint mask
// Section: Standard Device Requests
#define USB_REQUEST_GET_STATUS 0 // Standard Device Request - GET STATUS
#define USB_REQUEST_CLEAR_FEATURE 1 // Standard Device Request - CLEAR FEATURE
#define USB_REQUEST_SET_FEATURE 3 // Standard Device Request - SET FEATURE
#define USB_REQUEST_SET_ADDRESS 5 // Standard Device Request - SET ADDRESS
#define USB_REQUEST_GET_DESCRIPTOR 6 // Standard Device Request - GET DESCRIPTOR
#define USB_REQUEST_SET_DESCRIPTOR 7 // Standard Device Request - SET DESCRIPTOR
#define USB_REQUEST_GET_CONFIGURATION 8 // Standard Device Request - GET CONFIGURATION
#define USB_REQUEST_SET_CONFIGURATION 9 // Standard Device Request - SET CONFIGURATION
#define USB_REQUEST_GET_INTERFACE 10 // Standard Device Request - GET INTERFACE
#define USB_REQUEST_SET_INTERFACE 11 // Standard Device Request - SET INTERFACE
#define USB_REQUEST_SYNCH_FRAME 12 // Standard Device Request - SYNCH FRAME
#define USB_FEATURE_ENDPOINT_HALT 0 // CLEAR/SET FEATURE - Endpoint Halt
#define USB_FEATURE_DEVICE_REMOTE_WAKEUP 1 // CLEAR/SET FEATURE - Device remote wake-up
#define USB_FEATURE_TEST_MODE 2 // CLEAR/SET FEATURE - Test mode
// Section: Setup Data Constants
#define USB_SETUP_HOST_TO_DEVICE 0x00 // Device Request bmRequestType transfer direction - host to device transfer
#define USB_SETUP_DEVICE_TO_HOST 0x80 // Device Request bmRequestType transfer direction - device to host transfer
#define USB_SETUP_TYPE_STANDARD 0x00 // Device Request bmRequestType type - standard
#define USB_SETUP_TYPE_CLASS 0x20 // Device Request bmRequestType type - class
#define USB_SETUP_TYPE_VENDOR 0x40 // Device Request bmRequestType type - vendor
#define USB_SETUP_RECIPIENT_DEVICE 0x00 // Device Request bmRequestType recipient - device
#define USB_SETUP_RECIPIENT_INTERFACE 0x01 // Device Request bmRequestType recipient - interface
#define USB_SETUP_RECIPIENT_ENDPOINT 0x02 // Device Request bmRequestType recipient - endpoint
#define USB_SETUP_RECIPIENT_OTHER 0x03 // Device Request bmRequestType recipient - other
#define USB_SETUP_HOST_TO_DEVICE_BITFIELD (USB_SETUP_HOST_TO_DEVICE>>7) // Device Request bmRequestType transfer direction - host to device transfer - bit definition
#define USB_SETUP_DEVICE_TO_HOST_BITFIELD (USB_SETUP_DEVICE_TO_HOST>>7) // Device Request bmRequestType transfer direction - device to host transfer - bit definition
#define USB_SETUP_TYPE_STANDARD_BITFIELD (USB_SETUP_TYPE_STANDARD>>5) // Device Request bmRequestType type - standard
#define USB_SETUP_TYPE_CLASS_BITFIELD (USB_SETUP_TYPE_CLASS>>5) // Device Request bmRequestType type - class
#define USB_SETUP_TYPE_VENDOR_BITFIELD (USB_SETUP_TYPE_VENDOR>>5) // Device Request bmRequestType type - vendor
#define USB_SETUP_RECIPIENT_DEVICE_BITFIELD (USB_SETUP_RECIPIENT_DEVICE) // Device Request bmRequestType recipient - device
#define USB_SETUP_RECIPIENT_INTERFACE_BITFIELD (USB_SETUP_RECIPIENT_INTERFACE) // Device Request bmRequestType recipient - interface
#define USB_SETUP_RECIPIENT_ENDPOINT_BITFIELD (USB_SETUP_RECIPIENT_ENDPOINT) // Device Request bmRequestType recipient - endpoint
#define USB_SETUP_RECIPIENT_OTHER_BITFIELD (USB_SETUP_RECIPIENT_OTHER) // Device Request bmRequestType recipient - other
// Section: OTG SET FEATURE Constants
#define OTG_FEATURE_B_HNP_ENABLE 3 // SET FEATURE OTG - Enable B device to perform HNP
#define OTG_FEATURE_A_HNP_SUPPORT 4 // SET FEATURE OTG - A device supports HNP
#define OTG_FEATURE_A_ALT_HNP_SUPPORT 5 // SET FEATURE OTG - Another port on the A device supports HNP
// Section: USB Endpoint Transfer Types
#define USB_TRANSFER_TYPE_CONTROL 0x00 // Endpoint is a control endpoint.
#define USB_TRANSFER_TYPE_ISOCHRONOUS 0x01 // Endpoint is an isochronous endpoint.
#define USB_TRANSFER_TYPE_BULK 0x02 // Endpoint is a bulk endpoint.
#define USB_TRANSFER_TYPE_INTERRUPT 0x03 // Endpoint is an interrupt endpoint.
// Section: Standard Feature Selectors for CLEAR_FEATURE Requests
#define USB_FEATURE_ENDPOINT_STALL 0 // Endpoint recipient
#define USB_FEATURE_DEVICE_REMOTE_WAKEUP 1 // Device recipient
#define USB_FEATURE_TEST_MODE 2 // Device recipient
// Section: USB Class Code Definitions
#define USB_HUB_CLASSCODE 0x09 // Class code for a hub.
/********************************************************************
USB Endpoint Definitions
USB Standard EP Address Format: DIR:X:X:X:EP3:EP2:EP1:EP0
This is used in the descriptors.
********************************************************************/
#define _EP_IN 0x80
#define _EP_OUT 0x00
#define _EP01_OUT 0x01
#define _EP01_IN 0x81
#define _EP02_OUT 0x02
#define _EP02_IN 0x82
#define _EP03_OUT 0x03
#define _EP03_IN 0x83
#define _EP04_OUT 0x04
#define _EP04_IN 0x84
#define _EP05_OUT 0x05
#define _EP05_IN 0x85
#define _EP06_OUT 0x06
#define _EP06_IN 0x86
#define _EP07_OUT 0x07
#define _EP07_IN 0x87
#define _EP08_OUT 0x08
#define _EP08_IN 0x88
#define _EP09_OUT 0x09
#define _EP09_IN 0x89
#define _EP10_OUT 0x0A
#define _EP10_IN 0x8A
#define _EP11_OUT 0x0B
#define _EP11_IN 0x8B
#define _EP12_OUT 0x0C
#define _EP12_IN 0x8C
#define _EP13_OUT 0x0D
#define _EP13_IN 0x8D
#define _EP14_OUT 0x0E
#define _EP14_IN 0x8E
#define _EP15_OUT 0x0F
#define _EP15_IN 0x8F
/* Configuration Attributes */
#define _DEFAULT (0x01<<7) //Default Value (Bit 7 is set)
#define _SELF (0x01<<6) //Self-powered (Supports if set)
#define _RWU (0x01<<5) //Remote Wakeup (Supports if set)
#define _HNP (0x01 << 1) //HNP (Supports if set)
#define _SRP (0x01) //SRP (Supports if set)
/* Endpoint Transfer Type */
#define _CTRL 0x00 //Control Transfer
#define _ISO 0x01 //Isochronous Transfer
#define _BULK 0x02 //Bulk Transfer
#define _INTERRUPT 0x03 //Interrupt Transfer
#if defined(__18CXX) || defined(__C30__) || defined __XC16__ || defined(__XC8)
#define _INT 0x03 //Interrupt Transfer
#endif
/* Isochronous Endpoint Synchronization Type */
#define _NS (0x00<<2) //No Synchronization
#define _AS (0x01<<2) //Asynchronous
#define _AD (0x02<<2) //Adaptive
#define _SY (0x03<<2) //Synchronous
/* Isochronous Endpoint Usage Type */
#define _DE (0x00<<4) //Data endpoint
#define _FE (0x01<<4) //Feedback endpoint
#define _IE (0x02<<4) //Implicit feedback Data endpoint
//These are the directional indicators used for the USBTransferOnePacket()
// function.
#define OUT_FROM_HOST 0
#define IN_TO_HOST 1
#endif // _USB_CH9_H_
/*************************************************************************
* EOF
*/

474
inc/usb/usb_common.h Normal file
View File

@ -0,0 +1,474 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
/*******************************************************************************
Module for Microchip USB Library
Company:
Microchip Technology Inc.
File Name:
usb_common.h
Summary:
Defines types associated with both the USB host and USB device stacks but
not defined by the USB specification.
Description:
Defines types associated with both the USB host and USB device stacks but
not defined by the USB specification.
*******************************************************************************/
//DOM-IGNORE-BEGIN
#ifndef _USB_COMMON_H_
#define _USB_COMMON_H_
//DOM-IGNORE-END
#include <limits.h>
#include <stdbool.h>
#include <stdint.h>
// *****************************************************************************
// *****************************************************************************
// Section: USB Constants
// *****************************************************************************
// *****************************************************************************
// Section: Error Code Values
#define USB_SUCCESS 0x00 // USB operation successful.
#define USB_INVALID_STATE 0x01 // Operation cannot be performed in current state.
#define USB_BUSY 0x02 // A transaction is already in progress.
#define USB_ILLEGAL_REQUEST 0x03 // Cannot perform requested operation.
#define USB_INVALID_CONFIGURATION 0x04 // Configuration descriptor not found.
#define USB_MEMORY_ALLOCATION_ERROR 0x05 // Out of dynamic memory.
#define USB_UNKNOWN_DEVICE 0x06 // Device with specified address is not attached.
#define USB_CANNOT_ENUMERATE 0x07 // Cannot enumerate the attached device.
#define USB_EVENT_QUEUE_FULL 0x08 // Event queue was full when an event occured.
#define USB_ENDPOINT_BUSY 0x10 // Endpoint is currently processing a transaction.
#define USB_ENDPOINT_STALLED 0x11 // Endpoint is currently stalled. User must clear the condition.
#define USB_ENDPOINT_ERROR 0x12 // Will need more than this eventually
#define USB_ENDPOINT_ERROR_ILLEGAL_PID 0x13 // Illegal PID received.
#define USB_ENDPOINT_NOT_FOUND 0x14 // Requested endpoint does not exist on device.
#define USB_ENDPOINT_ILLEGAL_DIRECTION 0x15 // Reads must be performe on IN endpoints, writes on OUT endpoints.
//#define USB_ENDPOINT_TRANSACTION_IN_PROGRESS 0x16
#define USB_ENDPOINT_NAK_TIMEOUT 0x17 // Too many NAK's occurred while waiting for the current transaction.
#define USB_ENDPOINT_ILLEGAL_TYPE 0x18 // Transfer type must match endpoint description.
#define USB_ENDPOINT_UNRESOLVED_STATE 0x19 // Endpoint is in an unknown state after completing a transaction.
#define USB_ENDPOINT_ERROR_BIT_STUFF 0x20 // USB Module - Bit stuff error.
#define USB_ENDPOINT_ERROR_DMA 0x21 // USB Module - DMA error.
#define USB_ENDPOINT_ERROR_TIMEOUT 0x22 // USB Module - Bus timeout.
#define USB_ENDPOINT_ERROR_DATA_FIELD 0x23 // USB Module - Data field size error.
#define USB_ENDPOINT_ERROR_CRC16 0x24 // USB Module - CRC16 failure.
#define USB_ENDPOINT_ERROR_END_OF_FRAME 0x25 // USB Module - End of Frame error.
#define USB_ENDPOINT_ERROR_PID_CHECK 0x26 // USB Module - Illegal PID received.
#define USB_ENDPOINT_ERROR_BMX 0x27 // USB Module - Bus Matrix error.
#define USB_ERROR_INSUFFICIENT_POWER 0x28 // Too much power was requested
// Section: Return values for USBHostDeviceStatus()
#define USB_DEVICE_STATUS 0x30 // Offset for USBHostDeviceStatus() return codes
#define USB_DEVICE_ATTACHED (USB_DEVICE_STATUS | 0x30) // Device is attached and running
#define USB_DEVICE_DETACHED (USB_DEVICE_STATUS | 0x01) // No device is attached
#define USB_DEVICE_ENUMERATING (USB_DEVICE_STATUS | 0x02) // Device is enumerating
#define USB_HOLDING_OUT_OF_MEMORY (USB_DEVICE_STATUS | 0x03) // Not enough heap space available
#define USB_HOLDING_UNSUPPORTED_DEVICE (USB_DEVICE_STATUS | 0x04) // Invalid configuration or unsupported class
#define USB_HOLDING_UNSUPPORTED_HUB (USB_DEVICE_STATUS | 0x05) // Hubs are not supported
#define USB_HOLDING_INVALID_CONFIGURATION (USB_DEVICE_STATUS | 0x06) // Invalid configuration requested
#define USB_HOLDING_PROCESSING_CAPACITY (USB_DEVICE_STATUS | 0x07) // Processing requirement excessive
#define USB_HOLDING_POWER_REQUIREMENT (USB_DEVICE_STATUS | 0x08) // Power requirement excessive
#define USB_HOLDING_CLIENT_INIT_ERROR (USB_DEVICE_STATUS | 0x09) // Client driver failed to initialize
#define USB_DEVICE_SUSPENDED (USB_DEVICE_STATUS | 0x0A) // Device is suspended
#define USB_ERROR_CLASS_DEFINED 0x50 // Offset for application defined errors
#define USB_SINGLE_DEVICE_ADDRESS 0x01 // Default USB device address (single device support)
// *****************************************************************************
// *****************************************************************************
// Section: USB Data Types
// *****************************************************************************
// *****************************************************************************
// *****************************************************************************
/* Data Transfer Flags
The following flags are used in the flags parameter of the "USBDEVTransferData"
and "USBHALTransferData" routines. They can be accessed by the bitfield
definitions or the macros can be OR'd together to identify the endpoint number
and properties of the data transfer.
<code>
7 6 5 4 3 2 1 0 - Field name
| | | | \_____/
| | | | +----- ep_num - Endpoint number
| | | +---------- zero_pkt - End transfer with short or zero-sized packet
| | +------------ dts - 0=DATA0 packet, 1=DATA1 packet
| +-------------- force_dts - Force data toggle sync to match dts field
+---------------- direction - Transfer direction: 0=Receive, 1=Transmit
</code>
*/
typedef union
{
uint8_t bitmap;
struct
{
uint8_t ep_num: 4;
uint8_t zero_pkt: 1;
uint8_t dts: 1;
uint8_t force_dts: 1;
uint8_t direction: 1;
}field;
} TRANSFER_FLAGS;
// *****************************************************************************
/* Data Transfer Flags, Endpoint Number Constants
These macros can be used as values for the "ep_num" field of the TRANSFER_FLAGS
data type.
*/
#define USB_EP0 0 //
#define USB_EP1 1 //
#define USB_EP2 2 //
#define USB_EP3 3 //
#define USB_EP4 4 //
#define USB_EP5 5 //
#define USB_EP6 6 //
#define USB_EP7 7 //
#define USB_EP8 8 //
#define USB_EP9 9 //
#define USB_EP10 10 //
#define USB_EP11 11 //
#define USB_EP12 12 //
#define USB_EP13 13 //
#define USB_EP14 14 //
#define USB_EP15 15 //
// *****************************************************************************
/* Data Transfer Flags, Bitmap Constants
These macros can be used as values for the "bitmap" field of the TRANSFER_FLAGS
data type.
*/
#define USB_TRANSMIT 0x80 // Data will be transmitted to the USB
#define USB_RECEIVE 0x00 // Data will be received from the USB
#define USB_FORCE_DTS 0x40 // Forces data toggle sync as below:
#define USB_DTS_MASK 0x20 // Mask for DTS bit (below)
#define USB_ZERO_PKT 0x10 // End transfer w/a short or zero-length packet
#define USB_DATA0 0x00|USB_FORCE_DTS // Force DATA0
#define USB_DATA1 0x20|USB_FORCE_DTS // Force DATA1
#define USB_SETUP_PKT USB_RECEIVE|USB_DATA0|USB_EP0 // Setup Packet
#define USB_SETUP_DATA USB_DATA1|USB_ZERO_PKT|USB_EP0 // Setup-transfer Data Packet
#define USB_SETUP_STATUS USB_DATA1|USB_EP0 // Setup-transfer Status Packet
#define USB_EP_NUM_MASK 0x0F // Endpoint number (ep_num) mask
// *****************************************************************************
/* Data Transfer Flags, Initialization Macro
This macro can be used with the above bitmap constants to initialize a
TRANSFER_FLAGS value. It provides the correct data type to avoid compiler
warnings.
*/
#define XFLAGS(f) ((TRANSFER_FLAGS)((uint8_t)(f))) // Initialization Macro
// *****************************************************************************
/* USB Events
This enumeration identifies USB events that occur. It is used to
inform USB drivers and applications of events on the bus. It is passed
as a parameter to the event-handling routine, which must match the
prototype of the USB_CLIENT_EVENT_HANDLER data type, when an event occurs.
*/
typedef enum
{
// No event occured (NULL event)
EVENT_NONE = 0,
EVENT_DEVICE_STACK_BASE = 1,
EVENT_HOST_STACK_BASE = 100,
// A USB hub has been attached. Hub support is not currently available.
EVENT_HUB_ATTACH,
// A stall has occurred. This event is not used by the Host stack.
EVENT_STALL,
// VBus SRP Pulse, (VBus > 2.0v), Data: uint8_t Port Number (For future support)
EVENT_VBUS_SES_REQUEST,
// The voltage on Vbus has dropped below 4.4V/4.7V. The application is
// responsible for monitoring Vbus and calling USBHostVbusEvent() with this
// event. This event is not generated by the stack.
EVENT_VBUS_OVERCURRENT,
// An enumerating device is requesting power. The data associated with this
// event is of the data type USB_VBUS_POWER_EVENT_DATA. Note that
// the requested current is specified in 2mA units, identical to the power
// specification in a device's Configuration Descriptor.
EVENT_VBUS_REQUEST_POWER,
// Release power from a detaching device. The data associated with this
// event is of the data type USB_VBUS_POWER_EVENT_DATA. The current value
// specified in the data can be ignored.
EVENT_VBUS_RELEASE_POWER,
// The voltage on Vbus is good, and the USB OTG module can be powered on.
// The application is responsible for monitoring Vbus and calling
// USBHostVbusEvent() with this event. This event is not generated by the
// stack. If the application issues an EVENT_VBUS_OVERCURRENT, then no
// power will be applied to that port, and no device can attach to that
// port, until the application issues the EVENT_VBUS_POWER_AVAILABLE for
// the port.
EVENT_VBUS_POWER_AVAILABLE,
// The attached device is not supported by the application. The attached
// device is not allowed to enumerate.
EVENT_UNSUPPORTED_DEVICE,
// Cannot enumerate the attached device. This is generated if communication
// errors prevent the device from enumerating.
EVENT_CANNOT_ENUMERATE,
// The client driver cannot initialize the the attached device. The
// attached is not allowed to enumerate.
EVENT_CLIENT_INIT_ERROR,
// The Host stack does not have enough heap space to enumerate the device.
// Check the amount of heap space allocated to the application. In MPLAB,
// select Project> Build Options...> Project. Select the appropriate
// linker tab, and inspect the "Heap size" entry.
EVENT_OUT_OF_MEMORY,
// Unspecified host error. (This error should not occur).
EVENT_UNSPECIFIED_ERROR,
// USB cable has been detached. The data associated with this event is the
// address of detached device, a single uint8_t.
EVENT_DETACH,
// A USB transfer has completed. The data associated with this event is of
// the data type HOST_TRANSFER_DATA if the event is generated from the host
// stack.
EVENT_TRANSFER,
// A USB Start of Frame token has been received. This event is not
// used by the Host stack.
EVENT_SOF,
// Device-mode resume received. This event is not used by the Host stack.
EVENT_RESUME,
// Device-mode suspend/idle event received. This event is not used by the
// Host stack.
EVENT_SUSPEND,
// Device-mode bus reset received. This event is not used by the Host
// stack.
EVENT_RESET,
// In Host mode, an isochronous data read has completed. This event will only
// be passed to the DataEventHandler, which is only utilized if it is defined.
// Note that the DataEventHandler is called from within the USB interrupt, so
// it is critical that it return in time for the next isochronous data packet.
EVENT_DATA_ISOC_READ,
// In Host mode, an isochronous data write has completed. This event will only
// be passed to the DataEventHandler, which is only utilized if it is defined.
// Note that the DataEventHandler is called from within the USB interrupt, so
// it is critical that it return in time for the next isochronous data packet.
EVENT_DATA_ISOC_WRITE,
// In Host mode, this event gives the application layer the option to reject
// a client driver that was selected by the stack. This is needed when multiple
// devices are supported by class level support, but one configuration and client
// driver is preferred over another. Since configuration number is not guaranteed,
// the stack cannot do this automatically. This event is issued only when
// looking through configuration descriptors; the driver selected at the device
// level cannot be overridden, since there shouldn't be any other options to
// choose from.
EVENT_OVERRIDE_CLIENT_DRIVER_SELECTION,
// In host mode, this event is thrown for every millisecond that passes. Like all
// events, this is thrown from the USBHostTasks() or USBTasks() routine so its
// timeliness will be determined by the rate that these functions are called. If
// they are not called very often, then the 1ms events will build up and be
// dispatched as the USBTasks() or USBHostTasks() functions are called (one event
// per call to these functions.
EVENT_1MS,
// In device mode, this event is thrown when we receive a Set Interface request from
// the host. The stack will automatically handle the interface switch, but the app
// may need to know about the interface switch for performing tasks such as powering
// up/down audio hardware.
EVENT_ALT_INTERFACE,
// If the application layer must do things to the device before the device is
// configured, they should be done at this point. The application layer should
// return true to hold the USB state machine at this point, while any USB or other
// processing continues. When the USB state machine can safely proceed, the application
// layer should return FALSE.
EVENT_HOLD_BEFORE_CONFIGURATION,
// Class-defined event offsets start here:
EVENT_GENERIC_BASE = 400, // Offset for Generic class events
EVENT_MSD_BASE = 500, // Offset for Mass Storage Device class events
EVENT_HID_BASE = 600, // Offset for Human Interface Device class events
EVENT_PRINTER_BASE = 700, // Offset for Printer class events
EVENT_CDC_BASE = 800, // Offset for CDC class events
EVENT_CHARGER_BASE = 900, // Offset for Charger client driver events.
EVENT_AUDIO_BASE = 1000, // Offset for Audio client driver events.
EVENT_USER_BASE = 10000, // Add integral values to this event number
// to create user-defined events.
// There was a transfer error on the USB. The data associated with this
// event is of data type HOST_TRANSFER_DATA.
EVENT_BUS_ERROR = INT_MAX
} USB_EVENT;
// *****************************************************************************
/* EVENT_TRANSFER Data
This data structure is passed to the appropriate layer's
USB_EVENT_HANDLER when an EVT_XFER event has occurred, indicating
that a transfer has completed on the USB. It provides the endpoint,
direction, and actual size of the transfer.
*/
typedef struct _transfer_event_data
{
TRANSFER_FLAGS flags; // Transfer flags (see above)
uint32_t size; // Actual number of bytes transferred
uint8_t pid; // Packet ID
} USB_TRANSFER_EVENT_DATA;
// *****************************************************************************
/* EVENT_VBUS_REQUEST_POWER and EVENT_VBUS_RELEASE_POWER Data
This data structure is passed to the appropriate layer's
USB_EVENT_HANDLER when an EVENT_VBUS_REQUEST_POWER or EVENT_VBUS_RELEASE_POWER
event has occurred, indicating that a change in Vbus power is being requested.
*/
typedef struct _vbus_power_data
{
uint8_t port; // Physical port number
uint8_t current; // Current in 2mA units
} USB_VBUS_POWER_EVENT_DATA;
// *****************************************************************************
/* USB_OVERRIDE_CLIENT_DRIVER_EVENT_DATA Data
This data structure is passed to the application layer when a client driver is
select, in case multiple client drivers can support a particular device.
*/
typedef struct _override_client_driver_data
{
uint16_t idVendor;
uint16_t idProduct;
uint8_t bDeviceClass;
uint8_t bDeviceSubClass;
uint8_t bDeviceProtocol;
} USB_OVERRIDE_CLIENT_DRIVER_EVENT_DATA;
// *****************************************************************************
/* EVT_STALL Data
The EVT_STALL event has a 16-bit data value associated with it where
a bit is set in the position for each endpoint that is currently
stalled (ie. bit 0 = EP0, bit 1 = EP1, etc.)
*/
// *****************************************************************************
// *****************************************************************************
// Section: Event Handling Routines
// *****************************************************************************
// *****************************************************************************
/*******************************************************************************
Function:
bool <Event-handling Function Name> ( USB_EVENT event,
void *data, unsigned int size )
Description:
This routine is a "call out" routine that must be implemented by
any layer of the USB SW Stack (except the HAL which is at the
root of the event-call tree that needs to receive events. When
an event occurs, the HAL calls the next higher layer in the
stack to handle the event. Each layer either handles the event
or calls the layer above it to handle the event. Events are
identified by the "event" parameter and may have associated
data. If the higher layer was able to handle the event, it
should return true. If not, it should return false.
Preconditions:
USBInitialize must have been called to initialize the USB SW
Stack.
Parameters:
USB_EVENT event - Identifies the bus event that occurred
void *data - Pointer to event-specific data
unsigned int size - Size of the event-specific data
Return Values:
None
Remarks:
The function is name is defined by the layer that implements
it. A pointer to the function will be placed by into a table
that the lower-layer will use to call it. This requires the
function to use a specific call "signature" (return data type
and values and data parameter types and values).
*******************************************************************************/
typedef bool (*USB_EVENT_HANDLER) ( USB_EVENT event, void *data, unsigned int size );
#define USB_PING_PONG__NO_PING_PONG 0x00 //0b00
#define USB_PING_PONG__EP0_OUT_ONLY 0x01 //0b01
#define USB_PING_PONG__FULL_PING_PONG 0x02 //0b10
#define USB_PING_PONG__ALL_BUT_EP0 0x03 //0b11
#endif // _USB_COMMON_H_
/*************************************************************************
* EOF
*/

174
inc/usb/usb_config.h Normal file
View File

@ -0,0 +1,174 @@
/*******************************************************************************
Copyright 2016 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
/*********************************************************************
* Descriptor specific type definitions are defined in: usbd.h
********************************************************************/
#ifndef USBCFG_H
#define USBCFG_H
#include <usb_ch9.h>
/** DEFINITIONS ****************************************************/
#define USB_EP0_BUFF_SIZE 8 // Valid Options: 8, 16, 32, or 64 bytes.
// Using larger options take more SRAM, but
// does not provide much advantage in most types
// of applications. Exceptions to this, are applications
// that use EP0 IN or OUT for sending large amounts of
// application related data.
#define USB_MAX_NUM_INT 1 //Set this number to match the maximum interface number used in the descriptors for this firmware project
#define USB_MAX_EP_NUMBER 1 //Set this number to match the maximum endpoint number used in the descriptors for this firmware project
//Device descriptor - if these two definitions are not defined then
// a const USB_DEVICE_DESCRIPTOR variable by the exact name of device_dsc
// must exist.
#define USB_USER_DEVICE_DESCRIPTOR &device_dsc
#define USB_USER_DEVICE_DESCRIPTOR_INCLUDE extern const USB_DEVICE_DESCRIPTOR device_dsc
//Configuration descriptors - if these two definitions do not exist then
// a const BYTE *const variable named exactly USB_CD_Ptr[] must exist.
#define USB_USER_CONFIG_DESCRIPTOR USB_CD_Ptr
#define USB_USER_CONFIG_DESCRIPTOR_INCLUDE extern const uint8_t *const USB_CD_Ptr[]
//------------------------------------------------------------------------------
//Select an endpoint ping-pong bufferring mode. Some microcontrollers only
//support certain modes. For most applications, it is recommended to use either
//the USB_PING_PONG__FULL_PING_PONG or USB_PING_PONG__EP0_OUT_ONLY options.
//The other settings are supported on some devices, but they are not
//recommended, as they offer inferior control transfer timing performance.
//See inline code comments in usb_device.c for additional details.
//Enabling ping pong bufferring on an endpoint generally increases firmware
//overhead somewhat, but when both buffers are used simultaneously in the
//firmware, can offer better sustained bandwidth, especially for OUT endpoints.
//------------------------------------------------------
//#define USB_PING_PONG_MODE USB_PING_PONG__NO_PING_PONG //Not recommended
#define USB_PING_PONG_MODE USB_PING_PONG__FULL_PING_PONG //A good all around setting
//#define USB_PING_PONG_MODE USB_PING_PONG__EP0_OUT_ONLY //Another good setting
//#define USB_PING_PONG_MODE USB_PING_PONG__ALL_BUT_EP0 //Not recommended
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
//Select a USB stack operating mode. In the USB_INTERRUPT mode, the USB stack
//main task handler gets called only when necessary as an interrupt handler.
//This can potentially minimize CPU utilization, but adds context saving
//and restoring overhead associated with interrupts, which can potentially
//decrease performance.
//When the USB_POLLING mode is selected, the USB stack main task handler
//(ex: USBDeviceTasks()) must be called periodically by the application firmware
//at a minimum rate as described in the inline code comments in usb_device.c.
//------------------------------------------------------
#define USB_POLLING
//#define USB_INTERRUPT
//------------------------------------------------------------------------------
/* Parameter definitions are defined in usb_device.h */
#define USB_PULLUP_OPTION USB_PULLUP_ENABLE
//#define USB_PULLUP_OPTION USB_PULLUP_DISABLED
#define USB_TRANSCEIVER_OPTION USB_INTERNAL_TRANSCEIVER
//External Transceiver support is not available on all product families. Please
// refer to the product family datasheet for more information if this feature
// is available on the target processor.
//#define USB_TRANSCEIVER_OPTION USB_EXTERNAL_TRANSCEIVER
#define USB_SPEED_OPTION USB_FULL_SPEED
//#define USB_SPEED_OPTION USB_LOW_SPEED //(this mode is only supported on some microcontrollers)
//------------------------------------------------------------------------------------------------------------------
//Option to enable auto-arming of the status stage of control transfers, if no
//"progress" has been made for the USB_STATUS_STAGE_TIMEOUT value.
//If progress is made (any successful transactions completing on EP0 IN or OUT)
//the timeout counter gets reset to the USB_STATUS_STAGE_TIMEOUT value.
//
//During normal control transfer processing, the USB stack or the application
//firmware will call USBCtrlEPAllowStatusStage() as soon as the firmware is finished
//processing the control transfer. Therefore, the status stage completes as
//quickly as is physically possible. The USB_ENABLE_STATUS_STAGE_TIMEOUTS
//feature, and the USB_STATUS_STAGE_TIMEOUT value are only relevant, when:
//1. The application uses the USBDeferStatusStage() API function, but never calls
// USBCtrlEPAllowStatusStage(). Or:
//2. The application uses host to device (OUT) control transfers with data stage,
// and some abnormal error occurs, where the host might try to abort the control
// transfer, before it has sent all of the data it claimed it was going to send.
//
//If the application firmware never uses the USBDeferStatusStage() API function,
//and it never uses host to device control transfers with data stage, then
//it is not required to enable the USB_ENABLE_STATUS_STAGE_TIMEOUTS feature.
#define USB_ENABLE_STATUS_STAGE_TIMEOUTS //Comment this out to disable this feature.
//Section 9.2.6 of the USB 2.0 specifications indicate that:
//1. Control transfers with no data stage: Status stage must complete within
// 50ms of the start of the control transfer.
//2. Control transfers with (IN) data stage: Status stage must complete within
// 50ms of sending the last IN data packet in fullfilment of the data stage.
//3. Control transfers with (OUT) data stage: No specific status stage timing
// requirement. However, the total time of the entire control transfer (ex:
// including the OUT data stage and IN status stage) must not exceed 5 seconds.
//
//Therefore, if the USB_ENABLE_STATUS_STAGE_TIMEOUTS feature is used, it is suggested
//to set the USB_STATUS_STAGE_TIMEOUT value to timeout in less than 50ms. If the
//USB_ENABLE_STATUS_STAGE_TIMEOUTS feature is not enabled, then the USB_STATUS_STAGE_TIMEOUT
//parameter is not relevant.
#define USB_STATUS_STAGE_TIMEOUT (uint8_t)45 //Approximate timeout in milliseconds, except when
//USB_POLLING mode is used, and USBDeviceTasks() is called at < 1kHz
//In this special case, the timeout becomes approximately:
//Timeout(in milliseconds) = ((1000 * (USB_STATUS_STAGE_TIMEOUT - 1)) / (USBDeviceTasks() polling frequency in Hz))
//------------------------------------------------------------------------------------------------------------------
#define USB_SUPPORT_DEVICE
#define USB_NUM_STRING_DESCRIPTORS 3 //Set this number to match the total number of string descriptors that are implemented in the usb_descriptors.c file
/*******************************************************************
* Event disable options
* Enable a definition to suppress a specific event. By default
* all events are sent.
*******************************************************************/
//#define USB_DISABLE_SUSPEND_HANDLER
//#define USB_DISABLE_WAKEUP_FROM_SUSPEND_HANDLER
//#define USB_DISABLE_SOF_HANDLER
//#define USB_DISABLE_TRANSFER_TERMINATED_HANDLER
//#define USB_DISABLE_ERROR_HANDLER
//#define USB_DISABLE_NONSTANDARD_EP0_REQUEST_HANDLER
//#define USB_DISABLE_SET_DESCRIPTOR_HANDLER
//#define USB_DISABLE_SET_CONFIGURATION_HANDLER
//#define USB_DISABLE_TRANSFER_COMPLETE_HANDLER
/** DEVICE CLASS USAGE *********************************************/
#define USB_USE_HID
/** ENDPOINTS ALLOCATION *******************************************/
/* HID */
#define HID_INTF_ID 0x00
#define JOYSTICK_EP 1
#define HID_INT_OUT_EP_SIZE 64
#define HID_INT_IN_EP_SIZE 64
#define HID_NUM_OF_DSC 1
#define HID_RPT01_SIZE 49
/** DEFINITIONS ****************************************************/
#endif //USBCFG_H

2054
inc/usb/usb_device.h Normal file

File diff suppressed because it is too large Load Diff

307
inc/usb/usb_device_hid.h Normal file
View File

@ -0,0 +1,307 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
#ifndef HID_H
#define HID_H
/** INCLUDES *******************************************************/
#include "usb_ch9.h"
/** DEFINITIONS ****************************************************/
/* Class-Specific Requests */
#define GET_REPORT 0x01
#define GET_IDLE 0x02
#define GET_PROTOCOL 0x03
#define SET_REPORT 0x09
#define SET_IDLE 0x0A
#define SET_PROTOCOL 0x0B
/* Class Descriptor Types */
#define DSC_HID 0x21
#define DSC_RPT 0x22
#define DSC_PHY 0x23
/* Protocol Selection */
#define BOOT_PROTOCOL 0x00
#define RPT_PROTOCOL 0x01
/* HID Interface Class Code */
#define HID_INTF 0x03
/* HID Interface Class SubClass Codes */
#define BOOT_INTF_SUBCLASS 0x01
/* HID Interface Class Protocol Codes */
#define HID_PROTOCOL_NONE 0x00
#define HID_PROTOCOL_KEYBOARD 0x01
#define HID_PROTOCOL_MOUSE 0x02
/********************************************************************
Function:
void USBCheckHIDRequest(void)
Summary:
This routine handles HID specific request that happen on EP0.
This function should be called from the USBCBCheckOtherReq() call back
function whenever implementing a HID device.
Description:
This routine handles HID specific request that happen on EP0. These
include, but are not limited to, requests for the HID report
descriptors. This function should be called from the
USBCBCheckOtherReq() call back function whenever using an HID device.
Typical Usage:
<code>
void USBCBCheckOtherReq(void)
{
//Since the stack didn't handle the request I need to check
// my class drivers to see if it is for them
USBCheckHIDRequest();
}
</code>
PreCondition:
None
Parameters:
None
Return Values:
None
Remarks:
None
*******************************************************************/
void USBCheckHIDRequest(void);
/********************************************************************
Function:
bool HIDTxHandleBusy(USB_HANDLE handle)
Summary:
Retrieves the status of the buffer ownership
Description:
Retrieves the status of the buffer ownership. This function will
indicate if the previous transfer is complete or not.
This function will take the input handle (pointer to a BDT entry) and
will check the UOWN bit. If the UOWN bit is set then that indicates
that the transfer is not complete and the USB module still owns the data
memory. If the UOWN bit is clear that means that the transfer is
complete and that the CPU now owns the data memory.
For more information about the BDT, please refer to the appropriate
datasheet for the device in use.
Typical Usage:
<code>
//make sure that the last transfer isn't busy by checking the handle
if(!HIDTxHandleBusy(USBInHandle))
{
//Send the data contained in the ToSendDataBuffer[] array out on
// endpoint HID_EP
USBInHandle = HIDTxPacket(HID_EP,(uint8_t*)&ToSendDataBuffer[0],sizeof(ToSendDataBuffer));
}
</code>
PreCondition:
None.
Parameters:
USB_HANDLE handle - the handle for the transfer in question.
The handle is returned by the HIDTxPacket() and HIDRxPacket()
functions. Please insure that USB_HANDLE objects are initialized
to NULL.
Return Values:
TRUE - the HID handle is still busy
FALSE - the HID handle is not busy and is ready to send
additional data.
Remarks:
None
*******************************************************************/
#define HIDTxHandleBusy(handle) USBHandleBusy(handle)
/********************************************************************
Function:
bool HIDRxHandleBusy(USB_HANDLE handle)
Summary:
Retrieves the status of the buffer ownership
Description:
Retrieves the status of the buffer ownership. This function will
indicate if the previous transfer is complete or not.
This function will take the input handle (pointer to a BDT entry) and
will check the UOWN bit. If the UOWN bit is set then that indicates
that the transfer is not complete and the USB module still owns the data
memory. If the UOWN bit is clear that means that the transfer is
complete and that the CPU now owns the data memory.
For more information about the BDT, please refer to the appropriate
datasheet for the device in use.
Typical Usage:
<code>
if(!HIDRxHandleBusy(USBOutHandle))
{
//The data is available in the buffer that was specified when the
// HIDRxPacket() was called.
}
</code>
PreCondition:
None
Parameters:
USB_HANDLE handle - the handle for the transfer in question.
The handle is returned by the HIDTxPacket() and HIDRxPacket()
functions. Please insure that USB_HANDLE objects are initialized
to NULL.
Return Values:
TRUE - the HID handle is still busy
FALSE - the HID handle is not busy and is ready to receive
additional data.
Remarks:
None
*******************************************************************/
#define HIDRxHandleBusy(handle) USBHandleBusy(handle)
/********************************************************************
Function:
USB_HANDLE HIDTxPacket(uint8_t ep, uint8_t* data, uint16_t len)
Summary:
Sends the specified data out the specified endpoint
Description:
This function sends the specified data out the specified
endpoint and returns a handle to the transfer information.
Typical Usage:
<code>
//make sure that the last transfer isn't busy by checking the handle
if(!HIDTxHandleBusy(USBInHandle))
{
//Send the data contained in the ToSendDataBuffer[] array out on
// endpoint HID_EP
USBInHandle = HIDTxPacket(HID_EP,(uint8_t*)&ToSendDataBuffer[0],sizeof(ToSendDataBuffer));
}
</code>
PreCondition:
None
Parameters:
uint8_t ep - the endpoint you want to send the data out of
uint8_t* data - pointer to the data that you wish to send
uint16_t len - the length of the data that you wish to send
Return Values:
USB_HANDLE - a handle for the transfer. This information
should be kept to track the status of the transfer
Remarks:
None
*******************************************************************/
#define HIDTxPacket USBTxOnePacket
/********************************************************************
Function:
USB_HANDLE HIDRxPacket(uint8_t ep, uint8_t* data, uint16_t len)
Summary:
Receives the specified data out the specified endpoint
Description:
Receives the specified data out the specified endpoint.
Typical Usage:
<code>
//Read 64-uint8_ts from endpoint HID_EP, into the ReceivedDataBuffer array.
// Make sure to save the return handle so that we can check it later
// to determine when the transfer is complete.
USBOutHandle = HIDRxPacket(HID_EP,(uint8_t*)&ReceivedDataBuffer,64);
</code>
PreCondition:
None
Parameters:
uint8_t ep - the endpoint you want to receive the data into
uint8_t* data - pointer to where the data will go when it arrives
uint16_t len - the length of the data that you wish to receive
Return Values:
USB_HANDLE - a handle for the transfer. This information
should be kept to track the status of the transfer
Remarks:
None
*******************************************************************/
#define HIDRxPacket USBRxOnePacket
// Section: STRUCTURES *********************************************/
//USB HID Descriptor header as detailed in section
//"6.2.1 HID Descriptor" of the HID class definition specification
typedef struct _USB_HID_DSC_HEADER
{
uint8_t bDescriptorType; //offset 9
uint16_t wDscLength; //offset 10
} USB_HID_DSC_HEADER;
//USB HID Descriptor header as detailed in section
//"6.2.1 HID Descriptor" of the HID class definition specification
typedef struct _USB_HID_DSC
{
uint8_t bLength; //offset 0
uint8_t bDescriptorType; //offset 1
uint16_t bcdHID; //offset 2
uint8_t bCountryCode; //offset 4
uint8_t bNumDsc; //offset 5
//USB_HID_DSC_HEADER hid_dsc_header[HID_NUM_OF_DSC];
/* HID_NUM_OF_DSC is defined in usbcfg.h */
} USB_HID_DSC;
/** Section: EXTERNS ********************************************************/
extern volatile CTRL_TRF_SETUP SetupPkt;
extern const uint8_t configDescriptor1[];
extern volatile uint8_t CtrlTrfData[USB_EP0_BUFF_SIZE];
#endif //HID_H

424
inc/usb/usb_device_local.h Normal file
View File

@ -0,0 +1,424 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
#include "usb_config.h"
/* Short Packet States - Used by Control Transfer Read - CTRL_TRF_TX */
#define SHORT_PKT_NOT_USED 0
#define SHORT_PKT_PENDING 1
#define SHORT_PKT_SENT 2
/* Control Transfer States */
#define WAIT_SETUP 0
#define CTRL_TRF_TX 1
#define CTRL_TRF_RX 2
typedef union
{
struct
{
unsigned char ping_pong_state :1;
unsigned char transfer_terminated :1;
} bits;
uint8_t Val;
} EP_STATUS;
#if (USB_PING_PONG_MODE == USB_PING_PONG__NO_PING_PONG)
#define USB_NEXT_EP0_OUT_PING_PONG 0x0000 // Used in USB Device Mode only
#define USB_NEXT_EP0_IN_PING_PONG 0x0000 // Used in USB Device Mode only
#define USB_NEXT_PING_PONG 0x0000 // Used in USB Device Mode only
#define EP0_OUT_EVEN 0 // Used in USB Device Mode only
#define EP0_OUT_ODD 0 // Used in USB Device Mode only
#define EP0_IN_EVEN 1 // Used in USB Device Mode only
#define EP0_IN_ODD 1 // Used in USB Device Mode only
#define EP1_OUT_EVEN 2 // Used in USB Device Mode only
#define EP1_OUT_ODD 2 // Used in USB Device Mode only
#define EP1_IN_EVEN 3 // Used in USB Device Mode only
#define EP1_IN_ODD 3 // Used in USB Device Mode only
#define EP2_OUT_EVEN 4 // Used in USB Device Mode only
#define EP2_OUT_ODD 4 // Used in USB Device Mode only
#define EP2_IN_EVEN 5 // Used in USB Device Mode only
#define EP2_IN_ODD 5 // Used in USB Device Mode only
#define EP3_OUT_EVEN 6 // Used in USB Device Mode only
#define EP3_OUT_ODD 6 // Used in USB Device Mode only
#define EP3_IN_EVEN 7 // Used in USB Device Mode only
#define EP3_IN_ODD 7 // Used in USB Device Mode only
#define EP4_OUT_EVEN 8 // Used in USB Device Mode only
#define EP4_OUT_ODD 8 // Used in USB Device Mode only
#define EP4_IN_EVEN 9 // Used in USB Device Mode only
#define EP4_IN_ODD 9 // Used in USB Device Mode only
#define EP5_OUT_EVEN 10 // Used in USB Device Mode only
#define EP5_OUT_ODD 10 // Used in USB Device Mode only
#define EP5_IN_EVEN 11 // Used in USB Device Mode only
#define EP5_IN_ODD 11 // Used in USB Device Mode only
#define EP6_OUT_EVEN 12 // Used in USB Device Mode only
#define EP6_OUT_ODD 12 // Used in USB Device Mode only
#define EP6_IN_EVEN 13 // Used in USB Device Mode only
#define EP6_IN_ODD 13 // Used in USB Device Mode only
#define EP7_OUT_EVEN 14 // Used in USB Device Mode only
#define EP7_OUT_ODD 14 // Used in USB Device Mode only
#define EP7_IN_EVEN 15 // Used in USB Device Mode only
#define EP7_IN_ODD 15 // Used in USB Device Mode only
#define EP8_OUT_EVEN 16 // Used in USB Device Mode only
#define EP8_OUT_ODD 16 // Used in USB Device Mode only
#define EP8_IN_EVEN 17 // Used in USB Device Mode only
#define EP8_IN_ODD 17 // Used in USB Device Mode only
#define EP9_OUT_EVEN 18 // Used in USB Device Mode only
#define EP9_OUT_ODD 18 // Used in USB Device Mode only
#define EP9_IN_EVEN 19 // Used in USB Device Mode only
#define EP9_IN_ODD 19 // Used in USB Device Mode only
#define EP10_OUT_EVEN 20 // Used in USB Device Mode only
#define EP10_OUT_ODD 20 // Used in USB Device Mode only
#define EP10_IN_EVEN 21 // Used in USB Device Mode only
#define EP10_IN_ODD 21 // Used in USB Device Mode only
#define EP11_OUT_EVEN 22 // Used in USB Device Mode only
#define EP11_OUT_ODD 22 // Used in USB Device Mode only
#define EP11_IN_EVEN 23 // Used in USB Device Mode only
#define EP11_IN_ODD 23 // Used in USB Device Mode only
#define EP12_OUT_EVEN 24 // Used in USB Device Mode only
#define EP12_OUT_ODD 24 // Used in USB Device Mode only
#define EP12_IN_EVEN 25 // Used in USB Device Mode only
#define EP12_IN_ODD 25 // Used in USB Device Mode only
#define EP13_OUT_EVEN 26 // Used in USB Device Mode only
#define EP13_OUT_ODD 26 // Used in USB Device Mode only
#define EP13_IN_EVEN 27 // Used in USB Device Mode only
#define EP13_IN_ODD 27 // Used in USB Device Mode only
#define EP14_OUT_EVEN 28 // Used in USB Device Mode only
#define EP14_OUT_ODD 28 // Used in USB Device Mode only
#define EP14_IN_EVEN 29 // Used in USB Device Mode only
#define EP14_IN_ODD 29 // Used in USB Device Mode only
#define EP15_OUT_EVEN 30 // Used in USB Device Mode only
#define EP15_OUT_ODD 30 // Used in USB Device Mode only
#define EP15_IN_EVEN 31 // Used in USB Device Mode only
#define EP15_IN_ODD 31 // Used in USB Device Mode only
#define EP(ep,dir,pp) (2*ep+dir) // Used in USB Device Mode only
#define BD(ep,dir,pp) ((8 * ep) + (4 * dir)) // Used in USB Device Mode only
#elif (USB_PING_PONG_MODE == USB_PING_PONG__EP0_OUT_ONLY)
#define USB_NEXT_EP0_OUT_PING_PONG 0x0004
#define USB_NEXT_EP0_IN_PING_PONG 0x0000
#define USB_NEXT_PING_PONG 0x0000
#define EP0_OUT_EVEN 0
#define EP0_OUT_ODD 1
#define EP0_IN_EVEN 2
#define EP0_IN_ODD 2
#define EP1_OUT_EVEN 3
#define EP1_OUT_ODD 3
#define EP1_IN_EVEN 4
#define EP1_IN_ODD 4
#define EP2_OUT_EVEN 5
#define EP2_OUT_ODD 5
#define EP2_IN_EVEN 6
#define EP2_IN_ODD 6
#define EP3_OUT_EVEN 7
#define EP3_OUT_ODD 7
#define EP3_IN_EVEN 8
#define EP3_IN_ODD 8
#define EP4_OUT_EVEN 9
#define EP4_OUT_ODD 9
#define EP4_IN_EVEN 10
#define EP4_IN_ODD 10
#define EP5_OUT_EVEN 11
#define EP5_OUT_ODD 11
#define EP5_IN_EVEN 12
#define EP5_IN_ODD 12
#define EP6_OUT_EVEN 13
#define EP6_OUT_ODD 13
#define EP6_IN_EVEN 14
#define EP6_IN_ODD 14
#define EP7_OUT_EVEN 15
#define EP7_OUT_ODD 15
#define EP7_IN_EVEN 16
#define EP7_IN_ODD 16
#define EP8_OUT_EVEN 17
#define EP8_OUT_ODD 17
#define EP8_IN_EVEN 18
#define EP8_IN_ODD 18
#define EP9_OUT_EVEN 19
#define EP9_OUT_ODD 19
#define EP9_IN_EVEN 20
#define EP9_IN_ODD 20
#define EP10_OUT_EVEN 21
#define EP10_OUT_ODD 21
#define EP10_IN_EVEN 22
#define EP10_IN_ODD 22
#define EP11_OUT_EVEN 23
#define EP11_OUT_ODD 23
#define EP11_IN_EVEN 24
#define EP11_IN_ODD 24
#define EP12_OUT_EVEN 25
#define EP12_OUT_ODD 25
#define EP12_IN_EVEN 26
#define EP12_IN_ODD 26
#define EP13_OUT_EVEN 27
#define EP13_OUT_ODD 27
#define EP13_IN_EVEN 28
#define EP13_IN_ODD 28
#define EP14_OUT_EVEN 29
#define EP14_OUT_ODD 29
#define EP14_IN_EVEN 30
#define EP14_IN_ODD 30
#define EP15_OUT_EVEN 31
#define EP15_OUT_ODD 31
#define EP15_IN_EVEN 32
#define EP15_IN_ODD 32
#define EP(ep,dir,pp) (2u*ep+dir+(((ep==0)&&(dir==0))?pp:1))
#define BD(ep,dir,pp) (4u*((2u*ep)+dir+(((ep==0)&&(dir==0))?pp:1)))
#elif (USB_PING_PONG_MODE == USB_PING_PONG__FULL_PING_PONG)
#if defined (__18CXX) || defined(__C30__) || defined __XC16__ || defined(__XC8)
#if (defined (__dsPIC33E__) || defined (__PIC24E__))
#define USB_NEXT_EP0_OUT_PING_PONG 0x0008
#define USB_NEXT_EP0_IN_PING_PONG 0x0008
#define USB_NEXT_PING_PONG 0x0008
#else
#define USB_NEXT_EP0_OUT_PING_PONG 0x0004
#define USB_NEXT_EP0_IN_PING_PONG 0x0004
#define USB_NEXT_PING_PONG 0x0004
#endif
#elif defined(__C32__)
#define USB_NEXT_EP0_OUT_PING_PONG 0x0008
#define USB_NEXT_EP0_IN_PING_PONG 0x0008
#define USB_NEXT_PING_PONG 0x0008
#else
#error "Not defined for this compiler"
#endif
#define EP0_OUT_EVEN 0
#define EP0_OUT_ODD 1
#define EP0_IN_EVEN 2
#define EP0_IN_ODD 3
#define EP1_OUT_EVEN 4
#define EP1_OUT_ODD 5
#define EP1_IN_EVEN 6
#define EP1_IN_ODD 7
#define EP2_OUT_EVEN 8
#define EP2_OUT_ODD 9
#define EP2_IN_EVEN 10
#define EP2_IN_ODD 11
#define EP3_OUT_EVEN 12
#define EP3_OUT_ODD 13
#define EP3_IN_EVEN 14
#define EP3_IN_ODD 15
#define EP4_OUT_EVEN 16
#define EP4_OUT_ODD 17
#define EP4_IN_EVEN 18
#define EP4_IN_ODD 19
#define EP5_OUT_EVEN 20
#define EP5_OUT_ODD 21
#define EP5_IN_EVEN 22
#define EP5_IN_ODD 23
#define EP6_OUT_EVEN 24
#define EP6_OUT_ODD 25
#define EP6_IN_EVEN 26
#define EP6_IN_ODD 27
#define EP7_OUT_EVEN 28
#define EP7_OUT_ODD 29
#define EP7_IN_EVEN 30
#define EP7_IN_ODD 31
#define EP8_OUT_EVEN 32
#define EP8_OUT_ODD 33
#define EP8_IN_EVEN 34
#define EP8_IN_ODD 35
#define EP9_OUT_EVEN 36
#define EP9_OUT_ODD 37
#define EP9_IN_EVEN 38
#define EP9_IN_ODD 39
#define EP10_OUT_EVEN 40
#define EP10_OUT_ODD 41
#define EP10_IN_EVEN 42
#define EP10_IN_ODD 43
#define EP11_OUT_EVEN 44
#define EP11_OUT_ODD 45
#define EP11_IN_EVEN 46
#define EP11_IN_ODD 47
#define EP12_OUT_EVEN 48
#define EP12_OUT_ODD 49
#define EP12_IN_EVEN 50
#define EP12_IN_ODD 51
#define EP13_OUT_EVEN 52
#define EP13_OUT_ODD 53
#define EP13_IN_EVEN 54
#define EP13_IN_ODD 55
#define EP14_OUT_EVEN 56
#define EP14_OUT_ODD 57
#define EP14_IN_EVEN 58
#define EP14_IN_ODD 59
#define EP15_OUT_EVEN 60
#define EP15_OUT_ODD 61
#define EP15_IN_EVEN 62
#define EP15_IN_ODD 63
#define EP(ep,dir,pp) (4*ep+2*dir+pp)
#if defined (__18CXX) || defined(__C30__) || defined __XC16__ || (__XC8)
#if (defined(__dsPIC33E__) || defined (__PIC24E__))
#define BD(ep,dir,pp) (8*(4*ep+2*dir+pp))
#else
#define BD(ep,dir,pp) (4*(4*ep+2*dir+pp))
#endif
#elif defined(__C32__)
#define BD(ep,dir,pp) (8*(4*ep+2*dir+pp))
#else
#error "Not defined for this compiler"
#endif
#elif (USB_PING_PONG_MODE == USB_PING_PONG__ALL_BUT_EP0)
#define USB_NEXT_EP0_OUT_PING_PONG 0x0000
#define USB_NEXT_EP0_IN_PING_PONG 0x0000
#define USB_NEXT_PING_PONG 0x0004
#define EP0_OUT_EVEN 0
#define EP0_OUT_ODD 0
#define EP0_IN_EVEN 1
#define EP0_IN_ODD 1
#define EP1_OUT_EVEN 2
#define EP1_OUT_ODD 3
#define EP1_IN_EVEN 4
#define EP1_IN_ODD 5
#define EP2_OUT_EVEN 6
#define EP2_OUT_ODD 7
#define EP2_IN_EVEN 8
#define EP2_IN_ODD 9
#define EP3_OUT_EVEN 10
#define EP3_OUT_ODD 11
#define EP3_IN_EVEN 12
#define EP3_IN_ODD 13
#define EP4_OUT_EVEN 14
#define EP4_OUT_ODD 15
#define EP4_IN_EVEN 16
#define EP4_IN_ODD 17
#define EP5_OUT_EVEN 18
#define EP5_OUT_ODD 19
#define EP5_IN_EVEN 20
#define EP5_IN_ODD 21
#define EP6_OUT_EVEN 22
#define EP6_OUT_ODD 23
#define EP6_IN_EVEN 24
#define EP6_IN_ODD 25
#define EP7_OUT_EVEN 26
#define EP7_OUT_ODD 27
#define EP7_IN_EVEN 28
#define EP7_IN_ODD 29
#define EP8_OUT_EVEN 30
#define EP8_OUT_ODD 31
#define EP8_IN_EVEN 32
#define EP8_IN_ODD 33
#define EP9_OUT_EVEN 34
#define EP9_OUT_ODD 35
#define EP9_IN_EVEN 36
#define EP9_IN_ODD 37
#define EP10_OUT_EVEN 38
#define EP10_OUT_ODD 39
#define EP10_IN_EVEN 40
#define EP10_IN_ODD 41
#define EP11_OUT_EVEN 42
#define EP11_OUT_ODD 43
#define EP11_IN_EVEN 44
#define EP11_IN_ODD 45
#define EP12_OUT_EVEN 46
#define EP12_OUT_ODD 47
#define EP12_IN_EVEN 48
#define EP12_IN_ODD 49
#define EP13_OUT_EVEN 50
#define EP13_OUT_ODD 51
#define EP13_IN_EVEN 52
#define EP13_IN_ODD 53
#define EP14_OUT_EVEN 54
#define EP14_OUT_ODD 55
#define EP14_IN_EVEN 56
#define EP14_IN_ODD 57
#define EP15_OUT_EVEN 58
#define EP15_OUT_ODD 59
#define EP15_IN_EVEN 60
#define EP15_IN_ODD 61
#define EP(ep,dir,pp) (4*ep+2*dir+((ep==0)?0:(pp-2)))
#define BD(ep,dir,pp) (4*(4*ep+2*dir+((ep==0)?0:(pp-2))))
#else
#error "No ping pong mode defined."
#endif
/****** Event callback enabling/disabling macros ********************
This section of code is used to disable specific USB events that may not be
desired by the user. This can save code size and increase throughput and
decrease CPU utiliazation.
********************************************************************/
#if defined USB_DISABLE_SUSPEND_HANDLER
#define USB_SUSPEND_HANDLER(event,pointer,size)
#warning "Disabling the suspend handler is not recommended. Proper suspend handling is required to create a compliant USB device."
#else
#define USB_SUSPEND_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_WAKEUP_FROM_SUSPEND_HANDLER
#define USB_WAKEUP_FROM_SUSPEND_HANDLER(event,pointer,size)
#warning "Disabling the wake from suspend handler is not recommended. Proper suspend handling is required to create a compliant USB device."
#else
#define USB_WAKEUP_FROM_SUSPEND_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_SOF_HANDLER
#define USB_SOF_HANDLER(event,pointer,size)
#else
#define USB_SOF_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_TRANSFER_TERMINATED_HANDLER
#define USB_TRANSFER_TERMINATED_HANDLER(event,pointer,size)
#else
#define USB_TRANSFER_TERMINATED_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_ERROR_HANDLER
#define USB_ERROR_HANDLER(event,pointer,size)
#else
#define USB_ERROR_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_NONSTANDARD_EP0_REQUEST_HANDLER
#define USB_NONSTANDARD_EP0_REQUEST_HANDLER(event,pointer,size)
#else
#define USB_NONSTANDARD_EP0_REQUEST_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_SET_DESCRIPTOR_HANDLER
#define USB_SET_DESCRIPTOR_HANDLER(event,pointer,size)
#else
#define USB_SET_DESCRIPTOR_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_SET_CONFIGURATION_HANDLER
#define USB_SET_CONFIGURATION_HANDLER(event,pointer,size)
#else
#define USB_SET_CONFIGURATION_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif
#if defined USB_DISABLE_TRANSFER_COMPLETE_HANDLER
#define USB_TRANSFER_COMPLETE_HANDLER(event,pointer,size)
#else
#define USB_TRANSFER_COMPLETE_HANDLER(event,pointer,size) USER_USB_CALLBACK_EVENT_HANDLER(event,pointer,size)
#endif

614
inc/usb/usb_hal.h Normal file
View File

@ -0,0 +1,614 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
#ifndef _USB_HAL_H_
#define _USB_HAL_H_
// *****************************************************************************
// *****************************************************************************
// Section: Included Files
// *****************************************************************************
// *****************************************************************************
#include <stdint.h>
#if defined(__18CXX) || defined(__XC8)
#if defined(_PIC14E)
#include "usb_hal_pic16f1.h"
#else
#include "usb_hal_pic18.h"
#endif
#elif defined(__C30__) || defined __XC16__
#if defined(__dsPIC33E__)
#include "usb_hal_dspic33e.h"
#elif defined(__PIC24E__)
#include "usb_hal_pic24e.h"
#else
#include "usb_hal_pic24f.h"
#endif
#elif defined(__XC32__)
#if defined(__PIC32MM__)
#include "usb_hal_pic32mm.h"
#else
#error "Silicon Platform not defined"
#endif
#else
#error "Silicon Platform not defined"
#endif
#ifdef __cplusplus // Provide C++ Compatability
extern "C" {
#endif
// *****************************************************************************
// *****************************************************************************
// Section: Constants
// *****************************************************************************
// *****************************************************************************
/* USBHALControlUsbResistors flags */
#define USB_HAL_PULL_UP_D_PLUS 0x80 // Pull D+ line high
#define USB_HAL_PULL_UP_D_MINUS 0x40 // Pull D- line high
#define USB_HAL_PULL_DN_D_PLUS 0x20 // Pull D+ line low
#define USB_HAL_PULL_DN_D_MINUS 0x10 // Pull D- line low
/*
The following are defined for convenience:
*/
#define USB_HAL_DEV_CONN_FULL_SPD USB_HAL_PULL_UP_D_PLUS
#define USB_HAL_DEV_CONN_LOW_SPD USB_HAL_PULL_UP_D_MINUS
#define USB_HAL_DEV_DISCONNECT 0
/* USBHALControlBusPower Commands */
#define USB_VBUS_DISCHARGE 0 // Dicharge Vbus via resistor
#define USB_VBUS_CHARGE 1 // Charge Vbus via resistor
#define USB_VBUS_POWER_ON 3 // Supply power to Vbus
#define USB_VBUS_POWER_OFF 4 // Do not supply power to Vbus
/*
USBHALGetLastError Error Bits.
*/
#define USBHAL_PID_ERR 0x00000001 // Packet ID Error
#define USBHAL_CRC5 0x00000002 // (Host) Token CRC5 check failed
#define USBHAL_HOST_EOF 0x00000002 // (Host) EOF not reached before next SOF
#define USBHAL_CRC16 0x00000004 // Data packet CRC error
#define USBHAL_DFN8 0x00000008 // Data field size not n*8 bits
#define USBHAL_BTO_ERR 0x00000010 // Bus turn-around timeout
#define USBHAL_DMA_ERR 0x00000020 // DMA error, unable to read/write memory
#define USBHAL_BTS_ERR 0x00000080 // Bit-stuffing error
#define USBHAL_XFER_ID 0x00000100 // Unable to identify transfer EP
#define USBHAL_NO_EP 0x00000200 // Invalid endpoint number
#define USBHAL_DMA_ERR2 0x00000400 // Error starting DMA transaction
/* Flags for USBHALSetEpConfiguration */
#if defined(__18CXX) || defined(__XC8)
#define USB_HAL_TRANSMIT 0x0400 // Enable EP for transmitting data
#define USB_HAL_RECEIVE 0x0200 // Enable EP for receiving data
#define USB_HAL_HANDSHAKE 0x1000 // Enable EP to give ACK/NACK (non isoch)
#define USB_HAL_NO_INC 0x0010 // Use for DMA to another device FIFO
#define USB_HAL_HW_KEEPS 0x0020 // Cause HW to keep EP
#else
#define USB_HAL_TRANSMIT 0x0400 // Enable EP for transmitting data
#define USB_HAL_RECEIVE 0x0800 // Enable EP for receiving data
#define USB_HAL_HANDSHAKE 0x0100 // Enable EP to give ACK/NACK (non isoch)
/* Does not work, Fix this if needed. 3/1/07 - Bud
#define USB_HAL_NO_INC 0x0010 // Use for DMA to another device FIFO
#define USB_HAL_HW_KEEPS 0x0020 // Cause HW to keep EP
*/
#define USB_HAL_ALLOW_HUB 0x8000 // (host only) Enable low-spd hub support
#define USB_HAL_NO_RETRY 0x4000 // (host only) disable auto-retry on NACK
#endif
// *****************************************************************************
// *****************************************************************************
// Section: Data Types
// *****************************************************************************
// *****************************************************************************
// *****************************************************************************
// *****************************************************************************
// Section: Interface Routines
// *****************************************************************************
// *****************************************************************************
/*************************************************************************
Function:
void USBHALSetBusAddress( uint8_t addr )
Description:
This routine sets the address of the system on the USB
when acting as a peripheral device.
Preconditions:
1. USBHALInitialize must have been called to
initialize the USB HAL.
2. Endpoint zero (0) must be configured as appropriate
by calls to USBHALSetEpConfiguration.
3. The system must have been enumerated on the USB (as
a device).
Parameters:
addr Desired address of this device on the USB.
Return Values:
None
Side Effect:
The bus address has been set.
Remarks:
The address is assigned by the host and is received in
a SET_ADDRESS setup request.
*************************************************************************/
/*
This routine is implemented as a macro to a lower-level level routine.
*/
#define USBHALSetBusAddress OTGCORE_SetDeviceAddr
void USBHALSetBusAddress( uint8_t addr );
/*************************************************************************
Function:
void USBHALControlUsbResistors( uint8_t flags );
Description:
This routine enables or disables the USB pull-up or
pull-down resistors as requested.
Precondition:
USBInitialize must have been called to initialize the
USB SW stack.
Parameters:
flags - This is a bit-mapped flags value indicating
which resistors to enable or disable (see below).
Return Values:
true if successful, false if not.
Side Effects:
The resistors are enabled as requested.
Remarks:
Used for USB peripheral control to connect to or
disconnect from the bus. Otherwise, used for OTG
SRP/HNP and host support.
*************************************************************************/
/*
This routine is implemented as a macro to a lower-level level routine.
*/
#if defined(__18CXX) || defined(__XC8)
void USBHALControlUsbResistors( uint8_t flags );
#else
#define USBHALControlUsbResistors OTGCORE_ControlUsbResistors
void USBHALControlUsbResistors( uint8_t flags );
#endif
/*
MCHP: Define a method to check for SE0 & a way to send a reset (SE0).
*/
/*************************************************************************
Function:
bool USBHALSessionIsValid( void )
Description:
This routine determines if there is currently a valid
USB session or not.
Precondition:
USBInitialize must have been called to initialize the
USB SW stack.
Parameters:
None
Return Values:
true if the session is currently valid, false if not.
Remarks:
Only used for host and OTG support.
*************************************************************************/
bool USBHALSessionIsValid( void );
/*************************************************************************
Function:
USBHALControlBusPower
Description:
This routine provides a bitmap of the most recent
error conditions to occur.
Precondition:
USBInitialize must have been called to initialize the
USB SW stack.
Parameters:
cmd - Identifies desired command (see below).
Return Values:
true if successful, false if not.
Remarks:
Only used for host and OTG support.
*************************************************************************/
bool USBHALControlBusPower( uint8_t cmd );
/*************************************************************************
Function:
unsigned long USBHALGetLastError( void )
Description:
This routine provides a bitmap of the most recent
error conditions to occur.
Precondition:
USBInitialize must have been called to initialize the
USB SW stack.
Parameters:
None
Return Values:
Bitmap indicating the most recent error condition(s).
Side Effect:
Error record is cleared.
Remarks:
Although record of the error state is cleared, nothing
is done to fix the condition or recover from the
error. The client must take appropriate steps.
*************************************************************************/
unsigned long USBHALGetLastError( void );
/*************************************************************************
Function:
void USBHALHandleBusEvent ( void )
Description:
This routine checks the USB for any events that may
have occurred and handles them appropriately. It may
be called directly to poll the USB and handle events
or it may be called in response to an interrupt.
Precondition:
USBInitialize must have been called to initialize the
USB SW stack.
Parameters:
None
Return Values:
None
Side Effects:
Depend on the event that may have occurred.
Remarks:
None
*************************************************************************/
void USBHALHandleBusEvent ( void );
/*************************************************************************
Function:
bool USBHALStallPipe( TRANSFER_FLAGS pipe )
Description:
This routine stalls the given endpoint.
Preconditions:
USBHALInitialize must have been called to initialize
the USB HAL.
Parameters:
pipe - Uses the TRANSFER_FLAGS (see USBCommon.h) format to
identify the endpoint and direction making up the
pipe to stall.
Note: Only ep_num and direction fields are required.
Return Values:
true if able to stall endpoint, false if not.
Side Effects:
The endpoint will stall if additional data transfer is
attempted.
Given endpoint has been stalled.
Remarks:
Starting another data transfer automatically
"un-stalls" the endpoint.
*************************************************************************/
/*
Note: This function is implemented as a macro, calling directly into
an internal HAL routine.
*/
#define USBHALStallPipe OTGCORE_StallPipe
bool USBHALStallPipe( TRANSFER_FLAGS pipe );
/******************************************************************************
Function:
bool USBHALUnstallPipe( TRANSFER_FLAGS pipe )
Description:
This routine clears the stall condition for the given pipe.
PreCondition:
Assumes OTGCORE_DeviceEnable has been called and
OTGCORE_StallPipe has been called on the given pipe.
Parameters:
pipe - Uses the TRANSFER_FLAGS (see USBCommon.h) format to
identify the endpoint and direction making up the
pipe to un-stall.
Return Values:
true if able to stall the pipe, false if not.
Side Effects:
The BSTALL and UOWN bits (and all other control bits) in
the BDT for the given pipe will be cleared.
Remarks:
None
*****************************************************************************/
/*
Note: This function is implemented as a macro, calling directly into
an internal HAL routine.
*/
#define USBHALUnstallPipe OTGCORE_UnstallPipe
bool USBHALUnstallPipe( TRANSFER_FLAGS pipe );
/**************************************************************************
Function:
USBHALGetStalledEndpoints
Description:
This function returns a 16-bit bit-mapped value with a
bit set in the position of any endpoint that is stalled
(i.e. if endpoint 0 is stalled then bit 0 is set, if
endpoint 1 is stalled then bit 1 is set, etc.).
Preconditions:
USBHALInitialize must have been called to initialize
the USB HAL.
Parameters:
None
Return Values:
Bitmap of the currently stalled endpoints (see overview).
Remarks:
None
*************************************************************************/
/*
Note: This function is implemented as a macro, calling directly into
a HAL routine.
*/
#define USBHALGetStalledEndpoints OTGCORE_GetStalledEndpoints
uint16_t USBHALGetStalledEndpoints ( void );
/******************************************************************************
Function:
bool USBHALFlushPipe( TRANSFER_FLAGS pipe )
Description:
This routine clears any pending transfers on the given
pipe.
Preconditions:
USBHALInitialize must have been called to initialize the
USB HAL.
The caller must ensure that there is no possible way for
hardware to be currently accessing the pipe (see notes).
Parameters:
pipe - Uses the TRANSFER_FLAGS (see USBCommon.h) format to
identify the endpoint and direction making up the
pipe to flush.
Return Values:
true if successful, false if not.
Side Effects:
Transfer data for this pipe has been zeroed out.
Remarks:
This routine ignores the normal HW protocol for ownership
of the pipe data and flushes the pipe, even if it is in
process. Thus, the caller must ensure that data transfer
cannot be in process. This situation occurs when a
transfer has been terminated early by the host.
*****************************************************************************/
bool USBHALFlushPipe( TRANSFER_FLAGS pipe );
/**************************************************************************
Function:
USBHALTransferData
Description:
This routine prepares to transfer data on the USB.
If the system is in device mode, the actual transfer
will not occur until the host performs an OUT request
to the given endpoint. If the system is in host mode,
the transfer will not start until the token has been
sent on the bus.
Preconditions:
1. USBHALInitialize must have been called to
initialize the USB HAL.
2. The endpoint through which the data will be
transferred must be configured as appropriate by a
call to USBHALSetEpConfiguration.
3. The bus must have been enumerated (either as a host
or device). Except for EP0 transfers.
Parameters:
flags - Flags consists of the endpoint number OR'd
with one or more flags indicating transfer
direction and such (see "Data Transfer
Macros" in USBCommon.h):
7 6 5 4 3 2 1 0 - Description
| | | | \_____/
| | | | +----- Endpoint Number
| | | +---------- Short or zero-size packet
| | +------------ Data Toggle 0/1
| +-------------- Force Data Toggle
+---------------- 1=Transmit/0=Receive
buffer Address of the buffer to receive data.
size Number of uint8_ts of data to transfer.
Return Values:
true if the HAL was able to successfully start the
data transfer, false if not.
Side Effects:
The HAL has prepared to transfer the data on the USB.
Remarks:
The HAL will continue the data transfer, keeping track
of the buffer address, data remaining, and ping-pong
buffer details internally when USBHALHandleBusEvent is
called (either polled or in response to an interrupt).
The caller will receive notification that the transfer
has completed when the EVT_XFER event is passed into
the USBHALBusEventCallout call-out function.
*************************************************************************/
bool USBHALTransferData ( TRANSFER_FLAGS flags,
void *buffer,
unsigned int size );
/*************************************************************************
Function:
USBHALSetEpConfiguration
Description:
This routine allows the caller to configure various
options (see "Flags for USBHALSetEpConfiguration",
below) and set the behavior for the given endpoint.
Precondition:
USBHALInitialize has been called.
Parameters:
ep_num - Number of endpoint to configure, Must be
(ep_num >=0) && (ep_num <= USB_DEV_HIGHEST_EP_NUMBER)
max_pkt_size Size of largest packet this enpoint can
transfer.
flags - Configuration flags (see below)
Return Values:
true if successful, false if not.
Side Effects:
The endpoint has been configured as desired.
Remarks:
The base address and size of the buffer is not set by
this routine. Those features of an endpoint are
dynamically managed by the USBHALTransferData routine.
An endpoint can be "de-configured" by setting its max
packet size to 0. When doing this, you should also
set all flags to 0.
*************************************************************************/
bool USBHALSetEpConfiguration ( uint8_t ep_num, uint16_t max_pkt_size, uint16_t flags );
/*************************************************************************
Function:
USBHALInitialize
Description:
This call performs the basic initialization of the USB
HAL. This routine must be called before any of the
other HAL interface routines are called.
Precondition:
The system has been initialized.
Parameters:
flags - Initialization flags
Return Values:
true if successful, false if not.
Side Effects:
The USB HAL SW stack was initialized.
Remarks:
This routine can be called to reset the controller.
*************************************************************************/
bool USBHALInitialize ( unsigned long flags );
#ifdef __cplusplus // Provide C++ Compatibility
}
#endif
#endif // _USB_HAL_H_
/*************************************************************************
* EOF
*/

611
inc/usb/usb_hal_pic18.h Normal file
View File

@ -0,0 +1,611 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
#ifndef _USB_HAL_PIC18_H
#define _USB_HAL_PIC18_H
// *****************************************************************************
// *****************************************************************************
// Section: Included Files
// *****************************************************************************
// *****************************************************************************
/* This section lists the other files that are included in this file.
*/
#if defined(__XC8)
#include <xc.h>
#include <stdint.h>
#elif defined(__C18)
#include <p18cxxx.h>
#ifndef uint8_t
#define uint8_t unsigned char
#endif
#ifndef uint16_t
#define uint16_t unsigned int
#endif
#ifndef uint32_t
#define uint32_t unsigned long int
#endif
#endif
#include <string.h>
#include "usb_config.h"
#ifdef __cplusplus // Provide C++ Compatability
extern "C" {
#endif
// *****************************************************************************
// *****************************************************************************
// Section: Constants
// *****************************************************************************
// *****************************************************************************
#define USB_HAL_VBUSTristate() //No dedicated VBUS pin on these devices.
//----- USBEnableEndpoint() input definitions ----------------------------------
#define USB_HANDSHAKE_ENABLED 0x10
#define USB_HANDSHAKE_DISABLED 0x00
#define USB_OUT_ENABLED 0x04
#define USB_OUT_DISABLED 0x00
#define USB_IN_ENABLED 0x02
#define USB_IN_DISABLED 0x00
#define USB_ALLOW_SETUP 0x00
#define USB_DISALLOW_SETUP 0x08
#define USB_STALL_ENDPOINT 0x01
//----- usb_config.h input definitions -----------------------------------------
#define USB_PULLUP_ENABLE 0x10
#define USB_PULLUP_DISABLED 0x00
#define USB_INTERNAL_TRANSCEIVER 0x00
#define USB_EXTERNAL_TRANSCEIVER 0x08
#define USB_FULL_SPEED 0x04
#define USB_LOW_SPEED 0x00
//----- Interrupt Flag definitions --------------------------------------------
#define USBTransactionCompleteIE UIEbits.TRNIE
#define USBTransactionCompleteIF UIRbits.TRNIF
#define USBTransactionCompleteIFReg UIR
#define USBTransactionCompleteIFBitNum 0xF7 //AND mask for clearing TRNIF bit position 4
#define USBResetIE UIEbits.URSTIE
#define USBResetIF UIRbits.URSTIF
#define USBResetIFReg UIR
#define USBResetIFBitNum 0xFE //AND mask for clearing URSTIF bit position 0
#define USBIdleIE UIEbits.IDLEIE
#define USBIdleIF UIRbits.IDLEIF
#define USBIdleIFReg UIR
#define USBIdleIFBitNum 0xEF //AND mask for clearing IDLEIF bit position 5
#define USBActivityIE UIEbits.ACTVIE
#define USBActivityIF UIRbits.ACTVIF
#define USBActivityIFReg UIR
#define USBActivityIFBitNum 0xFB //AND mask for clearing ACTVIF bit position 2
#define USBSOFIE UIEbits.SOFIE
#define USBSOFIF UIRbits.SOFIF
#define USBSOFIFReg UIR
#define USBSOFIFBitNum 0xBF //AND mask for clearing SOFIF bit position 6
#define USBStallIE UIEbits.STALLIE
#define USBStallIF UIRbits.STALLIF
#define USBStallIFReg UIR
#define USBStallIFBitNum 0xDF //AND mask for clearing STALLIF bit position 5
#define USBErrorIE UIEbits.UERRIE
#define USBErrorIF UIRbits.UERRIF
#define USBErrorIFReg UIR
#define USBErrorIFBitNum 0xFD //UERRIF bit position 1. Note: This bit is read only and is cleared by clearing the enabled UEIR flags
//----- Event call back defintions --------------------------------------------
#if defined(USB_DISABLE_SOF_HANDLER)
#define USB_SOF_INTERRUPT 0x00
#else
#define USB_SOF_INTERRUPT 0x40
#endif
#if defined(USB_DISABLE_ERROR_HANDLER)
#define USB_ERROR_INTERRUPT 0x02
#else
#define USB_ERROR_INTERRUPT 0x02
#endif
//----- USB module control bits -----------------------------------------------
#define USBPingPongBufferReset UCONbits.PPBRST
#define USBSE0Event UCONbits.SE0
#define USBSuspendControl UCONbits.SUSPND
#define USBPacketDisable UCONbits.PKTDIS
#define USBResumeControl UCONbits.RESUME
//----- BDnSTAT bit definitions -----------------------------------------------
#define _BSTALL 0x04 //Buffer Stall enable
#define _DTSEN 0x08 //Data Toggle Synch enable
#define _INCDIS 0x10 //Address increment disable
#define _KEN 0x20 //SIE keeps buff descriptors enable
#define _DAT0 0x00 //DATA0 packet expected next
#define _DAT1 0x40 //DATA1 packet expected next
#define _DTSMASK 0x40 //DTS Mask
#define _USIE 0x80 //SIE owns buffer
#define _UCPU 0x00 //CPU owns buffer
#define _STAT_MASK 0xFF
#define USTAT_EP0_PP_MASK ~0x02
#define USTAT_EP_MASK 0x7E
#define USTAT_EP0_OUT 0x00
#define USTAT_EP0_OUT_EVEN 0x00
#define USTAT_EP0_OUT_ODD 0x02
#define USTAT_EP0_IN 0x04
#define USTAT_EP0_IN_EVEN 0x04
#define USTAT_EP0_IN_ODD 0x06
#define ENDPOINT_MASK 0b01111000
//----- U1EP bit definitions --------------------------------------------------
#define UEP_STALL 0x0001
// Cfg Control pipe for this ep
/* Endpoint configuration options for USBEnableEndpoint() function */
#define EP_CTRL 0x06 // Cfg Control pipe for this ep
#define EP_OUT 0x0C // Cfg OUT only pipe for this ep
#define EP_IN 0x0A // Cfg IN only pipe for this ep
#define EP_OUT_IN 0x0E // Cfg both OUT & IN pipes for this ep
//----- Remap the PIC18 register name space------------------------------------
#define U1ADDR UADDR
#define U1IE UIE
#define U1IR UIR
#define U1EIR UEIR
#define U1EIE UEIE
#define U1CON UCON
#define U1EP0 UEP0
#define U1CONbits UCONbits
#define U1EP1 UEP1
#define U1CNFG1 UCFG
#define U1STAT USTAT
#define U1EP0bits UEP0bits
//----- Defintions for BDT address --------------------------------------------
#if defined(__16F1454) || defined(__16F1455) || defined(__16F1459) || defined(__16LF1454) || defined(__16LF1455) || defined(__16LF1459)
#define USB_BDT_ADDRESS 0x020
#elif defined(__18F14K50) || defined(__18F13K50) || defined(__18LF14K50) || defined(__18LF13K50)
#define USB_BDT_ADDRESS 0x200 //See Linker Script, BDT in bank 2 on these devices - usb2:0x200-0x2FF(256-byte)
#elif defined(__18F24K50) || defined(__18F25K50) || defined(__18F45K50) || defined(__18LF24K50) || defined(__18LF25K50) || defined(__18LF45K50)
#define USB_BDT_ADDRESS 0x400 //See Linker Script, BDT in bank 4
#elif defined(__18F47J53) || defined(__18F46J53) || defined(__18F27J53) || defined(__18F26J53) || defined(__18LF47J53) || defined(__18LF46J53) || defined(__18LF27J53) || defined(__18LF26J53)
#define USB_BDT_ADDRESS 0xD00 //BDT in Bank 13 on these devices
#elif defined(__18F97J94) || defined(__18F87J94) || defined(__18F67J94) || defined(__18F96J94) || defined(__18F86J94) || defined(__18F66J94) || defined(__18F96J99) || defined(__18F95J94) || defined(__18F86J99) || defined(__18F85J94) || defined(__18F66J99) || defined(__18F65J94)
#define USB_BDT_ADDRESS 0x100 //BDT in Bank 1 on these devices
#else
#define USB_BDT_ADDRESS 0x400 //All other PIC18 devices place the BDT in usb4:0x400-0x4FF(256-byte)
#endif
#if (USB_PING_PONG_MODE == USB_PING_PONG__NO_PING_PONG)
#define BDT_NUM_ENTRIES ((USB_MAX_EP_NUMBER + 1) * 2)
#elif (USB_PING_PONG_MODE == USB_PING_PONG__EP0_OUT_ONLY)
#define BDT_NUM_ENTRIES (((USB_MAX_EP_NUMBER + 1) * 2)+1)
#elif (USB_PING_PONG_MODE == USB_PING_PONG__FULL_PING_PONG)
#define BDT_NUM_ENTRIES ((USB_MAX_EP_NUMBER + 1) * 4)
#elif (USB_PING_PONG_MODE == USB_PING_PONG__ALL_BUT_EP0)
#define BDT_NUM_ENTRIES (((USB_MAX_EP_NUMBER + 1) * 4)-2)
#else
#error "No ping pong mode defined."
#endif
#if defined(__XC8)
#define CTRL_TRF_SETUP_ADDRESS (USB_BDT_ADDRESS+(BDT_NUM_ENTRIES*4))
#define CTRL_TRF_DATA_ADDRESS (CTRL_TRF_SETUP_ADDRESS + USB_EP0_BUFF_SIZE)
#define BDT_BASE_ADDR_TAG @USB_BDT_ADDRESS
#define CTRL_TRF_SETUP_ADDR_TAG @CTRL_TRF_SETUP_ADDRESS
#define CTRL_TRF_DATA_ADDR_TAG @CTRL_TRF_DATA_ADDRESS
#if defined(USB_USE_MSD)
//MSD application specific USB endpoint buffer placement macros (so they
//get linked to a USB module accessible portion of RAM)
#define MSD_CBW_ADDRESS (CTRL_TRF_DATA_ADDRESS + USB_EP0_BUFF_SIZE)
#define MSD_CSW_ADDRESS (MSD_CBW_ADDRESS + MSD_OUT_EP_SIZE)
#define MSD_CBW_ADDR_TAG @MSD_CBW_ADDRESS
#define MSD_CSW_ADDR_TAG @MSD_CSW_ADDRESS
#endif
#else
#define BDT_BASE_ADDR_TAG __attribute__ ((aligned (512)))
#define CTRL_TRF_SETUP_ADDR_TAG
#define CTRL_TRF_DATA_ADDR_TAG
#define MSD_CBW_ADDR_TAG
#define MSD_CSW_ADDR_TAG
#endif
//----- Deprecated definitions - will be removed at some point of time----------
//--------- Deprecated in v2.2
#define _LS 0x00 // Use Low-Speed USB Mode
#define _FS 0x04 // Use Full-Speed USB Mode
#define _TRINT 0x00 // Use internal transceiver
#define _TREXT 0x08 // Use external transceiver
#define _PUEN 0x10 // Use internal pull-up resistor
#define _OEMON 0x40 // Use SIE output indicator
// *****************************************************************************
// *****************************************************************************
// Section: Data Types
// *****************************************************************************
// *****************************************************************************
// Buffer Descriptor Status Register layout.
typedef union _BD_STAT
{
uint8_t Val;
struct{
//If the CPU owns the buffer then these are the values
unsigned BC8:1; //bit 8 of the byte count
unsigned BC9:1; //bit 9 of the byte count
unsigned BSTALL:1; //Buffer Stall Enable
unsigned DTSEN:1; //Data Toggle Synch Enable
unsigned INCDIS:1; //Address Increment Disable
unsigned KEN:1; //BD Keep Enable
unsigned DTS:1; //Data Toggle Synch Value
unsigned UOWN:1; //USB Ownership
};
struct{
//if the USB module owns the buffer then these are
// the values
unsigned :2;
unsigned PID0:1; //Packet Identifier
unsigned PID1:1;
unsigned PID2:1;
unsigned PID3:1;
unsigned :1;
};
struct{
unsigned :2;
unsigned PID:4; //Packet Identifier
unsigned :2;
};
} BD_STAT; //Buffer Descriptor Status Register
// BDT Entry Layout
typedef union __BDT
{
struct
{
BD_STAT STAT;
uint8_t CNT;
uint8_t ADRL; //Buffer Address Low
uint8_t ADRH; //Buffer Address High
};
struct
{
unsigned :8;
unsigned :8;
uint16_t ADR; //Buffer Address
};
uint32_t Val;
uint8_t v[4];
} BDT_ENTRY;
// USTAT Register Layout
typedef union __USTAT
{
struct
{
unsigned char filler1:1;
unsigned char ping_pong:1;
unsigned char direction:1;
unsigned char endpoint_number:4;
};
uint8_t Val;
} USTAT_FIELDS;
//Macros for fetching parameters from a USTAT_FIELDS variable.
#define USBHALGetLastEndpoint(stat) stat.endpoint_number
#define USBHALGetLastDirection(stat) stat.direction
#define USBHALGetLastPingPong(stat) stat.ping_pong
typedef union _POINTER
{
struct
{
uint8_t bLow;
uint8_t bHigh;
//byte bUpper;
};
uint16_t _word; // bLow & bHigh
//pFunc _pFunc; // Usage: ptr.pFunc(); Init: ptr.pFunc = &<Function>;
uint8_t* bRam; // Ram byte pointer: 2 bytes pointer pointing
// to 1 byte of data
uint16_t* wRam; // Ram word poitner: 2 bytes poitner pointing
// to 2 bytes of data
const uint8_t* bRom; // Size depends on compiler setting
const uint16_t* wRom;
//rom near byte* nbRom; // Near = 2 bytes pointer
//rom near word* nwRom;
//rom far byte* fbRom; // Far = 3 bytes pointer
//rom far word* fwRom;
} POINTER;
// *****************************************************************************
// *****************************************************************************
// Section: Interface Routines
// *****************************************************************************
// *****************************************************************************
#define ConvertToPhysicalAddress(a) ((uint16_t)(a))
#define ConvertToVirtualAddress(a) ((void *)(a))
//------------------------------------------------------------------------------
//This section is for the PIC18F45K50 Family microcontrollers
//------------------------------------------------------------------------------
#if defined(__18F45K50) || defined(__18F25K50) || defined(__18F24K50) || defined(__18LF45K50) || defined(__18LF25K50) || defined(__18LF24K50)
#define USBClearUSBInterrupt() PIR3bits.USBIF = 0;
#if defined(USB_INTERRUPT)
#define USBMaskInterrupts() {PIE3bits.USBIE = 0;}
#define USBUnmaskInterrupts() {PIE3bits.USBIE = 1;}
#else
#define USBMaskInterrupts()
#define USBUnmaskInterrupts()
#endif
#define USBInterruptFlag PIR3bits.USBIF
//STALLIE, IDLEIE, TRNIE, and URSTIE are all enabled by default and are required
#if defined(USB_INTERRUPT)
#define USBEnableInterrupts() {RCONbits.IPEN = 1;IPR3bits.USBIP = 1;PIE3bits.USBIE = 1;INTCONbits.GIEH = 1;}
#else
#define USBEnableInterrupts()
#endif
#define USBDisableInterrupts() {PIE3bits.USBIE = 0;}
#define SetConfigurationOptions() {\
U1CNFG1 = USB_PULLUP_OPTION | USB_TRANSCEIVER_OPTION | USB_SPEED_OPTION | USB_PING_PONG_MODE;\
U1EIE = 0x9F;\
UIE = 0x39 | USB_SOF_INTERRUPT | USB_ERROR_INTERRUPT;\
}
//------------------------------------------------------------------------------
//This section is for the PIC16F145x Family Microcontrollers
//------------------------------------------------------------------------------
#elif defined(__16F1454) || defined(__16F1455) || defined(__16F1459) || defined(__16LF1454) || defined(__16LF1455) || defined(__16LF1459)
#define USBClearUSBInterrupt() PIR2bits.USBIF = 0;
#if defined(USB_INTERRUPT)
#define USBMaskInterrupts() {PIE2bits.USBIE = 0;}
#define USBUnmaskInterrupts() {PIE2bits.USBIE = 1;}
#else
#define USBMaskInterrupts()
#define USBUnmaskInterrupts()
#endif
#define USBInterruptFlag PIR2bits.USBIF
//STALLIE, IDLEIE, TRNIE, and URSTIE are all enabled by default and are required
#if defined(USB_INTERRUPT)
#define USBEnableInterrupts() {PIE2bits.USBIE = 1;INTCONbits.PEIE = 1;INTCONbits.GIE = 1;}
#else
#define USBEnableInterrupts()
#endif
#define USBDisableInterrupts() {PIE2bits.USBIE = 0;}
#define SetConfigurationOptions() {\
U1CNFG1 = USB_PULLUP_OPTION | USB_TRANSCEIVER_OPTION | USB_SPEED_OPTION | USB_PING_PONG_MODE;\
U1EIE = 0x9F;\
UIE = 0x39 | USB_SOF_INTERRUPT | USB_ERROR_INTERRUPT;\
}
#else
//------------------------------------------------------------------------------
//This section is for all other PIC18 USB microcontrollers
//------------------------------------------------------------------------------
#define USBClearUSBInterrupt() {PIR2bits.USBIF = 0;}
#if defined(USB_INTERRUPT)
#define USBMaskInterrupts() {PIE2bits.USBIE = 0;}
#define USBUnmaskInterrupts() {PIE2bits.USBIE = 1;}
#else
#define USBMaskInterrupts()
#define USBUnmaskInterrupts()
#endif
#define USBInterruptFlag PIR2bits.USBIF
//STALLIE, IDLEIE, TRNIE, and URSTIE are all enabled by default and are required
#if defined(USB_INTERRUPT)
#define USBEnableInterrupts() {RCONbits.IPEN = 1;IPR2bits.USBIP = 1;PIE2bits.USBIE = 1;INTCONbits.GIEH = 1;}
#else
#define USBEnableInterrupts()
#endif
#define USBDisableInterrupts() {PIE2bits.USBIE = 0;}
#define SetConfigurationOptions() {\
U1CNFG1 = USB_PULLUP_OPTION | USB_TRANSCEIVER_OPTION | USB_SPEED_OPTION | USB_PING_PONG_MODE;\
U1EIE = 0x9F;\
UIE = 0x39 | USB_SOF_INTERRUPT | USB_ERROR_INTERRUPT;\
}
#endif //end of #if defined(__18F45K50) || defined(__18F25K50)...
//------------------------------------------------------------------------------
/****************************************************************
Function:
void USBPowerModule(void)
Description:
This macro is used to power up the USB module if required<br>
PIC18: defines as nothing<br>
PIC24: defines as U1PWRCbits.USBPWR = 1;<br>
Parameters:
None
Return Values:
None
Remarks:
None
****************************************************************/
#define USBPowerModule()
/****************************************************************
Function:
void USBModuleDisable(void)
Description:
This macro is used to disable the USB module
Parameters:
None
Return Values:
None
Remarks:
None
****************************************************************/
#define USBModuleDisable() {\
UCON = 0;\
UIE = 0;\
USBDeviceState = DETACHED_STATE;\
}
/****************************************************************
Function:
USBSetBDTAddress(addr)
Description:
This macro is used to power up the USB module if required
Parameters:
None
Return Values:
None
Remarks:
None
****************************************************************/
#define USBSetBDTAddress(addr)
/********************************************************************
* Function (macro): void USBClearInterruptFlag(register, uint8_t if_and_flag_mask)
*
* PreCondition: None
*
* Input:
* register - the register mnemonic for the register holding the interrupt
flag to be cleared
* uint8_t if_and_flag_mask - an AND mask for the interrupt flag that will be
cleared
*
* Output: None
*
* Side Effects: None
*
* Overview: Clears the specified USB interrupt flag.
*
* Note:
*******************************************************************/
#define USBClearInterruptFlag(reg_name, if_and_flag_mask) (reg_name &= if_and_flag_mask)
/********************************************************************
Function:
void USBClearInterruptRegister(uint16_t reg)
Summary:
Clears the specified interrupt register
PreCondition:
None
Parameters:
uint16_t reg - the register name that needs to be cleared
Return Values:
None
Remarks:
None
*******************************************************************/
#define USBClearInterruptRegister(reg) {reg = 0;}
/********************************************************************
Function:
void DisableNonZeroEndpoints(UINT8 last_ep_num)
Summary:
Clears the control registers for the specified non-zero endpoints
PreCondition:
None
Parameters:
UINT8 last_ep_num - the last endpoint number to clear. This
number should include all endpoints used in any configuration.
Return Values:
None
Remarks:
None
*******************************************************************/
#define DisableNonZeroEndpoints(last_ep_num) memset((void*)&U1EP1,0x00,(last_ep_num));
/*****************************************************************************/
/****** Compiler checks ******************************************************/
/*****************************************************************************/
//Definitions for the BDT
#ifndef USB_PING_PONG_MODE
#error "No ping pong mode defined."
#endif
/*****************************************************************************/
/****** Extern variable definitions ******************************************/
/*****************************************************************************/
#if !defined(USBDEVICE_C)
extern USB_VOLATILE uint8_t USBActiveConfiguration;
extern USB_VOLATILE IN_PIPE inPipes[1];
extern USB_VOLATILE OUT_PIPE outPipes[1];
#endif
extern volatile BDT_ENTRY* pBDTEntryOut[USB_MAX_EP_NUMBER+1];
extern volatile BDT_ENTRY* pBDTEntryIn[USB_MAX_EP_NUMBER+1];
#ifdef __cplusplus // Provide C++ Compatibility
}
#endif
#endif //#ifndef _USB_HAL_PIC18_H

BIN
l.obj Normal file

Binary file not shown.

View File

@ -0,0 +1,583 @@
<?xml version="1.0" encoding="UTF-8"?>
<configurationDescriptor version="62">
<logicalFolder name="root" displayName="root" projectFiles="true">
<logicalFolder name="HeaderFiles"
displayName="Header Files"
projectFiles="true">
<logicalFolder name="f3" displayName="drivers" projectFiles="true">
<itemPath>inc/drivers/app_led_usb_status.h</itemPath>
<itemPath>inc/drivers/eeprom.h</itemPath>
<itemPath>inc/drivers/joystick.h</itemPath>
<itemPath>inc/drivers/adc.h</itemPath>
<itemPath>inc/drivers/buttons.h</itemPath>
<itemPath>inc/drivers/leds.h</itemPath>
</logicalFolder>
<logicalFolder name="f2" displayName="usb" projectFiles="true">
<itemPath>inc/usb/usb.h</itemPath>
<itemPath>inc/usb/usb_ch9.h</itemPath>
<itemPath>inc/usb/usb_common.h</itemPath>
<itemPath>inc/usb/usb_config.h</itemPath>
<itemPath>inc/usb/usb_device.h</itemPath>
<itemPath>inc/usb/usb_device_hid.h</itemPath>
<itemPath>inc/usb/usb_device_local.h</itemPath>
<itemPath>inc/usb/usb_hal.h</itemPath>
<itemPath>inc/usb/usb_hal_pic18.h</itemPath>
</logicalFolder>
<itemPath>inc/fixed_address_memory.h</itemPath>
<itemPath>inc/io_mapping.h</itemPath>
<itemPath>inc/system.h</itemPath>
</logicalFolder>
<logicalFolder name="LinkerScript"
displayName="Linker Files"
projectFiles="true">
</logicalFolder>
<logicalFolder name="SourceFiles"
displayName="Source Files"
projectFiles="true">
<logicalFolder name="f1" displayName="drivers" projectFiles="true">
<itemPath>src/drivers/app_led_usb_status.c</itemPath>
<itemPath>src/drivers/eeprom.c</itemPath>
<itemPath>src/drivers/joystick.c</itemPath>
<itemPath>src/drivers/adc.c</itemPath>
<itemPath>src/drivers/buttons.c</itemPath>
<itemPath>src/drivers/leds.c</itemPath>
</logicalFolder>
<logicalFolder name="f2" displayName="usb" projectFiles="true">
<itemPath>src/usb/usb_descriptors.c</itemPath>
<itemPath>src/usb/usb_events.c</itemPath>
<itemPath>src/usb/usb_device.c</itemPath>
<itemPath>src/usb/usb_device_hid.c</itemPath>
</logicalFolder>
<itemPath>src/main.c</itemPath>
<itemPath>src/system.c</itemPath>
</logicalFolder>
<logicalFolder name="ExternalFiles"
displayName="Important Files"
projectFiles="false">
<itemPath>Makefile</itemPath>
</logicalFolder>
</logicalFolder>
<sourceRootList>
<Elem>.</Elem>
<Elem>src/drivers</Elem>
<Elem>src/usb</Elem>
</sourceRootList>
<projectmakefile>Makefile</projectmakefile>
<confs>
<conf name="LPCUSBDK_18F14K50" type="2">
<toolsSet>
<developmentServer>localhost</developmentServer>
<targetDevice>PIC18F14K50</targetDevice>
<targetHeader></targetHeader>
<targetPluginBoard></targetPluginBoard>
<platformTool>PICkit2PlatformTool</platformTool>
<languageToolchain>XC8</languageToolchain>
<languageToolchainVersion>1.42</languageToolchainVersion>
<platform>4</platform>
</toolsSet>
<compileType>
<linkerTool>
<linkerLibItems>
</linkerLibItems>
</linkerTool>
<archiverTool>
</archiverTool>
<loading>
<useAlternateLoadableFile>false</useAlternateLoadableFile>
<parseOnProdLoad>true</parseOnProdLoad>
<alternateLoadableFile></alternateLoadableFile>
</loading>
<subordinates>
</subordinates>
</compileType>
<makeCustomizationType>
<makeCustomizationPreStepEnabled>false</makeCustomizationPreStepEnabled>
<makeCustomizationPreStep></makeCustomizationPreStep>
<makeCustomizationPostStepEnabled>false</makeCustomizationPostStepEnabled>
<makeCustomizationPostStep></makeCustomizationPostStep>
<makeCustomizationPutChecksumInUserID>false</makeCustomizationPutChecksumInUserID>
<makeCustomizationEnableLongLines>false</makeCustomizationEnableLongLines>
<makeCustomizationNormalizeHexFile>false</makeCustomizationNormalizeHexFile>
</makeCustomizationType>
<HI-TECH-COMP>
<property key="asmlist" value="true"/>
<property key="define-macros" value=""/>
<property key="disable-optimizations" value="false"/>
<property key="extra-include-directories" value=".;inc;inc/drivers;inc/usb"/>
<property key="favor-optimization-for" value="+speed,-space"/>
<property key="identifier-length" value="100"/>
<property key="local-generation" value="false"/>
<property key="operation-mode" value="pro"/>
<property key="opt-xc8-compiler-strict_ansi" value="false"/>
<property key="optimization-assembler" value="true"/>
<property key="optimization-assembler-files" value="false"/>
<property key="optimization-debug" value="false"/>
<property key="optimization-global" value="true"/>
<property key="optimization-invariant-enable" value="false"/>
<property key="optimization-invariant-value" value="16"/>
<property key="optimization-level" value="9"/>
<property key="optimization-set" value="default"/>
<property key="optimization-speed" value="true"/>
<property key="optimization-stable-enable" value="false"/>
<property key="preprocess-assembler" value="true"/>
<property key="undefine-macros" value=""/>
<property key="use-cci" value="false"/>
<property key="use-iar" value="false"/>
<property key="verbose" value="false"/>
<property key="warning-level" value="0"/>
<property key="what-to-do" value="ignore"/>
</HI-TECH-COMP>
<HI-TECH-LINK>
<property key="additional-options-checksum" value=""/>
<property key="additional-options-code-offset" value=""/>
<property key="additional-options-command-line" value=""/>
<property key="additional-options-errata" value=""/>
<property key="additional-options-extend-address" value="false"/>
<property key="additional-options-trace-type" value=""/>
<property key="additional-options-use-response-files" value="false"/>
<property key="backup-reset-condition-flags" value="false"/>
<property key="calibrate-oscillator" value="true"/>
<property key="calibrate-oscillator-value" value=""/>
<property key="clear-bss" value="true"/>
<property key="code-model-external" value="wordwrite"/>
<property key="code-model-rom" value=""/>
<property key="create-html-files" value="false"/>
<property key="data-model-ram" value=""/>
<property key="data-model-size-of-double" value="24"/>
<property key="data-model-size-of-float" value="24"/>
<property key="display-class-usage" value="false"/>
<property key="display-hex-usage" value="false"/>
<property key="display-overall-usage" value="true"/>
<property key="display-psect-usage" value="false"/>
<property key="fill-flash-options-addr" value=""/>
<property key="fill-flash-options-const" value=""/>
<property key="fill-flash-options-how" value="0"/>
<property key="fill-flash-options-inc-const" value="1"/>
<property key="fill-flash-options-increment" value=""/>
<property key="fill-flash-options-seq" value=""/>
<property key="fill-flash-options-what" value="0"/>
<property key="format-hex-file-for-download" value="false"/>
<property key="initialize-data" value="true"/>
<property key="keep-generated-startup.as" value="false"/>
<property key="link-in-c-library" value="true"/>
<property key="link-in-peripheral-library" value="false"/>
<property key="managed-stack" value="false"/>
<property key="opt-xc8-linker-file" value="false"/>
<property key="opt-xc8-linker-link_startup" value="false"/>
<property key="opt-xc8-linker-serial" value=""/>
<property key="program-the-device-with-default-config-words" value="true"/>
</HI-TECH-LINK>
<ICD3PlatformTool>
<property key="AutoSelectMemRanges" value="auto"/>
<property key="SecureSegment.SegmentProgramming" value="FullChipProgramming"/>
<property key="ToolFirmwareFilePath"
value="Press to browse for a specific firmware version"/>
<property key="ToolFirmwareOption.UseLatestFirmware" value="true"/>
<property key="debugoptions.useswbreakpoints" value="false"/>
<property key="hwtoolclock.frcindebug" value="false"/>
<property key="memories.aux" value="false"/>
<property key="memories.bootflash" value="false"/>
<property key="memories.configurationmemory" value="true"/>
<property key="memories.configurationmemory2" value="true"/>
<property key="memories.dataflash" value="true"/>
<property key="memories.eeprom" value="true"/>
<property key="memories.flashdata" value="true"/>
<property key="memories.id" value="true"/>
<property key="memories.programmemory" value="true"/>
<property key="memories.programmemory.end" value="0x3fff"/>
<property key="memories.programmemory.partition2" value="true"/>
<property key="memories.programmemory.partition2.end"
value="${memories.programmemory.partition2.end.value}"/>
<property key="memories.programmemory.partition2.start"
value="${memories.programmemory.partition2.start.value}"/>
<property key="memories.programmemory.start" value="0x0"/>
<property key="poweroptions.powerenable" value="false"/>
<property key="programoptions.donoteraseauxmem" value="false"/>
<property key="programoptions.eraseb4program" value="true"/>
<property key="programoptions.preservedataflash" value="false"/>
<property key="programoptions.preserveeeprom" value="false"/>
<property key="programoptions.preserveprogramrange" value="false"/>
<property key="programoptions.preserveprogramrange.end" value="0x3fff"/>
<property key="programoptions.preserveprogramrange.start" value="0x0"/>
<property key="programoptions.preserveuserid" value="false"/>
<property key="programoptions.programcalmem" value="false"/>
<property key="programoptions.programuserotp" value="false"/>
<property key="programoptions.testmodeentrymethod" value="VPPFirst"/>
<property key="programoptions.usehighvoltageonmclr" value="false"/>
<property key="programoptions.uselvpprogramming" value="false"/>
<property key="voltagevalue" value="3.25"/>
</ICD3PlatformTool>
<PICkit2PlatformTool>
<property key="pk2settings.3state" value="false"/>
<property key="pk2settings.preserveee" value="false"/>
<property key="pk2settings.setvddvoltage" value="3.30"/>
<property key="pk2settings.userpgmexec" value="true"/>
<property key="pk2settings.usetargetpower" value="false"/>
</PICkit2PlatformTool>
<Simulator>
<property key="codecoverage.enabled" value="Disable"/>
<property key="codecoverage.enableoutputtofile" value="false"/>
<property key="codecoverage.outputfile" value=""/>
<property key="oscillator.auxfrequency" value="120"/>
<property key="oscillator.auxfrequencyunit" value="Mega"/>
<property key="oscillator.frequency" value="1"/>
<property key="oscillator.frequencyunit" value="Mega"/>
<property key="oscillator.rcfrequency" value="250"/>
<property key="oscillator.rcfrequencyunit" value="Kilo"/>
<property key="periphADC1.altscl" value="false"/>
<property key="periphADC1.minTacq" value="5"/>
<property key="periphADC1.tacqunits" value="microseconds"/>
<property key="periphADC2.altscl" value="false"/>
<property key="periphADC2.minTacq" value=""/>
<property key="periphADC2.tacqunits" value="microseconds"/>
<property key="periphComp1.gte" value="gt"/>
<property key="periphComp2.gte" value="gt"/>
<property key="periphComp3.gte" value="gt"/>
<property key="periphComp4.gte" value="gt"/>
<property key="periphComp5.gte" value="gt"/>
<property key="periphComp6.gte" value="gt"/>
<property key="reset.scl" value="false"/>
<property key="reset.type" value="MCLR"/>
<property key="tracecontrol.include.timestamp" value="summarydataenabled"/>
<property key="tracecontrol.select" value="0"/>
<property key="tracecontrol.stallontracebufferfull" value="false"/>
<property key="tracecontrol.timestamp" value="0"/>
<property key="tracecontrol.tracebufmax" value="546000"/>
<property key="tracecontrol.tracefile" value="defmplabxtrace.log"/>
<property key="tracecontrol.traceresetonrun" value="false"/>
<property key="uart10io.output" value="window"/>
<property key="uart10io.outputfile" value=""/>
<property key="uart10io.uartioenabled" value="false"/>
<property key="uart1io.output" value="window"/>
<property key="uart1io.outputfile" value=""/>
<property key="uart1io.uartioenabled" value="false"/>
<property key="uart2io.output" value="window"/>
<property key="uart2io.outputfile" value=""/>
<property key="uart2io.uartioenabled" value="false"/>
<property key="uart3io.output" value="window"/>
<property key="uart3io.outputfile" value=""/>
<property key="uart3io.uartioenabled" value="false"/>
<property key="uart4io.output" value="window"/>
<property key="uart4io.outputfile" value=""/>
<property key="uart4io.uartioenabled" value="false"/>
<property key="uart5io.output" value="window"/>
<property key="uart5io.outputfile" value=""/>
<property key="uart5io.uartioenabled" value="false"/>
<property key="uart6io.output" value="window"/>
<property key="uart6io.outputfile" value=""/>
<property key="uart6io.uartioenabled" value="false"/>
<property key="uart7io.output" value="window"/>
<property key="uart7io.outputfile" value=""/>
<property key="uart7io.uartioenabled" value="false"/>
<property key="uart8io.output" value="window"/>
<property key="uart8io.outputfile" value=""/>
<property key="uart8io.uartioenabled" value="false"/>
<property key="uart9io.output" value="window"/>
<property key="uart9io.outputfile" value=""/>
<property key="uart9io.uartioenabled" value="false"/>
<property key="warningmessagebreakoptions.W0001_CORE_BITREV_MODULO_EN"
value="report"/>
<property key="warningmessagebreakoptions.W0002_CORE_SECURE_MEMORYACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0003_CORE_SW_RESET" value="report"/>
<property key="warningmessagebreakoptions.W0004_CORE_WDT_RESET" value="report"/>
<property key="warningmessagebreakoptions.W0005_CORE_IOPUW_RESET"
value="report"/>
<property key="warningmessagebreakoptions.W0006_CORE_CODE_GUARD_PFC_RESET"
value="report"/>
<property key="warningmessagebreakoptions.W0007_CORE_DO_LOOP_STACK_UNDERFLOW"
value="report"/>
<property key="warningmessagebreakoptions.W0008_CORE_DO_LOOP_STACK_OVERFLOW"
value="report"/>
<property key="warningmessagebreakoptions.W0009_CORE_NESTED_DO_LOOP_RANGE"
value="report"/>
<property key="warningmessagebreakoptions.W0010_CORE_SIM32_ODD_WORDACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0011_CORE_SIM32_UNIMPLEMENTED_RAMACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0012_CORE_STACK_OVERFLOW_RESET"
value="report"/>
<property key="warningmessagebreakoptions.W0013_CORE_STACK_UNDERFLOW_RESET"
value="report"/>
<property key="warningmessagebreakoptions.W0014_CORE_INVALID_OPCODE"
value="report"/>
<property key="warningmessagebreakoptions.W0015_CORE_INVALID_ALT_WREG_SET"
value="report"/>
<property key="warningmessagebreakoptions.W0016_CORE_STACK_ERROR"
value="report"/>
<property key="warningmessagebreakoptions.W0017_CORE_ODD_RAMWORDACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0018_CORE_UNIMPLEMENTED_RAMACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0019_CORE_UNIMPLEMENTED_PROMACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0020_CORE_ACCESS_NOTIN_X_SPACE"
value="report"/>
<property key="warningmessagebreakoptions.W0021_CORE_ACCESS_NOTIN_Y_SPACE"
value="report"/>
<property key="warningmessagebreakoptions.W0022_CORE_XMODEND_LESS_XMODSRT"
value="report"/>
<property key="warningmessagebreakoptions.W0023_CORE_YMODEND_LESS_YMODSRT"
value="report"/>
<property key="warningmessagebreakoptions.W0024_CORE_BITREV_MOD_IS_ZERO"
value="report"/>
<property key="warningmessagebreakoptions.W0025_CORE_HARD_TRAP" value="report"/>
<property key="warningmessagebreakoptions.W0026_CORE_UNIMPLEMENTED_MEMORYACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0027_CORE_UNIMPLEMENTED_EDSACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0028_TBLRD_WORM_CONFIG_MEMORY"
value="report"/>
<property key="warningmessagebreakoptions.W0029_TBLRD_DEVICE_ID" value="report"/>
<property key="warningmessagebreakoptions.W0030_CORE_UNIMPLEMENTED_MEMORY_ACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0031_BSLIM_INSUFFICIENT_BOOT_SEGMENT"
value="report"/>
<property key="warningmessagebreakoptions.W0032_BSLIM_LIMITS_EXCEEDS_PROG_MEMORY"
value="report"/>
<property key="warningmessagebreakoptions.W0033_CORE_UNPREDICTABLE_OPCODE"
value="report"/>
<property key="warningmessagebreakoptions.W0034_CORE_UNALIGNED_MEMORY_ACCESS"
value="report"/>
<property key="warningmessagebreakoptions.W0040_FPU_DIFF_CP10_CP11"
value="report"/>
<property key="warningmessagebreakoptions.W0041_FPU_ACCESS_DENIED"
value="report"/>
<property key="warningmessagebreakoptions.W0042_FPU_PRIVILEGED_ACCESS_ONLY"
value="report"/>
<property key="warningmessagebreakoptions.W0043_FPU_CP_RESERVED_VALUE"
value="report"/>
<property key="warningmessagebreakoptions.W0044_FPU_OUT_OF_RANGE"
value="report"/>
<property key="warningmessagebreakoptions.W0051_INSTRUCTION_DIV_NOT_ENOUGH_REPEAT"
value="report"/>
<property key="warningmessagebreakoptions.W0052_INSTRUCTION_DIV_TOO_MANY_REPEAT"
value="report"/>
<property key="warningmessagebreakoptions.W0101_SIM_UPDATE_FAILED"
value="report"/>
<property key="warningmessagebreakoptions.W0102_SIM_PERIPH_MISSING"
value="report"/>
<property key="warningmessagebreakoptions.W0103_SIM_PERIPH_FAILED"
value="report"/>
<property key="warningmessagebreakoptions.W0104_SIM_FAILED_TO_INIT_TOOL"
value="report"/>
<property key="warningmessagebreakoptions.W0105_SIM_INVALID_FIELD"
value="report"/>
<property key="warningmessagebreakoptions.W0106_SIM_PERIPH_PARTIAL_SUPPORT"
value="report"/>
<property key="warningmessagebreakoptions.W0107_SIM_NOT_SUPPORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0108_SIM_RESERVED_SETTING"
value="report"/>
<property key="warningmessagebreakoptions.W0109_SIM_PERIPHERAL_IN_DEVELOPMENT"
value="report"/>
<property key="warningmessagebreakoptions.W0110_SIM_UNEXPECTED_EVENT"
value="report"/>
<property key="warningmessagebreakoptions.W0201_ADC_NO_STIMULUS_FILE"
value="report"/>
<property key="warningmessagebreakoptions.W0202_ADC_GO_DONE_BIT" value="report"/>
<property key="warningmessagebreakoptions.W0203_ADC_MINIMUM_2_TAD"
value="report"/>
<property key="warningmessagebreakoptions.W0204_ADC_TAD_TOO_SMALL"
value="report"/>
<property key="warningmessagebreakoptions.W0205_ADC_UNEXPECTED_TRANSITION"
value="report"/>
<property key="warningmessagebreakoptions.W0206_ADC_SAMP_TIME_TOO_SHORT"
value="report"/>
<property key="warningmessagebreakoptions.W0207_ADC_NO_PINS_SCANNED"
value="report"/>
<property key="warningmessagebreakoptions.W0208_ADC_UNSUPPORTED_CLOCK_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W0209_ADC_ANALOG_CHANNEL_DIGITAL"
value="report"/>
<property key="warningmessagebreakoptions.W0210_ADC_ANALOG_CHANNEL_OUTPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0211_ADC_PIN_INVALID_CHANNEL"
value="report"/>
<property key="warningmessagebreakoptions.W0212_ADC_BAND_GAP_NOT_SUPPORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0213_ADC_RESERVED_SSRC"
value="report"/>
<property key="warningmessagebreakoptions.W0214_ADC_POSITIVE_INPUT_DIGITAL"
value="report"/>
<property key="warningmessagebreakoptions.W0215_ADC_POSITIVE_INPUT_OUTPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0216_ADC_NEGATIVE_INPUT_DIGITAL"
value="report"/>
<property key="warningmessagebreakoptions.W0217_ADC_NEGATIVE_INPUT_OUTPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0218_ADC_REFERENCE_HIGH_DIGITAL"
value="report"/>
<property key="warningmessagebreakoptions.W0219_ADC_REFERENCE_HIGH_OUTPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0220_ADC_REFERENCE_LOW_DIGITAL"
value="report"/>
<property key="warningmessagebreakoptions.W0221_ADC_REFERENCE_LOW_OUTPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0222_ADC_OVERFLOW" value="report"/>
<property key="warningmessagebreakoptions.W0223_ADC_UNDERFLOW" value="report"/>
<property key="warningmessagebreakoptions.W0224_ADC_CTMU_NOT_SUPPORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0225_ADC_INVALID_CH0S"
value="report"/>
<property key="warningmessagebreakoptions.W0226_ADC_VBAT_NOT_SUPPORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0227_ADC_INVALID_ADCS"
value="report"/>
<property key="warningmessagebreakoptions.W0228_ADC_INVALID_ADCS"
value="report"/>
<property key="warningmessagebreakoptions.W0229_ADC_INVALID_ADCS"
value="report"/>
<property key="warningmessagebreakoptions.W0230_ADC_TRIGSEL_NOT_SUPPORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0231_ADC_NOT_WARMED" value="report"/>
<property key="warningmessagebreakoptions.W0232_ADC_CALIBRATION_ABORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0233_ADC_CORE_POWERED_EARLY"
value="report"/>
<property key="warningmessagebreakoptions.W0234_ADC_ALREADY_CALIBRATING"
value="report"/>
<property key="warningmessagebreakoptions.W0235_ADC_CAL_TYPE_CHANGED"
value="report"/>
<property key="warningmessagebreakoptions.W0236_ADC_CAL_INVALIDATED"
value="report"/>
<property key="warningmessagebreakoptions.W0237_ADC_UNKNOWN_DATASHEET"
value="report"/>
<property key="warningmessagebreakoptions.W0238_ADC_INVALID_SFR_FIELD_VALUE"
value="report"/>
<property key="warningmessagebreakoptions.W0239_ADC_UNSUPPORTED_INPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0240_ADC_NOT_CALIBRATED"
value="report"/>
<property key="warningmessagebreakoptions.W0241_ADC_FRACTIONAL_NOT_ALLOWED"
value="report"/>
<property key="warningmessagebreakoptions.W0242_ADC_BG_INT_BEFORE_PWR"
value="report"/>
<property key="warningmessagebreakoptions.W0243_ADC_INVALID_TAD" value="report"/>
<property key="warningmessagebreakoptions.W0244_ADC_CONVERSION_ABORTED"
value="report"/>
<property key="warningmessagebreakoptions.W0400_PWM_PWM_FASTER_THAN_FOSC"
value="report"/>
<property key="warningmessagebreakoptions.W0700_CLC_GENERAL_WARNING"
value="report"/>
<property key="warningmessagebreakoptions.W0701_CLC_CLCOUT_AS_INPUT"
value="report"/>
<property key="warningmessagebreakoptions.W0702_CLC_CIRCULAR_LOOP"
value="report"/>
<property key="warningmessagebreakoptions.W10001_RESERVED_IRQ_HANDLER_INVOKED"
value="report"/>
<property key="warningmessagebreakoptions.W10002_UNSUPPORTED_CLK_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W1201_DATAFLASH_MEM_OUTSIDE_RANGE"
value="report"/>
<property key="warningmessagebreakoptions.W1202_DATAFLASH_ERASE_WHILE_LOCKED"
value="report"/>
<property key="warningmessagebreakoptions.W1203_DATAFLASH_WRITE_WHILE_LOCKED"
value="report"/>
<property key="warningmessagebreakoptions.W1401_DMA_PERIPH_NOT_AVAIL"
value="report"/>
<property key="warningmessagebreakoptions.W1402_DMA_INVALID_IRQ" value="report"/>
<property key="warningmessagebreakoptions.W1403_DMA_INVALID_SFR" value="report"/>
<property key="warningmessagebreakoptions.W1404_DMA_INVALID_DMA_ADDR"
value="report"/>
<property key="warningmessagebreakoptions.W1405_DMA_IRQ_DIR_MISMATCH"
value="report"/>
<property key="warningmessagebreakoptions.W1600_PPS_INVALID_MAP" value="report"/>
<property key="warningmessagebreakoptions.W1601_PPS_INVALID_PIN_DESCRIPTION"
value="report"/>
<property key="warningmessagebreakoptions.W1800_PWM_TIMER_SELECTION_NOT_AVIALABLE"
value="report"/>
<property key="warningmessagebreakoptions.W1801_PWM_TIMER_SELECTION_BAD_CLOCK_INPUT"
value="report"/>
<property key="warningmessagebreakoptions.W1802_PWM_TIMER_MISSING_PERSCALER_INFO"
value="report"/>
<property key="warningmessagebreakoptions.W2001_INPUTCAPTURE_TMR3_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W2002_INPUTCAPTURE_CAPTURE_EMPTY"
value="report"/>
<property key="warningmessagebreakoptions.W2003_INPUTCAPTURE_SYNCSEL_NOT_AVIALABLE"
value="report"/>
<property key="warningmessagebreakoptions.W2004_INPUTCAPTURE_BAD_SYNC_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W2501_OUTPUTCOMPARE_SYNCSEL_NOT_AVIALABLE"
value="report"/>
<property key="warningmessagebreakoptions.W2502_OUTPUTCOMPARE_BAD_SYNC_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W2503_OUTPUTCOMPARE_BAD_TRIGGER_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W2700_MPU_ILLEGAL_DREGION"
value="report"/>
<property key="warningmessagebreakoptions.W2701_MPU_INVALID_REGION"
value="report"/>
<property key="warningmessagebreakoptions.W7001_SMT_CLK_SELECTION_NOT_SUPPORT"
value="report"/>
<property key="warningmessagebreakoptions.W7002_SMT_SIG_SELECTION_NOT_SUPPORT"
value="report"/>
<property key="warningmessagebreakoptions.W7003_SMT_WIN_SELECTION_NOT_SUPPORT"
value="report"/>
<property key="warningmessagebreakoptions.W8001_OSC_INVALID_CLOCK_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W9001_TMR_GATE_AND_EXTCLOCK_ENABLED"
value="report"/>
<property key="warningmessagebreakoptions.W9002_TMR_NO_PIN_AVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9003_TMR_INVALID_CLOCK_SOURCE"
value="report"/>
<property key="warningmessagebreakoptions.W9201_UART_TX_OVERFLOW"
value="report"/>
<property key="warningmessagebreakoptions.W9202_UART_TX_CAPTUREFILE"
value="report"/>
<property key="warningmessagebreakoptions.W9203_UART_TX_INVALIDINTERRUPTMODE"
value="report"/>
<property key="warningmessagebreakoptions.W9204_UART_RX_EMPTY_QUEUE"
value="report"/>
<property key="warningmessagebreakoptions.W9205_UART_TX_BADFILE" value="report"/>
<property key="warningmessagebreakoptions.W9401_CVREF_INVALIDSOURCESELECTION"
value="report"/>
<property key="warningmessagebreakoptions.W9402_CVREF_INPUT_OUTPUTPINCONFLICT"
value="report"/>
<property key="warningmessagebreakoptions.W9601_COMP_FVR_SOURCE_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9602_COMP_DAC_SOURCE_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9603_COMP_CVREF_SOURCE_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9604_COMP_SLOPE_SOURCE_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9605_COMP_PRG_SOURCE_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9607_COMP_DGTL_FLTR_OPTION_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9609_COMP_DGTL_FLTR_CLK_UNAVAILABLE"
value="report"/>
<property key="warningmessagebreakoptions.W9801_FVR_INVALID_MODE_SELECTION"
value="report"/>
<property key="warningmessagebreakoptions.W9801_SCL_BAD_SUBTYPE_INDICATION"
value="report"/>
<property key="warningmessagebreakoptions.W9802_SCL_FILE_NOT_FOUND"
value="report"/>
<property key="warningmessagebreakoptions.W9803_SCL_FAILED_TO_READ_FILE"
value="report"/>
<property key="warningmessagebreakoptions.W9804_SCL_UNRECOGNIZED_LABEL"
value="report"/>
<property key="warningmessagebreakoptions.W9805_SCL_UNRECOGNIZED_VAR"
value="report"/>
<property key="warningmessagebreakoptions.W9901_RTSP_INVALID_OPERATION_SELECTION"
value="report"/>
<property key="warningmessagebreakoptions.W9902_RTSP_FLASH_PROGRAM_WRITE_PROTECTED"
value="report"/>
<property key="warningmessagebreakoptions.displaywarningmessagesoption"
value=""/>
<property key="warningmessagebreakoptions.warningmessages" value="holdstate"/>
</Simulator>
<XC8-config-global>
<property key="advanced-elf" value="true"/>
<property key="output-file-format" value="-mcof,+elf"/>
<property key="stack-size-high" value="auto"/>
<property key="stack-size-low" value="auto"/>
<property key="stack-size-main" value="auto"/>
<property key="stack-type" value="compiled"/>
</XC8-config-global>
</conf>
</confs>
</configurationDescriptor>

16
nbproject/project.xml Normal file
View File

@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://www.netbeans.org/ns/project/1">
<type>com.microchip.mplab.nbide.embedded.makeproject</type>
<configuration>
<data xmlns="http://www.netbeans.org/ns/make-project/1">
<name>Apple_II_USB</name>
<make-project-type>0</make-project-type>
<c-extensions>c</c-extensions>
<cpp-extensions/>
<header-extensions>h</header-extensions>
<sourceEncoding>UTF-8</sourceEncoding>
<asminc-extensions/>
<make-dep-projects/>
</data>
</configuration>
</project>

207
src/drivers/adc.c Normal file
View File

@ -0,0 +1,207 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#include <adc.h>
#include <stdint.h>
#include <stdbool.h>
#include <xc.h>
#include <adc.h>
#define PIN_ANALOG 1
#define PIN_DIGITAL 0
#define PIN_INPUT 1
#define PIN_OUTPUT 0
/*********************************************************************
* Function: ADC_ReadPercentage(ADC_CHANNEL channel);
*
* Overview: Reads the requested ADC channel and returns the percentage
* of that conversions result (0-100%).
*
* PreCondition: channel is configured via the ADCConfigure() function
*
* Input: ADC_CHANNEL channel - enumeration of the ADC channels
* available in this demo. They should be meaningful names and
* not the names of the ADC pins on the device (as the demo code
* may be ported to other boards).
* i.e. ADC_ReadPercentage(ADC_CHANNEL_POTENTIOMETER);
*
* Output: uint8_t indicating the percentage of the result 0-100% or
* 0xFF for an error
*
********************************************************************/
uint8_t ADC_ReadPercentage
(ADC_CHANNEL channel) {
uint8_t percent;
switch(channel)
{
case ADC_CHANNEL_8:
break;
case ADC_CHANNEL_9:
break;
default:
return 0xFF;
}
//A very crude percentage calculation
percent = (ADC_Read10bit(channel) / 10);
if(percent > 100)
{
percent = 100;
}
return percent;
}
/*********************************************************************
* Function: ADC_Read10bit(ADC_CHANNEL channel);
*
* Overview: Reads the requested ADC channel and returns the 10-bit
* representation of this data.
*
* PreCondition: channel is configured via the ADCConfigure() function
*
* Input: ADC_CHANNEL channel - enumeration of the ADC channels
* available in this demo. They should be meaningful names and
* not the names of the ADC pins on the device (as the demo code
* may be ported to other boards).
* i.e. - ADCReadPercentage(ADC_CHANNEL_POTENTIOMETER);
*
* Output: uint16_t the right adjusted 10-bit representation of the ADC
* channel conversion or 0xFFFF for an error.
*
********************************************************************/
uint16_t ADC_Read10bit(ADC_CHANNEL channel)
{
uint16_t result;
switch(channel)
{
case ADC_CHANNEL_8:
break;
case ADC_CHANNEL_9:
break;
default:
return 0xFFFF;
}
ADCON0bits.CHS = channel;
ADCON0bits.GO = 1; // Start AD conversion
while(ADCON0bits.NOT_DONE); // Wait for conversion
result = ADRESH;
result <<=8;
result |= ADRESL;
return result;
}
uint8_t ADC_Read8bit(ADC_CHANNEL channel)
{
uint8_t result;
switch(channel)
{
case ADC_CHANNEL_8:
break;
case ADC_CHANNEL_9:
break;
default:
return 0xFFFF;
}
ADCON0bits.CHS = channel;
ADCON0bits.GO = 1; // Start AD conversion
while(ADCON0bits.NOT_DONE); // Wait for conversion
result = ADRESH;
//result <<=8;
//result |= ADRESL;
return result;
}
/*********************************************************************
* Function: bool ADC_Enable(ADC_CHANNEL channel, ADC_CONFIGURATION configuration);
*
* Overview: Configures the ADC module to specified setting
*
* PreCondition: none
*
* Input: ADC_CHANNEL channel - the channel to enable
* ADC_CONFIGURATION configuration - the mode in which to run the ADC
*
* Output: bool - true if successfully configured. false otherwise.
*
********************************************************************/
bool ADC_Enable(ADC_CHANNEL channel)
{
switch(channel)
{
case ADC_CHANNEL_8:
TRISCbits.TRISC6 = PIN_INPUT;
ANSELHbits.ANS8 = PIN_ANALOG;
return true;
case ADC_CHANNEL_9:
TRISCbits.TRISC7 = PIN_INPUT;
ANSELHbits.ANS9 = PIN_ANALOG;
return true;
default:
return false;
}
}
/*********************************************************************
* Function: bool ADC_SetConfiguration(ADC_CONFIGURATION configuration)
*
* Overview: Configures the ADC module to specified setting
*
* PreCondition: none
*
* Input: ADC_CONFIGURATION configuration - the mode in which to run the ADC
*
* Output: bool - true if successfully configured. false otherwise.
*
********************************************************************/
bool ADC_SetConfiguration(ADC_CONFIGURATION configuration)
{
if(configuration == ADC_CONFIGURATION_DEFAULT)
{
//ADCON0=0b00000001;
ADCON0bits.ADON = 1;
ADCON1=0b00000000;
//ADCON2=0b00111110;
ADCON2bits.ACQT = 0b111;
ADCON2bits.ADCS = 0b110;
ADCON2bits.ADFM = 1;
return true;
}
return false;
}

View File

@ -0,0 +1,34 @@
#include "stdint.h"
#include "system.h"
#include "usb_device.h"
void APP_LEDUpdateUSBStatus(void) {
static uint16_t ledCount = 0;
// If device is suspended, LED is turned off
if (USBIsDeviceSuspended() == true) {
LED_Off(LED_USB_DEVICE_STATE);
return;
}
switch (USBGetDeviceState()) {
// If device is configured, LED on
case CONFIGURED_STATE:
LED_On(LED_USB_DEVICE_STATE);
break;
default:
// Not configured so slow blink
if (ledCount == 1) {
LED_On(LED_USB_DEVICE_STATE);
} else if (ledCount == 50) {
LED_Off(LED_USB_DEVICE_STATE);
} else if (ledCount > 950) {
ledCount = 0;
}
break;
}
/* Increment the millisecond counter. */
ledCount++;
}

105
src/drivers/buttons.c Normal file
View File

@ -0,0 +1,105 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#include <xc.h>
#include <stdbool.h>
#include <buttons.h>
/*** Button Definitions *********************************************/
#define S1_PORT PORTCbits.RC0
#define S2_PORT PORTCbits.RC1
#define S1_TRIS TRISCbits.TRISC0
#define S2_TRIS TRISCbits.TRISC1
#define BUTTON_PRESSED 1
#define BUTTON_NOT_PRESSED 0
#define PIN_INPUT 1
#define PIN_OUTPUT 0
#define PIN_DIGITAL 0
#define PIN_ANALOG 1
/*********************************************************************
* Function: bool BUTTON_IsPressed(BUTTON button);
*
* Overview: Returns the current state of the requested button
*
* PreCondition: button configured via BUTTON_SetConfiguration()
*
* Input: BUTTON button - enumeration of the buttons available in
* this demo. They should be meaningful names and not the names
* of the buttons on the silkscreen on the board (as the demo
* code may be ported to other boards).
* i.e. - ButtonIsPressed(BUTTON_SEND_MESSAGE);
*
* Output: TRUE if pressed; FALSE if not pressed.
*
********************************************************************/
bool BUTTON_IsPressed(BUTTON button) {
switch (button) {
case BUTTON_S1:
return ( (S1_PORT == BUTTON_PRESSED) ? true : false);
case BUTTON_S2:
return ( (S2_PORT == BUTTON_PRESSED) ? true : false);
case BUTTON_NONE:
return false;
}
return false;
}
/*********************************************************************
* Function: void BUTTON_Enable(BUTTON button);
*
* Overview: Returns the current state of the requested button
*
* PreCondition: button configured via BUTTON_SetConfiguration()
*
* Input: BUTTON button - enumeration of the buttons available in
* this demo. They should be meaningful names and not the names
* of the buttons on the silkscreen on the board (as the demo
* code may be ported to other boards).
* i.e. - ButtonIsPressed(BUTTON_SEND_MESSAGE);
*
* Output: None
*
********************************************************************/
void BUTTON_Enable(BUTTON button) {
switch (button) {
case BUTTON_S1:
S1_TRIS = PIN_INPUT;
ANSELbits.ANS4 = PIN_DIGITAL;
break;
case BUTTON_S2:
S2_TRIS = PIN_INPUT;
ANSELbits.ANS5 = PIN_DIGITAL;
break;
case BUTTON_NONE:
break;
}
}

51
src/drivers/eeprom.c Normal file
View File

@ -0,0 +1,51 @@
/*
* EEPROM routines
* www.flitey.com
*/
#include <xc.h>
#include <stdbool.h>
#include <stdint.h>
unsigned char EepromReadByte(uint8_t byteAddress) {
EEADR = byteAddress;
EECON1bits.CFGS = 0;
EECON1bits.EEPGD = 0;
EECON1bits.RD = 1;
Nop(); //Nop may be required for latency at high frequencies
Nop(); //Nop may be required for latency at high frequencies
return (EEDATA);
}
void EepromWriteByte(uint8_t byteAddress, uint8_t byteData) {
bool GIE_BIT_VAL;
EEADR = byteAddress;
EEDATA = byteData;
EECON1bits.EEPGD = 0;
EECON1bits.CFGS = 0;
EECON1bits.WREN = 1;
GIE_BIT_VAL = INTCONbits.GIE;
INTCONbits.GIE = 0;
EECON2 = 0x55; // critical unlock sequence
EECON2 = 0xAA;
EECON1bits.WR = 1; // end critical sequence
while (EECON1bits.WR); //Wait till the write completion
INTCONbits.GIE = GIE_BIT_VAL;
EECON1bits.WREN = 0;
}
uint16_t EepromReadTwoBytes(uint8_t startAddress) {
unsigned char highByte = EepromReadByte(startAddress);
unsigned char lowByte = EepromReadByte(startAddress + 1);
uint16_t result = (highByte << 8) | lowByte;
return result;
}
void EepromWriteTwoBytes(uint8_t startAddress, uint16_t value) {
uint8_t high = (value & 0xFF00) >> 8;
uint8_t low = (value & 0x00FF);
EepromWriteByte(startAddress, high);
EepromWriteByte(startAddress + 1, low);
}

271
src/drivers/joystick.c Normal file
View File

@ -0,0 +1,271 @@
/**
* Joystick functions
* www.flitey.com
*/
#ifndef USBJOYSTICK_C
#define USBJOYSTICK_C
/** INCLUDES *******************************************************/
#include "usb.h"
#include "usb_device_hid.h"
#include "system.h"
#include "app_led_usb_status.h"
#include "stdint.h"
#include "system.h"
#include "eeprom.h"
/** DECLARATIONS ***************************************************/
uint8_t joystick_counter = 0;
bool calibrated = false;
uint16_t x_axis_center = JOYSTICK_10_BIT_MID;
uint16_t y_axis_center = JOYSTICK_10_BIT_MID;
uint16_t x_axis_max = JOYSTICK_10_BIT_MID;
uint16_t x_axis_min = JOYSTICK_10_BIT_MID;
uint16_t y_axis_max = JOYSTICK_10_BIT_MID;
uint16_t y_axis_min = JOYSTICK_10_BIT_MID;
/** TYPE DEFINITIONS ************************************************/
typedef union _INTPUT_CONTROLS_TYPEDEF {
struct {
struct {
uint8_t x : 1;
uint8_t y : 1;
uint8_t:
6; //filler
} buttons;
struct {
uint8_t X;
uint8_t Y;
} analog_stick;
} members;
uint8_t val[3];
} INPUT_CONTROLS;
INPUT_CONTROLS joystick_input @ JOYSTICK_DATA_ADDRESS;
USB_VOLATILE USB_HANDLE lastTransmission = 0;
void JoystickInitialize(void) {
lastTransmission = 0;
//enable the HID endpoint
USBEnableEndpoint(JOYSTICK_EP, USB_IN_ENABLED | USB_HANDSHAKE_ENABLED | USB_DISALLOW_SETUP);
}
/**
* Calibrate the joystick potentiometers. We wait for the button to be released
* and then start the calibration. Calibration looks for the min and max values
* for each potentiometer and also checks if one of the buttons has been pressed.
* The button press indicates calibration is complete.
*/
void JoystickRunCalibration() {
while (BUTTON_IsPressed(GAME_SWITCH_0) == true || BUTTON_IsPressed(GAME_SWITCH_1) == true) {
// wait for buttons to be released
}
uint16_t ledCounter = 0;
while (!calibrated) {
if (ledCounter == 1) {
LED_On(LED_USB_DEVICE_STATE);
} else if (ledCounter == 5000) {
LED_Off(LED_USB_DEVICE_STATE);
} else if (ledCounter == 10000) {
ledCounter = 0;
}
uint16_t X_axis = ADC_Read10bit(PDL0);
uint16_t Y_axis = ADC_Read10bit(PDL1);
if (X_axis >= x_axis_max) {
x_axis_max = X_axis;
}
if (X_axis <= x_axis_min) {
x_axis_min = X_axis;
}
if (Y_axis >= y_axis_max) {
y_axis_max = Y_axis;
}
if (Y_axis <= y_axis_min) {
y_axis_min = Y_axis;
}
if (BUTTON_IsPressed(GAME_SWITCH_0) == true || BUTTON_IsPressed(GAME_SWITCH_1) == true) {
while (BUTTON_IsPressed(GAME_SWITCH_0) == true || BUTTON_IsPressed(GAME_SWITCH_1) == true) {
// wait
}
LED_Off(LED_USB_DEVICE_STATE);
// Very arbitrary wait time so we can make sure the center value is stable
uint16_t waitCount = 0;
for (uint8_t i = 0; i < 40; i++) {
while (waitCount < 65000) {
waitCount++;
}
}
X_axis = ADC_Read10bit(PDL0);
Y_axis = ADC_Read10bit(PDL1);
x_axis_center = X_axis;
y_axis_center = Y_axis;
EepromWriteTwoBytes(X_AXIS_MIN_EEPROM_ADDRESS, x_axis_min);
EepromWriteTwoBytes(X_AXIS_MID_EEPROM_ADDRESS, x_axis_center);
EepromWriteTwoBytes(X_AXIS_MAX_EEPROM_ADDRESS, x_axis_max);
EepromWriteTwoBytes(Y_AXIS_MIN_EEPROM_ADDRESS, y_axis_min);
EepromWriteTwoBytes(Y_AXIS_MID_EEPROM_ADDRESS, y_axis_center);
EepromWriteTwoBytes(Y_AXIS_MAX_EEPROM_ADDRESS, y_axis_max);
calibrated = true;
}
ledCounter++;
}
}
/**
* Verifies the specified value is within the valid range
* @param value the value to test
* @return true if value is within the range, otherwise false
*/
bool isValidCalibrationValue(uint16_t value) {
if (value <= JOYSTICK_10_BIT_MAX && value >= JOYSTICK_10_BIT_MIN) {
return true;
} else {
return false;
}
}
void JoystickUseSavedCalibration(uint16_t x_min, uint16_t x_mid, uint16_t x_max, uint16_t y_min, uint16_t y_mid, uint16_t y_max) {
if (isValidCalibrationValue(x_min)) {
x_axis_min = x_min;
} else {
x_axis_min = JOYSTICK_10_BIT_MIN;
}
if (isValidCalibrationValue(x_mid)) {
x_axis_center = x_mid;
} else {
x_axis_center = JOYSTICK_10_BIT_MID;
}
if (isValidCalibrationValue(x_max)) {
x_axis_max = x_max;
} else {
x_axis_max = JOYSTICK_10_BIT_MAX;
}
if (isValidCalibrationValue(y_min)) {
y_axis_min = y_min;
} else {
y_axis_min = JOYSTICK_10_BIT_MIN;
}
if (isValidCalibrationValue(y_mid)) {
y_axis_center = y_mid;
} else {
y_axis_center = JOYSTICK_10_BIT_MID;
}
if (isValidCalibrationValue(y_max)) {
y_axis_max = y_max;
} else {
y_axis_max = JOYSTICK_10_BIT_MAX;
}
calibrated = true;
}
/**
* Converts the ADC value to be within the calibration range.
* @param ADCValue the 10 bit value read from the ADC
* @param inputMin the min calibration value for this axis
* @param inputMid the midpoint calibration value for this axis
* @param inputMax the max calibration value for this axis
* @return the final joystick value mapped to the calibration range
*/
uint8_t convertValue(uint16_t ADCValue, uint16_t inputMin, uint16_t inputMid, uint16_t inputMax) {
// Prevent output from going beyond the min and max values
if (ADCValue > inputMax) {
ADCValue = inputMax;
} else if (ADCValue < inputMin) {
ADCValue = inputMin;
}
uint16_t input_end = inputMax;
uint16_t input_start = inputMid;
uint16_t output_end = JOYSTICK_8_BIT_MAX_OUTPUT;
uint16_t output_start = JOYSTICK_8_BIT_MID_OUTPUT;
if (ADCValue < inputMid) {
input_end = inputMid - 1;
input_start = inputMin;
output_end = JOYSTICK_8_BIT_MID_OUTPUT - 1;
output_start = JOYSTICK_8_BIT_MIN_OUTPUT;
}
double x_slope = 1.0 * (output_end - output_start) / (input_end - input_start);
uint16_t sixteenBitOutput = output_start + x_slope * (ADCValue - input_start);
uint8_t finalOutput = JOYSTICK_8_BIT_MAX_OUTPUT - (uint8_t) sixteenBitOutput;
return finalOutput;
}
void JoystickTasks(void) {
if (USBGetDeviceState() < CONFIGURED_STATE) {
return;
}
if (USBIsDeviceSuspended() == true) {
return;
}
//If the last transmission is complete
if (!HIDTxHandleBusy(lastTransmission)) {
if (joystick_counter > 5) {
if (BUTTON_IsPressed(GAME_SWITCH_0) == true) {
joystick_input.members.buttons.x = 1;
} else {
joystick_input.members.buttons.x = 0;
}
if (BUTTON_IsPressed(GAME_SWITCH_1) == true) {
joystick_input.members.buttons.y = 1;
} else {
joystick_input.members.buttons.y = 0;
}
uint16_t X_axis = ADC_Read10bit(PDL0);
uint16_t Y_axis = ADC_Read10bit(PDL1);
uint8_t x_output = convertValue(X_axis, x_axis_min, x_axis_center, x_axis_max);
uint8_t y_output = convertValue(Y_axis, y_axis_min, y_axis_center, y_axis_max);
joystick_input.members.analog_stick.X = x_output;
joystick_input.members.analog_stick.Y = y_output;
joystick_counter = 0;
} else {
joystick_counter++;
}
//Send the packet over USB to the host.
lastTransmission = HIDTxPacket(JOYSTICK_EP, (uint8_t*) & joystick_input, sizeof (joystick_input));
}
}
#endif

180
src/drivers/leds.c Normal file
View File

@ -0,0 +1,180 @@
/********************************************************************
Software License Agreement:
The software supplied herewith by Microchip Technology Incorporated
(the "Company") for its PIC(R) Microcontroller is intended and
supplied to you, the Company's customer, for use solely and
exclusively on Microchip PIC Microcontroller products. The
software is owned by the Company and/or its supplier, and is
protected under applicable copyright laws. All rights are reserved.
Any use in violation of the foregoing restrictions may subject the
user to criminal sanctions under applicable laws, as well as to
civil liability for the breach of the terms and conditions of this
license.
THIS SOFTWARE IS PROVIDED IN AN "AS IS" CONDITION. NO WARRANTIES,
WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT NOT LIMITED
TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. THE COMPANY SHALL NOT,
IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
*******************************************************************/
#include <leds.h>
#include <stdbool.h>
#include <xc.h>
#define LED_D1_LAT LATBbits.LATB4
#define LED_D1_TRIS TRISBbits.TRISB4
#define LED_ON 1
#define LED_OFF 0
#define PIN_INPUT 1
#define PIN_OUTPUT 0
/*********************************************************************
* Function: void LED_On(LED led);
*
* Overview: Turns requested LED on
*
* PreCondition: LED configured via LED_Configure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_On(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_On(LED led)
{
switch(led)
{
case LED_D1:
LED_D1_LAT = LED_ON;
break;
case LED_NONE:
break;
}
}
/*********************************************************************
* Function: void LED_Off(LED led);
*
* Overview: Turns requested LED off
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Off(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_Off(LED led)
{
switch(led)
{
case LED_D1:
LED_D1_LAT = LED_OFF;
break;
case LED_NONE:
break;
}
}
/*********************************************************************
* Function: void LED_Toggle(LED led);
*
* Overview: Toggles the state of the requested LED
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Toggle(LED_CONNECTION_DETECTED);
*
* Output: none
*
********************************************************************/
void LED_Toggle(LED led)
{
switch(led)
{
case LED_D1:
LED_D1_LAT ^= 1;
break;
case LED_NONE:
break;
}
}
/*********************************************************************
* Function: bool LED_Get(LED led);
*
* Overview: Returns the current state of the requested LED
*
* PreCondition: LED configured via LEDConfigure()
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
* i.e. - LED_Get(LED_CONNECTION_DETECTED);
*
* Output: true if on, false if off
*
********************************************************************/
bool LED_Get(LED led)
{
switch(led)
{
case LED_D1:
return ( (LED_D1_LAT == LED_ON) ? true : false );
case LED_NONE:
return false;
}
return false;
}
/*********************************************************************
* Function: void LED_Enable(LED led);
*
* Overview: Configures the LED for use by the other LED API
*
* PreCondition: none
*
* Input: LED led - enumeration of the LEDs available in this
* demo. They should be meaningful names and not the names of
* the LEDs on the silkscreen on the board (as the demo code may
* be ported to other boards).
*
* Output: none
*
********************************************************************/
void LED_Enable(LED led)
{
switch(led)
{
case LED_D1:
LED_D1_TRIS = PIN_OUTPUT;
break;
case LED_NONE:
break;
}
}

100
src/main.c Normal file
View File

@ -0,0 +1,100 @@
/**
* Apple II Joystick to USB Adapter
* www.flitey.com
*/
/** INCLUDES *******************************************************/
#include "system.h"
#include "usb.h"
#include "usb_device_hid.h"
#include "joystick.h"
#include "app_led_usb_status.h"
#include "eeprom.h"
// Define default EEPROM data for min/max calibration values
// [ X MIN ] [ X MID ] [ X MAX ] [ Y MIN ]
__EEPROM_DATA(0x00, 0x00, 0x01, 0xFF, 0x03, 0xFF, 0x00, 0x00);
// [ Y MID ] [ Y MAX ]
__EEPROM_DATA(0x01, 0xFF, 0x03, 0xFF, 0x00, 0x00, 0x00, 0x00);
/**
* Main function
*/
void main(void) {
// Initialize the buttons, LEDs, ADC
SYSTEM_Initialize(SYSTEM_STATE_USB_START);
// Check button states
bool isSwitch0Pressed = BUTTON_IsPressed(GAME_SWITCH_0);
bool isSwitch1Pressed = BUTTON_IsPressed(GAME_SWITCH_1);
// If both switches are pressed, we will reset the calibration to the
// standard values.
if (isSwitch0Pressed == true && isSwitch1Pressed == true) {
// First set the values to be used
JoystickUseSavedCalibration(JOYSTICK_10_BIT_MIN, JOYSTICK_10_BIT_MID,
JOYSTICK_10_BIT_MAX, JOYSTICK_10_BIT_MIN, JOYSTICK_10_BIT_MID,
JOYSTICK_10_BIT_MAX);
// And then save them to the EEPROM
EepromWriteTwoBytes(X_AXIS_MIN_EEPROM_ADDRESS, JOYSTICK_10_BIT_MIN);
EepromWriteTwoBytes(X_AXIS_MID_EEPROM_ADDRESS, JOYSTICK_10_BIT_MID);
EepromWriteTwoBytes(X_AXIS_MAX_EEPROM_ADDRESS, JOYSTICK_10_BIT_MAX);
EepromWriteTwoBytes(Y_AXIS_MIN_EEPROM_ADDRESS, JOYSTICK_10_BIT_MIN);
EepromWriteTwoBytes(Y_AXIS_MID_EEPROM_ADDRESS, JOYSTICK_10_BIT_MID);
EepromWriteTwoBytes(Y_AXIS_MAX_EEPROM_ADDRESS, JOYSTICK_10_BIT_MAX);
} else if (isSwitch0Pressed == true || isSwitch1Pressed == true) {
// If only one of the switches is pressed, we will run the calibration
// routine to get the new values and save them to EEPROM
JoystickRunCalibration();
} else {
// Otherwise, we will just retrieve the previous calibration values and
// run with those.
uint16_t x_min = EepromReadTwoBytes(X_AXIS_MIN_EEPROM_ADDRESS);
uint16_t x_mid = EepromReadTwoBytes(X_AXIS_MID_EEPROM_ADDRESS);
uint16_t x_max = EepromReadTwoBytes(X_AXIS_MAX_EEPROM_ADDRESS);
uint16_t y_min = EepromReadTwoBytes(Y_AXIS_MIN_EEPROM_ADDRESS);
uint16_t y_mid = EepromReadTwoBytes(Y_AXIS_MID_EEPROM_ADDRESS);
uint16_t y_max = EepromReadTwoBytes(Y_AXIS_MAX_EEPROM_ADDRESS);
JoystickUseSavedCalibration(x_min, x_mid, x_max, y_min, y_mid, y_max);
}
// Initialize USB
USBDeviceInit();
// Attach USB
USBDeviceAttach();
// Now just loop forever here
while (1) {
// We are using USB_POLLING so do USB tasks
USBDeviceTasks();
// If we are not configured, break from the loop
if (USBGetDeviceState() < CONFIGURED_STATE) {
continue;
}
// If we are suspended, break from the loop
if (USBIsDeviceSuspended() == true) {
continue;
}
// Perform joystick related actions
JoystickTasks();
}
}

54
src/system.c Normal file
View File

@ -0,0 +1,54 @@
#include "system.h"
/** CONFIGURATION Bits **********************************************/
#pragma config CPUDIV = NOCLKDIV
#pragma config USBDIV = OFF
#pragma config FOSC = HS
#pragma config PLLEN = ON
#pragma config FCMEN = OFF
#pragma config IESO = OFF
#pragma config PWRTEN = OFF
#pragma config BOREN = OFF
#pragma config BORV = 30
#pragma config WDTEN = OFF
#pragma config WDTPS = 32768
#pragma config MCLRE = OFF
#pragma config HFOFST = OFF
#pragma config STVREN = ON
#pragma config LVP = OFF
#pragma config XINST = OFF
#pragma config BBSIZ = OFF
#pragma config CP0 = OFF
#pragma config CP1 = OFF
#pragma config CPB = OFF
#pragma config WRT0 = OFF
#pragma config WRT1 = OFF
#pragma config WRTB = OFF
#pragma config WRTC = OFF
#pragma config EBTR0 = OFF
#pragma config EBTR1 = OFF
#pragma config EBTRB = OFF
void SYSTEM_Initialize(SYSTEM_STATE state) {
switch (state) {
case SYSTEM_STATE_USB_START:
LED_Enable(LED_USB_DEVICE_STATE);
BUTTON_Enable(GAME_SWITCH_0);
BUTTON_Enable(GAME_SWITCH_1);
ADC_SetConfiguration(ADC_CONFIGURATION_DEFAULT);
ADC_Enable(PDL0);
ADC_Enable(PDL1);
break;
case SYSTEM_STATE_USB_SUSPEND:
break;
case SYSTEM_STATE_USB_RESUME:
break;
}
}

269
src/usb/usb_descriptors.c Normal file
View File

@ -0,0 +1,269 @@
/*******************************************************************************
Copyright 2016 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
/********************************************************************
-usb_descriptors.c-
-------------------------------------------------------------------
Filling in the descriptor values in the usb_descriptors.c file:
-------------------------------------------------------------------
[Device Descriptors]
The device descriptor is defined as a USB_DEVICE_DESCRIPTOR type.
This type is defined in usb_ch9.h Each entry into this structure
needs to be the correct length for the data type of the entry.
[Configuration Descriptors]
The configuration descriptor was changed in v2.x from a structure
to a uint8_t array. Given that the configuration is now a byte array
each byte of multi-byte fields must be listed individually. This
means that for fields like the total size of the configuration where
the field is a 16-bit value "64,0," is the correct entry for a
configuration that is only 64 bytes long and not "64," which is one
too few bytes.
The configuration attribute must always have the _DEFAULT
definition at the minimum. Additional options can be ORed
to the _DEFAULT attribute. Available options are _SELF and _RWU.
These definitions are defined in the usb_device.h file. The
_SELF tells the USB host that this device is self-powered. The
_RWU tells the USB host that this device supports Remote Wakeup.
[Endpoint Descriptors]
Like the configuration descriptor, the endpoint descriptors were
changed in v2.x of the stack from a structure to a uint8_t array. As
endpoint descriptors also has a field that are multi-byte entities,
please be sure to specify both bytes of the field. For example, for
the endpoint size an endpoint that is 64 bytes needs to have the size
defined as "64,0," instead of "64,"
Take the following example:
// Endpoint Descriptor //
0x07, //the size of this descriptor //
USB_DESCRIPTOR_ENDPOINT, //Endpoint Descriptor
_EP02_IN, //EndpointAddress
_INT, //Attributes
0x08,0x00, //size (note: 2 bytes)
0x02, //Interval
The first two parameters are self-explanatory. They specify the
length of this endpoint descriptor (7) and the descriptor type.
The next parameter identifies the endpoint, the definitions are
defined in usb_device.h and has the following naming
convention:
_EP<##>_<dir>
where ## is the endpoint number and dir is the direction of
transfer. The dir has the value of either 'OUT' or 'IN'.
The next parameter identifies the type of the endpoint. Available
options are _BULK, _INT, _ISO, and _CTRL. The _CTRL is not
typically used because the default control transfer endpoint is
not defined in the USB descriptors. When _ISO option is used,
addition options can be ORed to _ISO. Example:
_ISO|_AD|_FE
This describes the endpoint as an isochronous pipe with adaptive
and feedback attributes. See usb_device.h and the USB
specification for details. The next parameter defines the size of
the endpoint. The last parameter in the polling interval.
-------------------------------------------------------------------
Adding a USB String
-------------------------------------------------------------------
A string descriptor array should have the following format:
rom struct{byte bLength;byte bDscType;word string[size];}sdxxx={
sizeof(sdxxx),DSC_STR,<text>};
The above structure provides a means for the C compiler to
calculate the length of string descriptor sdxxx, where xxx is the
index number. The first two bytes of the descriptor are descriptor
length and type. The rest <text> are string texts which must be
in the unicode format. The unicode format is achieved by declaring
each character as a word type. The whole text string is declared
as a word array with the number of characters equals to <size>.
<size> has to be manually counted and entered into the array
declaration. Let's study this through an example:
if the string is "USB" , then the string descriptor should be:
(Using index 02)
rom struct{byte bLength;byte bDscType;word string[3];}sd002={
sizeof(sd002),DSC_STR,'U','S','B'};
A USB project may have multiple strings and the firmware supports
the management of multiple strings through a look-up table.
The look-up table is defined as:
rom const unsigned char *rom USB_SD_Ptr[]={&sd000,&sd001,&sd002};
The above declaration has 3 strings, sd000, sd001, and sd002.
Strings can be removed or added. sd000 is a specialized string
descriptor. It defines the language code, usually this is
US English (0x0409). The index of the string must match the index
position of the USB_SD_Ptr array, &sd000 must be in position
USB_SD_Ptr[0], &sd001 must be in position USB_SD_Ptr[1] and so on.
The look-up table USB_SD_Ptr is used by the get string handler
function.
-------------------------------------------------------------------
The look-up table scheme also applies to the configuration
descriptor. A USB device may have multiple configuration
descriptors, i.e. CFG01, CFG02, etc. To add a configuration
descriptor, user must implement a structure similar to CFG01.
The next step is to add the configuration descriptor name, i.e.
cfg01, cfg02,.., to the look-up table USB_CD_Ptr. USB_CD_Ptr[0]
is a dummy place holder since configuration 0 is the un-configured
state according to the definition in the USB specification.
********************************************************************/
/*********************************************************************
* Descriptor specific type definitions are defined in:
* usb_device.h
*
* Configuration options are defined in:
* usb_config.h
********************************************************************/
/** INCLUDES *******************************************************/
#include "usb.h"
#include "usb_device_hid.h"
/** CONSTANTS ******************************************************/
#if defined(COMPILER_MPLAB_C18)
#pragma romdata
#endif
/* Device Descriptor */
const USB_DEVICE_DESCRIPTOR device_dsc=
{
0x12, // Size of this descriptor in bytes
USB_DESCRIPTOR_DEVICE, // DEVICE descriptor type
0x0200, // USB Spec Release Number in BCD format
0x00, // Class Code
0x00, // Subclass code
0x00, // Protocol code
USB_EP0_BUFF_SIZE, // Max packet size for EP0, see usb_config.h
0x04D8, // Vendor ID, see usb_config.h
0x005E, // Product ID, see usb_config.h
0x0001, // Device release number in BCD format
0x01, // Manufacturer string index
0x02, // Product string index
0x00, // Device serial number string index
0x01 // Number of possible configurations
};
/* Configuration 1 Descriptor */
const uint8_t configDescriptor1[]={
/* Configuration Descriptor */
0x09,//sizeof(USB_CFG_DSC), // Size of this descriptor in bytes
USB_DESCRIPTOR_CONFIGURATION, // CONFIGURATION descriptor type
DESC_CONFIG_WORD(0x0022), // Total length of data for this cfg
1, // Number of interfaces in this cfg
1, // Index value of this configuration
0, // Configuration string index
_DEFAULT | _SELF, // Attributes, see usb_device.h
50, // Max power consumption (2X mA)
/* Interface Descriptor */
0x09,//sizeof(USB_INTF_DSC), // Size of this descriptor in bytes
USB_DESCRIPTOR_INTERFACE, // INTERFACE descriptor type
0, // Interface Number
0, // Alternate Setting Number
1, // Number of endpoints in this intf
HID_INTF, // Class code
0, // Subclass code
0, // Protocol code
0, // Interface string index
/* HID Class-Specific Descriptor */
0x09,//sizeof(USB_HID_DSC)+3, // Size of this descriptor in bytes RRoj hack
DSC_HID, // HID descriptor type
DESC_CONFIG_WORD(0x0111), // HID Spec Release Number in BCD format (1.11)
0x00, // Country Code (0x00 for Not supported)
HID_NUM_OF_DSC, // Number of class descriptors, see usbcfg.h
DSC_RPT, // Report descriptor type
DESC_CONFIG_WORD(HID_RPT01_SIZE), //sizeof(hid_rpt01), // Size of the report descriptor
/* Endpoint Descriptor */
0x07,/*sizeof(USB_EP_DSC)*/
USB_DESCRIPTOR_ENDPOINT, //Endpoint Descriptor
JOYSTICK_EP | _EP_IN, //EndpointAddress
_INTERRUPT, //Attributes
DESC_CONFIG_WORD(64), //size
0x01, //Interval
};
//Language code string descriptor
const struct{uint8_t bLength;uint8_t bDscType;uint16_t string[1];}sd000={
sizeof(sd000),USB_DESCRIPTOR_STRING,{0x0409
}};
//Manufacturer string descriptor
const struct{uint8_t bLength;uint8_t bDscType;uint16_t string[14];}sd001={
sizeof(sd001),USB_DESCRIPTOR_STRING,
{'F','l','i','t','e','y',' ','D','e','s','i','g','n','s'
}};
//Product string descriptor
const struct{uint8_t bLength;uint8_t bDscType;uint16_t string[17];}sd002={
sizeof(sd002),USB_DESCRIPTOR_STRING,
{'A','p','p','l','e',' ','I','I',' ','J','o','y','s','t','i','c','k'
}};
//Array of configuration descriptors
const uint8_t *const USB_CD_Ptr[]=
{
(const uint8_t *const)&configDescriptor1
};
//Array of string descriptors
const uint8_t *const USB_SD_Ptr[]=
{
(const uint8_t *const)&sd000,
(const uint8_t *const)&sd001,
(const uint8_t *const)&sd002
};
const struct{uint8_t report[HID_RPT01_SIZE];}hid_rpt01={{
0x05,0x01, //USAGE_PAGE (Generic Desktop)
0x09,0x04, //USAGE (Game Pad)
0xA1,0x01, //COLLECTION (Application)
0x15,0x00, // LOGICAL_MINIMUM(0)
0x25,0x01, // LOGICAL_MAXIMUM(1)
0x35,0x00, // PHYSICAL_MINIMUM(0)
0x45,0x01, // PHYSICAL_MAXIMUM(1)
0x75,0x01, // REPORT_SIZE(1)
0x95,0x02, // REPORT_COUNT(2)
0x05,0x09, // USAGE_PAGE(Button)
0x19,0x01, // USAGE_MINIMUM(Button 1)
0x29,0x02, // USAGE_MAXIMUM(Button 2)
0x81,0x02, // INPUT(Data,Var,Abs)
0x95,0x06, // REPORT_COUNT(6) // filler
0x81,0x01, // INPUT(Cnst,Ary,Abs)
0x05,0x01, // USAGE_PAGE(Generic Desktop)
0x26,0xFF,0x00, // LOGICAL_MAXIMUM(255)
0x46,0xFF,0x00, // PHYSICAL_MAXIMUM(255)
0x09,0x30, // USAGE(X)
0x09,0x31, // USAGE(Y)
0x75,0x08, // REPORT_SIZE(8)
0x95,0x02, // REPORT_COUNT(2)
0x81,0x02, // INPUT(Data,Var,Abs)
0xC0 //END_COLLECTION
}
};
/** EOF usb_descriptors.c ***************************************************/

3129
src/usb/usb_device.c Normal file

File diff suppressed because it is too large Load Diff

321
src/usb/usb_device_hid.c Normal file
View File

@ -0,0 +1,321 @@
// DOM-IGNORE-BEGIN
/*******************************************************************************
Copyright 2015 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
//DOM-IGNORE-END
/*******************************************************************************
USB Device Human Interface Device (HID) Layer
Company:
Microchip Technology Inc.
File Name:
usb_device_hid.c
Summary:
USB Device Human Interface Device (HID) Layer interface API.
Description:
USB Device Human Interface Device (HID) Layer interface API.
*******************************************************************************/
// *****************************************************************************
// *****************************************************************************
// Section: Included Files
// *****************************************************************************
// *****************************************************************************
#include "usb_config.h"
#include "usb.h"
#include "usb_device_hid.h"
// *****************************************************************************
// *****************************************************************************
// Section: File Scope or Global Constants
// *****************************************************************************
// *****************************************************************************
// *****************************************************************************
// *****************************************************************************
// Section: File Scope Data Types
// *****************************************************************************
// *****************************************************************************
typedef struct __attribute__((packed))
{
unsigned :8;
unsigned :8;
uint8_t reportId;
uint8_t duration;
} USB_SETUP_SET_IDLE_RATE;
typedef struct __attribute__((packed))
{
unsigned :8;
unsigned :8;
uint8_t protocol;
} USB_SETUP_SET_PROTOCOL;
// *****************************************************************************
// *****************************************************************************
// Section: Variables
// *****************************************************************************
// *****************************************************************************
static uint8_t idle_rate;
static uint8_t active_protocol; // [0] Boot Protocol [1] Report Protocol
extern const struct{uint8_t report[HID_RPT01_SIZE];}hid_rpt01;
// *****************************************************************************
// *****************************************************************************
// Section: Prototypes
// *****************************************************************************
// *****************************************************************************
#if defined USER_GET_REPORT_HANDLER
void USER_GET_REPORT_HANDLER(void);
#endif
#if defined USER_SET_REPORT_HANDLER
extern void USER_SET_REPORT_HANDLER(void);
#endif
// *****************************************************************************
// *****************************************************************************
// Section: Macros or Functions
// *****************************************************************************
// *****************************************************************************
//To implement a set idle rate callback function in the application,
//Make sure "#define USB_DEVICE_HID_IDLE_RATE_CALLBACK(reportID, newIdleRate) USBHIDCBSetIdleRateHandler(reportID, newIdleRate)"
//is placed in your usb_config.h file, and then in your application .c file,
//add the void USBHIDCBSetIdleRateHandler(reportID, newIdleRate) function
//implementation that saves the new idle rate and report ID info, so that it
//gets used later when sending subsequent HID input report packets to the host.
#ifndef USB_DEVICE_HID_IDLE_RATE_CALLBACK
#define USB_DEVICE_HID_IDLE_RATE_CALLBACK(reportId, idleRate)
#else
extern void USB_DEVICE_HID_IDLE_RATE_CALLBACK(uint8_t reportId, uint8_t idleRate);
#endif
/********************************************************************
Function:
void USBCheckHIDRequest(void)
Summary:
This routine handles HID specific request that happen on EP0.
This function should be called from the USBCBCheckOtherReq() call back
function whenever implementing a HID device.
Description:
This routine handles HID specific request that happen on EP0. These
include, but are not limited to, requests for the HID report
descriptors. This function should be called from the
USBCBCheckOtherReq() call back function whenever using an HID device.
Typical Usage:
<code>
void USBCBCheckOtherReq(void)
{
//Since the stack didn't handle the request I need to check
// my class drivers to see if it is for them
USBCheckHIDRequest();
}
</code>
PreCondition:
None
Parameters:
None
Return Values:
None
Remarks:
None
*******************************************************************/
void USBCheckHIDRequest(void)
{
if(SetupPkt.Recipient != USB_SETUP_RECIPIENT_INTERFACE_BITFIELD) return;
if(SetupPkt.bIntfID != HID_INTF_ID) return;
/*
* There are two standard requests that hid.c may support.
* 1. GET_DSC(DSC_HID,DSC_RPT,DSC_PHY);
* 2. SET_DSC(DSC_HID,DSC_RPT,DSC_PHY);
*/
if(SetupPkt.bRequest == USB_REQUEST_GET_DESCRIPTOR)
{
switch(SetupPkt.bDescriptorType)
{
case DSC_HID: //HID Descriptor
if(USBActiveConfiguration == 1)
{
USBEP0SendROMPtr(
(const uint8_t*)&configDescriptor1 + 18, //18 is a magic number. It is the offset from start of the configuration descriptor to the start of the HID descriptor.
sizeof(USB_HID_DSC)+3,
USB_EP0_INCLUDE_ZERO);
}
break;
case DSC_RPT: //Report Descriptor
//if(USBActiveConfiguration == 1)
{
USBEP0SendROMPtr(
(const uint8_t*)&hid_rpt01,
HID_RPT01_SIZE, //See usbcfg.h
USB_EP0_INCLUDE_ZERO);
}
break;
case DSC_PHY: //Physical Descriptor
//Note: The below placeholder code is commented out. HID Physical Descriptors are optional and are not used
//in many types of HID applications. If an application does not have a physical descriptor,
//then the device should return STALL in response to this request (stack will do this automatically
//if no-one claims ownership of the control transfer).
//If an application does implement a physical descriptor, then make sure to declare
//hid_phy01 (rom structure containing the descriptor data), and hid_phy01 (the size of the descriptors in uint8_ts),
//and then uncomment the below code.
//if(USBActiveConfiguration == 1)
//{
// USBEP0SendROMPtr((const uint8_t*)&hid_phy01, sizeof(hid_phy01), USB_EP0_INCLUDE_ZERO);
//}
break;
}//end switch(SetupPkt.bDescriptorType)
}//end if(SetupPkt.bRequest == GET_DSC)
if(SetupPkt.RequestType != USB_SETUP_TYPE_CLASS_BITFIELD)
{
return;
}
switch(SetupPkt.bRequest)
{
case GET_REPORT:
#if defined USER_GET_REPORT_HANDLER
USER_GET_REPORT_HANDLER();
#endif
break;
case SET_REPORT:
#if defined USER_SET_REPORT_HANDLER
USER_SET_REPORT_HANDLER();
#endif
break;
case GET_IDLE:
USBEP0SendRAMPtr(
(uint8_t*)&idle_rate,
1,
USB_EP0_INCLUDE_ZERO);
break;
case SET_IDLE:
USBEP0Transmit(USB_EP0_NO_DATA);
idle_rate = SetupPkt.W_Value.byte.HB;
USB_DEVICE_HID_IDLE_RATE_CALLBACK(SetupPkt.W_Value.byte.LB, idle_rate);
break;
case GET_PROTOCOL:
USBEP0SendRAMPtr(
(uint8_t*)&active_protocol,
1,
USB_EP0_NO_OPTIONS);
break;
case SET_PROTOCOL:
USBEP0Transmit(USB_EP0_NO_DATA);
active_protocol = SetupPkt.W_Value.byte.LB;
break;
}//end switch(SetupPkt.bRequest)
}//end USBCheckHIDRequest
/********************************************************************
Function:
USB_HANDLE HIDTxPacket(uint8_t ep, uint8_t* data, uint16_t len)
Summary:
Sends the specified data out the specified endpoint
Description:
This function sends the specified data out the specified
endpoint and returns a handle to the transfer information.
Typical Usage:
<code>
//make sure that the last transfer isn't busy by checking the handle
if(!HIDTxHandleBusy(USBInHandle))
{
//Send the data contained in the ToSendDataBuffer[] array out on
// endpoint HID_EP
USBInHandle = HIDTxPacket(HID_EP,(uint8_t*)&ToSendDataBuffer[0],sizeof(ToSendDataBuffer));
}
</code>
PreCondition:
None
Parameters:
uint8_t ep - the endpoint you want to send the data out of
uint8_t* data - pointer to the data that you wish to send
uint16_t len - the length of the data that you wish to send
Return Values:
USB_HANDLE - a handle for the transfer. This information
should be kept to track the status of the transfer
Remarks:
None
*******************************************************************/
// Implemented as a macro. See usb_function_hid.h
/********************************************************************
Function:
USB_HANDLE HIDRxPacket(uint8_t ep, uint8_t* data, uint16_t len)
Summary:
Receives the specified data out the specified endpoint
Description:
Receives the specified data out the specified endpoint.
Typical Usage:
<code>
//Read 64-uint8_ts from endpoint HID_EP, into the ReceivedDataBuffer array.
// Make sure to save the return handle so that we can check it later
// to determine when the transfer is complete.
USBOutHandle = HIDRxPacket(HID_EP,(uint8_t*)&ReceivedDataBuffer,64);
</code>
PreCondition:
None
Parameters:
uint8_t ep - the endpoint you want to receive the data into
uint8_t* data - pointer to where the data will go when it arrives
uint16_t len - the length of the data that you wish to receive
Return Values:
USB_HANDLE - a handle for the transfer. This information
should be kept to track the status of the transfer
Remarks:
None
*******************************************************************/
// Implemented as a macro. See usb_function_hid.h
/*******************************************************************************
End of File
*/

118
src/usb/usb_events.c Normal file
View File

@ -0,0 +1,118 @@
/*******************************************************************************
Copyright 2016 Microchip Technology Inc. (www.microchip.com)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
To request to license the code under the MLA license (www.microchip.com/mla_license),
please contact mla_licensing@microchip.com
*******************************************************************************/
/** INCLUDES *******************************************************/
#include "system.h"
#include "usb.h"
#include "usb_device_hid.h"
#include "joystick.h"
#include "app_led_usb_status.h"
/*******************************************************************
* Function: bool USER_USB_CALLBACK_EVENT_HANDLER(
* USB_EVENT event, void *pdata, uint16_t size)
*
* PreCondition: None
*
* Input: USB_EVENT event - the type of event
* void *pdata - pointer to the event data
* uint16_t size - size of the event data
*
* Output: None
*
* Side Effects: None
*
* Overview: This function is called from the USB stack to
* notify a user application that a USB event
* occured. This callback is in interrupt context
* when the USB_INTERRUPT option is selected.
*
* Note: None
*******************************************************************/
bool USER_USB_CALLBACK_EVENT_HANDLER(USB_EVENT event, void *pdata, uint16_t size)
{
switch( (int) event )
{
case EVENT_TRANSFER:
break;
case EVENT_SOF:
/* We are using the SOF as a timer to time the LED indicator. Call
* the LED update function here. */
APP_LEDUpdateUSBStatus();
break;
case EVENT_SUSPEND:
/* Update the LED status for the suspend event. */
APP_LEDUpdateUSBStatus();
//Call the hardware platform specific handler for suspend events for
//possible further action (like optionally going reconfiguring the application
//for lower power states and going to sleep during the suspend event). This
//would normally be done in USB compliant bus powered applications, although
//no further processing is needed for purely self powered applications that
//don't consume power from the host.
SYSTEM_Initialize(SYSTEM_STATE_USB_SUSPEND);
break;
case EVENT_RESUME:
/* Update the LED status for the resume event. */
APP_LEDUpdateUSBStatus();
//Call the hardware platform specific resume from suspend handler (ex: to
//restore I/O pins to higher power states if they were changed during the
//preceding SYSTEM_Initialize(SYSTEM_STATE_USB_SUSPEND) call at the start
//of the suspend condition.
SYSTEM_Initialize(SYSTEM_STATE_USB_RESUME);
break;
case EVENT_CONFIGURED:
/* When the device is configured, we can (re)initialize the demo
* code. */
JoystickInitialize();
break;
case EVENT_SET_DESCRIPTOR:
break;
case EVENT_EP0_REQUEST:
/* We have received a non-standard USB request. The HID driver
* needs to check to see if the request was for it. */
USBCheckHIDRequest();
break;
case EVENT_BUS_ERROR:
break;
case EVENT_TRANSFER_TERMINATED:
break;
default:
break;
}
return true;
}
/*******************************************************************************
End of File
*/