aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--common/host.c36
-rw-r--r--common/report.h36
-rw-r--r--keyboard/hhkb/Makefile.lufa8
-rw-r--r--keyboard/hhkb/Makefile.pjrc4
-rw-r--r--keyboard/hhkb/Makefile.tmk129
-rw-r--r--keyboard/hhkb/config.h2
-rw-r--r--protocol/lufa/descriptor.c65
-rw-r--r--protocol/lufa/descriptor.h24
-rw-r--r--protocol/lufa/lufa.c28
-rw-r--r--protocol/pjrc/usb_keyboard.c13
10 files changed, 168 insertions, 177 deletions
diff --git a/common/host.c b/common/host.c
index 2c2279aa4..569451652 100644
--- a/common/host.c
+++ b/common/host.c
@@ -37,8 +37,10 @@ static uint16_t last_consumer_report = 0;
37 37
38static inline void add_key_byte(uint8_t code); 38static inline void add_key_byte(uint8_t code);
39static inline void del_key_byte(uint8_t code); 39static inline void del_key_byte(uint8_t code);
40#ifdef NKRO_ENABLE
40static inline void add_key_bit(uint8_t code); 41static inline void add_key_bit(uint8_t code);
41static inline void del_key_bit(uint8_t code); 42static inline void del_key_bit(uint8_t code);
43#endif
42 44
43 45
44void host_set_driver(host_driver_t *d) 46void host_set_driver(host_driver_t *d)
@@ -63,11 +65,11 @@ void host_keyboard_send(report_keyboard_t *report)
63 (*driver->send_keyboard)(report); 65 (*driver->send_keyboard)(report);
64 66
65 if (debug_keyboard) { 67 if (debug_keyboard) {
66 dprint("keys: "); 68 dprint("keyboard_report: ");
67 for (int i = 0; i < REPORT_KEYS; i++) { 69 for (uint8_t i = 0; i < REPORT_SIZE; i++) {
68 dprintf("%02X ", keyboard_report->keys[i]); 70 dprintf("%02X ", keyboard_report->raw[i]);
69 } 71 }
70 dprintf(" mods: %02X\n", keyboard_report->mods); 72 dprint("\n");
71 } 73 }
72} 74}
73 75
@@ -122,8 +124,9 @@ void host_del_key(uint8_t key)
122 124
123void host_clear_keys(void) 125void host_clear_keys(void)
124{ 126{
125 for (int8_t i = 0; i < REPORT_KEYS; i++) { 127 // not clea mods
126 keyboard_report->keys[i] = 0; 128 for (int8_t i = 1; i < REPORT_SIZE; i++) {
129 keyboard_report->raw[i] = 0;
127 } 130 }
128} 131}
129 132
@@ -155,8 +158,8 @@ void host_clear_mods(void)
155uint8_t host_has_anykey(void) 158uint8_t host_has_anykey(void)
156{ 159{
157 uint8_t cnt = 0; 160 uint8_t cnt = 0;
158 for (int i = 0; i < REPORT_KEYS; i++) { 161 for (uint8_t i = 1; i < REPORT_SIZE; i++) {
159 if (keyboard_report->keys[i]) 162 if (keyboard_report->raw[i])
160 cnt++; 163 cnt++;
161 } 164 }
162 return cnt; 165 return cnt;
@@ -172,9 +175,9 @@ uint8_t host_get_first_key(void)
172#ifdef NKRO_ENABLE 175#ifdef NKRO_ENABLE
173 if (keyboard_nkro) { 176 if (keyboard_nkro) {
174 uint8_t i = 0; 177 uint8_t i = 0;
175 for (; i < REPORT_KEYS && !keyboard_report->keys[i]; i++) 178 for (; i < REPORT_BITS && !keyboard_report->nkro.bits[i]; i++)
176 ; 179 ;
177 return i<<3 | biton(keyboard_report->keys[i]); 180 return i<<3 | biton(keyboard_report->nkro.bits[i]);
178 } 181 }
179#endif 182#endif
180 return keyboard_report->keys[0]; 183 return keyboard_report->keys[0];
@@ -222,18 +225,18 @@ static inline void add_key_byte(uint8_t code)
222 225
223static inline void del_key_byte(uint8_t code) 226static inline void del_key_byte(uint8_t code)
224{ 227{
225 int i = 0; 228 for (uint8_t i = 0; i < REPORT_KEYS; i++) {
226 for (; i < REPORT_KEYS; i++) {
227 if (keyboard_report->keys[i] == code) { 229 if (keyboard_report->keys[i] == code) {
228 keyboard_report->keys[i] = 0; 230 keyboard_report->keys[i] = 0;
229 } 231 }
230 } 232 }
231} 233}
232 234
235#ifdef NKRO_ENABLE
233static inline void add_key_bit(uint8_t code) 236static inline void add_key_bit(uint8_t code)
234{ 237{
235 if ((code>>3) < REPORT_KEYS) { 238 if ((code>>3) < REPORT_BITS) {
236 keyboard_report->keys[code>>3] |= 1<<(code&7); 239 keyboard_report->nkro.bits[code>>3] |= 1<<(code&7);
237 } else { 240 } else {
238 dprintf("add_key_bit: can't add: %02X\n", code); 241 dprintf("add_key_bit: can't add: %02X\n", code);
239 } 242 }
@@ -241,9 +244,10 @@ static inline void add_key_bit(uint8_t code)
241 244
242static inline void del_key_bit(uint8_t code) 245static inline void del_key_bit(uint8_t code)
243{ 246{
244 if ((code>>3) < REPORT_KEYS) { 247 if ((code>>3) < REPORT_BITS) {
245 keyboard_report->keys[code>>3] &= ~(1<<(code&7)); 248 keyboard_report->nkro.bits[code>>3] &= ~(1<<(code&7));
246 } else { 249 } else {
247 dprintf("del_key_bit: can't del: %02X\n", code); 250 dprintf("del_key_bit: can't del: %02X\n", code);
248 } 251 }
249} 252}
253#endif
diff --git a/common/report.h b/common/report.h
index 02deb7797..91982840a 100644
--- a/common/report.h
+++ b/common/report.h
@@ -72,14 +72,20 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
72 72
73 73
74/* key report size(NKRO or boot mode) */ 74/* key report size(NKRO or boot mode) */
75#if defined(PROTOCOL_PJRC) 75#if defined(PROTOCOL_PJRC) && defined(NKRO_ENABLE)
76# include "usb.h" 76# include "usb.h"
77# if defined(KBD2_REPORT_KEYS) && KBD2_REPORT_KEYS > KBD_REPORT_KEYS 77# define REPORT_SIZE KBD2_SIZE
78# define REPORT_KEYS KBD2_REPORT_KEYS 78# define REPORT_KEYS (KBD2_SIZE - 2)
79# else 79# define REPORT_BITS (KBD2_SIZE - 1)
80# define REPORT_KEYS KBD_REPORT_KEYS 80
81# endif 81#elif defined(PROTOCOL_LUFA) && defined(NKRO_ENABLE)
82# include "protocol/lufa/descriptor.h"
83# define REPORT_SIZE NKRO_EPSIZE
84# define REPORT_KEYS (NKRO_EPSIZE - 2)
85# define REPORT_BITS (NKRO_EPSIZE - 1)
86
82#else 87#else
88# define REPORT_SIZE 8
83# define REPORT_KEYS 6 89# define REPORT_KEYS 6
84#endif 90#endif
85 91
@@ -88,11 +94,27 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
88extern "C" { 94extern "C" {
89#endif 95#endif
90 96
97typedef union {
98 uint8_t raw[REPORT_SIZE];
99 struct {
100 uint8_t mods;
101 uint8_t reserved;
102 uint8_t keys[REPORT_KEYS];
103 };
104#ifdef NKRO_ENABLE
105 struct {
106 uint8_t mods;
107 uint8_t bits[REPORT_BITS];
108 } nkro;
109#endif
110} __attribute__ ((packed)) report_keyboard_t;
111/*
91typedef struct { 112typedef struct {
92 uint8_t mods; 113 uint8_t mods;
93 uint8_t rserved; 114 uint8_t reserved;
94 uint8_t keys[REPORT_KEYS]; 115 uint8_t keys[REPORT_KEYS];
95} __attribute__ ((packed)) report_keyboard_t; 116} __attribute__ ((packed)) report_keyboard_t;
117*/
96 118
97typedef struct { 119typedef struct {
98 uint8_t buttons; 120 uint8_t buttons;
diff --git a/keyboard/hhkb/Makefile.lufa b/keyboard/hhkb/Makefile.lufa
index 97b8faab6..262282a01 100644
--- a/keyboard/hhkb/Makefile.lufa
+++ b/keyboard/hhkb/Makefile.lufa
@@ -57,8 +57,8 @@ CONFIG_H = config.h
57 57
58 58
59# MCU name 59# MCU name
60MCU = at90usb1286 60#MCU = at90usb1286
61#MCU = atmega32u4 61MCU = atmega32u4
62 62
63# Processor frequency. 63# Processor frequency.
64# This will define a symbol, F_CPU, in all source code files equal to the 64# This will define a symbol, F_CPU, in all source code files equal to the
@@ -103,7 +103,7 @@ OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
103# Atmel DFU loader 4096 103# Atmel DFU loader 4096
104# LUFA bootloader 4096 104# LUFA bootloader 4096
105# USBaspLoader 2048 105# USBaspLoader 2048
106OPT_DEFS += -DBOOTLOADER_SIZE=512 106OPT_DEFS += -DBOOTLOADER_SIZE=4096
107 107
108 108
109# Build Options 109# Build Options
@@ -114,7 +114,7 @@ MOUSEKEY_ENABLE = yes # Mouse keys
114EXTRAKEY_ENABLE = yes # Audio control and System control 114EXTRAKEY_ENABLE = yes # Audio control and System control
115CONSOLE_ENABLE = yes # Console for debug 115CONSOLE_ENABLE = yes # Console for debug
116COMMAND_ENABLE = yes # Commands for debug and configuration 116COMMAND_ENABLE = yes # Commands for debug and configuration
117#NKRO_ENABLE = yes # USB Nkey Rollover 117NKRO_ENABLE = yes # USB Nkey Rollover
118 118
119 119
120# Search Path 120# Search Path
diff --git a/keyboard/hhkb/Makefile.pjrc b/keyboard/hhkb/Makefile.pjrc
index f64cd9be4..5a781dd23 100644
--- a/keyboard/hhkb/Makefile.pjrc
+++ b/keyboard/hhkb/Makefile.pjrc
@@ -23,9 +23,9 @@ CONFIG_H = config.h
23# MCU name, you MUST set this to match the board you are using 23# MCU name, you MUST set this to match the board you are using
24# type "make clean" after changing this, so all files will be rebuilt 24# type "make clean" after changing this, so all files will be rebuilt
25#MCU = at90usb162 # Teensy 1.0 25#MCU = at90usb162 # Teensy 1.0
26#MCU = atmega32u4 # Teensy 2.0 26MCU = atmega32u4 # Teensy 2.0
27#MCU = at90usb646 # Teensy++ 1.0 27#MCU = at90usb646 # Teensy++ 1.0
28MCU = at90usb1286 # Teensy++ 2.0 28#MCU = at90usb1286 # Teensy++ 2.0
29 29
30 30
31# Processor frequency. 31# Processor frequency.
diff --git a/keyboard/hhkb/Makefile.tmk b/keyboard/hhkb/Makefile.tmk
deleted file mode 100644
index d3730081f..000000000
--- a/keyboard/hhkb/Makefile.tmk
+++ /dev/null
@@ -1,129 +0,0 @@
1#----------------------------------------------------------------------------
2# On command line:
3#
4# make all = Make software.
5#
6# make clean = Clean out built project files.
7#
8# make coff = Convert ELF to AVR COFF.
9#
10# make extcoff = Convert ELF to AVR Extended COFF.
11#
12# make program = Download the hex file to the device.
13# Please customize your programmer settings(PROGRAM_CMD)
14#
15# make teensy = Download the hex file to the device, using teensy_loader_cli.
16# (must have teensy_loader_cli installed).
17#
18# make dfu = Download the hex file to the device, using dfu-programmer (must
19# have dfu-programmer installed).
20#
21# make flip = Download the hex file to the device, using Atmel FLIP (must
22# have Atmel FLIP installed).
23#
24# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
25# (must have dfu-programmer installed).
26#
27# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
28# (must have Atmel FLIP installed).
29#
30# make debug = Start either simulavr or avarice as specified for debugging,
31# with avr-gdb or avr-insight as the front end for debugging.
32#
33# make filename.s = Just compile filename.c into the assembler code only.
34#
35# make filename.i = Create a preprocessed source file for use in submitting
36# bug reports to the GCC project.
37#
38# To rebuild project do "make clean" then "make all".
39#----------------------------------------------------------------------------
40
41# Target file name (without extension).
42TARGET = hhkb_tmk
43
44# Directory common source filess exist
45TOP_DIR = ../..
46
47# Directory keyboard dependent files exist
48TARGET_DIR = .
49
50
51# List C source files here. (C dependencies are automatically generated.)
52SRC += keymap.c \
53 matrix.c \
54 led.c
55
56CONFIG_H = config.h
57
58
59# MCU name
60#MCU = at90usb1286
61MCU = atmega32u4
62
63# Processor frequency.
64# This will define a symbol, F_CPU, in all source code files equal to the
65# processor frequency in Hz. You can then use this symbol in your source code to
66# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
67# automatically to create a 32-bit value in your source code.
68#
69# This will be an integer division of F_USB below, as it is sourced by
70# F_USB after it has run through any CPU prescalers. Note that this value
71# does not *change* the processor frequency - it should merely be updated to
72# reflect the processor speed set externally so that the code can use accurate
73# software delays.
74F_CPU = 16000000
75
76
77#
78# LUFA specific
79#
80# Target architecture (see library "Board Types" documentation).
81ARCH = AVR8
82
83# Input clock frequency.
84# This will define a symbol, F_USB, in all source code files equal to the
85# input clock frequency (before any prescaling is performed) in Hz. This value may
86# differ from F_CPU if prescaling is used on the latter, and is required as the
87# raw input clock is fed directly to the PLL sections of the AVR for high speed
88# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
89# at the end, this will be done automatically to create a 32-bit value in your
90# source code.
91#
92# If no clock division is performed on the input clock inside the AVR (via the
93# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
94F_USB = $(F_CPU)
95
96# Interrupt driven control endpoint task
97OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
98
99
100# Boot Section Size in *bytes*
101# Teensy halfKay 512
102# Teensy++ halfKay 1024
103# Atmel DFU loader 4096
104# LUFA bootloader 4096
105# USBaspLoader 2048
106OPT_DEFS += -DBOOTLOADER_SIZE=4096
107
108
109# Build Options
110# comment out to disable the options.
111#
112#BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration
113MOUSEKEY_ENABLE = yes # Mouse keys
114EXTRAKEY_ENABLE = yes # Audio control and System control
115CONSOLE_ENABLE = yes # Console for debug
116COMMAND_ENABLE = yes # Commands for debug and configuration
117#NKRO_ENABLE = yes # USB Nkey Rollover
118
119
120# Search Path
121VPATH += $(TARGET_DIR)
122VPATH += $(TOP_DIR)
123
124include $(TOP_DIR)/protocol/lufa.mk
125include $(TOP_DIR)/common.mk
126include $(TOP_DIR)/rules.mk
127
128debug-on: EXTRAFLAGS += -DDEBUG
129debug-on: all
diff --git a/keyboard/hhkb/config.h b/keyboard/hhkb/config.h
index 8c93f97da..ebee0c036 100644
--- a/keyboard/hhkb/config.h
+++ b/keyboard/hhkb/config.h
@@ -21,7 +21,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
21 21
22#define VENDOR_ID 0xFEED 22#define VENDOR_ID 0xFEED
23#define PRODUCT_ID 0xCAFE 23#define PRODUCT_ID 0xCAFE
24#define DEVICE_VER 0x0103 24#define DEVICE_VER 0x0104
25#define MANUFACTURER t.m.k. 25#define MANUFACTURER t.m.k.
26#define PRODUCT HHKB mod 26#define PRODUCT HHKB mod
27#define DESCRIPTION t.m.k. keyboard firmware for HHKB mod 27#define DESCRIPTION t.m.k. keyboard firmware for HHKB mod
diff --git a/protocol/lufa/descriptor.c b/protocol/lufa/descriptor.c
index d34ab1c5a..a46ba3ec6 100644
--- a/protocol/lufa/descriptor.c
+++ b/protocol/lufa/descriptor.c
@@ -57,9 +57,11 @@ const USB_Descriptor_HIDReport_Datatype_t PROGMEM KeyboardReport[] =
57 HID_RI_REPORT_COUNT(8, 0x08), 57 HID_RI_REPORT_COUNT(8, 0x08),
58 HID_RI_REPORT_SIZE(8, 0x01), 58 HID_RI_REPORT_SIZE(8, 0x01),
59 HID_RI_INPUT(8, HID_IOF_DATA | HID_IOF_VARIABLE | HID_IOF_ABSOLUTE), 59 HID_RI_INPUT(8, HID_IOF_DATA | HID_IOF_VARIABLE | HID_IOF_ABSOLUTE),
60
60 HID_RI_REPORT_COUNT(8, 0x01), 61 HID_RI_REPORT_COUNT(8, 0x01),
61 HID_RI_REPORT_SIZE(8, 0x08), 62 HID_RI_REPORT_SIZE(8, 0x08),
62 HID_RI_INPUT(8, HID_IOF_CONSTANT), 63 HID_RI_INPUT(8, HID_IOF_CONSTANT), /* reserved */
64
63 HID_RI_USAGE_PAGE(8, 0x08), /* LEDs */ 65 HID_RI_USAGE_PAGE(8, 0x08), /* LEDs */
64 HID_RI_USAGE_MINIMUM(8, 0x01), /* Num Lock */ 66 HID_RI_USAGE_MINIMUM(8, 0x01), /* Num Lock */
65 HID_RI_USAGE_MAXIMUM(8, 0x05), /* Kana */ 67 HID_RI_USAGE_MAXIMUM(8, 0x05), /* Kana */
@@ -69,6 +71,7 @@ const USB_Descriptor_HIDReport_Datatype_t PROGMEM KeyboardReport[] =
69 HID_RI_REPORT_COUNT(8, 0x01), 71 HID_RI_REPORT_COUNT(8, 0x01),
70 HID_RI_REPORT_SIZE(8, 0x03), 72 HID_RI_REPORT_SIZE(8, 0x03),
71 HID_RI_OUTPUT(8, HID_IOF_CONSTANT), 73 HID_RI_OUTPUT(8, HID_IOF_CONSTANT),
74
72 HID_RI_USAGE_PAGE(8, 0x07), /* Keyboard */ 75 HID_RI_USAGE_PAGE(8, 0x07), /* Keyboard */
73 HID_RI_USAGE_MINIMUM(8, 0x00), /* Reserved (no event indicated) */ 76 HID_RI_USAGE_MINIMUM(8, 0x00), /* Reserved (no event indicated) */
74 HID_RI_USAGE_MAXIMUM(8, 0xFF), /* Keyboard Application */ 77 HID_RI_USAGE_MAXIMUM(8, 0xFF), /* Keyboard Application */
@@ -210,11 +213,13 @@ const USB_Descriptor_HIDReport_Datatype_t PROGMEM NKROReport[] =
210 213
211 HID_RI_USAGE_PAGE(8, 0x07), /* Key Codes */ 214 HID_RI_USAGE_PAGE(8, 0x07), /* Key Codes */
212 HID_RI_USAGE_MINIMUM(8, 0x00), /* Keyboard 0 */ 215 HID_RI_USAGE_MINIMUM(8, 0x00), /* Keyboard 0 */
213 HID_RI_USAGE_MAXIMUM(8, NKRO_SIZE*8-1), /* Keyboard Right GUI */ 216 HID_RI_USAGE_MAXIMUM(8, (NKRO_EPSIZE-1)*8-1), /* Keyboard Right GUI */
214 HID_RI_LOGICAL_MINIMUM(8, 0x00), 217 HID_RI_LOGICAL_MINIMUM(8, 0x00),
215 HID_RI_LOGICAL_MAXIMUM(8, 0x01), 218 HID_RI_LOGICAL_MAXIMUM(8, 0x01),
216 HID_RI_REPORT_COUNT(8, NKRO_SIZE*8), 219 HID_RI_REPORT_COUNT(8, (NKRO_EPSIZE-1)*8),
217 HID_RI_REPORT_SIZE(8, 0x01), 220 HID_RI_REPORT_SIZE(8, 0x01),
221 HID_RI_INPUT(8, HID_IOF_DATA | HID_IOF_VARIABLE | HID_IOF_ABSOLUTE),
222 HID_RI_END_COLLECTION(0),
218}; 223};
219#endif 224#endif
220 225
@@ -439,6 +444,48 @@ const USB_Descriptor_Configuration_t PROGMEM ConfigurationDescriptor =
439 .PollingIntervalMS = 0x01 444 .PollingIntervalMS = 0x01
440 }, 445 },
441#endif 446#endif
447
448 /*
449 * NKRO
450 */
451#ifdef NKRO_ENABLE
452 .NKRO_Interface =
453 {
454 .Header = {.Size = sizeof(USB_Descriptor_Interface_t), .Type = DTYPE_Interface},
455
456 .InterfaceNumber = NKRO_INTERFACE,
457 .AlternateSetting = 0x00,
458
459 .TotalEndpoints = 1,
460
461 .Class = HID_CSCP_HIDClass,
462 .SubClass = HID_CSCP_NonBootSubclass,
463 .Protocol = HID_CSCP_NonBootProtocol,
464
465 .InterfaceStrIndex = NO_DESCRIPTOR
466 },
467
468 .NKRO_HID =
469 {
470 .Header = {.Size = sizeof(USB_HID_Descriptor_HID_t), .Type = HID_DTYPE_HID},
471
472 .HIDSpec = VERSION_BCD(01.11),
473 .CountryCode = 0x00,
474 .TotalReportDescriptors = 1,
475 .HIDReportType = HID_DTYPE_Report,
476 .HIDReportLength = sizeof(NKROReport)
477 },
478
479 .NKRO_INEndpoint =
480 {
481 .Header = {.Size = sizeof(USB_Descriptor_Endpoint_t), .Type = DTYPE_Endpoint},
482
483 .EndpointAddress = (ENDPOINT_DIR_IN | NKRO_IN_EPNUM),
484 .Attributes = (EP_TYPE_INTERRUPT | ENDPOINT_ATTR_NO_SYNC | ENDPOINT_USAGE_DATA),
485 .EndpointSize = NKRO_EPSIZE,
486 .PollingIntervalMS = 0x01
487 },
488#endif
442}; 489};
443 490
444 491
@@ -536,6 +583,12 @@ uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue,
536 Size = sizeof(USB_HID_Descriptor_HID_t); 583 Size = sizeof(USB_HID_Descriptor_HID_t);
537 break; 584 break;
538#endif 585#endif
586#ifdef NKRO_ENABLE
587 case NKRO_INTERFACE:
588 Address = &ConfigurationDescriptor.NKRO_HID;
589 Size = sizeof(USB_HID_Descriptor_HID_t);
590 break;
591#endif
539 } 592 }
540 break; 593 break;
541 case HID_DTYPE_Report: 594 case HID_DTYPE_Report:
@@ -562,6 +615,12 @@ uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue,
562 Size = sizeof(ConsoleReport); 615 Size = sizeof(ConsoleReport);
563 break; 616 break;
564#endif 617#endif
618#ifdef NKRO_ENABLE
619 case NKRO_INTERFACE:
620 Address = &NKROReport;
621 Size = sizeof(NKROReport);
622 break;
623#endif
565 } 624 }
566 break; 625 break;
567 } 626 }
diff --git a/protocol/lufa/descriptor.h b/protocol/lufa/descriptor.h
index 44f20d5a2..9ee1c04d7 100644
--- a/protocol/lufa/descriptor.h
+++ b/protocol/lufa/descriptor.h
@@ -1,5 +1,5 @@
1/* 1/*
2 * Copyright 2012 Jun Wako <wakojun@gmail.com> 2 * Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
3 * This file is based on: 3 * This file is based on:
4 * LUFA-120219/Demos/Device/Lowlevel/KeyboardMouse 4 * LUFA-120219/Demos/Device/Lowlevel/KeyboardMouse
5 * LUFA-120219/Demos/Device/Lowlevel/GenericHID 5 * LUFA-120219/Demos/Device/Lowlevel/GenericHID
@@ -78,6 +78,13 @@ typedef struct
78 USB_Descriptor_Endpoint_t Console_INEndpoint; 78 USB_Descriptor_Endpoint_t Console_INEndpoint;
79 USB_Descriptor_Endpoint_t Console_OUTEndpoint; 79 USB_Descriptor_Endpoint_t Console_OUTEndpoint;
80#endif 80#endif
81
82#ifdef NKRO_ENABLE
83 // NKRO HID Interface
84 USB_Descriptor_Interface_t NKRO_Interface;
85 USB_HID_Descriptor_HID_t NKRO_HID;
86 USB_Descriptor_Endpoint_t NKRO_INEndpoint;
87#endif
81} USB_Descriptor_Configuration_t; 88} USB_Descriptor_Configuration_t;
82 89
83 90
@@ -102,9 +109,15 @@ typedef struct
102# define CONSOLE_INTERFACE EXTRAKEY_INTERFACE 109# define CONSOLE_INTERFACE EXTRAKEY_INTERFACE
103#endif 110#endif
104 111
112#ifdef NKRO_ENABLE
113# define NKRO_INTERFACE (CONSOLE_INTERFACE + 1)
114#else
115# define NKRO_INTERFACE CONSOLE_INTERFACE
116#endif
117
105 118
106/* nubmer of interfaces */ 119/* nubmer of interfaces */
107#define TOTAL_INTERFACES (CONSOLE_INTERFACE + 1) 120#define TOTAL_INTERFACES (NKRO_INTERFACE + 1)
108 121
109 122
110// Endopoint number and size 123// Endopoint number and size
@@ -125,6 +138,12 @@ typedef struct
125#ifdef CONSOLE_ENABLE 138#ifdef CONSOLE_ENABLE
126# define CONSOLE_IN_EPNUM (EXTRAKEY_IN_EPNUM + 1) 139# define CONSOLE_IN_EPNUM (EXTRAKEY_IN_EPNUM + 1)
127# define CONSOLE_OUT_EPNUM (EXTRAKEY_IN_EPNUM + 2) 140# define CONSOLE_OUT_EPNUM (EXTRAKEY_IN_EPNUM + 2)
141#else
142# define CONSOLE_OUT_EPNUM EXTRAKEY_IN_EPNUM
143#endif
144
145#ifdef NKRO_ENABLE
146# define NKRO_IN_EPNUM (CONSOLE_OUT_EPNUM + 1)
128#endif 147#endif
129 148
130 149
@@ -132,6 +151,7 @@ typedef struct
132#define MOUSE_EPSIZE 8 151#define MOUSE_EPSIZE 8
133#define EXTRAKEY_EPSIZE 8 152#define EXTRAKEY_EPSIZE 8
134#define CONSOLE_EPSIZE 32 153#define CONSOLE_EPSIZE 32
154#define NKRO_EPSIZE 16
135 155
136 156
137uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue, 157uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue,
diff --git a/protocol/lufa/lufa.c b/protocol/lufa/lufa.c
index a863b8d23..c1617cd05 100644
--- a/protocol/lufa/lufa.c
+++ b/protocol/lufa/lufa.c
@@ -220,6 +220,12 @@ void EVENT_USB_Device_ConfigurationChanged(void)
220 ConfigSuccess &= ENDPOINT_CONFIG(CONSOLE_OUT_EPNUM, EP_TYPE_INTERRUPT, ENDPOINT_DIR_OUT, 220 ConfigSuccess &= ENDPOINT_CONFIG(CONSOLE_OUT_EPNUM, EP_TYPE_INTERRUPT, ENDPOINT_DIR_OUT,
221 CONSOLE_EPSIZE, ENDPOINT_BANK_SINGLE); 221 CONSOLE_EPSIZE, ENDPOINT_BANK_SINGLE);
222#endif 222#endif
223
224#ifdef NKRO_ENABLE
225 /* Setup NKRO HID Report Endpoints */
226 ConfigSuccess &= ENDPOINT_CONFIG(NKRO_IN_EPNUM, EP_TYPE_INTERRUPT, ENDPOINT_DIR_IN,
227 NKRO_EPSIZE, ENDPOINT_BANK_SINGLE);
228#endif
223} 229}
224 230
225/* 231/*
@@ -350,15 +356,31 @@ static void send_keyboard(report_keyboard_t *report)
350 if (USB_DeviceState != DEVICE_STATE_Configured) 356 if (USB_DeviceState != DEVICE_STATE_Configured)
351 return; 357 return;
352 358
353 // TODO: handle NKRO report
354 /* Select the Keyboard Report Endpoint */ 359 /* Select the Keyboard Report Endpoint */
355 Endpoint_SelectEndpoint(KEYBOARD_IN_EPNUM); 360#ifdef NKRO_ENABLE
361 if (keyboard_nkro) {
362 Endpoint_SelectEndpoint(NKRO_IN_EPNUM);
363 }
364 else
365#endif
366 {
367 Endpoint_SelectEndpoint(KEYBOARD_IN_EPNUM);
368 }
356 369
357 /* Check if Keyboard Endpoint Ready for Read/Write */ 370 /* Check if Keyboard Endpoint Ready for Read/Write */
358 while (--timeout && !Endpoint_IsReadWriteAllowed()) ; 371 while (--timeout && !Endpoint_IsReadWriteAllowed()) ;
359 372
360 /* Write Keyboard Report Data */ 373 /* Write Keyboard Report Data */
361 Endpoint_Write_Stream_LE(report, sizeof(report_keyboard_t), NULL); 374#ifdef NKRO_ENABLE
375 if (keyboard_nkro) {
376 Endpoint_Write_Stream_LE(report, NKRO_EPSIZE, NULL);
377 }
378 else
379#endif
380 {
381 /* boot mode */
382 Endpoint_Write_Stream_LE(report, KEYBOARD_EPSIZE, NULL);
383 }
362 384
363 /* Finalize the stream transfer to send the last packet */ 385 /* Finalize the stream transfer to send the last packet */
364 Endpoint_ClearIN(); 386 Endpoint_ClearIN();
diff --git a/protocol/pjrc/usb_keyboard.c b/protocol/pjrc/usb_keyboard.c
index 49b85c179..de798fcc2 100644
--- a/protocol/pjrc/usb_keyboard.c
+++ b/protocol/pjrc/usb_keyboard.c
@@ -57,12 +57,12 @@ int8_t usb_keyboard_send_report(report_keyboard_t *report)
57 57
58#ifdef NKRO_ENABLE 58#ifdef NKRO_ENABLE
59 if (keyboard_nkro) 59 if (keyboard_nkro)
60 result = send_report(report, KBD2_ENDPOINT, 0, KBD2_REPORT_KEYS); 60 result = send_report(report, KBD2_ENDPOINT, 0, KBD2_SIZE);
61 else 61 else
62#endif 62#endif
63 { 63 {
64 if (usb_keyboard_protocol) 64 if (usb_keyboard_protocol)
65 result = send_report(report, KBD_ENDPOINT, 0, KBD_REPORT_KEYS); 65 result = send_report(report, KBD_ENDPOINT, 0, KBD_SIZE);
66 else 66 else
67 result = send_report(report, KBD_ENDPOINT, 0, 6); 67 result = send_report(report, KBD_ENDPOINT, 0, 6);
68 } 68 }
@@ -104,15 +104,8 @@ static inline int8_t send_report(report_keyboard_t *report, uint8_t endpoint, ui
104 cli(); 104 cli();
105 UENUM = endpoint; 105 UENUM = endpoint;
106 } 106 }
107 UEDATX = report->mods;
108#ifdef NKRO_ENABLE
109 if (!keyboard_nkro)
110 UEDATX = 0;
111#else
112 UEDATX = 0;
113#endif
114 for (uint8_t i = keys_start; i < keys_end; i++) { 107 for (uint8_t i = keys_start; i < keys_end; i++) {
115 UEDATX = report->keys[i]; 108 UEDATX = report->raw[i];
116 } 109 }
117 UEINTX = 0x3A; 110 UEINTX = 0x3A;
118 SREG = intr_state; 111 SREG = intr_state;