diff options
Diffstat (limited to 'tmk_core/common')
27 files changed, 617 insertions, 616 deletions
diff --git a/tmk_core/common/action.c b/tmk_core/common/action.c index 055bd91de0..5660c3fa1f 100644 --- a/tmk_core/common/action.c +++ b/tmk_core/common/action.c @@ -133,7 +133,8 @@ void process_hand_swap(keyevent_t *event) { bool do_swap = event->pressed ? swap_hands : swap_state[pos.row] & (col_bit); if (do_swap) { - event->key = hand_swap_config[pos.row][pos.col]; + event->key.row = pgm_read_byte(&hand_swap_config[pos.row][pos.col].row); + event->key.col = pgm_read_byte(&hand_swap_config[pos.row][pos.col].col); swap_state[pos.row] |= col_bit; } else { swap_state[pos.row] &= ~(col_bit); @@ -772,10 +773,9 @@ void register_code(uint8_t code) { } #endif - else if - IS_KEY(code) { - // TODO: should push command_proc out of this block? - if (command_proc(code)) return; + else if IS_KEY (code) { + // TODO: should push command_proc out of this block? + if (command_proc(code)) return; #ifndef NO_ACTION_ONESHOT /* TODO: remove @@ -792,35 +792,33 @@ void register_code(uint8_t code) { } else */ #endif - { - // Force a new key press if the key is already pressed - // without this, keys with the same keycode, but different - // modifiers will be reported incorrectly, see issue #1708 - if (is_key_pressed(keyboard_report, code)) { - del_key(code); - send_keyboard_report(); - } - add_key(code); + { + // Force a new key press if the key is already pressed + // without this, keys with the same keycode, but different + // modifiers will be reported incorrectly, see issue #1708 + if (is_key_pressed(keyboard_report, code)) { + del_key(code); send_keyboard_report(); } - } - else if - IS_MOD(code) { - add_mods(MOD_BIT(code)); + add_key(code); send_keyboard_report(); } + } else if IS_MOD (code) { + add_mods(MOD_BIT(code)); + send_keyboard_report(); + } #ifdef EXTRAKEY_ENABLE - else if - IS_SYSTEM(code) { host_system_send(KEYCODE2SYSTEM(code)); } - else if - IS_CONSUMER(code) { host_consumer_send(KEYCODE2CONSUMER(code)); } + else if IS_SYSTEM (code) { + host_system_send(KEYCODE2SYSTEM(code)); + } else if IS_CONSUMER (code) { + host_consumer_send(KEYCODE2CONSUMER(code)); + } #endif #ifdef MOUSEKEY_ENABLE - else if - IS_MOUSEKEY(code) { - mousekey_on(code); - mousekey_send(); - } + else if IS_MOUSEKEY (code) { + mousekey_on(code); + mousekey_send(); + } #endif } @@ -865,26 +863,22 @@ void unregister_code(uint8_t code) { } #endif - else if - IS_KEY(code) { - del_key(code); - send_keyboard_report(); - } - else if - IS_MOD(code) { - del_mods(MOD_BIT(code)); - send_keyboard_report(); - } - else if - IS_SYSTEM(code) { host_system_send(0); } - else if - IS_CONSUMER(code) { host_consumer_send(0); } + else if IS_KEY (code) { + del_key(code); + send_keyboard_report(); + } else if IS_MOD (code) { + del_mods(MOD_BIT(code)); + send_keyboard_report(); + } else if IS_SYSTEM (code) { + host_system_send(0); + } else if IS_CONSUMER (code) { + host_consumer_send(0); + } #ifdef MOUSEKEY_ENABLE - else if - IS_MOUSEKEY(code) { - mousekey_off(code); - mousekey_send(); - } + else if IS_MOUSEKEY (code) { + mousekey_off(code); + mousekey_send(); + } #endif } diff --git a/tmk_core/common/action.h b/tmk_core/common/action.h index 9a991de1c2..8cb4722c6e 100644 --- a/tmk_core/common/action.h +++ b/tmk_core/common/action.h @@ -77,8 +77,8 @@ extern bool disable_action_cache; /* Code for handling one-handed key modifiers. */ #ifdef SWAP_HANDS_ENABLE -extern bool swap_hands; -extern const keypos_t hand_swap_config[MATRIX_ROWS][MATRIX_COLS]; +extern bool swap_hands; +extern const keypos_t PROGMEM hand_swap_config[MATRIX_ROWS][MATRIX_COLS]; # if (MATRIX_COLS <= 8) typedef uint8_t swap_state_row_t; # elif (MATRIX_COLS <= 16) diff --git a/tmk_core/common/action_util.c b/tmk_core/common/action_util.c index 000503b082..a57c8bf66a 100644 --- a/tmk_core/common/action_util.c +++ b/tmk_core/common/action_util.c @@ -147,12 +147,16 @@ void clear_oneshot_swaphands(void) { * FIXME: needs doc */ void set_oneshot_layer(uint8_t layer, uint8_t state) { - oneshot_layer_data = layer << 3 | state; - layer_on(layer); + if (!keymap_config.oneshot_disable) { + oneshot_layer_data = layer << 3 | state; + layer_on(layer); # if (defined(ONESHOT_TIMEOUT) && (ONESHOT_TIMEOUT > 0)) - oneshot_layer_time = timer_read(); + oneshot_layer_time = timer_read(); # endif - oneshot_layer_changed_kb(get_oneshot_layer()); + oneshot_layer_changed_kb(get_oneshot_layer()); + } else { + layer_on(layer); + } } /** \brief Reset oneshot layer * @@ -172,7 +176,7 @@ void reset_oneshot_layer(void) { void clear_oneshot_layer_state(oneshot_fullfillment_t state) { uint8_t start_state = oneshot_layer_data; oneshot_layer_data &= ~state; - if (!get_oneshot_layer_state() && start_state != oneshot_layer_data) { + if ((!get_oneshot_layer_state() && start_state != oneshot_layer_data) || keymap_config.oneshot_disable) { layer_off(get_oneshot_layer()); reset_oneshot_layer(); } @@ -182,6 +186,39 @@ void clear_oneshot_layer_state(oneshot_fullfillment_t state) { * FIXME: needs doc */ bool is_oneshot_layer_active(void) { return get_oneshot_layer_state(); } + +/** \brief set oneshot + * + * FIXME: needs doc + */ +void oneshot_set(bool active) { + if (keymap_config.oneshot_disable != active) { + keymap_config.oneshot_disable = active; + eeconfig_update_keymap(keymap_config.raw); + dprintf("Oneshot: active: %d\n", active); + } +} + +/** \brief toggle oneshot + * + * FIXME: needs doc + */ +void oneshot_toggle(void) { oneshot_set(!keymap_config.oneshot_disable); } + +/** \brief enable oneshot + * + * FIXME: needs doc + */ +void oneshot_enable(void) { oneshot_set(true); } + +/** \brief disable oneshot + * + * FIXME: needs doc + */ +void oneshot_disable(void) { oneshot_set(false); } + +bool is_oneshot_enabled(void) { return keymap_config.oneshot_disable; } + #endif /** \brief Send keyboard report @@ -321,14 +358,17 @@ void del_oneshot_mods(uint8_t mods) { * FIXME: needs doc */ void set_oneshot_mods(uint8_t mods) { - if (oneshot_mods != mods) { + if (!keymap_config.oneshot_disable) { + if (oneshot_mods != mods) { # if (defined(ONESHOT_TIMEOUT) && (ONESHOT_TIMEOUT > 0)) - oneshot_time = timer_read(); + oneshot_time = timer_read(); # endif - oneshot_mods = mods; - oneshot_mods_changed_kb(mods); + oneshot_mods = mods; + oneshot_mods_changed_kb(mods); + } } } + /** \brief clear oneshot mods * * FIXME: needs doc diff --git a/tmk_core/common/action_util.h b/tmk_core/common/action_util.h index ff29f79b09..f2b3897ae5 100644 --- a/tmk_core/common/action_util.h +++ b/tmk_core/common/action_util.h @@ -85,6 +85,11 @@ void oneshot_mods_changed_kb(uint8_t mods); void oneshot_layer_changed_user(uint8_t layer); void oneshot_layer_changed_kb(uint8_t layer); +void oneshot_toggle(void); +void oneshot_enable(void); +void oneshot_disable(void); +bool is_oneshot_enabled(void); + /* inspect */ uint8_t has_anymod(void); diff --git a/tmk_core/common/arm_atsam/_wait.h b/tmk_core/common/arm_atsam/_wait.h new file mode 100644 index 0000000000..41b686b56c --- /dev/null +++ b/tmk_core/common/arm_atsam/_wait.h @@ -0,0 +1,22 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#pragma once + +#include "clks.h" + +#define wait_ms(ms) CLK_delay_ms(ms) +#define wait_us(us) CLK_delay_us(us) +#define waitInputPinDelay() diff --git a/tmk_core/common/avr/_wait.h b/tmk_core/common/avr/_wait.h new file mode 100644 index 0000000000..56eb316faf --- /dev/null +++ b/tmk_core/common/avr/_wait.h @@ -0,0 +1,29 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#pragma once + +#include <util/delay.h> + +#define wait_ms(ms) _delay_ms(ms) +#define wait_us(us) _delay_us(us) + +/* The AVR series GPIOs have a one clock read delay for changes in the digital input signal. + * But here's more margin to make it two clocks. */ +#ifndef GPIO_INPUT_PIN_DELAY +# define GPIO_INPUT_PIN_DELAY 2 +#endif + +#define waitInputPinDelay() __builtin_avr_delay_cycles(GPIO_INPUT_PIN_DELAY) diff --git a/tmk_core/common/avr/suspend.c b/tmk_core/common/avr/suspend.c index 47a82a2eec..690d7f38ca 100644 --- a/tmk_core/common/avr/suspend.c +++ b/tmk_core/common/avr/suspend.c @@ -28,6 +28,13 @@ # include "rgblight.h" #endif +#ifdef LED_MATRIX_ENABLE +# include "led_matrix.h" +#endif +#ifdef RGB_MATRIX_ENABLE +# include "rgb_matrix.h" +#endif + /** \brief Suspend idle * * FIXME: needs doc @@ -156,6 +163,13 @@ void suspend_power_down(void) { rgblight_suspend(); # endif +# if defined(LED_MATRIX_ENABLE) + led_matrix_set_suspend_state(true); +# endif +# if defined(RGB_MATRIX_ENABLE) + rgb_matrix_set_suspend_state(true); +# endif + // Enter sleep state if possible (ie, the MCU has a watchdog timeout interrupt) # if defined(WDT_vect) power_down(WDTO_15MS); @@ -208,6 +222,13 @@ void suspend_wakeup_init(void) { rgblight_wakeup(); #endif +#if defined(LED_MATRIX_ENABLE) + led_matrix_set_suspend_state(false); +#endif +#if defined(RGB_MATRIX_ENABLE) + rgb_matrix_set_suspend_state(false); +#endif + suspend_wakeup_init_kb(); } diff --git a/tmk_core/common/bootmagic.c b/tmk_core/common/bootmagic.c deleted file mode 100644 index c1b3adf94d..0000000000 --- a/tmk_core/common/bootmagic.c +++ /dev/null @@ -1,163 +0,0 @@ -#include <stdint.h> -#include <stdbool.h> -#include "wait.h" -#include "matrix.h" -#include "bootloader.h" -#include "debug.h" -#include "keymap.h" -#include "host.h" -#include "action_layer.h" -#include "eeconfig.h" -#include "bootmagic.h" - -keymap_config_t keymap_config; - -/** \brief Bootmagic - * - * FIXME: needs doc - */ -void bootmagic(void) { - /* check signature */ - if (!eeconfig_is_enabled()) { - eeconfig_init(); - } - - /* do scans in case of bounce */ - print("bootmagic scan: ... "); - uint8_t scan = 100; - while (scan--) { - matrix_scan(); - wait_ms(10); - } - print("done.\n"); - - /* bootmagic skip */ - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SKIP)) { - return; - } - - /* eeconfig clear */ - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_EEPROM_CLEAR)) { - eeconfig_init(); - } - - /* bootloader */ - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_BOOTLOADER)) { - bootloader_jump(); - } - - /* debug enable */ - debug_config.raw = eeconfig_read_debug(); - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEBUG_ENABLE)) { - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEBUG_MATRIX)) { - debug_config.matrix = !debug_config.matrix; - } else if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEBUG_KEYBOARD)) { - debug_config.keyboard = !debug_config.keyboard; - } else if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEBUG_MOUSE)) { - debug_config.mouse = !debug_config.mouse; - } else { - debug_config.enable = !debug_config.enable; - } - } - eeconfig_update_debug(debug_config.raw); - - /* keymap config */ - keymap_config.raw = eeconfig_read_keymap(); - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SWAP_CONTROL_CAPSLOCK)) { - keymap_config.swap_control_capslock = !keymap_config.swap_control_capslock; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_CAPSLOCK_TO_CONTROL)) { - keymap_config.capslock_to_control = !keymap_config.capslock_to_control; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SWAP_LALT_LGUI)) { - keymap_config.swap_lalt_lgui = !keymap_config.swap_lalt_lgui; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SWAP_RALT_RGUI)) { - keymap_config.swap_ralt_rgui = !keymap_config.swap_ralt_rgui; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_NO_GUI)) { - keymap_config.no_gui = !keymap_config.no_gui; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SWAP_GRAVE_ESC)) { - keymap_config.swap_grave_esc = !keymap_config.swap_grave_esc; - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_SWAP_BACKSLASH_BACKSPACE)) { - keymap_config.swap_backslash_backspace = !keymap_config.swap_backslash_backspace; - } - if (bootmagic_scan_keycode(BOOTMAGIC_HOST_NKRO)) { - keymap_config.nkro = !keymap_config.nkro; - } - eeconfig_update_keymap(keymap_config.raw); - - /* default layer */ - uint8_t default_layer = 0; - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_0)) { - default_layer |= (1 << 0); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_1)) { - default_layer |= (1 << 1); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_2)) { - default_layer |= (1 << 2); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_3)) { - default_layer |= (1 << 3); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_4)) { - default_layer |= (1 << 4); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_5)) { - default_layer |= (1 << 5); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_6)) { - default_layer |= (1 << 6); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_DEFAULT_LAYER_7)) { - default_layer |= (1 << 7); - } - if (default_layer) { - eeconfig_update_default_layer(default_layer); - default_layer_set((layer_state_t)default_layer); - } else { - default_layer = eeconfig_read_default_layer(); - default_layer_set((layer_state_t)default_layer); - } - /* Also initialize layer state to trigger callback functions for layer_state */ - layer_state_set_kb((layer_state_t)layer_state); - - /* EE_HANDS handedness */ - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_EE_HANDS_LEFT)) { - eeconfig_update_handedness(true); - } - if (bootmagic_scan_keycode(BOOTMAGIC_KEY_EE_HANDS_RIGHT)) { - eeconfig_update_handedness(false); - } -} - -/** \brief Scan Keycode - * - * FIXME: needs doc - */ -static bool scan_keycode(uint8_t keycode) { - for (uint8_t r = 0; r < MATRIX_ROWS; r++) { - matrix_row_t matrix_row = matrix_get_row(r); - for (uint8_t c = 0; c < MATRIX_COLS; c++) { - if (matrix_row & ((matrix_row_t)1 << c)) { - if (keycode == keymap_key_to_keycode(0, (keypos_t){.row = r, .col = c})) { - return true; - } - } - } - } - return false; -} - -/** \brief Bootmagic Scan Keycode - * - * FIXME: needs doc - */ -bool bootmagic_scan_keycode(uint8_t keycode) { - if (!scan_keycode(BOOTMAGIC_KEY_SALT)) return false; - - return scan_keycode(keycode); -} diff --git a/tmk_core/common/bootmagic.h b/tmk_core/common/bootmagic.h deleted file mode 100644 index 8209d0194f..0000000000 --- a/tmk_core/common/bootmagic.h +++ /dev/null @@ -1,102 +0,0 @@ -#pragma once - -/* FIXME: Add special doxygen comments for defines here. */ - -/* bootmagic salt key */ -#ifndef BOOTMAGIC_KEY_SALT -# define BOOTMAGIC_KEY_SALT KC_SPACE -#endif - -/* skip bootmagic and eeconfig */ -#ifndef BOOTMAGIC_KEY_SKIP -# define BOOTMAGIC_KEY_SKIP KC_ESC -#endif - -/* eeprom clear */ -#ifndef BOOTMAGIC_KEY_EEPROM_CLEAR -# define BOOTMAGIC_KEY_EEPROM_CLEAR KC_BSPACE -#endif - -/* kick up bootloader */ -#ifndef BOOTMAGIC_KEY_BOOTLOADER -# define BOOTMAGIC_KEY_BOOTLOADER KC_B -#endif - -/* debug enable */ -#ifndef BOOTMAGIC_KEY_DEBUG_ENABLE -# define BOOTMAGIC_KEY_DEBUG_ENABLE KC_D -#endif -#ifndef BOOTMAGIC_KEY_DEBUG_MATRIX -# define BOOTMAGIC_KEY_DEBUG_MATRIX KC_X -#endif -#ifndef BOOTMAGIC_KEY_DEBUG_KEYBOARD -# define BOOTMAGIC_KEY_DEBUG_KEYBOARD KC_K -#endif -#ifndef BOOTMAGIC_KEY_DEBUG_MOUSE -# define BOOTMAGIC_KEY_DEBUG_MOUSE KC_M -#endif -#ifndef BOOTMAGIC_KEY_EE_HANDS_LEFT -# define BOOTMAGIC_KEY_EE_HANDS_LEFT KC_L -#endif -#ifndef BOOTMAGIC_KEY_EE_HANDS_RIGHT -# define BOOTMAGIC_KEY_EE_HANDS_RIGHT KC_R -#endif - -/* - * keymap config - */ -#ifndef BOOTMAGIC_KEY_SWAP_CONTROL_CAPSLOCK -# define BOOTMAGIC_KEY_SWAP_CONTROL_CAPSLOCK KC_LCTRL -#endif -#ifndef BOOTMAGIC_KEY_CAPSLOCK_TO_CONTROL -# define BOOTMAGIC_KEY_CAPSLOCK_TO_CONTROL KC_CAPSLOCK -#endif -#ifndef BOOTMAGIC_KEY_SWAP_LALT_LGUI -# define BOOTMAGIC_KEY_SWAP_LALT_LGUI KC_LALT -#endif -#ifndef BOOTMAGIC_KEY_SWAP_RALT_RGUI -# define BOOTMAGIC_KEY_SWAP_RALT_RGUI KC_RALT -#endif -#ifndef BOOTMAGIC_KEY_NO_GUI -# define BOOTMAGIC_KEY_NO_GUI KC_LGUI -#endif -#ifndef BOOTMAGIC_KEY_SWAP_GRAVE_ESC -# define BOOTMAGIC_KEY_SWAP_GRAVE_ESC KC_GRAVE -#endif -#ifndef BOOTMAGIC_KEY_SWAP_BACKSLASH_BACKSPACE -# define BOOTMAGIC_KEY_SWAP_BACKSLASH_BACKSPACE KC_BSLASH -#endif -#ifndef BOOTMAGIC_HOST_NKRO -# define BOOTMAGIC_HOST_NKRO KC_N -#endif - -/* - * change default layer - */ -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_0 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_0 KC_0 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_1 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_1 KC_1 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_2 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_2 KC_2 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_3 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_3 KC_3 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_4 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_4 KC_4 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_5 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_5 KC_5 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_6 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_6 KC_6 -#endif -#ifndef BOOTMAGIC_KEY_DEFAULT_LAYER_7 -# define BOOTMAGIC_KEY_DEFAULT_LAYER_7 KC_7 -#endif - -void bootmagic(void); -bool bootmagic_scan_keycode(uint8_t keycode); diff --git a/tmk_core/common/bootmagic_lite.c b/tmk_core/common/bootmagic_lite.c deleted file mode 100644 index cbf756a175..0000000000 --- a/tmk_core/common/bootmagic_lite.c +++ /dev/null @@ -1,49 +0,0 @@ -#include "quantum.h" - -/** \brief Reset eeprom - * - * ...just incase someone wants to only change the eeprom behaviour - */ -__attribute__((weak)) void bootmagic_lite_reset_eeprom(void) { -#if defined(VIA_ENABLE) - via_eeprom_reset(); -#else - eeconfig_disable(); -#endif -} - -/** \brief The lite version of TMK's bootmagic based on Wilba. - * - * 100% less potential for accidentally making the keyboard do stupid things. - */ -__attribute__((weak)) void bootmagic_lite(void) { - // We need multiple scans because debouncing can't be turned off. - matrix_scan(); -#if defined(DEBOUNCE) && DEBOUNCE > 0 - wait_ms(DEBOUNCE * 2); -#else - wait_ms(30); -#endif - matrix_scan(); - - // If the configured key (commonly Esc) is held down on power up, - // reset the EEPROM valid state and jump to bootloader. - // This isn't very generalized, but we need something that doesn't - // rely on user's keymaps in firmware or EEPROM. - uint8_t row = BOOTMAGIC_LITE_ROW; - uint8_t col = BOOTMAGIC_LITE_COLUMN; - -#if defined(SPLIT_KEYBOARD) && defined(BOOTMAGIC_LITE_ROW_RIGHT) && defined(BOOTMAGIC_LITE_COLUMN_RIGHT) - if (!is_keyboard_left()) { - row = BOOTMAGIC_LITE_ROW_RIGHT; - col = BOOTMAGIC_LITE_COLUMN_RIGHT; - } -#endif - - if (matrix_get_row(row) & (1 << col)) { - bootmagic_lite_reset_eeprom(); - - // Jump to bootloader. - bootloader_jump(); - } -} diff --git a/tmk_core/common/chibios/_wait.h b/tmk_core/common/chibios/_wait.h new file mode 100644 index 0000000000..5bface53e1 --- /dev/null +++ b/tmk_core/common/chibios/_wait.h @@ -0,0 +1,55 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#pragma once + +#include <ch.h> + +/* chThdSleepX of zero maps to infinite - so we map to a tiny delay to still yield */ +#define wait_ms(ms) \ + do { \ + if (ms != 0) { \ + chThdSleepMilliseconds(ms); \ + } else { \ + chThdSleepMicroseconds(1); \ + } \ + } while (0) +#define wait_us(us) \ + do { \ + if (us != 0) { \ + chThdSleepMicroseconds(us); \ + } else { \ + chThdSleepMicroseconds(1); \ + } \ + } while (0) + +/* For GPIOs on ARM-based MCUs, the input pins are sampled by the clock of the bus + * to which the GPIO is connected. + * The connected buses differ depending on the various series of MCUs. + * And since the instruction execution clock of the CPU and the bus clock of GPIO are different, + * there is a delay of several clocks to read the change of the input signal. + * + * Define this delay with the GPIO_INPUT_PIN_DELAY macro. + * If the GPIO_INPUT_PIN_DELAY macro is not defined, the following default values will be used. + * (A fairly large value of 0.25 microseconds is set.) + */ + +#include "wait.c" + +#ifndef GPIO_INPUT_PIN_DELAY +# define GPIO_INPUT_PIN_DELAY (STM32_SYSCLK / 1000000L / 4) +#endif + +#define waitInputPinDelay() wait_cpuclock(GPIO_INPUT_PIN_DELAY) diff --git a/tmk_core/common/chibios/bootloader.c b/tmk_core/common/chibios/bootloader.c index 6cabcc4b81..11f7abf432 100644 --- a/tmk_core/common/chibios/bootloader.c +++ b/tmk_core/common/chibios/bootloader.c @@ -13,7 +13,23 @@ # define STM32_BOOTLOADER_DUAL_BANK FALSE #endif -#if STM32_BOOTLOADER_DUAL_BANK +#ifdef BOOTLOADER_TINYUF2 + +# define DBL_TAP_MAGIC 0xf01669ef // From tinyuf2's board_api.h + +// defined by linker script +extern uint32_t _board_dfu_dbl_tap[]; +# define DBL_TAP_REG _board_dfu_dbl_tap[0] + +void bootloader_jump(void) { + DBL_TAP_REG = DBL_TAP_MAGIC; + NVIC_SystemReset(); +} + +void enter_bootloader_mode_if_requested(void) { /* not needed, no two-stage reset */ +} + +#elif STM32_BOOTLOADER_DUAL_BANK // Need pin definitions # include "config_common.h" @@ -79,7 +95,7 @@ void enter_bootloader_mode_if_requested(void) { } } -#elif defined(KL2x) || defined(K20x) // STM32_BOOTLOADER_DUAL_BANK // STM32_BOOTLOADER_ADDRESS +#elif defined(KL2x) || defined(K20x) || defined(MK66F18) // STM32_BOOTLOADER_DUAL_BANK // STM32_BOOTLOADER_ADDRESS /* Kinetis */ # if defined(BOOTLOADER_KIIBOHD) diff --git a/tmk_core/common/chibios/chibios_config.h b/tmk_core/common/chibios/chibios_config.h index b4d96465d1..1d8ace4955 100644 --- a/tmk_core/common/chibios/chibios_config.h +++ b/tmk_core/common/chibios/chibios_config.h @@ -15,6 +15,8 @@ */ #pragma once +#define SPLIT_USB_DETECT // Force this on for now + #if defined(STM32F1XX) # define USE_GPIOV1 #endif @@ -28,4 +30,9 @@ # define USE_I2CV1 # define USE_I2CV1_CONTRIB // for some reason a bunch of ChibiOS-Contrib boards only have clock_speed # define USE_GPIOV1 +# define STM32_SYSCLK KINETIS_SYSCLK_FREQUENCY +#endif + +#if defined(MK66F18) +# define STM32_SYSCLK KINETIS_SYSCLK_FREQUENCY #endif diff --git a/tmk_core/common/chibios/pin_defs.h b/tmk_core/common/chibios/pin_defs.h index 86bc1076e8..c03f8de0c2 100644 --- a/tmk_core/common/chibios/pin_defs.h +++ b/tmk_core/common/chibios/pin_defs.h @@ -70,6 +70,23 @@ # define A13 PAL_LINE(GPIOA, 13) # define A14 PAL_LINE(GPIOA, 14) # define A15 PAL_LINE(GPIOA, 15) +# define A16 PAL_LINE(GPIOA, 16) +# define A17 PAL_LINE(GPIOA, 17) +# define A18 PAL_LINE(GPIOA, 18) +# define A19 PAL_LINE(GPIOA, 19) +# define A20 PAL_LINE(GPIOA, 20) +# define A21 PAL_LINE(GPIOA, 21) +# define A22 PAL_LINE(GPIOA, 22) +# define A23 PAL_LINE(GPIOA, 23) +# define A24 PAL_LINE(GPIOA, 24) +# define A25 PAL_LINE(GPIOA, 25) +# define A26 PAL_LINE(GPIOA, 26) +# define A27 PAL_LINE(GPIOA, 27) +# define A28 PAL_LINE(GPIOA, 28) +# define A29 PAL_LINE(GPIOA, 29) +# define A30 PAL_LINE(GPIOA, 30) +# define A31 PAL_LINE(GPIOA, 31) +# define A32 PAL_LINE(GPIOA, 32) # define B0 PAL_LINE(GPIOB, 0) # define B1 PAL_LINE(GPIOB, 1) # define B2 PAL_LINE(GPIOB, 2) @@ -90,6 +107,19 @@ # define B17 PAL_LINE(GPIOB, 17) # define B18 PAL_LINE(GPIOB, 18) # define B19 PAL_LINE(GPIOB, 19) +# define B20 PAL_LINE(GPIOB, 20) +# define B21 PAL_LINE(GPIOB, 21) +# define B22 PAL_LINE(GPIOB, 22) +# define B23 PAL_LINE(GPIOB, 23) +# define B24 PAL_LINE(GPIOB, 24) +# define B25 PAL_LINE(GPIOB, 25) +# define B26 PAL_LINE(GPIOB, 26) +# define B27 PAL_LINE(GPIOB, 27) +# define B28 PAL_LINE(GPIOB, 28) +# define B29 PAL_LINE(GPIOB, 29) +# define B30 PAL_LINE(GPIOB, 30) +# define B31 PAL_LINE(GPIOB, 31) +# define B32 PAL_LINE(GPIOB, 32) # define C0 PAL_LINE(GPIOC, 0) # define C1 PAL_LINE(GPIOC, 1) # define C2 PAL_LINE(GPIOC, 2) @@ -106,6 +136,23 @@ # define C13 PAL_LINE(GPIOC, 13) # define C14 PAL_LINE(GPIOC, 14) # define C15 PAL_LINE(GPIOC, 15) +# define C16 PAL_LINE(GPIOC, 16) +# define C17 PAL_LINE(GPIOC, 17) +# define C18 PAL_LINE(GPIOC, 18) +# define C19 PAL_LINE(GPIOC, 19) +# define C20 PAL_LINE(GPIOC, 20) +# define C21 PAL_LINE(GPIOC, 21) +# define C22 PAL_LINE(GPIOC, 22) +# define C23 PAL_LINE(GPIOC, 23) +# define C24 PAL_LINE(GPIOC, 24) +# define C25 PAL_LINE(GPIOC, 25) +# define C26 PAL_LINE(GPIOC, 26) +# define C27 PAL_LINE(GPIOC, 27) +# define C28 PAL_LINE(GPIOC, 28) +# define C29 PAL_LINE(GPIOC, 29) +# define C30 PAL_LINE(GPIOC, 30) +# define C31 PAL_LINE(GPIOC, 31) +# define C32 PAL_LINE(GPIOC, 32) # define D0 PAL_LINE(GPIOD, 0) # define D1 PAL_LINE(GPIOD, 1) # define D2 PAL_LINE(GPIOD, 2) @@ -122,6 +169,23 @@ # define D13 PAL_LINE(GPIOD, 13) # define D14 PAL_LINE(GPIOD, 14) # define D15 PAL_LINE(GPIOD, 15) +# define D16 PAL_LINE(GPIOD, 16) +# define D17 PAL_LINE(GPIOD, 17) +# define D18 PAL_LINE(GPIOD, 18) +# define D19 PAL_LINE(GPIOD, 19) +# define D20 PAL_LINE(GPIOD, 20) +# define D21 PAL_LINE(GPIOD, 21) +# define D22 PAL_LINE(GPIOD, 22) +# define D23 PAL_LINE(GPIOD, 23) +# define D24 PAL_LINE(GPIOD, 24) +# define D25 PAL_LINE(GPIOD, 25) +# define D26 PAL_LINE(GPIOD, 26) +# define D27 PAL_LINE(GPIOD, 27) +# define D28 PAL_LINE(GPIOD, 28) +# define D29 PAL_LINE(GPIOD, 29) +# define D30 PAL_LINE(GPIOD, 30) +# define D31 PAL_LINE(GPIOD, 31) +# define D32 PAL_LINE(GPIOD, 32) # define E0 PAL_LINE(GPIOE, 0) # define E1 PAL_LINE(GPIOE, 1) # define E2 PAL_LINE(GPIOE, 2) @@ -138,6 +202,23 @@ # define E13 PAL_LINE(GPIOE, 13) # define E14 PAL_LINE(GPIOE, 14) # define E15 PAL_LINE(GPIOE, 15) +# define E16 PAL_LINE(GPIOE, 16) +# define E17 PAL_LINE(GPIOE, 17) +# define E18 PAL_LINE(GPIOE, 18) +# define E19 PAL_LINE(GPIOE, 19) +# define E20 PAL_LINE(GPIOE, 20) +# define E21 PAL_LINE(GPIOE, 21) +# define E22 PAL_LINE(GPIOE, 22) +# define E23 PAL_LINE(GPIOE, 23) +# define E24 PAL_LINE(GPIOE, 24) +# define E25 PAL_LINE(GPIOE, 25) +# define E26 PAL_LINE(GPIOE, 26) +# define E27 PAL_LINE(GPIOE, 27) +# define E28 PAL_LINE(GPIOE, 28) +# define E29 PAL_LINE(GPIOE, 29) +# define E30 PAL_LINE(GPIOE, 30) +# define E31 PAL_LINE(GPIOE, 31) +# define E32 PAL_LINE(GPIOE, 32) # define F0 PAL_LINE(GPIOF, 0) # define F1 PAL_LINE(GPIOF, 1) # define F2 PAL_LINE(GPIOF, 2) diff --git a/tmk_core/common/chibios/sleep_led.c b/tmk_core/common/chibios/sleep_led.c index 5595eec0e5..1c65016a42 100644 --- a/tmk_core/common/chibios/sleep_led.c +++ b/tmk_core/common/chibios/sleep_led.c @@ -9,21 +9,13 @@ * Use LP timer on Kinetises, TIM14 on STM32F0. */ -#if defined(KL2x) || defined(K20x) - -/* Use Low Power Timer (LPTMR) */ -# define TIMER_INTERRUPT_VECTOR KINETIS_LPTMR0_IRQ_VECTOR -# define RESET_COUNTER LPTMR0->CSR |= LPTMRx_CSR_TCF - -#elif defined(STM32F0XX) - -/* Use TIM14 manually */ -# define TIMER_INTERRUPT_VECTOR STM32_TIM14_HANDLER -# define RESET_COUNTER STM32_TIM14->SR &= ~STM32_TIM_SR_UIF - +#ifndef SLEEP_LED_GPT_DRIVER +# if defined(STM32F0XX) +# define SLEEP_LED_GPT_DRIVER GPTD14 +# endif #endif -#if defined(KL2x) || defined(K20x) || defined(STM32F0XX) /* common parts for timers/interrupts */ +#if defined(KL2x) || defined(K20x) || defined(SLEEP_LED_GPT_DRIVER) /* common parts for timers/interrupts */ /* Breathing Sleep LED brighness(PWM On period) table * (64[steps] * 4[duration]) / 64[PWM periods/s] = 4 second breath cycle @@ -33,10 +25,7 @@ */ static const uint8_t breathing_table[64] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 4, 6, 10, 15, 23, 32, 44, 58, 74, 93, 113, 135, 157, 179, 199, 218, 233, 245, 252, 255, 252, 245, 233, 218, 199, 179, 157, 135, 113, 93, 74, 58, 44, 32, 23, 15, 10, 6, 4, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; -/* interrupt handler */ -OSAL_IRQ_HANDLER(TIMER_INTERRUPT_VECTOR) { - OSAL_IRQ_PROLOGUE(); - +void sleep_led_timer_callback(void) { /* Software PWM * timer:1111 1111 1111 1111 * \_____/\/ \_______/____ count(0-255) @@ -64,20 +53,19 @@ OSAL_IRQ_HANDLER(TIMER_INTERRUPT_VECTOR) { if (timer.pwm.count == breathing_table[timer.pwm.index]) { led_set(0); } - - /* Reset the counter */ - RESET_COUNTER; - - OSAL_IRQ_EPILOGUE(); } #endif /* common parts for known platforms */ #if defined(KL2x) || defined(K20x) /* platform selection: familiar Kinetis chips */ +/* Use Low Power Timer (LPTMR) */ +# define TIMER_INTERRUPT_VECTOR KINETIS_LPTMR0_IRQ_VECTOR +# define RESET_COUNTER LPTMR0->CSR |= LPTMRx_CSR_TCF + /* LPTMR clock options */ # define LPTMR_CLOCK_MCGIRCLK 0 /* 4MHz clock */ -# define LPTMR_CLOCK_LPO 1 /* 1kHz clock */ +# define LPTMR_CLOCK_LPO 1 /* 1kHz clock */ # define LPTMR_CLOCK_ERCLK32K 2 /* external 32kHz crystal */ # define LPTMR_CLOCK_OSCERCLK 3 /* output from OSC */ @@ -86,6 +74,18 @@ OSAL_IRQ_HANDLER(TIMER_INTERRUPT_VECTOR) { # define SIM_SCGC5_LPTMR SIM_SCGC5_LPTIMER # endif +/* interrupt handler */ +OSAL_IRQ_HANDLER(TIMER_INTERRUPT_VECTOR) { + OSAL_IRQ_PROLOGUE(); + + sleep_led_timer_callback(); + + /* Reset the counter */ + RESET_COUNTER; + + OSAL_IRQ_EPILOGUE(); +} + /* Initialise the timer */ void sleep_led_init(void) { /* Make sure the clock to the LPTMR is enabled */ @@ -121,7 +121,7 @@ void sleep_led_init(void) { MCG->C2 |= MCG_C2_IRCS; // fast (4MHz) internal ref clock # if defined(KL27) // divide the 8MHz IRC by 2, to have the same MCGIRCLK speed as others MCG->MC |= MCG_MC_LIRC_DIV2_DIV2; -# endif /* KL27 */ +# endif /* KL27 */ MCG->C1 |= MCG_C1_IRCLKEN; // enable internal ref clock // to work in stop mode, also MCG_C1_IREFSTEN // Divide 4MHz by 2^N (N=6) => 62500 irqs/sec => @@ -159,45 +159,23 @@ void sleep_led_toggle(void) { LPTMR0->CSR ^= LPTMRx_CSR_TEN; } -#elif defined(STM32F0XX) /* platform selection: STM32F0XX */ - -/* Initialise the timer */ -void sleep_led_init(void) { - /* enable clock */ - rccEnableTIM14(FALSE); /* low power enable = FALSE */ - rccResetTIM14(); - - /* prescale */ - /* Assuming 48MHz internal clock */ - /* getting cca 65484 irqs/sec */ - STM32_TIM14->PSC = 733; +#elif defined(SLEEP_LED_GPT_DRIVER) - /* auto-reload */ - /* 0 => interrupt every time */ - STM32_TIM14->ARR = 3; +static void gptTimerCallback(GPTDriver *gptp) { + (void)gptp; + sleep_led_timer_callback(); +} - /* enable counter update event interrupt */ - STM32_TIM14->DIER |= STM32_TIM_DIER_UIE; +static const GPTConfig gptcfg = {1000000, gptTimerCallback, 0, 0}; - /* register interrupt vector */ - nvicEnableVector(STM32_TIM14_NUMBER, 2); /* vector, priority */ -} +/* Initialise the timer */ +void sleep_led_init(void) { gptStart(&SLEEP_LED_GPT_DRIVER, &gptcfg); } -void sleep_led_enable(void) { - /* Enable the timer */ - STM32_TIM14->CR1 = STM32_TIM_CR1_CEN | STM32_TIM_CR1_URS; - /* URS => update event only on overflow; setting UG bit disabled */ -} +void sleep_led_enable(void) { gptStartContinuous(&SLEEP_LED_GPT_DRIVER, gptcfg.frequency / 0xFFFF); } -void sleep_led_disable(void) { - /* Disable the timer */ - STM32_TIM14->CR1 = 0; -} +void sleep_led_disable(void) { gptStopTimer(&SLEEP_LED_GPT_DRIVER); } -void sleep_led_toggle(void) { - /* Toggle the timer */ - STM32_TIM14->CR1 ^= STM32_TIM_CR1_CEN; -} +void sleep_led_toggle(void) { (SLEEP_LED_GPT_DRIVER.state == GPT_READY) ? sleep_led_enable() : sleep_led_disable(); } #else /* platform selection: not on familiar chips */ diff --git a/tmk_core/common/chibios/suspend.c b/tmk_core/common/chibios/suspend.c index 49e20641fb..38517e06f0 100644 --- a/tmk_core/common/chibios/suspend.c +++ b/tmk_core/common/chibios/suspend.c @@ -24,6 +24,13 @@ # include "rgblight.h" #endif +#ifdef LED_MATRIX_ENABLE +# include "led_matrix.h" +#endif +#ifdef RGB_MATRIX_ENABLE +# include "rgb_matrix.h" +#endif + /** \brief suspend idle * * FIXME: needs doc @@ -53,6 +60,13 @@ void suspend_power_down(void) { backlight_set(0); #endif +#ifdef LED_MATRIX_ENABLE + led_matrix_task(); +#endif +#ifdef RGB_MATRIX_ENABLE + rgb_matrix_task(); +#endif + // Turn off LED indicators uint8_t leds_off = 0; #if defined(BACKLIGHT_CAPS_LOCK) && defined(BACKLIGHT_ENABLE) @@ -69,6 +83,13 @@ void suspend_power_down(void) { #if defined(RGBLIGHT_SLEEP) && defined(RGBLIGHT_ENABLE) rgblight_suspend(); #endif + +#if defined(LED_MATRIX_ENABLE) + led_matrix_set_suspend_state(true); +#endif +#if defined(RGB_MATRIX_ENABLE) + rgb_matrix_set_suspend_state(true); +#endif #ifdef AUDIO_ENABLE stop_all_notes(); #endif /* AUDIO_ENABLE */ @@ -137,5 +158,12 @@ void suspend_wakeup_init(void) { #if defined(RGBLIGHT_SLEEP) && defined(RGBLIGHT_ENABLE) rgblight_wakeup(); #endif + +#if defined(LED_MATRIX_ENABLE) + led_matrix_set_suspend_state(false); +#endif +#if defined(RGB_MATRIX_ENABLE) + rgb_matrix_set_suspend_state(false); +#endif suspend_wakeup_init_kb(); } diff --git a/tmk_core/common/chibios/wait.c b/tmk_core/common/chibios/wait.c new file mode 100644 index 0000000000..c6270fd95e --- /dev/null +++ b/tmk_core/common/chibios/wait.c @@ -0,0 +1,89 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +#ifndef __OPTIMIZE__ +# pragma message "Compiler optimizations disabled; wait_cpuclock() won't work as designed" +#endif + +#define CLOCK_DELAY_NOP8 "nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t" + +__attribute__((always_inline)) static inline void wait_cpuclock(unsigned int n) { /* n: 1..135 */ + /* The argument n must be a constant expression. + * That way, compiler optimization will remove unnecessary code. */ + if (n < 1) { + return; + } + if (n > 8) { + unsigned int n8 = n / 8; + n = n - n8 * 8; + switch (n8) { + case 16: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 15: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 14: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 13: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 12: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 11: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 10: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 9: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 8: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 7: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 6: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 5: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 4: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 3: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 2: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 1: + asm volatile(CLOCK_DELAY_NOP8::: "memory"); + case 0: + break; + } + } + switch (n) { + case 8: + asm volatile("nop" ::: "memory"); + case 7: + asm volatile("nop" ::: "memory"); + case 6: + asm volatile("nop" ::: "memory"); + case 5: + asm volatile("nop" ::: "memory"); + case 4: + asm volatile("nop" ::: "memory"); + case 3: + asm volatile("nop" ::: "memory"); + case 2: + asm volatile("nop" ::: "memory"); + case 1: + asm volatile("nop" ::: "memory"); + case 0: + break; + } +}
\ No newline at end of file diff --git a/tmk_core/common/eeconfig.c b/tmk_core/common/eeconfig.c index 60b2dcb7e7..57c468ed7a 100644 --- a/tmk_core/common/eeconfig.c +++ b/tmk_core/common/eeconfig.c @@ -60,10 +60,12 @@ void eeconfig_init_quantum(void) { eeprom_update_dword(EECONFIG_HAPTIC, 0); eeprom_update_byte(EECONFIG_VELOCIKEY, 0); eeprom_update_dword(EECONFIG_RGB_MATRIX, 0); - eeprom_update_byte(EECONFIG_RGB_MATRIX_SPEED, 0); + eeprom_update_word(EECONFIG_RGB_MATRIX_EXTENDED, 0); + #ifdef ORYX_ENABLE eeconfig_init_oryx(); #endif + // TODO: Remove once ARM has a way to configure EECONFIG_HANDEDNESS // within the emulated eeprom via dfu-util or another tool #if defined INIT_EE_HANDS_LEFT @@ -160,17 +162,6 @@ void eeconfig_update_keymap(uint16_t val) { eeprom_update_byte(EECONFIG_KEYMAP_UPPER_BYTE, (val >> 8) & 0xFF); } -/** \brief eeconfig read backlight - * - * FIXME: needs doc - */ -uint8_t eeconfig_read_backlight(void) { return eeprom_read_byte(EECONFIG_BACKLIGHT); } -/** \brief eeconfig update backlight - * - * FIXME: needs doc - */ -void eeconfig_update_backlight(uint8_t val) { eeprom_update_byte(EECONFIG_BACKLIGHT, val); } - /** \brief eeconfig read audio * * FIXME: needs doc diff --git a/tmk_core/common/eeconfig.h b/tmk_core/common/eeconfig.h index 86b9e6f99b..a88071729d 100644 --- a/tmk_core/common/eeconfig.h +++ b/tmk_core/common/eeconfig.h @@ -21,7 +21,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. #include <stdbool.h> #ifndef EECONFIG_MAGIC_NUMBER -# define EECONFIG_MAGIC_NUMBER (uint16_t)0xFEEB // When changing, decrement this value to avoid future re-init issues +# define EECONFIG_MAGIC_NUMBER (uint16_t)0xFEEA // When changing, decrement this value to avoid future re-init issues #endif #define EECONFIG_MAGIC_NUMBER_OFF (uint16_t)0xFFFF @@ -43,12 +43,18 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. #define EECONFIG_VELOCIKEY (uint8_t *)23 #define EECONFIG_HAPTIC (uint32_t *)24 + +// Mutually exclusive +#define EECONFIG_LED_MATRIX (uint32_t *)28 #define EECONFIG_RGB_MATRIX (uint32_t *)28 -#define EECONFIG_RGB_MATRIX_SPEED (uint8_t *)32 +// Speed & Flags +#define EECONFIG_LED_MATRIX_EXTENDED (uint16_t *)32 +#define EECONFIG_RGB_MATRIX_EXTENDED (uint16_t *)32 + // TODO: Combine these into a single word and single block of EEPROM -#define EECONFIG_KEYMAP_UPPER_BYTE (uint8_t *)33 +#define EECONFIG_KEYMAP_UPPER_BYTE (uint8_t *)34 // Size of EEPROM being used, other code can refer to this for available EEPROM -#define EECONFIG_SIZE 34 +#define EECONFIG_SIZE 35 /* debug bit */ #define EECONFIG_DEBUG_ENABLE (1 << 0) #define EECONFIG_DEBUG_MATRIX (1 << 1) @@ -88,11 +94,6 @@ void eeconfig_update_default_layer(uint8_t val); uint16_t eeconfig_read_keymap(void); void eeconfig_update_keymap(uint16_t val); -#ifdef BACKLIGHT_ENABLE -uint8_t eeconfig_read_backlight(void); -void eeconfig_update_backlight(uint8_t val); -#endif - #ifdef AUDIO_ENABLE uint8_t eeconfig_read_audio(void); void eeconfig_update_audio(uint8_t val); diff --git a/tmk_core/common/keyboard.c b/tmk_core/common/keyboard.c index ce3255c069..3d6092e71c 100644 --- a/tmk_core/common/keyboard.c +++ b/tmk_core/common/keyboard.c @@ -34,11 +34,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. #ifdef BACKLIGHT_ENABLE # include "backlight.h" #endif -#ifdef BOOTMAGIC_ENABLE -# include "bootmagic.h" -#else -# include "magic.h" -#endif #ifdef MOUSEKEY_ENABLE # include "mousekey.h" #endif @@ -54,6 +49,9 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. #ifdef RGBLIGHT_ENABLE # include "rgblight.h" #endif +#ifdef LED_MATRIX_ENABLE +# include "led_matrix.h" +#endif #ifdef RGB_MATRIX_ENABLE # include "rgb_matrix.h" #endif @@ -96,6 +94,12 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. #ifdef DIP_SWITCH_ENABLE # include "dip_switch.h" #endif +#ifdef STM32_EEPROM_ENABLE +# include "eeprom_stm32.h" +#endif +#ifdef EEPROM_DRIVER +# include "eeprom_driver.h" +#endif static uint32_t last_input_modification_time = 0; uint32_t last_input_activity_time(void) { return last_input_modification_time; } @@ -233,6 +237,12 @@ void keyboard_setup(void) { disable_jtag(); #endif print_set_sendchar(sendchar); +#ifdef STM32_EEPROM_ENABLE + EEPROM_Init(); +#endif +#ifdef EEPROM_DRIVER + eeprom_driver_init(); +#endif matrix_setup(); keyboard_pre_init_kb(); } @@ -270,6 +280,15 @@ __attribute__((weak)) void housekeeping_task_kb(void) {} */ __attribute__((weak)) void housekeeping_task_user(void) {} +/** \brief housekeeping_task + * + * Invokes hooks for executing code after QMK is done after each loop iteration. + */ +void housekeeping_task(void) { + housekeeping_task_kb(); + housekeeping_task_user(); +} + /** \brief keyboard_init * * FIXME: needs doc @@ -296,11 +315,6 @@ void keyboard_init(void) { #ifdef ADB_MOUSE_ENABLE adb_mouse_init(); #endif -#ifdef BOOTMAGIC_ENABLE - bootmagic(); -#else - magic(); -#endif #ifdef BACKLIGHT_ENABLE backlight_init(); #endif @@ -337,6 +351,9 @@ void keyboard_init(void) { * This is differnet than keycode events as no layer processing, or filtering occurs. */ void switch_events(uint8_t row, uint8_t col, bool pressed) { +#if defined(LED_MATRIX_ENABLE) + process_led_matrix(row, col, pressed); +#endif #if defined(RGB_MATRIX_ENABLE) process_rgb_matrix(row, col, pressed); #endif @@ -366,9 +383,6 @@ void keyboard_task(void) { bool encoders_changed = false; #endif - housekeeping_task_kb(); - housekeeping_task_user(); - uint8_t matrix_changed = matrix_scan(); if (matrix_changed) last_matrix_activity_trigger(); @@ -422,6 +436,9 @@ MATRIX_LOOP_END: rgblight_task(); #endif +#ifdef LED_MATRIX_ENABLE + led_matrix_task(); +#endif #ifdef RGB_MATRIX_ENABLE rgb_matrix_task(); #endif diff --git a/tmk_core/common/keyboard.h b/tmk_core/common/keyboard.h index eaf74bac58..08f4e84f94 100644 --- a/tmk_core/common/keyboard.h +++ b/tmk_core/common/keyboard.h @@ -70,8 +70,9 @@ void keyboard_pre_init_user(void); void keyboard_post_init_kb(void); void keyboard_post_init_user(void); -void housekeeping_task_kb(void); -void housekeeping_task_user(void); +void housekeeping_task(void); // To be executed by the main loop in each backend TMK protocol +void housekeeping_task_kb(void); // To be overridden by keyboard-level code +void housekeeping_task_user(void); // To be overridden by user/keymap-level code uint32_t last_input_activity_time(void); // Timestamp of the last matrix or encoder activity uint32_t last_input_activity_elapsed(void); // Number of milliseconds since the last matrix or encoder activity diff --git a/tmk_core/common/magic.c b/tmk_core/common/magic.c deleted file mode 100644 index e14994164e..0000000000 --- a/tmk_core/common/magic.c +++ /dev/null @@ -1,39 +0,0 @@ -#include <stdint.h> -#include <stdbool.h> -#if defined(__AVR__) -# include <util/delay.h> -#endif -#include "matrix.h" -#include "bootloader.h" -#include "debug.h" -#include "keymap.h" -#include "host.h" -#include "action_layer.h" -#include "eeconfig.h" -#include "magic.h" - -keymap_config_t keymap_config; - -/** \brief Magic - * - * FIXME: Needs doc - */ -void magic(void) { - /* check signature */ - if (!eeconfig_is_enabled()) { - eeconfig_init(); - } - - /* debug enable */ - debug_config.raw = eeconfig_read_debug(); - - /* keymap config */ - keymap_config.raw = eeconfig_read_keymap(); - - uint8_t default_layer = 0; - default_layer = eeconfig_read_default_layer(); - default_layer_set((layer_state_t)default_layer); - - /* Also initialize layer state to trigger callback functions for layer_state */ - layer_state_set_kb((layer_state_t)layer_state); -} diff --git a/tmk_core/common/magic.h b/tmk_core/common/magic.h deleted file mode 100644 index a6552c04dc..0000000000 --- a/tmk_core/common/magic.h +++ /dev/null @@ -1,3 +0,0 @@ -#pragma once - -void magic(void); diff --git a/tmk_core/common/test/_wait.h b/tmk_core/common/test/_wait.h new file mode 100644 index 0000000000..4e22f593b7 --- /dev/null +++ b/tmk_core/common/test/_wait.h @@ -0,0 +1,22 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#pragma once + +#include <inttypes.h> + +void wait_ms(uint32_t ms); +#define wait_us(us) wait_ms(us / 1000) +#define waitInputPinDelay() diff --git a/tmk_core/common/usb_util.c b/tmk_core/common/usb_util.c new file mode 100644 index 0000000000..e4c50fcb10 --- /dev/null +++ b/tmk_core/common/usb_util.c @@ -0,0 +1,29 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#include "usb_util.h" +#include "wait.h" + +__attribute__((weak)) void usb_disable(void) {} +__attribute__((weak)) bool usb_connected_state(void) { return true; } +__attribute__((weak)) bool usb_vbus_state(void) { +#ifdef USB_VBUS_PIN + setPinInput(USB_VBUS_PIN); + wait_us(5); + return readPin(USB_VBUS_PIN); +#else + return true; +#endif +} diff --git a/tmk_core/common/usb_util.h b/tmk_core/common/usb_util.h new file mode 100644 index 0000000000..4ebedb1e71 --- /dev/null +++ b/tmk_core/common/usb_util.h @@ -0,0 +1,22 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ +#pragma once + +#include <stdbool.h> + +void usb_disable(void); +bool usb_connected_state(void); +bool usb_vbus_state(void); diff --git a/tmk_core/common/wait.h b/tmk_core/common/wait.h index 28224fe3aa..cf7180fb07 100644 --- a/tmk_core/common/wait.h +++ b/tmk_core/common/wait.h @@ -1,3 +1,18 @@ +/* Copyright 2021 QMK + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ #pragma once #include <inttypes.h> @@ -6,114 +21,8 @@ extern "C" { #endif -#if defined(__ARMEL__) || defined(__ARMEB__) -# ifndef __OPTIMIZE__ -# pragma message "Compiler optimizations disabled; wait_cpuclock() won't work as designed" -# endif - -# define wait_cpuclock(x) wait_cpuclock_allnop(x) - -# define CLOCK_DELAY_NOP8 "nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t nop\n\t" - -__attribute__((always_inline)) static inline void wait_cpuclock_allnop(unsigned int n) { /* n: 1..135 */ - /* The argument n must be a constant expression. - * That way, compiler optimization will remove unnecessary code. */ - if (n < 1) { - return; - } - if (n > 8) { - unsigned int n8 = n / 8; - n = n - n8 * 8; - switch (n8) { - case 16: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 15: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 14: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 13: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 12: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 11: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 10: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 9: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 8: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 7: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 6: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 5: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 4: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 3: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 2: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 1: - asm volatile(CLOCK_DELAY_NOP8::: "memory"); - case 0: - break; - } - } - switch (n) { - case 8: - asm volatile("nop" ::: "memory"); - case 7: - asm volatile("nop" ::: "memory"); - case 6: - asm volatile("nop" ::: "memory"); - case 5: - asm volatile("nop" ::: "memory"); - case 4: - asm volatile("nop" ::: "memory"); - case 3: - asm volatile("nop" ::: "memory"); - case 2: - asm volatile("nop" ::: "memory"); - case 1: - asm volatile("nop" ::: "memory"); - case 0: - break; - } -} -#endif - -#if defined(__AVR__) -# include <util/delay.h> -# define wait_ms(ms) _delay_ms(ms) -# define wait_us(us) _delay_us(us) -# define wait_cpuclock(x) __builtin_avr_delay_cycles(x) -#elif defined PROTOCOL_CHIBIOS -# include <ch.h> -# define wait_ms(ms) \ - do { \ - if (ms != 0) { \ - chThdSleepMilliseconds(ms); \ - } else { \ - chThdSleepMicroseconds(1); \ - } \ - } while (0) -# define wait_us(us) \ - do { \ - if (us != 0) { \ - chThdSleepMicroseconds(us); \ - } else { \ - chThdSleepMicroseconds(1); \ - } \ - } while (0) -#elif defined PROTOCOL_ARM_ATSAM -# include "clks.h" -# define wait_ms(ms) CLK_delay_ms(ms) -# define wait_us(us) CLK_delay_us(us) -#else // Unit tests -void wait_ms(uint32_t ms); -# define wait_us(us) wait_ms(us / 1000) +#if __has_include_next("_wait.h") +# include_next "_wait.h" /* Include the platforms _wait.h */ #endif #ifdef __cplusplus |