Skip to content

Commit 3538955

Browse files
yiancarfauxpark
authored andcommitted
Usbasploader bootloader option addition (qmk#6304)
* Added USBasp bootloader option for USBasploader * author comment * ifdef fix :) * Add usbasp target * Update docs/flashing.md Co-Authored-By: fauxpark <[email protected]> * Update docs/flashing.md Co-Authored-By: fauxpark <[email protected]> * Update docs/flashing.md Co-Authored-By: fauxpark <[email protected]>
1 parent 7d557a0 commit 3538955

File tree

6 files changed

+78
-37
lines changed

6 files changed

+78
-37
lines changed

bootloader.mk

+4
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,10 @@ ifeq ($(strip $(BOOTLOADER)), bootloadHID)
7676
OPT_DEFS += -DBOOTLOADER_BOOTLOADHID
7777
BOOTLOADER_SIZE = 4096
7878
endif
79+
ifeq ($(strip $(BOOTLOADER)), USBasp)
80+
OPT_DEFS += -DBOOTLOADER_USBASP
81+
BOOTLOADER_SIZE = 4096
82+
endif
7983

8084
ifdef BOOTLOADER_SIZE
8185
OPT_DEFS += -DBOOTLOADER_SIZE=$(strip $(BOOTLOADER_SIZE))

docs/config_options.md

