From 266b59b851e1ebc41a1b991ed6d8a09ada74a576 Mon Sep 17 00:00:00 2001 From: Jacob Alexander Date: Tue, 1 Nov 2011 00:02:10 -0700 Subject: [PATCH] Initial commit of the Kaypro1 scan module - Does not output to usb yet - USART is functionally getting characters from the keyboard and sending beep codes and ACK request code (Baud rate properly calculated) - Uses hard-coded keys for the PC to Keyboard commands (not desireable) - Keyboard sends ASCII data, which makes doing things like holding multiple keys almost impossible to detect (the board isn't NKRO anyways, though I've found 8+ key combos that work) --- CMakeLists.txt | 2 +- Scan/Kaypro1/scan_loop.c | 232 +++++++++++++++++++++++++++++++++++++++ Scan/Kaypro1/scan_loop.h | 55 ++++++++++ Scan/Kaypro1/setup.cmake | 29 +++++ setup.cmake | 2 +- 5 files changed, 318 insertions(+), 2 deletions(-) create mode 100644 Scan/Kaypro1/scan_loop.c create mode 100644 Scan/Kaypro1/scan_loop.h create mode 100644 Scan/Kaypro1/setup.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 08182eb..e275627 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -54,7 +54,7 @@ set( SRCS main.c ${SCAN_SRCS} ${MACRO_SRCS} ${USB_SRCS} ${DEBUG_SRCS} ) #| "atmega32u4" # Teensy 2.0 #| "at90usb646" # Teensy++ 1.0 #| "at90usb1286" # Teensy++ 2.0 -set( MCU "atmega32u4" ) +set( MCU "at90usb1286" ) #| Compiler flag to set the C Standard level. diff --git a/Scan/Kaypro1/scan_loop.c b/Scan/Kaypro1/scan_loop.c new file mode 100644 index 0000000..1f7b0fe --- /dev/null +++ b/Scan/Kaypro1/scan_loop.c @@ -0,0 +1,232 @@ +/* Copyright (C) 2011 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 + * 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. + */ + +// ----- Includes ----- + +// AVR Includes +#include +#include + +// Project Includes +#include +#include + +// Local Includes +#include "scan_loop.h" + + + +// ----- Defines ----- + + + +// ----- Macros ----- + + + +// ----- Variables ----- + +uint8_t KeyIndex_Array[KEYBOARD_SIZE + 1]; + + +// Known signals +static uint8_t cmd_clickOFF = 0x0A; // Short beep, turns off clicker +static uint8_t cmd_clickON = 0x04; // Long beep, turns on clicker +static uint8_t cmd_ACK_AA = 0x10; // Keyboard will send ack (0xAA) back to PC + +// Other known signals +// 0x02 turns on clicker but with short beep + + + +// ----- Functions ----- + +// Setup +inline void scan_setup() +{ + // Setup the the USART interface for keyboard data input + + // Setup baud rate + // 16 MHz / ( 16 * Baud ) = UBRR + // Baud <- 3.358 ms per bit, thus 1000 / 3.358 = 297.80 + // Thus baud = 3357 + uint16_t baud = 3357; // Max setting of 4095 + UBRR1H = (uint8_t)(baud >> 8); + UBRR1L = (uint8_t)baud; + + // Enable the receiver, transitter, and RX Complete Interrupt + UCSR1B = 0x98; + + // Set frame format: 8 data, no stop bits or parity + // Asynchrounous USART mode + // Kaypro sends ASCII codes (mostly standard) with 1 start bit and 8 data bits, with no trailing stop or parity bits + UCSR1C = 0x06; +} + + +// Main Detection Loop +inline uint8_t scan_loop() +{ + /* + // Packet Read + if ( packet_index == 8 ) + { + // Disable Error LED, proper key found + errorLED( 0 ); + +//#ifdef MAX_DEBUG + // Crazy Debug (Read the Scan Code) + char tmpStr[3]; + hexToStr_op( inputData, tmpStr, 2 ); + dPrintStrsNL( "Read Data: 0x", tmpStr ); +//#endif + // - Map the scan code to the index array - + // If the 8th bit is high, remove the keypress, else, add the keypress + // The lower 7 bits are the array index + KeyIndex_Array[(inputData & 0x7F)] = (inputData & 0x80) ? 0x00 : 0x80; + + // Reset Containers + packet_index = 0; + inputData = 0xFF; + } + // Bad Packet + else if ( packet_index > 8 ) + { + // Signal Error + errorLED( 1 ); + + char tmpStr[3]; + int8ToStr( packet_index, tmpStr ); + erro_dPrint( "Big packet? Mismatched... ", tmpStr ); + + packet_index = 0; + inputData = 0xFF; + } + */ + /* + // Disable keyboard interrupt (does nothing if already off) + UNSET_INTR(); + + // Read the clock 8 times + if ( READ_CLK ) + { + // Mis-read packet, set back to 0 + if ( packet_index == -1 ) + packet_index = 0; + + // Append 1 bit of data + inputData &= ~(READ_DATA << packet_index); + packet_index++; + + // 8 Bits have been read + if ( packet_index == 8 ) + { + // Wait till clock edge falls + while ( READ_CLK ); + + // Sample both lines to make sure this is not a data value + // and definitely the end of packet data blip + uint16_t badDataCounter = 0; + while ( !( READ_DATA ) && !( READ_CLK ) ) + badDataCounter++; + + if ( badDataCounter < 25 ) + { +//#ifdef MAX_DEBUG + // Crazy Debug (Read the Scan Code) + char tmpStr[3]; + hexToStr_op( inputData, tmpStr, 2 ); + dbug_dPrint( "Read Data: 0x", tmpStr ); +//#endif + // - Map the scan code to the index array - + // If the 8th bit is high, remove the keypress, else, add the keypress + // The lower 7 bits are the array index + KeyIndex_Array[(inputData & 0x7F)] = (inputData & 0x80) ? 0x00 : 0x80; + } + // Even though this is a mis-read packet, we still know what the value is + else + { + // Signal Error + errorLED( 1 ); + char tmpStr[3]; + hexToStr_op( inputData, tmpStr, 2 ); + erro_dPrint( "Bad packet? Mismatched... 0x", tmpStr ); + } + + // Reset Containers + inputData = 0xFF; + packet_index = 0; + + // Interrupt the keyboard, so we don't get packet pieces... + SET_INTR(); + + // Do not wait for next clock, let USB do it's thing (if desired) + return packet_index; + } + + // Wait till clock edge falls + while ( READ_CLK ); + } + + // Interrupt keyboard if there is no pending packet + SET_INTR(); + */ + return 0; +} + +// USART Receive Buffer Full Interrupt +ISR(USART1_RX_vect) +{ + cli(); // Disable Interrupts + + uint8_t keyValue = UDR1; + char tmpStr1[6]; + hexToStr( keyValue, tmpStr1 ); + dPrintStrs( tmpStr1, " " ); + + // Special keys - For communication to the keyboard + // TODO Try to push this functionality into the macros...somehow + switch ( keyValue ) + { + case 0xC3: // Keypad Enter + print("\n"); + info_print("BEEEEP! - Clicker on"); + UDR1 = cmd_clickON; + break; + + case 0xB2: // Keypad Decimal + print("\n"); + info_print("BEEP! - Clicker off"); + UDR1 = cmd_clickOFF; + break; + + case 0x0A: // Line Feed + print("\n"); + info_print("ACK!!"); + UDR1 = cmd_ACK_AA; + break; + } + + // Add key to processing buffer + + sei(); // Re-enable Interrupts +} + diff --git a/Scan/Kaypro1/scan_loop.h b/Scan/Kaypro1/scan_loop.h new file mode 100644 index 0000000..423381b --- /dev/null +++ b/Scan/Kaypro1/scan_loop.h @@ -0,0 +1,55 @@ +/* Copyright (C) 2011 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 + * 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. + */ + +#ifndef __SCAN_LOOP_H +#define __SCAN_LOOP_H + +// ----- Includes ----- + +// Compiler Includes +#include + +// Local Includes + + + +// ----- Defines ----- + +#define KEYBOARD_SIZE 0x4c // 76 - Size of the array space for the keyboardr(max index) + + + +// ----- Variables ----- + +// NOTE: Highest Bit: Valid keypress (0x80 is valid keypress) +// Other Bits: Pressed state sample counter +extern uint8_t KeyIndex_Array [KEYBOARD_SIZE + 1]; + static const uint8_t KeyIndex_Size = KEYBOARD_SIZE; + + + +// ----- Functions ----- + +void scan_setup( void ); +uint8_t scan_loop( void ); + +#endif // __SCAN_LOOP_H + diff --git a/Scan/Kaypro1/setup.cmake b/Scan/Kaypro1/setup.cmake new file mode 100644 index 0000000..cb3bf6a --- /dev/null +++ b/Scan/Kaypro1/setup.cmake @@ -0,0 +1,29 @@ +###| CMake Kiibohd Controller Scan Module |### +# +# Written by Jacob Alexander in 2011 for the Kiibohd Controller +# +# Released into the Public Domain +# +### + + +### +# Module C files +# + +set( SCAN_SRCS + scan_loop.c +) + + +### +# Module Specific Options +# +add_definitions( -I${HEAD_DIR}/Keymap ) + +#| Keymap Settings +add_definitions( + -DMODIFIER_MASK=tandy1000_modifierMask + -DKEYINDEX_MASK=tandy1000_colemak +) + diff --git a/setup.cmake b/setup.cmake index 719d5a7..7bac7fc 100644 --- a/setup.cmake +++ b/setup.cmake @@ -20,7 +20,7 @@ #| Please 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 "HeathZenith" ) +set( ScanModule "Kaypro1" ) ##| Uses the key index and potentially applies special conditions to it, mapping it to a usb key code set( MacroModule "basic" )