From 15ec4ff71c1f92ce2e20302195a91e0c8390ad8a Mon Sep 17 00:00:00 2001 From: Jacob Alexander Date: Mon, 31 Mar 2014 01:07:48 -0700 Subject: [PATCH] Adding CLI and CDC Serial support for Teensy 2.0 and Teensy 2.0++ - Includes serial putchar and getchar cleanup (overall) - Moved avr-capsense to DPH (renaming) - Basic cleanup for including CLI on the avr architecture --- CMakeLists.txt | 7 +- Debug/cli/cli.c | 9 +- Debug/print/print.c | 34 +- Debug/print/print.h | 25 +- Lib/_buildvars.h | 2 +- Output/pjrcUSB/arm/usb_desc.c | 5 +- Output/pjrcUSB/arm/usb_desc.h | 11 +- Output/pjrcUSB/avr/usb_keyboard_debug.c | 705 -------------- Output/pjrcUSB/avr/usb_keyboard_debug.h | 90 -- Output/pjrcUSB/avr/usb_keyboard_serial.c | 1126 ++++++++++++++++++++++ Output/pjrcUSB/avr/usb_keyboard_serial.h | 221 +++++ Output/pjrcUSB/output_com.c | 127 ++- Output/pjrcUSB/output_com.h | 9 +- Output/pjrcUSB/setup.cmake | 2 +- README | 29 +- Scan/{avr-capsense => DPH}/scan_loop.c | 2 +- Scan/{avr-capsense => DPH}/scan_loop.h | 0 Scan/{avr-capsense => DPH}/setup.cmake | 2 +- Scan/SKM67001/setup.cmake | 2 +- Scan/matrix/matrix_scan.c | 8 +- Scan/matrix/matrix_scan.h | 8 +- Scan/matrix/matrix_template.h | 10 +- Scan/matrix/scan_loop.c | 8 +- Scan/matrix/scan_loop.h | 8 +- avr.cmake | 19 +- main.c | 58 +- setup.cmake | 2 +- 27 files changed, 1596 insertions(+), 933 deletions(-) delete mode 100644 Output/pjrcUSB/avr/usb_keyboard_debug.c delete mode 100644 Output/pjrcUSB/avr/usb_keyboard_debug.h create mode 100644 Output/pjrcUSB/avr/usb_keyboard_serial.c create mode 100644 Output/pjrcUSB/avr/usb_keyboard_serial.h rename Scan/{avr-capsense => DPH}/scan_loop.c (99%) rename Scan/{avr-capsense => DPH}/scan_loop.h (100%) rename Scan/{avr-capsense => DPH}/setup.cmake (91%) diff --git a/CMakeLists.txt b/CMakeLists.txt index 53cb140..1bc0c56 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -28,8 +28,8 @@ include( AddFileDependencies ) #| "avr" # Teensy++ 2.0 #| "arm" # Teensy 3.0 #| "arm" # Teensy 3.1 -set( COMPILER_FAMILY "arm" ) -#set( COMPILER_FAMILY "avr" ) +#set( COMPILER_FAMILY "arm" ) +set( COMPILER_FAMILY "avr" ) message( STATUS "Compiler Family:" ) message( "${COMPILER_FAMILY}" ) @@ -138,9 +138,10 @@ add_custom_command( TARGET ${TARGET_ELF} POST_BUILD # #| After Changes Size Information +#| TODO Do lookup on Flash and RAM sizes and do % used add_custom_target( SizeAfter ALL ${SIZE} --target=${FORMAT} ${TARGET_HEX} ${TARGET_ELF} DEPENDS ${TARGET_ELF} - COMMENT "Size after generation:" + COMMENT "Size after generation\n\tFlash Usage: data (hex)\n\t RAM Usage: data (elf)" ) diff --git a/Debug/cli/cli.c b/Debug/cli/cli.c index 07e80ce..11dcbb1 100644 --- a/Debug/cli/cli.c +++ b/Debug/cli/cli.c @@ -85,15 +85,14 @@ void process_cli() uint8_t prev_buf_pos = CLILineBufferCurrent; // Process each character while available - int result = 0; while ( 1 ) { // No more characters to process - result = usb_serial_getchar(); // Retrieve from serial module // TODO Make USB agnostic - if ( result == -1 ) + if ( output_availablechar() == 0 ) break; - char cur_char = (char)result; + // Retrieve from output module + char cur_char = (char)output_getchar(); // Make sure buffer isn't full if ( CLILineBufferCurrent >= CLILineBufferMaxSize ) @@ -405,7 +404,7 @@ void cliFunc_reset( char* args ) void cliFunc_restart( char* args ) { // Trigger an overall software reset - SOFTWARE_RESET(); + output_softReset(); } void cliFunc_version( char* args ) diff --git a/Debug/print/print.c b/Debug/print/print.c index d5eb3fe..5c6cb53 100644 --- a/Debug/print/print.c +++ b/Debug/print/print.c @@ -31,24 +31,8 @@ // ----- Functions ----- -// USB HID String Output -void usb_debug_putstr( char* s ) -{ -#if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) // AVR - while ( *s != '\0' ) - usb_debug_putchar( *s++ ); -#elif defined(_mk20dx128_) || defined(_mk20dx256_) // ARM - // Count characters until NULL character, then send the amount counted - uint32_t count = 0; - while ( s[count] != '\0' ) - count++; - - usb_serial_write( s, count ); -#endif -} - // Multiple string Output -void usb_debug_putstrs( char* first, ... ) +void printstrs( char* first, ... ) { // Initialize the variadic function parameter list va_list ap; @@ -61,7 +45,7 @@ void usb_debug_putstrs( char* first, ... ) while ( !( cur[0] == '\0' && cur[1] == '\0' && cur[2] == '\0' ) ) { // Print out the given string - usb_debug_putstr( cur ); + output_putstr( cur ); // Get the next argument ready cur = va_arg( ap, char* ); @@ -71,21 +55,17 @@ void usb_debug_putstrs( char* first, ... ) } // Print a constant string -void _print(const char *s) +void _print( const char* s ) { #if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) // AVR + // Pull string out of flash char c; - - // Acquire the character from flash, and print it, as long as it's not NULL - // Also, if a newline is found, print a carrige return as well - while ( ( c = pgm_read_byte(s++) ) != '\0' ) + while ( ( c = pgm_read_byte( s++ ) ) != '\0' ) { - if ( c == '\n' ) - usb_debug_putchar('\r'); - usb_debug_putchar(c); + output_putchar( c ); } #elif defined(_mk20dx128_) || defined(_mk20dx256_) // ARM - usb_debug_putstr( (char*)s ); + output_putstr( (char*)s ); #endif } diff --git a/Debug/print/print.h b/Debug/print/print.h index e2498c4..8eeee96 100644 --- a/Debug/print/print.h +++ b/Debug/print/print.h @@ -26,16 +26,12 @@ // Compiler Includes #if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) - #include -#include "avr/usb_keyboard_debug.h" - -#elif defined(_mk20dx128_) || defined(_mk20dx256_) - -#include "arm/usb_serial.h" - #endif +// Project Includes +#include + // ----- Defines ----- @@ -50,15 +46,15 @@ */ // Function Aliases -#define dPrint(c) usb_debug_putstr(c) -#define dPrintStr(c) usb_debug_putstr(c) -#define dPrintStrs(...) usb_debug_putstrs(__VA_ARGS__, "\0\0\0") // Convenience Variadic Macro -#define dPrintStrNL(c) dPrintStrs (c, NL) // Appends New Line Macro -#define dPrintStrsNL(...) usb_debug_putstrs(__VA_ARGS__, NL, "\0\0\0") // Appends New Line Macro +#define dPrint(c) output_putstr(c) +#define dPrintStr(c) output_putstr(c) +#define dPrintStrs(...) printstrs(__VA_ARGS__, "\0\0\0") // Convenience Variadic Macro +#define dPrintStrNL(c) dPrintStrs (c, NL) // Appends New Line Macro +#define dPrintStrsNL(...) printstrs(__VA_ARGS__, NL, "\0\0\0") // Appends New Line Macro // Special Msg Constructs (Uses VT100 tags) #define dPrintMsg(colour_code_str,msg,...) \ - usb_debug_putstrs("\033[", colour_code_str, "m", msg, "\033[0m - ", __VA_ARGS__, NL, "\0\0\0") + printstrs("\033[", colour_code_str, "m", msg, "\033[0m - ", __VA_ARGS__, NL, "\0\0\0") #define printMsgNL(colour_code_str,msg,str) \ print("\033[" colour_code_str "m" msg "\033[0m - " str NL) #define printMsg(colour_code_str,msg,str) \ @@ -89,8 +85,7 @@ #define print(s) _print(PSTR(s)) void _print(const char *s); -void usb_debug_putstr( char* s ); -void usb_debug_putstrs( char* first, ... ); +void printstrs( char* first, ... ); // Printing numbers diff --git a/Lib/_buildvars.h b/Lib/_buildvars.h index 3cf21b5..18a3f4f 100644 --- a/Lib/_buildvars.h +++ b/Lib/_buildvars.h @@ -30,7 +30,7 @@ // You can change these to give your code its own name. #define STR_MANUFACTURER L"@MANUFACTURER@" -#define STR_PRODUCT L"ForceGauge - @ScanModule@ @MacroModule@ @OutputModule@ @DebugModule@" +#define STR_PRODUCT L"Keyboard - @ScanModule@ @MacroModule@ @OutputModule@ @DebugModule@" #define STR_SERIAL L"@GitLastCommitDate@" diff --git a/Output/pjrcUSB/arm/usb_desc.c b/Output/pjrcUSB/arm/usb_desc.c index c5d9982..4d1cdf0 100644 --- a/Output/pjrcUSB/arm/usb_desc.c +++ b/Output/pjrcUSB/arm/usb_desc.c @@ -1,6 +1,7 @@ /* Teensyduino Core Library * http://www.pjrc.com/teensy/ * Copyright (c) 2013 PJRC.COM, LLC. + * Modified by Jacob Alexander (2013-2014) * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -10,10 +11,10 @@ * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * - * 1. The above copyright notice and this permission notice shall be + * 1. The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * - * 2. If the Software is incorporated into a build system that allows + * 2. If the Software is incorporated into a build system that allows * selection among a list of target devices, then similar target * devices manufactured by PJRC.COM must be included in the list of * target devices and selectable in the same manner. diff --git a/Output/pjrcUSB/arm/usb_desc.h b/Output/pjrcUSB/arm/usb_desc.h index acebf5f..ba8d409 100644 --- a/Output/pjrcUSB/arm/usb_desc.h +++ b/Output/pjrcUSB/arm/usb_desc.h @@ -1,6 +1,7 @@ /* Teensyduino Core Library * http://www.pjrc.com/teensy/ * Copyright (c) 2013 PJRC.COM, LLC. + * Modified by Jacob Alexander (2013-2014) * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -10,10 +11,10 @@ * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * - * 1. The above copyright notice and this permission notice shall be + * 1. The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * - * 2. If the Software is incorporated into a build system that allows + * 2. If the Software is incorporated into a build system that allows * selection among a list of target devices, then similar target * devices manufactured by PJRC.COM must be included in the list of * target devices and selectable in the same manner. @@ -89,6 +90,7 @@ let me know? http://forum.pjrc.com/forums/4-Suggestions-amp-Bug-Reports #define NUM_ENDPOINTS 6 #define NUM_USB_BUFFERS 30 #define NUM_INTERFACE 4 + #define CDC_IAD_DESCRIPTOR 1 #define CDC_STATUS_INTERFACE 0 #define CDC_DATA_INTERFACE 1 // Serial @@ -98,22 +100,27 @@ let me know? http://forum.pjrc.com/forums/4-Suggestions-amp-Bug-Reports #define CDC_ACM_SIZE 16 #define CDC_RX_SIZE 64 #define CDC_TX_SIZE 64 + #define KEYBOARD_INTERFACE 2 // Keyboard #define KEYBOARD_ENDPOINT 1 #define KEYBOARD_SIZE 8 #define KEYBOARD_INTERVAL 1 + #define MOUSE_INTERFACE 3 // Mouse #define MOUSE_ENDPOINT 5 #define MOUSE_SIZE 8 #define MOUSE_INTERVAL 2 + #define JOYSTICK_INTERFACE 4 // Joystick #define JOYSTICK_ENDPOINT 6 #define JOYSTICK_SIZE 16 #define JOYSTICK_INTERVAL 1 + #define KEYBOARD_DESC_OFFSET (9+8 + 9+5+5+4+5+7+9+7+7 + 9) #define MOUSE_DESC_OFFSET (9+8 + 9+5+5+4+5+7+9+7+7 + 9+9+7 + 9) #define JOYSTICK_DESC_OFFSET (9+8 + 9+5+5+4+5+7+9+7+7 + 9+9+7 + 9+9+7 + 9) #define CONFIG_DESC_SIZE (9+8 + 9+5+5+4+5+7+9+7+7 + 9+9+7 + 9+9+7 + 9+9+7) + #define ENDPOINT1_CONFIG ENDPOINT_TRANSIMIT_ONLY #define ENDPOINT2_CONFIG ENDPOINT_TRANSIMIT_ONLY #define ENDPOINT3_CONFIG ENDPOINT_RECEIVE_ONLY diff --git a/Output/pjrcUSB/avr/usb_keyboard_debug.c b/Output/pjrcUSB/avr/usb_keyboard_debug.c deleted file mode 100644 index 3a792cf..0000000 --- a/Output/pjrcUSB/avr/usb_keyboard_debug.c +++ /dev/null @@ -1,705 +0,0 @@ -/* USB Keyboard Plus Debug Channel Example for Teensy USB Development Board - * http://www.pjrc.com/teensy/usb_keyboard.html - * Copyright (c) 2009 PJRC.COM, LLC - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ - -// Version 1.0: Initial Release -// Version 1.1: Add support for Teensy 2.0 - -#define USB_SERIAL_PRIVATE_INCLUDE -#include "usb_keyboard_debug.h" - -/************************************************************************** - * - * Configurable Options - * - **************************************************************************/ - -// USB devices are supposed to implment a halt feature, which is -// rarely (if ever) used. If you comment this line out, the halt -// code will be removed, saving 102 bytes of space (gcc 4.3.0). -// This is not strictly USB compliant, but works with all major -// operating systems. -#define SUPPORT_ENDPOINT_HALT - - - -/************************************************************************** - * - * Endpoint Buffer Configuration - * - **************************************************************************/ - -#define ENDPOINT0_SIZE 32 - -#define KEYBOARD_INTERFACE 0 -#define KEYBOARD_ENDPOINT 3 -#define KEYBOARD_SIZE 8 -#define KEYBOARD_BUFFER EP_DOUBLE_BUFFER - -#define DEBUG_INTERFACE 1 -#define DEBUG_TX_ENDPOINT 4 -#define DEBUG_TX_SIZE 32 -#define DEBUG_TX_BUFFER EP_DOUBLE_BUFFER - -static const uint8_t PROGMEM endpoint_config_table[] = { - 0, - 0, - 1, EP_TYPE_INTERRUPT_IN, EP_SIZE(KEYBOARD_SIZE) | KEYBOARD_BUFFER, - 1, EP_TYPE_INTERRUPT_IN, EP_SIZE(DEBUG_TX_SIZE) | DEBUG_TX_BUFFER -}; - - -/************************************************************************** - * - * Descriptor Data - * - **************************************************************************/ - -// Descriptors are the data that your computer reads when it auto-detects -// this USB device (called "enumeration" in USB lingo). The most commonly -// changed items are editable at the top of this file. Changing things -// in here should only be done by those who've read chapter 9 of the USB -// spec and relevant portions of any USB class specifications! - - -static const uint8_t PROGMEM device_descriptor[] = { - 18, // bLength - 1, // bDescriptorType - 0x00, 0x02, // bcdUSB - 0, // bDeviceClass - 0, // bDeviceSubClass - 0, // bDeviceProtocol - ENDPOINT0_SIZE, // bMaxPacketSize0 - LSB(VENDOR_ID), MSB(VENDOR_ID), // idVendor - LSB(PRODUCT_ID), MSB(PRODUCT_ID), // idProduct - 0x00, 0x01, // bcdDevice - 1, // iManufacturer - 2, // iProduct - 3, // iSerialNumber - 1 // bNumConfigurations -}; - -// Keyboard Protocol 1, HID 1.11 spec, Appendix B, page 59-60 -static const uint8_t PROGMEM keyboard_hid_report_desc[] = { - 0x05, 0x01, // Usage Page (Generic Desktop), - 0x09, 0x06, // Usage (Keyboard), - 0xA1, 0x01, // Collection (Application), - 0x75, 0x01, // Report Size (1), - 0x95, 0x08, // Report Count (8), - 0x05, 0x07, // Usage Page (Key Codes), - 0x19, 0xE0, // Usage Minimum (224), - 0x29, 0xE7, // Usage Maximum (231), - 0x15, 0x00, // Logical Minimum (0), - 0x25, 0x01, // Logical Maximum (1), - 0x81, 0x02, // Input (Data, Variable, Absolute), ;Modifier byte - 0x95, 0x01, // Report Count (1), - 0x75, 0x08, // Report Size (8), - 0x81, 0x03, // Input (Constant), ;Reserved byte - 0x95, 0x05, // Report Count (5), - 0x75, 0x01, // Report Size (1), - 0x05, 0x08, // Usage Page (LEDs), - 0x19, 0x01, // Usage Minimum (1), - 0x29, 0x05, // Usage Maximum (5), - 0x91, 0x02, // Output (Data, Variable, Absolute), ;LED report - 0x95, 0x01, // Report Count (1), - 0x75, 0x03, // Report Size (3), - 0x91, 0x03, // Output (Constant), ;LED report padding - 0x95, 0x06, // Report Count (6), - 0x75, 0x08, // Report Size (8), - 0x15, 0x00, // Logical Minimum (0), - 0x25, 0x68, // Logical Maximum(104), - 0x05, 0x07, // Usage Page (Key Codes), - 0x19, 0x00, // Usage Minimum (0), - 0x29, 0x68, // Usage Maximum (104), - 0x81, 0x00, // Input (Data, Array), - 0xc0 // End Collection -}; - -static const uint8_t PROGMEM debug_hid_report_desc[] = { - //0x06, 0x30, 0xFF, // Usage Page 0xFF31 (vendor defined) - 0x06, 0x31, 0xFF, // Usage Page 0xFF31 (vendor defined) - 0x09, 0x74, // Usage 0x74 - 0xA1, 0x53, // Collection 0x53 - 0x75, 0x08, // report size = 8 bits - 0x15, 0x00, // logical minimum = 0 - 0x26, 0xFF, 0x00, // logical maximum = 255 - 0x95, DEBUG_TX_SIZE, // report count - 0x09, 0x75, // usage - 0x81, 0x02, // Input (array) - 0xC0 // end collection -}; - -#define CONFIG1_DESC_SIZE (9+9+9+7+9+9+7) -#define KEYBOARD_HID_DESC_OFFSET (9+9) -#define DEBUG_HID_DESC_OFFSET (9+9+9+7+9) -static const uint8_t PROGMEM config1_descriptor[CONFIG1_DESC_SIZE] = { - // configuration descriptor, USB spec 9.6.3, page 264-266, Table 9-10 - 9, // bLength; - 2, // bDescriptorType; - LSB(CONFIG1_DESC_SIZE), // wTotalLength - MSB(CONFIG1_DESC_SIZE), - 2, // bNumInterfaces - 1, // bConfigurationValue - 0, // iConfiguration - 0xC0, // bmAttributes - 50, // bMaxPower - // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12 - 9, // bLength - 4, // bDescriptorType - KEYBOARD_INTERFACE, // bInterfaceNumber - 0, // bAlternateSetting - 1, // bNumEndpoints - 0x03, // bInterfaceClass (0x03 = HID) - 0x01, // bInterfaceSubClass (0x01 = Boot) - 0x01, // bInterfaceProtocol (0x01 = Keyboard) - 0, // iInterface - // HID interface descriptor, HID 1.11 spec, section 6.2.1 - 9, // bLength - 0x21, // bDescriptorType - 0x11, 0x01, // bcdHID - 0, // bCountryCode - 1, // bNumDescriptors - 0x22, // bDescriptorType - sizeof(keyboard_hid_report_desc), // wDescriptorLength - 0, - // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 - 7, // bLength - 5, // bDescriptorType - KEYBOARD_ENDPOINT | 0x80, // bEndpointAddress - 0x03, // bmAttributes (0x03=intr) - KEYBOARD_SIZE, 0, // wMaxPacketSize - 1, // bInterval - // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12 - 9, // bLength - 4, // bDescriptorType - DEBUG_INTERFACE, // bInterfaceNumber - 0, // bAlternateSetting - 1, // bNumEndpoints - 0x03, // bInterfaceClass (0x03 = HID) - 0x00, // bInterfaceSubClass - 0x00, // bInterfaceProtocol - 0, // iInterface - // HID interface descriptor, HID 1.11 spec, section 6.2.1 - 9, // bLength - 0x21, // bDescriptorType - 0x11, 0x01, // bcdHID - 0, // bCountryCode - 1, // bNumDescriptors - 0x22, // bDescriptorType - sizeof(debug_hid_report_desc), // wDescriptorLength - 0, - // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 - 7, // bLength - 5, // bDescriptorType - DEBUG_TX_ENDPOINT | 0x80, // bEndpointAddress - 0x03, // bmAttributes (0x03=intr) - DEBUG_TX_SIZE, 0, // wMaxPacketSize - 1 // bInterval -}; - -// If you're desperate for a little extra code memory, these strings -// can be completely removed if iManufacturer, iProduct, iSerialNumber -// in the device desciptor are changed to zeros. -struct usb_string_descriptor_struct { - uint8_t bLength; - uint8_t bDescriptorType; - int16_t wString[]; -}; -static const struct usb_string_descriptor_struct PROGMEM string0 = { - 4, - 3, - {0x0409} -}; -static const struct usb_string_descriptor_struct PROGMEM string1 = { - sizeof(STR_MANUFACTURER), - 3, - STR_MANUFACTURER -}; -static const struct usb_string_descriptor_struct PROGMEM string2 = { - sizeof(STR_PRODUCT), - 3, - STR_PRODUCT -}; -static const struct usb_string_descriptor_struct PROGMEM string3 = { - sizeof(STR_SERIAL), - 3, - STR_SERIAL -}; - -// This table defines which descriptor data is sent for each specific -// request from the host (in wValue and wIndex). -static const struct descriptor_list_struct { - uint16_t wValue; - uint16_t wIndex; - const uint8_t *addr; - uint8_t length; -} PROGMEM descriptor_list[] = { - {0x0100, 0x0000, device_descriptor, sizeof(device_descriptor)}, - {0x0200, 0x0000, config1_descriptor, sizeof(config1_descriptor)}, - {0x2200, KEYBOARD_INTERFACE, keyboard_hid_report_desc, sizeof(keyboard_hid_report_desc)}, - {0x2100, KEYBOARD_INTERFACE, config1_descriptor+KEYBOARD_HID_DESC_OFFSET, 9}, - {0x2200, DEBUG_INTERFACE, debug_hid_report_desc, sizeof(debug_hid_report_desc)}, - {0x2100, DEBUG_INTERFACE, config1_descriptor+DEBUG_HID_DESC_OFFSET, 9}, - {0x0300, 0x0000, (const uint8_t *)&string0, 4}, - {0x0301, 0x0409, (const uint8_t *)&string1, sizeof(STR_MANUFACTURER)}, - {0x0302, 0x0409, (const uint8_t *)&string2, sizeof(STR_PRODUCT)}, - {0x0303, 0x0409, (const uint8_t *)&string3, sizeof(STR_SERIAL)} -}; -#define NUM_DESC_LIST (sizeof(descriptor_list)/sizeof(struct descriptor_list_struct)) - - -/************************************************************************** - * - * Variables - these are the only non-stack RAM usage - * - **************************************************************************/ - -// zero when we are not configured, non-zero when enumerated -static volatile uint8_t usb_configuration=0; - -// the time remaining before we transmit any partially full -// packet, or send a zero length packet. -static volatile uint8_t debug_flush_timer=0; - - -/************************************************************************** - * - * Public Functions - these are the API intended for the user - * - **************************************************************************/ - - -// initialize USB -void usb_init(void) -{ - HW_CONFIG(); - USB_FREEZE(); // enable USB - PLL_CONFIG(); // config PLL - while (!(PLLCSR & (1<= NUM_DESC_LIST) { - UECONX = (1< desc_length) len = desc_length; - do { - // wait for host ready for IN packet - do { - i = UEINTX; - } while (!(i & ((1<= 1 && i <= MAX_ENDPOINT) { - usb_send_in(); - UENUM = i; - if (bRequest == SET_FEATURE) { - UECONX = (1<> 8); - USBKeys_Idle_Count = 0; - //usb_wait_in_ready(); - usb_send_in(); - return; - } - if (bRequest == HID_SET_PROTOCOL) { - USBKeys_Protocol = wValue; - //usb_wait_in_ready(); - usb_send_in(); - return; - } - } - } - if (wIndex == DEBUG_INTERFACE) { - if (bRequest == HID_GET_REPORT && bmRequestType == 0xA1) { - len = wLength; - do { - // wait for host ready for IN packet - do { - i = UEINTX; - } while (!(i & ((1< -#include "output_com.h" - -void usb_init(void); // initialize everything -uint8_t usb_configured(void); // is the USB port configured - -int8_t usb_keyboard_send(void); - - -int8_t usb_debug_putchar(uint8_t c); // transmit a character -void usb_debug_flush_output(void); // immediately transmit any buffered output -#define USB_DEBUG_HID - - -// Everything below this point is only intended for usb_serial.c -#ifdef USB_SERIAL_PRIVATE_INCLUDE -#include -#include -#include - -#define EP_TYPE_CONTROL 0x00 -#define EP_TYPE_BULK_IN 0x81 -#define EP_TYPE_BULK_OUT 0x80 -#define EP_TYPE_INTERRUPT_IN 0xC1 -#define EP_TYPE_INTERRUPT_OUT 0xC0 -#define EP_TYPE_ISOCHRONOUS_IN 0x41 -#define EP_TYPE_ISOCHRONOUS_OUT 0x40 - -#define EP_SINGLE_BUFFER 0x02 -#define EP_DOUBLE_BUFFER 0x06 - -#define EP_SIZE(s) ((s) == 64 ? 0x30 : \ - ((s) == 32 ? 0x20 : \ - ((s) == 16 ? 0x10 : \ - 0x00))) - -#define MAX_ENDPOINT 4 - -#define LSB(n) (n & 255) -#define MSB(n) ((n >> 8) & 255) - -#if defined(__AVR_AT90USB162__) -#define HW_CONFIG() -#define PLL_CONFIG() (PLLCSR = ((1< + + +#define CONFIG1_DESC_SIZE (9 + 9+9+7 + 8+9+5+5+4+5+7+9+7+7) +#define KEYBOARD_HID_DESC_OFFSET (9 + 9) +#define SERIAL_CDC_DESC_OFFSET (9 + 9+9+7) +static const uint8_t PROGMEM config1_descriptor[CONFIG1_DESC_SIZE] = { +// --- Configuration --- +// - 9 bytes - + // configuration descriptor, USB spec 9.6.3, page 264-266, Table 9-10 + 9, // bLength; + 2, // bDescriptorType; + LSB(CONFIG1_DESC_SIZE), // wTotalLength + MSB(CONFIG1_DESC_SIZE), + 3, // bNumInterfaces + 1, // bConfigurationValue + 0, // iConfiguration + 0xC0, // bmAttributes + 50, // bMaxPower + +// --- Keyboard HID --- +// - 9 bytes - + // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12 + 9, // bLength + 4, // bDescriptorType + KEYBOARD_INTERFACE, // bInterfaceNumber + 0, // bAlternateSetting + 1, // bNumEndpoints + 0x03, // bInterfaceClass (0x03 = HID) + 0x01, // bInterfaceSubClass (0x01 = Boot) + 0x01, // bInterfaceProtocol (0x01 = Keyboard) + 0, // iInterface +// - 9 bytes - + // HID interface descriptor, HID 1.11 spec, section 6.2.1 + 9, // bLength + 0x21, // bDescriptorType + 0x11, 0x01, // bcdHID + 0, // bCountryCode + 1, // bNumDescriptors + 0x22, // bDescriptorType + LSB(sizeof(keyboard_hid_report_desc)), // wDescriptorLength + MSB(sizeof(keyboard_hid_report_desc)), +// - 7 bytes - + // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 + 7, // bLength + 5, // bDescriptorType + KEYBOARD_ENDPOINT | 0x80, // bEndpointAddress + 0x03, // bmAttributes (0x03=intr) + KEYBOARD_SIZE, 0, // wMaxPacketSize + KEYBOARD_INTERVAL, // bInterval + +// --- Serial CDC --- +// - 8 bytes - + // interface association descriptor, USB ECN, Table 9-Z + 8, // bLength + 11, // bDescriptorType + CDC_STATUS_INTERFACE, // bFirstInterface + 2, // bInterfaceCount + 0x02, // bFunctionClass + 0x02, // bFunctionSubClass + 0x01, // bFunctionProtocol + 4, // iFunction +// - 9 bytes - + // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12 + 9, // bLength + 4, // bDescriptorType + CDC_STATUS_INTERFACE, // bInterfaceNumber + 0, // bAlternateSetting + 1, // bNumEndpoints + 0x02, // bInterfaceClass + 0x02, // bInterfaceSubClass + 0x01, // bInterfaceProtocol + 0, // iInterface +// - 5 bytes - + // CDC Header Functional Descriptor, CDC Spec 5.2.3.1, Table 26 + 5, // bFunctionLength + 0x24, // bDescriptorType + 0x00, // bDescriptorSubtype + 0x10, 0x01, // bcdCDC +// - 5 bytes - + // Call Management Functional Descriptor, CDC Spec 5.2.3.2, Table 27 + 5, // bFunctionLength + 0x24, // bDescriptorType + 0x01, // bDescriptorSubtype + 0x01, // bmCapabilities + 1, // bDataInterface +// - 4 bytes - + // Abstract Control Management Functional Descriptor, CDC Spec 5.2.3.3, Table 28 + 4, // bFunctionLength + 0x24, // bDescriptorType + 0x02, // bDescriptorSubtype + 0x06, // bmCapabilities +// - 5 bytes - + // Union Functional Descriptor, CDC Spec 5.2.3.8, Table 33 + 5, // bFunctionLength + 0x24, // bDescriptorType + 0x06, // bDescriptorSubtype + CDC_STATUS_INTERFACE, // bMasterInterface + CDC_DATA_INTERFACE, // bSlaveInterface0 +// - 7 bytes - + // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 + 7, // bLength + 5, // bDescriptorType + CDC_ACM_ENDPOINT | 0x80, // bEndpointAddress + 0x03, // bmAttributes (0x03=intr) + CDC_ACM_SIZE, 0, // wMaxPacketSize + 64, // bInterval +// - 9 bytes - + // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12 + 9, // bLength + 4, // bDescriptorType + CDC_DATA_INTERFACE, // bInterfaceNumber + 0, // bAlternateSetting + 2, // bNumEndpoints + 0x0A, // bInterfaceClass + 0x00, // bInterfaceSubClass + 0x00, // bInterfaceProtocol + 0, // iInterface +// - 7 bytes - + // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 + 7, // bLength + 5, // bDescriptorType + CDC_RX_ENDPOINT, // bEndpointAddress + 0x02, // bmAttributes (0x02=bulk) + CDC_RX_SIZE, 0, // wMaxPacketSize + 0, // bInterval +// - 7 bytes - + // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 + 7, // bLength + 5, // bDescriptorType + CDC_TX_ENDPOINT | 0x80, // bEndpointAddress + 0x02, // bmAttributes (0x02=bulk) + CDC_TX_SIZE, 0, // wMaxPacketSize + 0, // bInterval +}; + +// If you're desperate for a little extra code memory, these strings +// can be completely removed if iManufacturer, iProduct, iSerialNumber +// in the device desciptor are changed to zeros. +struct usb_string_descriptor_struct { + uint8_t bLength; + uint8_t bDescriptorType; + int16_t wString[]; +}; +static const struct usb_string_descriptor_struct PROGMEM string0 = { + 4, + 3, + {0x0409} +}; +static const struct usb_string_descriptor_struct PROGMEM string1 = { + sizeof(STR_MANUFACTURER), + 3, + STR_MANUFACTURER +}; +static const struct usb_string_descriptor_struct PROGMEM string2 = { + sizeof(STR_PRODUCT), + 3, + STR_PRODUCT +}; +static const struct usb_string_descriptor_struct PROGMEM string3 = { + sizeof(STR_SERIAL), + 3, + STR_SERIAL +}; + +// This table defines which descriptor data is sent for each specific +// request from the host (in wValue and wIndex). +static const struct descriptor_list_struct { + uint16_t wValue; + uint16_t wIndex; + const uint8_t *addr; + uint8_t length; +} PROGMEM descriptor_list[] = { + {0x0100, 0x0000, device_descriptor, sizeof(device_descriptor)}, + {0x0200, 0x0000, config1_descriptor, sizeof(config1_descriptor)}, + {0x2200, KEYBOARD_INTERFACE, keyboard_hid_report_desc, sizeof(keyboard_hid_report_desc)}, + {0x2100, KEYBOARD_INTERFACE, config1_descriptor+KEYBOARD_HID_DESC_OFFSET, 9}, + {0x0300, 0x0000, (const uint8_t *)&string0, 4}, + {0x0301, 0x0409, (const uint8_t *)&string1, sizeof(STR_MANUFACTURER)}, + {0x0302, 0x0409, (const uint8_t *)&string2, sizeof(STR_PRODUCT)}, + {0x0303, 0x0409, (const uint8_t *)&string3, sizeof(STR_SERIAL)} +}; +#define NUM_DESC_LIST (sizeof(descriptor_list)/sizeof(struct descriptor_list_struct)) + + +/************************************************************************** + * + * Variables - these are the only non-stack RAM usage + * + **************************************************************************/ + +// zero when we are not configured, non-zero when enumerated +static volatile uint8_t usb_configuration=0; + +// the time remaining before we transmit any partially full +// packet, or send a zero length packet. +static volatile uint8_t transmit_flush_timer=0; +static uint8_t transmit_previous_timeout=0; + +// serial port settings (baud rate, control signals, etc) set +// by the PC. These are ignored, but kept in RAM. +static uint8_t cdc_line_coding[7]={0x00, 0xE1, 0x00, 0x00, 0x00, 0x00, 0x08}; +static uint8_t cdc_line_rtsdtr=0; + + +/************************************************************************** + * + * Public Functions - these are the API intended for the user + * + **************************************************************************/ + + +// initialize USB +void usb_init(void) +{ + HW_CONFIG(); + USB_FREEZE(); // enable USB + PLL_CONFIG(); // config PLL + while (!(PLLCSR & (1< size) write_size = size; + size -= write_size; + + // write the packet + switch (write_size) { + #if (CDC_TX_SIZE == 64) + case 64: UEDATX = *buffer++; + case 63: UEDATX = *buffer++; + case 62: UEDATX = *buffer++; + case 61: UEDATX = *buffer++; + case 60: UEDATX = *buffer++; + case 59: UEDATX = *buffer++; + case 58: UEDATX = *buffer++; + case 57: UEDATX = *buffer++; + case 56: UEDATX = *buffer++; + case 55: UEDATX = *buffer++; + case 54: UEDATX = *buffer++; + case 53: UEDATX = *buffer++; + case 52: UEDATX = *buffer++; + case 51: UEDATX = *buffer++; + case 50: UEDATX = *buffer++; + case 49: UEDATX = *buffer++; + case 48: UEDATX = *buffer++; + case 47: UEDATX = *buffer++; + case 46: UEDATX = *buffer++; + case 45: UEDATX = *buffer++; + case 44: UEDATX = *buffer++; + case 43: UEDATX = *buffer++; + case 42: UEDATX = *buffer++; + case 41: UEDATX = *buffer++; + case 40: UEDATX = *buffer++; + case 39: UEDATX = *buffer++; + case 38: UEDATX = *buffer++; + case 37: UEDATX = *buffer++; + case 36: UEDATX = *buffer++; + case 35: UEDATX = *buffer++; + case 34: UEDATX = *buffer++; + case 33: UEDATX = *buffer++; + #endif + #if (CDC_TX_SIZE >= 32) + case 32: UEDATX = *buffer++; + case 31: UEDATX = *buffer++; + case 30: UEDATX = *buffer++; + case 29: UEDATX = *buffer++; + case 28: UEDATX = *buffer++; + case 27: UEDATX = *buffer++; + case 26: UEDATX = *buffer++; + case 25: UEDATX = *buffer++; + case 24: UEDATX = *buffer++; + case 23: UEDATX = *buffer++; + case 22: UEDATX = *buffer++; + case 21: UEDATX = *buffer++; + case 20: UEDATX = *buffer++; + case 19: UEDATX = *buffer++; + case 18: UEDATX = *buffer++; + case 17: UEDATX = *buffer++; + #endif + #if (CDC_TX_SIZE >= 16) + case 16: UEDATX = *buffer++; + case 15: UEDATX = *buffer++; + case 14: UEDATX = *buffer++; + case 13: UEDATX = *buffer++; + case 12: UEDATX = *buffer++; + case 11: UEDATX = *buffer++; + case 10: UEDATX = *buffer++; + case 9: UEDATX = *buffer++; + #endif + case 8: UEDATX = *buffer++; + case 7: UEDATX = *buffer++; + case 6: UEDATX = *buffer++; + case 5: UEDATX = *buffer++; + case 4: UEDATX = *buffer++; + case 3: UEDATX = *buffer++; + case 2: UEDATX = *buffer++; + default: + case 1: UEDATX = *buffer++; + case 0: break; + } + // if this completed a packet, transmit it now! + if (!(UEINTX & (1<= NUM_DESC_LIST) { + UECONX = (1< desc_length) len = desc_length; + do { + // wait for host ready for IN packet + do { + i = UEINTX; + } while (!(i & ((1<= 1 && i <= MAX_ENDPOINT) { + usb_send_in(); + UENUM = i; + if (bRequest == SET_FEATURE) { + UECONX = (1<> 8); + USBKeys_Idle_Count = 0; + //usb_wait_in_ready(); + usb_send_in(); + return; + } + if (bRequest == HID_SET_PROTOCOL) { + USBKeys_Protocol = wValue; + //usb_wait_in_ready(); + usb_send_in(); + return; + } + } + } + } + UECONX = (1< + +// AVR Includes +#include +#include +#include +#include + +// AVR Util Includes +#include + +// Local Includes +#include "output_com.h" + + +// ----- Function Declarations ----- + +// Basic USB Configuration +void usb_init(void); // initialize everything +uint8_t usb_configured(void); // is the USB port configured + +// Keyboard HID Functions +int8_t usb_keyboard_send(void); + +// Chip Level Functions +void usb_debug_reload(); // Enable firmware reflash mode +void wdt_init(void) __attribute__((naked)) __attribute__((section(".init3"))); // Needed for software reset + +// USB Serial CDC Functions +int16_t usb_serial_getchar(void); // receive a character (-1 if timeout/error) +uint8_t usb_serial_available(void); // number of bytes in receive buffer +void usb_serial_flush_input(void); // discard any buffered input + +// transmitting data +int8_t usb_serial_putchar(uint8_t c); // transmit a character +int8_t usb_serial_putchar_nowait(uint8_t c); // transmit a character, do not wait +int8_t usb_serial_write(const char *buffer, uint16_t size); // transmit a buffer +void usb_serial_flush_output(void); // immediately transmit any buffered output + +// serial parameters +uint32_t usb_serial_get_baud(void); // get the baud rate +uint8_t usb_serial_get_stopbits(void); // get the number of stop bits +uint8_t usb_serial_get_paritytype(void);// get the parity type +uint8_t usb_serial_get_numbits(void); // get the number of data bits +uint8_t usb_serial_get_control(void); // get the RTS and DTR signal state +int8_t usb_serial_set_control(uint8_t signals); // set DSR, DCD, RI, etc + + + +// ----- Macros ----- + +// Software reset the chip +#define usb_debug_software_reset() do { wdt_enable( WDTO_15MS ); for(;;); } while(0) + +#define EP_SIZE(s) ((s) == 64 ? 0x30 : \ + ((s) == 32 ? 0x20 : \ + ((s) == 16 ? 0x10 : \ + 0x00))) + +#define LSB(n) (n & 255) +#define MSB(n) ((n >> 8) & 255) + + + +// ----- Defines ----- + +// constants corresponding to the various serial parameters +#define USB_SERIAL_DTR 0x01 +#define USB_SERIAL_RTS 0x02 +#define USB_SERIAL_1_STOP 0 +#define USB_SERIAL_1_5_STOP 1 +#define USB_SERIAL_2_STOP 2 +#define USB_SERIAL_PARITY_NONE 0 +#define USB_SERIAL_PARITY_ODD 1 +#define USB_SERIAL_PARITY_EVEN 2 +#define USB_SERIAL_PARITY_MARK 3 +#define USB_SERIAL_PARITY_SPACE 4 +#define USB_SERIAL_DCD 0x01 +#define USB_SERIAL_DSR 0x02 +#define USB_SERIAL_BREAK 0x04 +#define USB_SERIAL_RI 0x08 +#define USB_SERIAL_FRAME_ERR 0x10 +#define USB_SERIAL_PARITY_ERR 0x20 +#define USB_SERIAL_OVERRUN_ERR 0x40 + +#define EP_TYPE_CONTROL 0x00 +#define EP_TYPE_BULK_IN 0x81 +#define EP_TYPE_BULK_OUT 0x80 +#define EP_TYPE_INTERRUPT_IN 0xC1 +#define EP_TYPE_INTERRUPT_OUT 0xC0 +#define EP_TYPE_ISOCHRONOUS_IN 0x41 +#define EP_TYPE_ISOCHRONOUS_OUT 0x40 + +#define EP_SINGLE_BUFFER 0x02 +#define EP_DOUBLE_BUFFER 0x06 + +#define MAX_ENDPOINT 4 + +#if defined(__AVR_AT90USB162__) +#define HW_CONFIG() +#define PLL_CONFIG() (PLLCSR = ((1< // Project Includes +#include +#include #include // USB Includes #if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) -#include "avr/usb_keyboard_debug.h" +#include "avr/usb_keyboard_serial.h" #elif defined(_mk20dx128_) || defined(_mk20dx256_) #include "arm/usb_keyboard.h" #include "arm/usb_dev.h" @@ -40,8 +42,31 @@ +// ----- Function Declarations ----- + +void cliFunc_holdKey ( char* args ); +void cliFunc_readLEDs ( char* args ); +void cliFunc_releaseKey( char* args ); +void cliFunc_sendKey ( char* args ); +void cliFunc_setLEDs ( char* args ); +void cliFunc_setMod ( char* args ); + + // ----- Variables ----- +// Output Module command dictionary +char* outputCLIDictName = "USB Module Commands"; +CLIDictItem outputCLIDict[] = { + { "holdKey", "Hold a space separated list of USB codes. Ignores already pressed keys.", cliFunc_holdKey }, + { "readLEDs", "Read LED byte. See setLEDs.", cliFunc_readLEDs }, + { "releaseKey", "Release a space separated list of USB codes. Ignores unpressed keys.", cliFunc_releaseKey }, + { "sendKey", "Send a space separated list of USB codes. Press/Release.", cliFunc_sendKey }, + { "setLEDs", "Set LED byte: 1 NumLck, 2 CapsLck, 4 ScrlLck, 16 Kana, etc.", cliFunc_setLEDs }, + { "setMod", "Set the modfier byte: 1 LCtrl, 2 LShft, 4 LAlt, 8 LGUI, 16 RCtrl, 32 RShft, 64 RAlt, 128 RGUI", cliFunc_setMod }, + { 0, 0, 0 } // Null entry for dictionary end +}; + + // which modifier keys are currently pressed // 1=left ctrl, 2=left shift, 4=left alt, 8=left gui // 16=right ctrl, 32=right shift, 64=right alt, 128=right gui @@ -69,7 +94,6 @@ volatile uint8_t USBKeys_LEDs = 0; uint8_t USBKeys_Idle_Count = 0; - // ----- Functions ----- // USB Module Setup @@ -81,9 +105,12 @@ inline void output_setup() usb_init(); while ( !usb_configured() ) /* wait */ ; + // Register USB Output dictionary + registerDictionary_cli( outputCLIDict, outputCLIDictName ); + // Wait an extra second for the PC's operating system to load drivers // and do whatever it does to actually be ready for input - //_delay_ms(1000); // TODO + //_delay_ms(1000); // TODO (is this actually necessary?) } @@ -110,8 +137,102 @@ inline void output_send(void) inline void output_firmwareReload() { #if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) + usb_debug_reload(); #elif defined(_mk20dx128_) || defined(_mk20dx256_) usb_device_reload(); #endif } + +// USB Input buffer available +inline unsigned int output_availablechar() +{ + return usb_serial_available(); +} + + +// USB Get Character from input buffer +inline int output_getchar() +{ +#if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) + // XXX Make sure to check output_availablechar() first! Information is lost with the cast (error codes) + return (int)usb_serial_getchar(); +#elif defined(_mk20dx128_) || defined(_mk20dx256_) + return usb_serial_getchar(); +#endif +} + + +// USB Send Character to output buffer +inline int output_putchar( char c ) +{ + return usb_serial_putchar( c ); +} + + +// USB Send String to output buffer, null terminated +inline int output_putstr( char* str ) +{ +#if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) // AVR + uint16_t count = 0; +#elif defined(_mk20dx128_) || defined(_mk20dx256_) // ARM + uint32_t count = 0; +#endif + // Count characters until NULL character, then send the amount counted + while ( str[count] != '\0' ) + count++; + + return usb_serial_write( str, count ); +} + + +// Soft Chip Reset +inline void output_softReset() +{ +#if defined(_at90usb162_) || defined(_atmega32u4_) || defined(_at90usb646_) || defined(_at90usb1286_) + usb_debug_software_reset(); +#elif defined(_mk20dx128_) || defined(_mk20dx256_) + SOFTWARE_RESET(); +#endif +} + + +// ----- CLI Command Functions ----- + +void cliFunc_holdKey( char* args ) +{ + // TODO +} + + +void cliFunc_readLEDs( char* args ) +{ + // TODO +} + + +void cliFunc_releaseKey( char* args ) +{ + // TODO +} + + +void cliFunc_sendKey( char* args ) +{ + // TODO Argument handling + USBKeys_Array[0] = 4; // KEY_A + USBKeys_Sent = 1; +} + + +void cliFunc_setLEDs( char* args ) +{ + // TODO +} + + +void cliFunc_setMod( char* args ) +{ + // TODO +} + diff --git a/Output/pjrcUSB/output_com.h b/Output/pjrcUSB/output_com.h index a8a84ef..fae1197 100644 --- a/Output/pjrcUSB/output_com.h +++ b/Output/pjrcUSB/output_com.h @@ -59,10 +59,17 @@ extern uint8_t USBKeys_Idle_Count; // ----- Functions ----- void output_setup(); - void output_send(); void output_firmwareReload(); +void output_softReset(); + +// Relies on USB serial module +unsigned int output_availablechar(); + +int output_getchar(); +int output_putchar( char c ); +int output_putstr( char* str ); #endif diff --git a/Output/pjrcUSB/setup.cmake b/Output/pjrcUSB/setup.cmake index 157dfc2..d982976 100644 --- a/Output/pjrcUSB/setup.cmake +++ b/Output/pjrcUSB/setup.cmake @@ -17,7 +17,7 @@ if ( ${COMPILER_FAMILY} MATCHES "avr" ) set( OUTPUT_SRCS output_com.c - avr/usb_keyboard_debug.c + avr/usb_keyboard_serial.c ) #| ARM Compiler diff --git a/README b/README index e521bbc..0169e50 100644 --- a/README +++ b/README @@ -24,10 +24,12 @@ AVR Specific (Teensy 1.0/++,2.0/++) (try to use something recent, suggested vers - avr-libc (1.8.0) -ARM Specific (Teensy 3.0) (Sourcery CodeBench Lite for ARM EABI +ARM Specific (Teensy 3.0/3.1) (Sourcery CodeBench Lite for ARM EABI (http://www.mentor.com/embedded-software/sourcery-tools/sourcery-codebench/editions/lite-edition/) - arm-none-eabi -- TODO? +OR +- arm-none-eabi-gcc +- arm-none-eaby-binutils @@ -42,6 +44,7 @@ The options are: - Teensy 2.0 - Teensy 2.0++ - Teensy 3.0 + - Teensy 3.1 Open up CMakeLists.txt in your favourite text editor. You are looking for: @@ -57,13 +60,14 @@ You are looking for: #| "avr" # Teensy++ 1.0 #| "avr" # Teensy++ 2.0 #| "arm" # Teensy 3.0 + #| "arm" # Teensy 3.1 set( COMPILER_FAMILY "avr" ) Just change the COMPILER_FAMILY variable to whatever you are trying to build for. -NOTE: If you change this option, you will *may* to delete the build directory that is created in the Building sections below. +NOTE: If you change this option, you will *may* to delete the build directory that is created in the Building sections below. @@ -102,6 +106,7 @@ You are looking for: #| type "make clean" after changing this, so all files will be rebuilt #| #| "mk20dx128" # Teensy 3.0 + #| "mk20dx256" # Teensy 3.1 set( CHIP "mk20dx128" ) @@ -123,7 +128,7 @@ The Kiibohd Controller is designed around a set of 4 types of modules that corre - Scan Module - Macro Module -- USB Module +- Output Module - Debug Module The Scan Module is where the most interesting stuff happens. These modules take in "keypress data". @@ -135,11 +140,11 @@ Each Scan Module has it's own default keymap/modifier map. (TODO recommend keyma Some scan modules have very specialized hardware requirements, each module directory should have at least a link to the needed parts and/or schematics (TODO!). -The Macro Module takes care of the mapping of the key press/release code into a USB scan code. +The Macro Module takes care of the mapping of the key press/release code into an Output (USB) scan code. Any layering, macros, keypress intelligence/reaction is done here. -The USB Module is the output module of the microcontroller. Currently USB is the only output protocol. +The Output Module is the module dealing with output from the microcontroller. Currently USB is the only output protocol. Different USB output implementations are available, pjrc being the safest/least featureful one. Debug capabilities may depend on the module selected. @@ -161,7 +166,7 @@ Look for: #| All of the modules must be specified, as they generate the sources list of files to compile #| Any modifications to this file will cause a complete rebuild of the project - #| Please look at the {Scan,Macro,USB,Debug}/module.txt for information on the modules and how to create new ones + #| Please look at the {Scan,Macro,Output,Debug}/module.txt for information on the modules and how to create new ones ##| Deals with acquiring the keypress information and turning it into a key index set( ScanModule "avr-capsense" ) @@ -170,7 +175,7 @@ Look for: set( MacroModule "buffer" ) ##| Sends the current list of usb key codes through USB HID - set( USBModule "pjrc" ) + set( OutputModule "pjrc" ) ##| Debugging source to use, each module has it's own set of defines that it sets set( DebugModule "full" ) @@ -206,8 +211,8 @@ Example output: Scan/avr-capsense/scan_loop.c -- Detected Macro Module Source Files: Macro/buffer/macro.c - -- Detected USB Module Source Files: - USB/pjrc/usb_com.c;USB/pjrc/avr/usb_keyboard_debug.c + -- Detected Output Module Source Files: + Output/pjrc/usb_com.c;Output/pjrc/avr/usb_keyboard_debug.c -- Detected Debug Module Source Files: Debug/full/../led/led.c;Debug/full/../print/print.c -- Configuring done @@ -218,8 +223,8 @@ Example output: [ 12%] Building C object CMakeFiles/kiibohd.elf.dir/main.c.o [ 25%] Building C object CMakeFiles/kiibohd.elf.dir/Scan/avr-capsense/scan_loop.c.o [ 37%] Building C object CMakeFiles/kiibohd.elf.dir/Macro/buffer/macro.c.o - [ 50%] Building C object CMakeFiles/kiibohd.elf.dir/USB/pjrc/usb_com.c.o - [ 62%] Building C object CMakeFiles/kiibohd.elf.dir/USB/pjrc/avr/usb_keyboard_debug.c.o + [ 50%] Building C object CMakeFiles/kiibohd.elf.dir/Output/pjrc/usb_com.c.o + [ 62%] Building C object CMakeFiles/kiibohd.elf.dir/Output/pjrc/avr/usb_keyboard_debug.c.o [ 75%] Building C object CMakeFiles/kiibohd.elf.dir/Debug/led/led.c.o [ 87%] Building C object CMakeFiles/kiibohd.elf.dir/Debug/print/print.c.o Linking C executable kiibohd.elf diff --git a/Scan/avr-capsense/scan_loop.c b/Scan/DPH/scan_loop.c similarity index 99% rename from Scan/avr-capsense/scan_loop.c rename to Scan/DPH/scan_loop.c index c8f7f1f..c8f928e 100644 --- a/Scan/avr-capsense/scan_loop.c +++ b/Scan/DPH/scan_loop.c @@ -1,5 +1,5 @@ /* Copyright (C) 2011-2013 by Joseph Makuch - * Additions by Jacob Alexander (2013) + * Additions by Jacob Alexander (2013-2014) * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public diff --git a/Scan/avr-capsense/scan_loop.h b/Scan/DPH/scan_loop.h similarity index 100% rename from Scan/avr-capsense/scan_loop.h rename to Scan/DPH/scan_loop.h diff --git a/Scan/avr-capsense/setup.cmake b/Scan/DPH/setup.cmake similarity index 91% rename from Scan/avr-capsense/setup.cmake rename to Scan/DPH/setup.cmake index ca7c719..35ec76e 100644 --- a/Scan/avr-capsense/setup.cmake +++ b/Scan/DPH/setup.cmake @@ -1,6 +1,6 @@ ###| CMake Kiibohd Controller Scan Module |### # -# Written by Jacob Alexander in 2013 for the Kiibohd Controller +# Written by Jacob Alexander in 2013-2014 for the Kiibohd Controller # # Released into the Public Domain # diff --git a/Scan/SKM67001/setup.cmake b/Scan/SKM67001/setup.cmake index 2b71198..c618919 100644 --- a/Scan/SKM67001/setup.cmake +++ b/Scan/SKM67001/setup.cmake @@ -24,7 +24,7 @@ set( SCAN_SRCS add_definitions( -I${HEAD_DIR}/Keymap ) add_definitions( -I${HEAD_DIR}/Scan/matrix -) +) #| Keymap Settings add_definitions( diff --git a/Scan/matrix/matrix_scan.c b/Scan/matrix/matrix_scan.c index 77623b3..5987016 100644 --- a/Scan/matrix/matrix_scan.c +++ b/Scan/matrix/matrix_scan.c @@ -1,15 +1,15 @@ -/* Copyright (C) 2011 by Jacob Alexander - * +/* Copyright (C) 2011,2014 by Jacob Alexander + * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: - * + * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. - * + * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE diff --git a/Scan/matrix/matrix_scan.h b/Scan/matrix/matrix_scan.h index df5202d..2c3a65f 100644 --- a/Scan/matrix/matrix_scan.h +++ b/Scan/matrix/matrix_scan.h @@ -1,15 +1,15 @@ -/* Copyright (C) 2011 by Jacob Alexander - * +/* Copyright (C) 2011,2014 by Jacob Alexander + * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: - * + * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. - * + * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE diff --git a/Scan/matrix/matrix_template.h b/Scan/matrix/matrix_template.h index 719fd0a..41ca233 100644 --- a/Scan/matrix/matrix_template.h +++ b/Scan/matrix/matrix_template.h @@ -1,15 +1,15 @@ -/* Copyright (C) 2011 by Jacob Alexander - * +/* Copyright (C) 2011,2014 by Jacob Alexander + * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: - * + * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. - * + * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE @@ -69,7 +69,7 @@ static const uint8_t matrix_pinout[][MAX_ROW_SIZE + 1] = { // Just layout the matrix by rows and columns // Usually you'll want to set the scanMode above to scanDual or scanCol_powrRow/scanRow_powrCol // The mode allows for optimization in the kind of scanning algorithms that are done -// +// // The key numbers are used to translate into the keymap table (array) (and always start from 1, not 0). // Thus if a row doesn't use all the key positions, you can denote it as 0, which will be ignored/skipped on each scan // See the keymap.h file for the various preconfigured arrays. diff --git a/Scan/matrix/scan_loop.c b/Scan/matrix/scan_loop.c index 3bca054..e9d8de2 100644 --- a/Scan/matrix/scan_loop.c +++ b/Scan/matrix/scan_loop.c @@ -1,15 +1,15 @@ -/* Copyright (C) 2011-2012 by Jacob Alexander - * +/* Copyright (C) 2011-2012,2014 by Jacob Alexander + * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: - * + * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. - * + * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE diff --git a/Scan/matrix/scan_loop.h b/Scan/matrix/scan_loop.h index d3fa133..5259154 100644 --- a/Scan/matrix/scan_loop.h +++ b/Scan/matrix/scan_loop.h @@ -1,15 +1,15 @@ -/* Copyright (C) 2011-2012 by Jacob Alexander - * +/* Copyright (C) 2011-2012,2014 by Jacob Alexander + * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: - * + * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. - * + * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE diff --git a/avr.cmake b/avr.cmake index c39ed0d..239563a 100644 --- a/avr.cmake +++ b/avr.cmake @@ -1,6 +1,6 @@ ###| CMAKE Kiibohd Controller |### # -# Jacob Alexander 2011-2013 +# Jacob Alexander 2011-2014 # Due to this file's usefulness: # # Released into the Public Domain @@ -37,8 +37,8 @@ set( SIZE "avr-size" ) #| "atmega32u4" # Teensy 2.0 #| "at90usb646" # Teensy++ 1.0 #| "at90usb1286" # Teensy++ 2.0 -#set( MCU "atmega32u4" ) -set( MCU "at90usb1286" ) +set( MCU "atmega32u4" ) +#set( MCU "at90usb1286" ) message( STATUS "MCU Selected:" ) message( "${MCU}" ) @@ -51,6 +51,15 @@ set( COMPILER_SRCS ) +#| CPU Type +#| This is only informational for AVR microcontrollers +#| The field can be determined by the microcontroller chip, but currently only one CPU type is used atm +set( CPU "megaAVR" ) + +message( STATUS "CPU Selected:" ) +message( "${CPU}" ) + + #| USB Defines set( VENDOR_ID "0x16C0" ) set( PRODUCT_ID "0x047D" ) @@ -66,7 +75,7 @@ set( CSTANDARD "-std=gnu99" ) #| Warning Options #| -Wall...: warning level -set( WARN "-Wall -Wstrict-prototypes" ) +set( WARN "-Wall" ) #| Tuning Options @@ -75,7 +84,7 @@ set( WARN "-Wall -Wstrict-prototypes" ) set( TUNING "-funsigned-char -funsigned-bitfields -ffunction-sections -fpack-struct -fshort-enums" ) -#| Optimization level, can be [0, 1, 2, 3, s]. +#| Optimization level, can be [0, 1, 2, 3, s]. #| 0 = turn off optimization. s = optimize for size. #| (Note: 3 is not always the best optimization level. See avr-libc FAQ.) set( OPT "s" ) diff --git a/main.c b/main.c index 56487b6..7412fc6 100644 --- a/main.c +++ b/main.c @@ -139,57 +139,43 @@ int main(void) { // Configuring Pins pinSetup(); - init_errorLED(); - - // Setup Output Module - output_setup(); // Enable CLI init_cli(); + // Setup Output Module + output_setup(); + // Setup ISR Timer for flagging a kepress send to USB usbTimerSetup(); + // Setup the scanning module + //scan_setup(); + // Main Detection Loop - uint8_t ledTimer = F_CPU / 1000000; // Enable LED for a short time while ( 1 ) { - // Setup the scanning module - scan_setup(); + // Process CLI + process_cli(); - while ( 1 ) - { - // Acquire Key Indices - // Loop continuously until scan_loop returns 0 - cli(); - while ( scan_loop() ); - sei(); + // Acquire Key Indices + // Loop continuously until scan_loop returns 0 + cli(); + //while ( scan_loop() ); + sei(); - // Run Macros over Key Indices and convert to USB Keys - process_macros(); + // Run Macros over Key Indices and convert to USB Keys + process_macros(); - // Send keypresses over USB if the ISR has signalled that it's time - if ( !sendKeypresses ) - continue; + // Send keypresses over USB if the ISR has signalled that it's time + if ( !sendKeypresses ) + continue; - // Send USB Data - output_send(); + // Send USB Data + output_send(); - // Clear sendKeypresses Flag - sendKeypresses = 0; - - // Indicate Error, if valid - errorLED( ledTimer ); - - if ( ledTimer > 0 ) - ledTimer--; - } - - // Loop should never get here (indicate error) - ledTimer = 255; - - // HID Debug Error message - erro_print("Detection loop error, this is very bad...bug report!"); + // Clear sendKeypresses Flag + sendKeypresses = 0; } } diff --git a/setup.cmake b/setup.cmake index aa1362d..57b19d2 100644 --- a/setup.cmake +++ b/setup.cmake @@ -20,7 +20,7 @@ #| Please look at the {Scan,Macro,USB,Debug}/module.txt for information on the modules and how to create new ones ##| Deals with acquiring the keypress information and turning it into a key index -set( ScanModule "MBC-55X" ) +set( ScanModule "SKM67001" ) ##| Uses the key index and potentially applies special conditions to it, mapping it to a usb key code set( MacroModule "buffer" )