+1
Original file line numberDiff line numberDiff line change
@@ -289,6 +289,7 @@ This is a [make](https://www.gnu.org/software/make/manual/make.html) file that i
289289
* `halfkay`
290290
* `caterina`
291291
* `bootloadHID`
292+
* `USBasp`
292293

293294
## Feature Options
294295

docs/flashing.md

+25
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,31 @@ Flashing sequence:
119119
3. Flash a .hex file
120120
4. Reset the device into application mode (may be done automatically)
121121

122+
## USBasploader
123+
124+
USBasploader is a bootloader developed by matrixstorm. It is used in some non-USB AVR chips such as the ATmega328P, which run V-USB.
125+
126+
To ensure compatibility with the USBasploader bootloader, make sure this block is present in your `rules.mk`:
127+
128+
# Bootloader
129+
# This definition is optional, and if your keyboard supports multiple bootloaders of
130+
# different sizes, comment this out, and the correct address will be loaded
131+
# automatically (+60). See bootloader.mk for all options.
132+
BOOTLOADER = USBasp
133+
134+
Compatible flashers:
135+
136+
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox/releases) (recommended GUI)
137+
* [avrdude](http://www.nongnu.org/avrdude/) with the `usbasp` programmer
138+
* [AVRDUDESS](https://github.com/zkemble/AVRDUDESS)
139+
140+
Flashing sequence:
141+
142+
1. Press the `RESET` keycode, or keep the boot pin shorted to GND while quickly shorting RST to GND
143+
2. Wait for the OS to detect the device
144+
3. Flash a .hex file
145+
4. Reset the device into application mode (may be done automatically)
146+
122147
## STM32
123148

124149
All STM32 chips come preloaded with a factory bootloader that cannot be modified nor deleted. Some STM32 chips have bootloaders that do not come with USB programming (e.g. STM32F103) but the process is still the same.

keyboards/gingham/rules.mk

+1-3
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
4949
# atmega32a bootloadHID
5050
#
5151
# This uses usbaspbootloader
52-
# BOOTLOADER = atmel-dfu
52+
BOOTLOADER = USBasp
5353

5454
# If you don't know the bootloader type, then you can specify the
5555
# Boot Section Size in *bytes* by uncommenting out the OPT_DEFS line
@@ -58,8 +58,6 @@ OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
5858
# Atmel DFU loader 4096
5959
# LUFA bootloader 4096
6060
# USBaspLoader 2048
61-
# OPT_DEFS += -DBOOTLOADER_SIZE=4096
62-
OPT_DEFS += -DBOOTLOADER_SIZE=2048
6361

6462
# Flash program via avrdude, but default command is not suitable.
6563
# You can use plaid:default:program

tmk_core/avr.mk

+4
Original file line numberDiff line numberDiff line change
@@ -245,6 +245,10 @@ avrdude-split-left: $(BUILD_DIR)/$(TARGET).hex check-size cpfirmware
245245
avrdude-split-right: $(BUILD_DIR)/$(TARGET).hex check-size cpfirmware
246246
$(call EXEC_AVRDUDE,eeprom-righthand.eep)
247247

248+
usbasp: $(BUILD_DIR)/$(TARGET).hex check-size cpfirmware
249+
avrdude -p $(MCU) -c usbasp -U flash:w:$(BUILD_DIR)/$(TARGET).hex
250+
251+
248252
# Convert hex to bin.
249253
bin: $(BUILD_DIR)/$(TARGET).hex
250254
$(OBJCOPY) -Iihex -Obinary $(BUILD_DIR)/$(TARGET).hex $(BUILD_DIR)/$(TARGET).bin

tmk_core/common/avr/bootloader.c

+43-34
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,13 @@
6565
#define BOOT_SIZE_1024 0b010
6666
#define BOOT_SIZE_2048 0b000
6767

68+
//compatibility between ATMega8 and ATMega88
69+
#if !defined (MCUCSR)
70+
#if defined (MCUSR)
71+
#define MCUCSR MCUSR
72+
#endif
73+
#endif
74+
6875
/** \brief Entering the Bootloader via Software
6976
*
7077
* http://www.fourwalledcubicle.com/files/LUFA/Doc/120730/html/_page__software_bootloader_start.html
@@ -149,6 +156,39 @@ void bootloader_jump(void) {
149156

150157
while(1) {} // wait for watchdog timer to trigger
151158

159+
#elif defined(BOOTLOADER_USBASP)
160+
// Taken with permission of Stephan Baerwolf from https://github.com/tinyusbboard/API/blob/master/apipage.c
161+
wdt_enable(WDTO_15MS);
162+
wdt_reset();
163+
asm volatile (
164+
"cli \n\t"
165+
"ldi r29 , %[ramendhi] \n\t"
166+
"ldi r28 , %[ramendlo] \n\t"
167+
#if (FLASHEND>131071)
168+
"ldi r18 , %[bootaddrhi] \n\t"
169+
"st Y+, r18 \n\t"
170+
#endif
171+
"ldi r18 , %[bootaddrme] \n\t"
172+
"st Y+, r18 \n\t"
173+
"ldi r18 , %[bootaddrlo] \n\t"
174+
"st Y+, r18 \n\t"
175+
"out %[mcucsrio], __zero_reg__ \n\t"
176+
"bootloader_startup_loop%=: \n\t"
177+
"rjmp bootloader_startup_loop%= \n\t"
178+
:
179+
: [mcucsrio] "I" (_SFR_IO_ADDR(MCUCSR)),
180+
#if (FLASHEND>131071)
181+
[ramendhi] "M" (((RAMEND - 2) >> 8) & 0xff),
182+
[ramendlo] "M" (((RAMEND - 2) >> 0) & 0xff),
183+
[bootaddrhi] "M" ((((FLASH_SIZE - BOOTLOADER_SIZE) >> 1) >>16) & 0xff),
184+
#else
185+
[ramendhi] "M" (((RAMEND - 1) >> 8) & 0xff),
186+
[ramendlo] "M" (((RAMEND - 1) >> 0) & 0xff),
187+
#endif
188+
[bootaddrme] "M" ((((FLASH_SIZE - BOOTLOADER_SIZE) >> 1) >> 8) & 0xff),
189+
[bootaddrlo] "M" ((((FLASH_SIZE - BOOTLOADER_SIZE) >> 1) >> 0) & 0xff)
190+
);
191+
152192
#else // Assume remaining boards are DFU, even if the flag isn't set
153193

154194
#if !(defined(__AVR_ATmega32A__) || defined(__AVR_ATmega328P__)) // no USB - maybe BOOTLOADER_BOOTLOADHID instead though?
@@ -172,24 +212,19 @@ void bootloader_jump(void) {
172212

173213
}
174214

175-
#ifdef __AVR_ATmega32A__
176-
// MCUSR is actually called MCUCSR in ATmega32A
177-
#define MCUSR MCUCSR
178-
#endif
179-
180215
/* this runs before main() */
181216
void bootloader_jump_after_watchdog_reset(void) __attribute__ ((used, naked, section (".init3")));
182217
void bootloader_jump_after_watchdog_reset(void)
183218
{
184219
#ifndef BOOTLOADER_HALFKAY
185-
if ((MCUSR & (1<<WDRF)) && reset_key == BOOTLOADER_RESET_KEY) {
220+
if ((MCUCSR & (1<<WDRF)) && reset_key == BOOTLOADER_RESET_KEY) {
186221
reset_key = 0;
187222

188223
// My custom USBasploader requires this to come up.
189-
MCUSR = 0;
224+
MCUCSR = 0;
190225

191226
// Seems like Teensy halfkay loader requires clearing WDRF and disabling watchdog.
192-
MCUSR &= ~(1<<WDRF);
227+
MCUCSR &= ~(1<<WDRF);
193228
wdt_disable();
194229

195230

@@ -202,29 +237,3 @@ void bootloader_jump_after_watchdog_reset(void)
202237
}
203238
#endif
204239
}
205-
206-
207-
#if 0
208-
/*
209-
* USBaspLoader - I'm not sure if this is used at all in any projects
210-
* would love to support it if it is -Jack
211-
*/
212-
#if defined(__AVR_ATmega168__) || defined(__AVR_ATmega168P__) || defined(__AVR_ATmega328P__)
213-
// This makes custom USBasploader come up.
214-
MCUSR = 0;
215-
216-
// initialize ports
217-
PORTB = 0; PORTC= 0; PORTD = 0;
218-
DDRB = 0; DDRC= 0; DDRD = 0;
219-
220-
// disable interrupts
221-
EIMSK = 0; EECR = 0; SPCR = 0;
222-
ACSR = 0; SPMCSR = 0; WDTCSR = 0; PCICR = 0;
223-
TIMSK0 = 0; TIMSK1 = 0; TIMSK2 = 0;
224-
ADCSRA = 0; TWCR = 0; UCSR0B = 0;
225-
#endif
226-
227-
// This is compled into 'icall', address should be in word unit, not byte.
228-
((void (*)(void))(BOOTLOADER_START/2))();
229-
}
230-
#endif

0 commit comments

Comments
 (0)