From a160cf37e30d1e0739d1e41210a0a1e6eb9aa1e7 Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 28 Jul 2019 12:31:04 +0200 Subject: [PATCH 001/351] Fix trivial typo in pin to interrupt macro --- megaavr/cores/coreX-corefiles/Arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index a067138..1892a7a 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -125,7 +125,7 @@ bool isDoubleBondedActive(uint8_t pin); #define portToPortStruct(port) ( (port < NUM_TOTAL_PORTS) ? ((PORT_t *)&PORTA + port) : NULL) #define digitalPinToPortStruct(pin) ( (pin < NUM_TOTAL_PINS) ? ((PORT_t *)&PORTA + digitalPinToPort(pin)) : NULL) #define getPINnCTRLregister(port, bit_pos) ( ((port != NULL) && (bit_pos < NOT_A_PIN)) ? ((volatile uint8_t *)&(port->PIN0CTRL) + bit_pos) : NULL ) -#define digitalPinToInterrupt(p) (P) +#define digitalPinToInterrupt(P) (P) #define portOutputRegister(P) ( (volatile uint8_t *)( &portToPortStruct(P)->OUT ) ) #define portInputRegister(P) ( (volatile uint8_t *)( &portToPortStruct(P)->IN ) ) From 0812f76c60c6716ffd2f951ecd385d35d7d3a8a4 Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 28 Jul 2019 12:40:38 +0200 Subject: [PATCH 002/351] Spelling in text --- megaavr/libraries/SPI/src/SPI.cpp | 4 ++-- megaavr/variants/48pin-standard/pins_arduino.h | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index ba6c28f..b8a53e2 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -44,7 +44,7 @@ void SPIClass::begin() PORTMUX.TWISPIROUTEA |= _uc_mux; - // We don't need HW SS since salve/master mode is selected via registers, so make it simply INPUT + // We don't need HW SS since slave/master mode is selected via registers, so make it simply INPUT pinMode(_uc_pinSS, INPUT); pinMode(_uc_pinMosi, OUTPUT); pinMode(_uc_pinSCK, OUTPUT); @@ -265,4 +265,4 @@ void SPIClass::transfer(void *buf, size_t count) #if SPI_INTERFACES_COUNT > 0 SPIClass SPI (PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_MOSI, PIN_SPI_SS, SPI_MUX); -#endif \ No newline at end of file +#endif diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 8067c79..e2fb179 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -7,10 +7,10 @@ | ATmega3209 | | | | Note that this pinout is not directly compatible | -| with the UNO Wifi Rev2 hardware without preforming | +| with the UNO Wifi Rev2 hardware without performing | | pinswaps. This pinout is supposed to be as close | | to the metal as possible. The only peripherals | -| that is swapped to other pins by default are the | +| that are swapped to other pins by default are the | | PWM outputs. | | | |****************************************************/ From 06497fbde67f94d71031bec8e00b7d140aff2507 Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 28 Jul 2019 12:42:43 +0200 Subject: [PATCH 003/351] Wring pins numbers for Serial1 in 48 pin variant --- megaavr/variants/48pin-standard/pins_arduino.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index e2fb179..9150e7d 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -98,10 +98,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_ALT1_gc) -#define PIN_WIRE_HWSERIAL1_TX (12) -#define PIN_WIRE_HWSERIAL1_RX (13) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (14) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (15) +#define PIN_WIRE_HWSERIAL1_TX (14) +#define PIN_WIRE_HWSERIAL1_RX (15) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (18) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (19) // USART 2 // No pinswap by default From 1945d72b97d4dfeb486287283768ae0377f2fa6b Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 28 Jul 2019 13:14:38 +0200 Subject: [PATCH 004/351] Add support for jtag2updi programmer --- megaavr/avrdude.conf | 10 ++++++++++ megaavr/platform.txt | 2 +- megaavr/programmers.txt | 6 ++++++ 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 1898252..5de202b 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -1393,6 +1393,16 @@ programmer miso = ~8; ; +# JTAG2UPDI +# https://github.com/ElTangas/jtag2updi +programmer + id = "jtag2updi"; + desc = "JTAGv2 to UPDI bridge"; + type = "jtagmkii_pdi"; + connection_type = serial; + baudrate = 115200; +; + # # PART DEFINITIONS # diff --git a/megaavr/platform.txt b/megaavr/platform.txt index f26ec07..7d43fc8 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -91,7 +91,7 @@ recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} { # AVR Uploader/Programmers tools # ------------------------------ -tools.avrdude.path={runtime.tools.avrdude-6.3.0-arduino14.path} +tools.avrdude.path={runtime.tools.avrdude-6.3.0-arduino16.path} tools.avrdude.cmd.path={path}/bin/avrdude tools.avrdude.config.path={runtime.platform.path}/avrdude.conf diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index f0c864d..19ac466 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -18,3 +18,9 @@ edbg.protocol=xplainedpro_updi edbg.program.protocol=xplainedpro_updi edbg.program.tool=avrdude edbg.program.extra_params=-Pusb + +jtag2updi.name=JTAG2UPDI +jtag2updi.communication=serial +jtag2updi.protocol=jtag2updi +jtag2updi.program.tool=avrdude +jtag2updi.program.extra_params=-P{serial.port} From 075dcb9ecf5022991a9be82c74e87cb43beddc51 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 29 Jul 2019 11:21:57 +0200 Subject: [PATCH 005/351] Change mode of timer A from SINGLE to SPLIT, so we can support 6 instead of 3 PWM outputs. Timer A does not seems to be used for other purposes than PWM, so we believe this change is safe. Also note that this change also properly implements all promised PWM outputs for all variants, with the exception of the Uno variant, which worked fine. For the others, PWMs on PC3 through PC5 did not work. --- megaavr/cores/coreX-corefiles/wiring_analog.c | 19 ++++++++++------ .../cores/coreX-corefiles/wiring_digital.c | 6 +++-- megaavr/variants/28pin-standard/variant.c | 22 ++++++++++++------- megaavr/variants/32pin-standard/variant.c | 22 ++++++++++++------- megaavr/variants/48pin-standard/variant.c | 22 ++++++++++++------- megaavr/variants/uno-wifi/variant.c | 22 ++++++++++++------- 6 files changed, 72 insertions(+), 41 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index c5a715b..4720523 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -143,22 +143,27 @@ void analogWrite(uint8_t pin, int val) /* Get timer */ uint8_t digital_pin_timer = digitalPinToTimer(pin); - uint16_t* timer_cmp_out; + uint8_t* timer_cmp_out; TCB_t *timer_B; /* Find out Port and Pin to correctly handle port mux, and timer. */ switch (digital_pin_timer) { case TIMERA0: - /* Calculate correct compare buffer register */ - timer_cmp_out = ((uint16_t*) (&TCA0.SINGLE.CMP0BUF)) + bit_pos; + /* Split mode, 2x3 8 bit registers. (chapter 19.7) */ + if (bit_pos >= 3) { + timer_cmp_out = ((uint8_t*) (&TCA0.SPLIT.HCMP0)) + 2*(bit_pos-3); + ++bit_pos; /* Upper 3 bits are shifted by 1 */ + } else { + /* Calculate correct compare buffer register */ + timer_cmp_out = ((uint8_t*) (&TCA0.SPLIT.LCMP0)) + 2*bit_pos; + } /* Configure duty cycle for correct compare channel */ - (*timer_cmp_out) = (val); + (*timer_cmp_out) = val; /* Enable output on pin */ - TCA0.SINGLE.CTRLB |= (1 << (TCA_SINGLE_CMP0EN_bp + bit_pos)); - + TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); break; case TIMERB0: @@ -191,4 +196,4 @@ void analogWrite(uint8_t pin, int val) break; } } -} \ No newline at end of file +} diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index 0d51d57..0c25d73 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -79,7 +79,8 @@ void pinMode(uint8_t pin, PinMode mode) // user than calling. (It will take more bytes on the 168.) // // But shouldn't this be moved into pinMode? Seems silly to check and do on -// each digitalread or write. +// each digitalread or write. One issue that then needs to be fixed is that +// current implementation on analogWrite() depends on this behaviour. // // Mark Sproul: // - Removed inline. Save 170 bytes on atmega1280 @@ -107,7 +108,8 @@ static void turnOffPWM(uint8_t pin) bit_pos = digitalPinToBitPosition(pin); /* Disable corresponding channel */ - TCA0.SINGLE.CTRLB &= ~(1 << (TCA_SINGLE_CMP0EN_bp + bit_pos)); + if (bit_pos >= 3) ++bit_pos; /* Upper 3 bits are shifted by 1 */ + TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); break; diff --git a/megaavr/variants/28pin-standard/variant.c b/megaavr/variants/28pin-standard/variant.c index e54d4d4..ec4c3f2 100644 --- a/megaavr/variants/28pin-standard/variant.c +++ b/megaavr/variants/28pin-standard/variant.c @@ -12,19 +12,23 @@ void setup_timers() { // PORTMUX setting for TCA -> outputs [2:3] point to PORTC pins [2:3] PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - // Setup timers for single slope PWM, but do not enable, will do in analogWrite() - TCA0.SINGLE.CTRLB = TCA_SINGLE_WGMODE_SINGLESLOPE_gc; + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - // Period setting, 16 bit register but val resolution is 8 bit - TCA0.SINGLE.PER = PWM_TIMER_PERIOD; + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; // Default duty 50%, will re-assign in analogWrite() - TCA0.SINGLE.CMP0BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP1BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP2BUF = PWM_TIMER_COMPARE; + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV64_gc) | (TCA_SINGLE_ENABLE_bm); + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); // TYPE B TIMERS @@ -110,6 +114,8 @@ FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { (Using SPI Enable bit as indicator of SPI activity) */ //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; + // May check Serial1 that may conflict with A-timers (swapped or not) + return false; } diff --git a/megaavr/variants/32pin-standard/variant.c b/megaavr/variants/32pin-standard/variant.c index e54d4d4..ec4c3f2 100644 --- a/megaavr/variants/32pin-standard/variant.c +++ b/megaavr/variants/32pin-standard/variant.c @@ -12,19 +12,23 @@ void setup_timers() { // PORTMUX setting for TCA -> outputs [2:3] point to PORTC pins [2:3] PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - // Setup timers for single slope PWM, but do not enable, will do in analogWrite() - TCA0.SINGLE.CTRLB = TCA_SINGLE_WGMODE_SINGLESLOPE_gc; + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - // Period setting, 16 bit register but val resolution is 8 bit - TCA0.SINGLE.PER = PWM_TIMER_PERIOD; + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; // Default duty 50%, will re-assign in analogWrite() - TCA0.SINGLE.CMP0BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP1BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP2BUF = PWM_TIMER_COMPARE; + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV64_gc) | (TCA_SINGLE_ENABLE_bm); + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); // TYPE B TIMERS @@ -110,6 +114,8 @@ FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { (Using SPI Enable bit as indicator of SPI activity) */ //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; + // May check Serial1 that may conflict with A-timers (swapped or not) + return false; } diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index 0951a66..5f7e9a8 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -12,19 +12,23 @@ void setup_timers() { // PORTMUX setting for TCA -> outputs [2:5] point to PORTC pins [2:5] PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - // Setup timers for single slope PWM, but do not enable, will do in analogWrite() - TCA0.SINGLE.CTRLB = TCA_SINGLE_WGMODE_SINGLESLOPE_gc; + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - // Period setting, 16 bit register but val resolution is 8 bit - TCA0.SINGLE.PER = PWM_TIMER_PERIOD; + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; // Default duty 50%, will re-assign in analogWrite() - TCA0.SINGLE.CMP0BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP1BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP2BUF = PWM_TIMER_COMPARE; + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV64_gc) | (TCA_SINGLE_ENABLE_bm); + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); // TYPE B TIMERS @@ -110,6 +114,8 @@ FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { (Using SPI Enable bit as indicator of SPI activity) */ //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; + // May check Serial1 that may conflict with A-timers (swapped or not) + return false; } diff --git a/megaavr/variants/uno-wifi/variant.c b/megaavr/variants/uno-wifi/variant.c index 4190726..d185de7 100644 --- a/megaavr/variants/uno-wifi/variant.c +++ b/megaavr/variants/uno-wifi/variant.c @@ -12,19 +12,23 @@ void setup_timers() { // PORTMUX setting for TCA -> all outputs [0:2] point to PORTB pins [0:2] PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTB_gc; - // Setup timers for single slope PWM, but do not enable, will do in analogWrite() - TCA0.SINGLE.CTRLB = TCA_SINGLE_WGMODE_SINGLESLOPE_gc; + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - // Period setting, 16 bit register but val resolution is 8 bit - TCA0.SINGLE.PER = PWM_TIMER_PERIOD; + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; // Default duty 50%, will re-assign in analogWrite() - TCA0.SINGLE.CMP0BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP1BUF = PWM_TIMER_COMPARE; - TCA0.SINGLE.CMP2BUF = PWM_TIMER_COMPARE; + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV64_gc) | (TCA_SINGLE_ENABLE_bm); + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); // TYPE B TIMERS @@ -110,6 +114,8 @@ FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { (Using SPI Enable bit as indicator of SPI activity) */ //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; + // May check Serial3 that may conflict with A-timers + return false; } From 100b83fcdf176aea645e87439f6b39ff0a350c49 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 29 Jul 2019 11:30:09 +0200 Subject: [PATCH 006/351] For all the N-pin variants we can support PWM on the two pins assigned to Serial1. If Serial1 is not used, there are two additional PWM outputs. This means the 48 pin variant has 8 potential PWM output pins. --- megaavr/variants/28pin-standard/pins_arduino.h | 18 +++++++++--------- megaavr/variants/32pin-standard/pins_arduino.h | 18 +++++++++--------- megaavr/variants/48pin-standard/pins_arduino.h | 18 +++++++++--------- 3 files changed, 27 insertions(+), 27 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 743772e..f42071e 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -33,7 +33,7 @@ #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) -#define digitalPinHasPWM(p) ((p) == 10 || (p) == 11) +#define digitalPinHasPWM(p) ((p) >= 8 && (p) <= 11) // SPI 0 // No pinswap by default @@ -142,8 +142,8 @@ const uint8_t PROGMEM digital_pin_to_port[] = { PA, // 5 PA5/MISO PA, // 6 PA6/SCK PA, // 7 PA7/SS/CLKOUT - PC, // 8 PC0/USART1_Tx - PC, // 9 PC1/USART1_Rx + PC, // 8 PC0/USART1_Tx/TCA0 PWM + PC, // 9 PC1/USART1_Rx/TCA0 PWM PC, // 10 PC2/TCA0 PWM PC, // 11 PC3/TCA0 PWM PD, // 12 PD0/AIN0 @@ -169,8 +169,8 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK PIN7_bp, // 7 PA7/SS/CLKOUT - PIN0_bp, // 8 PC0/USART1_Tx - PIN1_bp, // 9 PC1/USART1_Rx + PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM PIN2_bp, // 10 PC2/TCA0 PWM PIN3_bp, // 11 PC3/TCA0 PWM PIN0_bp, // 12 PD0/AIN0 @@ -196,8 +196,8 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK PIN7_bm, // 7 PA7/SS/CLKOUT - PIN0_bm, // 8 PC0/USART1_Tx - PIN1_bm, // 9 PC1/USART1_Rx + PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM PIN2_bm, // 10 PC2/TCA0 PWM PIN3_bm, // 11 PC3/TCA0 PWM PIN0_bm, // 12 PD0/AIN0 @@ -222,8 +222,8 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK NOT_ON_TIMER, // 7 PA7/SS/CLKOUT - NOT_ON_TIMER, // 8 PC0/USART1_Tx - NOT_ON_TIMER, // 9 PC1/USART1_Rx + TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM + TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM TIMERA0, // 10 PC2/TCA0 PWM TIMERA0, // 11 PC3/TCA0 PWM NOT_ON_TIMER, // 12 PD0/AIN0 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 45b95df..2601f8f 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -33,7 +33,7 @@ #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) -#define digitalPinHasPWM(p) ((p) == 10 || (p) == 11 || (p) == 24 || (p) == 25) +#define digitalPinHasPWM(p) (((p) >= 8 && (p) <= 11) || (p) == 24 || (p) == 25) // SPI 0 // No pinswap enabled by default @@ -150,8 +150,8 @@ const uint8_t PROGMEM digital_pin_to_port[] = { PA, // 5 PA5/MISO PA, // 6 PA6/SCK PA, // 7 PA7/SS/CLKOUT - PC, // 8 PC0/USART1_Tx - PC, // 9 PC1/USART1_Rx + PC, // 8 PC0/USART1_Tx/TCA0 PWM + PC, // 9 PC1/USART1_Rx/TCA0 PWM PC, // 10 PC2/TCA0 PWM PC, // 11 PC3/TCA0 PWM PD, // 12 PD0/AIN0 @@ -181,8 +181,8 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK PIN7_bp, // 7 PA7/SS/CLKOUT - PIN0_bp, // 8 PC0/USART1_Tx - PIN1_bp, // 9 PC1/USART1_Rx + PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM PIN2_bp, // 10 PC2/TCA0 PWM PIN3_bp, // 11 PC3/TCA0 PWM PIN0_bp, // 12 PD0/AIN0 @@ -212,8 +212,8 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK PIN7_bm, // 7 PA7/SS/CLKOUT - PIN0_bm, // 8 PC0/USART1_Tx - PIN1_bm, // 9 PC1/USART1_Rx + PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM PIN2_bm, // 10 PC2/TCA0 PWM PIN3_bm, // 11 PC3/TCA0 PWM PIN0_bm, // 12 PD0/AIN0 @@ -242,8 +242,8 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK NOT_ON_TIMER, // 7 PA7/SS/CLKOUT - NOT_ON_TIMER, // 8 PC0/USART1_Tx - NOT_ON_TIMER, // 9 PC1/USART1_Rx + TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM + TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM TIMERA0, // 10 PC2/TCA0 PWM TIMERA0, // 11 PC3/TCA0 PWM NOT_ON_TIMER, // 12 PD0/AIN0 diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 8067c79..262d8d0 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -38,7 +38,7 @@ #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) -#define digitalPinHasPWM(p) ((p) == 16 || (p) == 17 || (p) == 18 || (p) == 19 || (p) == 38 || (p) == 39) +#define digitalPinHasPWM(p) (((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) // SPI 0 // No pinswap enabled by default @@ -183,8 +183,8 @@ const uint8_t PROGMEM digital_pin_to_port[] = { PB, // 11 PB3 PB, // 12 PB4 PB, // 13 PB5 - PC, // 14 PC0/USART1_Tx - PC, // 15 PC1/USART1_Rx + PC, // 14 PC0/USART1_Tx/TCA0 PWM + PC, // 15 PC1/USART1_Rx/TCA0 PWM PC, // 16 PC2/TCA0 PWM PC, // 17 PC3/TCA0 PWM PC, // 18 PC4/TCA0 PWM @@ -228,8 +228,8 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { PIN3_bp, // 11 PB3 PIN4_bp, // 12 PB4 PIN5_bp, // 13 PB5 - PIN0_bp, // 14 PC0/USART1_Tx - PIN1_bp, // 15 PC1/USART1_Rx + PIN0_bp, // 14 PC0/USART1_Tx/TCA0 PWM + PIN1_bp, // 15 PC1/USART1_Rx/TCA0 PWM PIN2_bp, // 16 PC2/TCA0 PWM PIN3_bp, // 17 PC3/TCA0 PWM PIN4_bp, // 18 PC4/TCA0 PWM @@ -273,8 +273,8 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN3_bm, // 11 PB3 PIN4_bm, // 12 PB4 PIN5_bm, // 13 PB5 - PIN0_bm, // 14 PC0/USART1_Tx - PIN1_bm, // 15 PC1/USART1_Rx + PIN0_bm, // 14 PC0/USART1_Tx/TCA0 PWM + PIN1_bm, // 15 PC1/USART1_Rx/TCA0 PWM PIN2_bm, // 16 PC2/TCA0 PWM PIN3_bm, // 17 PC3/TCA0 PWM PIN4_bm, // 18 PC4/TCA0 PWM @@ -317,8 +317,8 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 11 PB3 NOT_ON_TIMER, // 12 PB4 NOT_ON_TIMER, // 13 PB5 - NOT_ON_TIMER, // 14 PC0/USART1_Tx - NOT_ON_TIMER, // 15 PC1/USART1_Rx + TIMERA0, // 14 PC0/USART1_Tx/TCA0 PWM + TIMERA0, // 15 PC1/USART1_Rx/TCA0 PWM TIMERA0, // 16 PC2/TCA0 PWM TIMERA0, // 17 PC3/TCA0 PWM TIMERA0, // 18 PC4/TCA0 PWM From 80fb977cd7642403e484a75ac6c1c74de9ad66ce Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 30 Jul 2019 10:07:53 +0200 Subject: [PATCH 007/351] Avoid compiler warnings when using SPI --- megaavr/libraries/SPI/src/SPI.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index b8a53e2..9097628 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -131,7 +131,7 @@ void SPIClass::detachMaskedInterrupts() { uint8_t shift = 0; while (temp != 0) { if (temp & 1) { - uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); + volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); irqMap[shift] = *pin_ctrl_reg; *pin_ctrl_reg &= ~(PORT_ISC_gm); } @@ -142,7 +142,7 @@ void SPIClass::detachMaskedInterrupts() { shift = 32; while (temp != 0) { if (temp & 1) { - uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); + volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); irqMap[shift] = *pin_ctrl_reg; *pin_ctrl_reg &= ~(PORT_ISC_gm); } From 05fef82a43692d4ab8f5ce2c2c1ddb8a55a920c7 Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 30 Jul 2019 10:40:05 +0200 Subject: [PATCH 008/351] Forgot two additional places that should be 'volatile' --- megaavr/libraries/SPI/src/SPI.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index 9097628..3d961ba 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -156,7 +156,7 @@ void SPIClass::reattachMaskedInterrupts() { uint8_t shift = 0; while (temp != 0) { if (temp & 1) { - uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); + volatile int8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); *pin_ctrl_reg |= irqMap[shift]; } temp = temp >> 1; @@ -166,7 +166,7 @@ void SPIClass::reattachMaskedInterrupts() { shift = 32; while (temp != 0) { if (temp & 1) { - uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); + volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); *pin_ctrl_reg |= irqMap[shift]; } temp = temp >> 1; From 07172382074c7dbde83cf793746ec6157a9cfffc Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 30 Jul 2019 10:44:07 +0200 Subject: [PATCH 009/351] Fixed typo in previous commit. --- megaavr/libraries/SPI/src/SPI.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index 3d961ba..fbc6ac8 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -156,7 +156,7 @@ void SPIClass::reattachMaskedInterrupts() { uint8_t shift = 0; while (temp != 0) { if (temp & 1) { - volatile int8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); + volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(portToPortStruct(shift/8), shift%8); *pin_ctrl_reg |= irqMap[shift]; } temp = temp >> 1; From 6f15e33353b551169b4f11932f885d702c2b247c Mon Sep 17 00:00:00 2001 From: egil Date: Wed, 31 Jul 2019 10:31:36 +0200 Subject: [PATCH 010/351] Document which PWM outputs are available --- README.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/README.md b/README.md index 5e3f1d0..0cf25a8 100644 --- a/README.md +++ b/README.md @@ -25,6 +25,8 @@ ATmega3208, ATmega4808, ATmega3209 and ATmega4809. * [BOD option](#bod-option) * [Reset pin](#reset-pin) * [Pinout](#pinout) +* [Pin swaps](#pin-swaps) +* [PWM output](#pwm-output) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) @@ -106,6 +108,57 @@ Please have a look at the pins_arduino.h files for detailed info.

|
|







| +## Pin swaps +The megaAVR-0 microcontrollers has some capabilities to swap pins for some of the built in devices. +This is specified by invoking the `pins()` method before the `begin()`. +The `pins()` method will return `true` if the pin combination is supported. +For `Serial` the method is `pins(tx,rx)`. This is the same pin sequence as used for the +ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses. +For `Wire` the method is `pins(sda,scl)`, and for `SPI` it is `pins(mosi,miso,scl,ss)`. + +Available pin swaps for the *48 pin standard* pinout are: + +| Device | Default | Alternative 1 | Alternative 2 | +|-----------|----------------------|----------------------|----------------------| +| `Serial` | `pins(0,1)` | `pins(4,5)` | | +| `Wire` | `pins(2,3)` | `pins(16,17)` | | +| `SPI` | `pins(4,5,6,7)` | `pins(14,15,16,17)` | `pins(30,31,32,33)` | +| `Serial3` | `pins(8,9)` | `pins(12,13)` | | +| `Serial1` | `pins(12,13)` | `pins(14,15)` | | +| `Serial2` | `pins(32,35)` | `pins(38,39)` | | + +Available pin swaps for the *28 pin* and *32 pin standard* pinouts are: + +| Device | Default | Alternative | +|-----------|----------------------|----------------------| +| `Serial` | `pins(0,1)` | `pins(4,5)` | +| `Wire` | `pins(2,3)` | `pins(10,11)` | +| `SPI` | `pins(4,5,6,7)` | `pins(8,9,10,11)` | +| `Serial1` | `pins(8,9)` | | +| `Serial2` | `pins(20,21)` | `pins(24,25)` | + +Available pin swaps for the *Uno WiFi* pinout are: + +| Device | Default | Alternative | +|-----------|----------------------|----------------------| +| `Serial1` | `pins(1,0)` | `pins(32,33)` | +| `Wire` | `pins(20,21)` | | +| `Serial2` | `pins(24,23)` | `pins(2,7)` | +| `Serial` | `pins(27,26)` | `pins(9,10)` | +| `SPI` | `pins(32,33,34,10)` | | + + +## PWM output +PWM output, `analogWrite()`, is available for the following pins: + +| Pinout | Available PWM pins | +|-------------------|-------------------------| +| *28 pin standard* | 8,9,10,11 | +| *32 pin standard* | 8,9,10,11,24,25 | +| *48 pin standard* | 14,15,16,17,18,19,38,39 | +| *Uno WiFi* | 3,5,6,9,10 | + + ## How to install #### Boards Manager Installation *Not yet implemented* From 0410732b965ade8ea73c7c120f684a740e17f5e4 Mon Sep 17 00:00:00 2001 From: egil Date: Fri, 2 Aug 2019 06:31:43 +0200 Subject: [PATCH 011/351] Remove pretty catastrophic loop in the USART serial transmit handler causing CPU to stay in interrupt handler more or less the entire time untill the character was transmitted. Thus blocking out other interrupts, such as receive on other ports, and also wasting CPU resources. --- megaavr/cores/coreX-corefiles/UART.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index 3f4234c..e49cfb1 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -107,8 +107,6 @@ void UartClass::_tx_data_empty_irq(void) (*_hwserial_module).TXDATAL = c; - while(!((*_hwserial_module).STATUS & USART_DREIF_bm)); - if (_tx_buffer_head == _tx_buffer_tail) { // Buffer empty, so disable "data register empty" interrupt (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); From 4ecda27da5167a895445e443ae8963ae7286002e Mon Sep 17 00:00:00 2001 From: egil Date: Fri, 2 Aug 2019 20:47:13 +0200 Subject: [PATCH 012/351] Implement baud rate setting according to the book, and also compensate according to clock, either 20 or 16Mhz (or multiples thereof) This in practice means the baudrate is within 0.1% or so. --- megaavr/cores/coreX-corefiles/UART.cpp | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index 3f4234c..8bc4918 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -140,7 +140,7 @@ void UartClass::begin(unsigned long baud, uint16_t config) uint8_t oldSREG = SREG; cli(); - baud_setting = (((8 * F_CPU_CORRECTED) / baud) + 1) / 2; + baud_setting = (((8 * F_CPU) / baud) + 1) / 2; // Disable CLK2X (*_hwserial_module).CTRLB &= (~USART_RXMODE_CLK2X_gc); (*_hwserial_module).CTRLB |= USART_RXMODE_NORMAL_gc; @@ -154,9 +154,13 @@ void UartClass::begin(unsigned long baud, uint16_t config) digitalWrite(_hwserial_tx_pin, HIGH); pinMode(_hwserial_tx_pin, OUTPUT); +#if F_CPU == 20000000L + // BUG: should also differentiate between 5V and 3V + int8_t sigrow_val = SIGROW.OSC20ERR5V; +#else int8_t sigrow_val = SIGROW.OSC16ERR5V; - baud_setting *= (1024 + sigrow_val); - baud_setting /= (1024 - abs(sigrow_val)); +#endif + baud_setting += (baud_setting * sigrow_val) / 1024; // assign the baud_setting, a.k.a. BAUD (USART Baud Rate Register) (*_hwserial_module).BAUD = (int16_t) baud_setting; From a43c8e1cee51321d732f97af90a3bf9c6685d88d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 19 Aug 2019 22:00:35 +0200 Subject: [PATCH 013/351] Add ATmega808/1608 and ATmega809/1609 --- README.md | 17 +- megaavr/avrdude.conf | 96 ++++++++++++ megaavr/boards.txt | 363 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 467 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 5e3f1d0..cb08489 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,6 @@ # MegaCoreX An Arduino core for the new megaAVR series! -ATmega3208, ATmega4808, ATmega3209 and ATmega4809. **TODO:** * ~~UART pin swap inegraion~~ **DONE! use Serial.swap()** @@ -36,14 +35,14 @@ ATmega3208, ATmega4808, ATmega3209 and ATmega4809. ## Supported microcontrollers -| | ATmega4809 | ATmega4808 | ATmega3209 | ATmega3208 | -|------------------------|------------------|-----------------------------|------------------|-----------------------------| -| **Flash** | 48 kB | 48 kB | 32 kB | 32 kB | -| **RAM** | 6 kB | 6 kB | 4 kB | 4 kB | -| **EEPROM** | 256 B | 256 B | 256 B | 256 B | -| **Serial ports** | 4 | 3 | 4 | 3 | -| **IO pins** | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | -| **Available packages** | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | +| | ATmega4809 | ATmega4808 | ATmega3209 | ATmega3208 | ATmega1609 | ATmega1608 | ATmega809 | ATmega808 | +|------------------------|----------------------------|-----------------------------|------------------|-----------------------------|------------------|-----------------------------|------------------|-----------------------------| +| **Flash** | 48 kB | 48 kB | 32 kB | 32 kB | 16 kB | 16 kB | 8 kB | 8 kB | +| **RAM** | 6 kB | 6 kB | 4 kB | 4 kB | 2 kB | 2 kB | 1 kB | 1 kB | +| **EEPROM** | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | +| **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | +| **IO pins** | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | +| **Available packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | * Physical reset pin is disabled SSOP28 package diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 5de202b..10c32a1 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -15793,6 +15793,102 @@ part parent ".avr8x_tiny" ; ; +#------------------------------------------------------------ +# ATmega808 +#------------------------------------------------------------ + +part parent ".avr8x_mega" + id = "m808"; + desc = "ATmega808"; + signature = 0x1E 0x93 0x26; + + memory "flash" + size = 0x2000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATmega809 +#------------------------------------------------------------ + +part parent ".avr8x_mega" + id = "m809"; + desc = "ATmega809"; + signature = 0x1E 0x93 0x2A; + + memory "flash" + size = 0x2000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATmega1608 +#------------------------------------------------------------ + +part parent ".avr8x_mega" + id = "m1608"; + desc = "ATmega1608"; + signature = 0x1E 0x94 0x27; + + memory "flash" + size = 0x4000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATmega1609 +#------------------------------------------------------------ + +part parent ".avr8x_mega" + id = "m1609"; + desc = "ATmega1609"; + signature = 0x1E 0x94 0x26; + + memory "flash" + size = 0x4000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; +; + #------------------------------------------------------------ # ATmega3208 #------------------------------------------------------------ diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 1f9ad9f..b548e9f 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -366,3 +366,366 @@ menu.resetpin=Reset pin 3208.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 3208.menu.clock.1MHz_div.build.f_cpu=1000000L + + +##################### +#### ATmega1609 #### +##################### + +# General +1609.name=Atmega1609 +1609.upload.tool=avrdude +1609.upload.maximum_size=16384 +1609.upload.maximum_data_size=2048 +1609.upload.speed=115200 +1609.bootloader.tool=avrdude +1609.build.core=coreX-corefiles +1609.build.board=AVR_ATmega1609 +1609.build.mcu=atmega1609 + +# Fuses we don't need to modify in the tools menu +1609.bootloader.WDTCFG=0x00 +1609.bootloader.TCD0CFG=0x00 +1609.bootloader.SYSCFG1=0x06 +1609.bootloader.APPEND=0x00 +1609.bootloader.BOOTEND=0x00 +1609.bootloader.LOCKBIT=0xC5 + +# Pinouts +1609.menu.pinout.uno_wifi=Uno WiFi +1609.menu.pinout.uno_wifi.build.variant=uno-wifi +1609.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +1609.menu.pinout.48pin_standard=48 pin standard +1609.menu.pinout.48pin_standard.build.variant=48pin-standard + +# Reset pin +1609.menu.resetpin.reset=Reset +1609.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +1609.menu.resetpin.gpio=GPIO +1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 + +# Brown out detection +1609.menu.BOD.2v6=BOD 2.6V +1609.menu.BOD.2v6.bootloader.BODCFG=0x54 +1609.menu.BOD.4v2=BOD 4.2V +1609.menu.BOD.4v2.bootloader.BODCFG=0xF4 +1609.menu.BOD.4v0=BOD 4.0V +1609.menu.BOD.4v0.bootloader.BODCFG=0xD4 +1609.menu.BOD.3v7=BOD 3.7V +1609.menu.BOD.3v7.bootloader.BODCFG=0xB4 +1609.menu.BOD.3v3=BOD 3.3V +1609.menu.BOD.3v3.bootloader.BODCFG=0x94 +1609.menu.BOD.2v9=BOD 2.9V +1609.menu.BOD.2v9.bootloader.BODCFG=0x74 +1609.menu.BOD.2v1=BOD 2.1V +1609.menu.BOD.2v1.bootloader.BODCFG=0x34 +1609.menu.BOD.1v8=BOD 1.8V +1609.menu.BOD.1v8.bootloader.BODCFG=0x14 +1609.menu.BOD.disabled=BOD disabled +1609.menu.BOD.disabled.bootloader.BODCFG=0x00 + +# Clock +1609.menu.clock.16MHz=16 MHz +1609.menu.clock.16MHz.upload.speed=115200 +1609.menu.clock.16MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.16MHz.build.f_cpu=16000000L + +1609.menu.clock.20MHz=20 MHz +1609.menu.clock.20MHz.upload.speed=115200 +1609.menu.clock.20MHz.bootloader.OSCCFG=0x02 +1609.menu.clock.20MHz.build.f_cpu=20000000L + +1609.menu.clock.8MHz_div=8 MHz (divided) +1609.menu.clock.8MHz_div.upload.speed=115200 +1609.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.8MHz_div.build.f_cpu=8000000L + +1609.menu.clock.4MHz_div=4 MHz (divided) +1609.menu.clock.4MHz_div.upload.speed=115200 +1609.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.4MHz_div.build.f_cpu=4000000L + +1609.menu.clock.2MHz_div=2 MHz (divided) +1609.menu.clock.2MHz_div.upload.speed=115200 +1609.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.2MHz_div.build.f_cpu=2000000L + +1609.menu.clock.1MHz_div=1 MHz (divided) +1609.menu.clock.1MHz_div.upload.speed=115200 +1609.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.1MHz_div.build.f_cpu=1000000L + +# ATmega328 emulation +1609.menu.emulation.false=No +1609.menu.emulation.true=Yes +1609.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE + + + +#################### +#### ATmega1608 #### +#################### + +# General +1608.name=Atmega1608 +1608.upload.tool=avrdude +1608.upload.maximum_size=16384 +1608.upload.maximum_data_size=2048 +1608.upload.speed=115200 +1608.bootloader.tool=avrdude +1608.build.core=coreX-corefiles +1608.build.board=AVR_ATmega1608 +1608.build.mcu=atmega1608 + +# Fuses we don't need to modify in the tools menu +1608.bootloader.WDTCFG=0x00 +1608.bootloader.TCD0CFG=0x00 +1608.bootloader.SYSCFG1=0x06 +1608.bootloader.APPEND=0x00 +1608.bootloader.BOOTEND=0x00 +1608.bootloader.LOCKBIT=0xC5 + +# Pinouts +1608.menu.pinout.32pin_standard=32 pin standard +1608.menu.pinout.32pin_standard.build.variant=32pin-standard +1608.menu.pinout.28pin_standard=28 pin standard +1608.menu.pinout.28pin_standard.build.variant=28pin-standard + +# Reset pin +1608.menu.resetpin.reset=Reset +1608.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +1608.menu.resetpin.gpio=GPIO +1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 + +# Brown out detection +1608.menu.BOD.2v6=BOD 2.6V +1608.menu.BOD.2v6.bootloader.BODCFG=0x54 +1608.menu.BOD.4v2=BOD 4.2V +1608.menu.BOD.4v2.bootloader.BODCFG=0xF4 +1608.menu.BOD.4v0=BOD 4.0V +1608.menu.BOD.4v0.bootloader.BODCFG=0xD4 +1608.menu.BOD.3v7=BOD 3.7V +1608.menu.BOD.3v7.bootloader.BODCFG=0xB4 +1608.menu.BOD.3v3=BOD 3.3V +1608.menu.BOD.3v3.bootloader.BODCFG=0x94 +1608.menu.BOD.2v9=BOD 2.9V +1608.menu.BOD.2v9.bootloader.BODCFG=0x74 +1608.menu.BOD.2v1=BOD 2.1V +1608.menu.BOD.2v1.bootloader.BODCFG=0x34 +1608.menu.BOD.1v8=BOD 1.8V +1608.menu.BOD.1v8.bootloader.BODCFG=0x14 +1608.menu.BOD.disabled=BOD disabled +1608.menu.BOD.disabled.bootloader.BODCFG=0x00 + +# Clock +1608.menu.clock.16MHz=16 MHz +1608.menu.clock.16MHz.upload.speed=115200 +1608.menu.clock.16MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.16MHz.build.f_cpu=16000000L + +1608.menu.clock.20MHz=20 MHz +1608.menu.clock.20MHz.upload.speed=115200 +1608.menu.clock.20MHz.bootloader.OSCCFG=0x02 +1608.menu.clock.20MHz.build.f_cpu=20000000L + +1608.menu.clock.8MHz_div=8 MHz (divided) +1608.menu.clock.8MHz_div.upload.speed=115200 +1608.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.8MHz_div.build.f_cpu=8000000L + +1608.menu.clock.4MHz_div=4 MHz (divided) +1608.menu.clock.4MHz_div.upload.speed=115200 +1608.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.4MHz_div.build.f_cpu=4000000L + +1608.menu.clock.2MHz_div=2 MHz (divided) +1608.menu.clock.2MHz_div.upload.speed=115200 +1608.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.2MHz_div.build.f_cpu=2000000L + +1608.menu.clock.1MHz_div=1 MHz (divided) +1608.menu.clock.1MHz_div.upload.speed=115200 +1608.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.1MHz_div.build.f_cpu=1000000L + + + +################### +#### ATmega809 #### +################### + +# General +809.name=Atmega809 +809.upload.tool=avrdude +809.upload.maximum_size=8192 +809.upload.maximum_data_size=1024 +809.upload.speed=115200 +809.bootloader.tool=avrdude +809.build.core=coreX-corefiles +809.build.board=AVR_ATmega809 +809.build.mcu=atmega809 + +# Fuses we don't need to modify in the tools menu +809.bootloader.WDTCFG=0x00 +809.bootloader.TCD0CFG=0x00 +809.bootloader.SYSCFG1=0x06 +809.bootloader.APPEND=0x00 +809.bootloader.BOOTEND=0x00 +809.bootloader.LOCKBIT=0xC5 + +# Pinouts +809.menu.pinout.uno_wifi=Uno WiFi +809.menu.pinout.uno_wifi.build.variant=uno-wifi +809.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +809.menu.pinout.48pin_standard=48 pin standard +809.menu.pinout.48pin_standard.build.variant=48pin-standard + +# Reset pin +809.menu.resetpin.reset=Reset +809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +809.menu.resetpin.gpio=GPIO +809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 + +# Brown out detection +809.menu.BOD.2v6=BOD 2.6V +809.menu.BOD.2v6.bootloader.BODCFG=0x54 +809.menu.BOD.4v2=BOD 4.2V +809.menu.BOD.4v2.bootloader.BODCFG=0xF4 +809.menu.BOD.4v0=BOD 4.0V +809.menu.BOD.4v0.bootloader.BODCFG=0xD4 +809.menu.BOD.3v7=BOD 3.7V +809.menu.BOD.3v7.bootloader.BODCFG=0xB4 +809.menu.BOD.3v3=BOD 3.3V +809.menu.BOD.3v3.bootloader.BODCFG=0x94 +809.menu.BOD.2v9=BOD 2.9V +809.menu.BOD.2v9.bootloader.BODCFG=0x74 +809.menu.BOD.2v1=BOD 2.1V +809.menu.BOD.2v1.bootloader.BODCFG=0x34 +809.menu.BOD.1v8=BOD 1.8V +809.menu.BOD.1v8.bootloader.BODCFG=0x14 +809.menu.BOD.disabled=BOD disabled +809.menu.BOD.disabled.bootloader.BODCFG=0x00 + +# Clock +809.menu.clock.16MHz=16 MHz +809.menu.clock.16MHz.upload.speed=115200 +809.menu.clock.16MHz.bootloader.OSCCFG=0x01 +809.menu.clock.16MHz.build.f_cpu=16000000L + +809.menu.clock.20MHz=20 MHz +809.menu.clock.20MHz.upload.speed=115200 +809.menu.clock.20MHz.bootloader.OSCCFG=0x02 +809.menu.clock.20MHz.build.f_cpu=20000000L + +809.menu.clock.8MHz_div=8 MHz (divided) +809.menu.clock.8MHz_div.upload.speed=115200 +809.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.8MHz_div.build.f_cpu=8000000L + +809.menu.clock.4MHz_div=4 MHz (divided) +809.menu.clock.4MHz_div.upload.speed=115200 +809.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.4MHz_div.build.f_cpu=4000000L + +809.menu.clock.2MHz_div=2 MHz (divided) +809.menu.clock.2MHz_div.upload.speed=115200 +809.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.2MHz_div.build.f_cpu=2000000L + +809.menu.clock.1MHz_div=1 MHz (divided) +809.menu.clock.1MHz_div.upload.speed=115200 +809.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.1MHz_div.build.f_cpu=1000000L + +# ATmega328 emulation +809.menu.emulation.false=No +809.menu.emulation.true=Yes +809.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE + + + +################### +#### ATmega808 #### +################### + +# General +808.name=Atmega808 +808.upload.tool=avrdude +808.upload.maximum_size=8192 +808.upload.maximum_data_size=1024 +808.upload.speed=115200 +808.bootloader.tool=avrdude +808.build.core=coreX-corefiles +808.build.board=AVR_ATmega808 +808.build.mcu=atmega808 + +# Fuses we don't need to modify in the tools menu +808.bootloader.WDTCFG=0x00 +808.bootloader.TCD0CFG=0x00 +808.bootloader.SYSCFG1=0x06 +808.bootloader.APPEND=0x00 +808.bootloader.BOOTEND=0x00 +808.bootloader.LOCKBIT=0xC5 + +# Pinouts +808.menu.pinout.32pin_standard=32 pin standard +808.menu.pinout.32pin_standard.build.variant=32pin-standard +808.menu.pinout.28pin_standard=28 pin standard +808.menu.pinout.28pin_standard.build.variant=28pin-standard + +# Reset pin +808.menu.resetpin.reset=Reset +808.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +808.menu.resetpin.gpio=GPIO +808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 + +# Brown out detection +808.menu.BOD.2v6=BOD 2.6V +808.menu.BOD.2v6.bootloader.BODCFG=0x54 +808.menu.BOD.4v2=BOD 4.2V +808.menu.BOD.4v2.bootloader.BODCFG=0xF4 +808.menu.BOD.4v0=BOD 4.0V +808.menu.BOD.4v0.bootloader.BODCFG=0xD4 +808.menu.BOD.3v7=BOD 3.7V +808.menu.BOD.3v7.bootloader.BODCFG=0xB4 +808.menu.BOD.3v3=BOD 3.3V +808.menu.BOD.3v3.bootloader.BODCFG=0x94 +808.menu.BOD.2v9=BOD 2.9V +808.menu.BOD.2v9.bootloader.BODCFG=0x74 +808.menu.BOD.2v1=BOD 2.1V +808.menu.BOD.2v1.bootloader.BODCFG=0x34 +808.menu.BOD.1v8=BOD 1.8V +808.menu.BOD.1v8.bootloader.BODCFG=0x14 +808.menu.BOD.disabled=BOD disabled +808.menu.BOD.disabled.bootloader.BODCFG=0x00 + +# Clock +808.menu.clock.16MHz=16 MHz +808.menu.clock.16MHz.upload.speed=115200 +808.menu.clock.16MHz.bootloader.OSCCFG=0x01 +808.menu.clock.16MHz.build.f_cpu=16000000L + +808.menu.clock.20MHz=20 MHz +808.menu.clock.20MHz.upload.speed=115200 +808.menu.clock.20MHz.bootloader.OSCCFG=0x02 +808.menu.clock.20MHz.build.f_cpu=20000000L + +808.menu.clock.8MHz_div=8 MHz (divided) +808.menu.clock.8MHz_div.upload.speed=115200 +808.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.8MHz_div.build.f_cpu=8000000L + +808.menu.clock.4MHz_div=4 MHz (divided) +808.menu.clock.4MHz_div.upload.speed=115200 +808.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.4MHz_div.build.f_cpu=4000000L + +808.menu.clock.2MHz_div=2 MHz (divided) +808.menu.clock.2MHz_div.upload.speed=115200 +808.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.2MHz_div.build.f_cpu=2000000L + +808.menu.clock.1MHz_div=1 MHz (divided) +808.menu.clock.1MHz_div.upload.speed=115200 +808.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.1MHz_div.build.f_cpu=1000000L From 1e27866420da9853ac544a7fa6a2d1d0074ca9fd Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Sep 2019 19:11:52 +0200 Subject: [PATCH 014/351] Add Atmel ICE UPDI programmer Closes #10 --- megaavr/programmers.txt | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index 19ac466..b242e5e 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -24,3 +24,10 @@ jtag2updi.communication=serial jtag2updi.protocol=jtag2updi jtag2updi.program.tool=avrdude jtag2updi.program.extra_params=-P{serial.port} + +atmelice_updi.name=Atmel-ICE (UPDI) +atmelice_updi.communication=usb +atmelice_updi.protocol=atmelice_updi +atmelice_updi.program.protocol=jtagice3_updi +atmelice_updi.program.tool=avrdude +atmelice_updi.program.extra_params=-Pusb From 9f54d2550601bc299f98bd01829f1403263ca542 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Sep 2019 19:34:07 +0200 Subject: [PATCH 015/351] Fix UART issue See https://github.com/arduino/ArduinoCore-megaavr/pull/42/ for details Thanks to @egilkv for providing a fix --- megaavr/cores/coreX-corefiles/UART.cpp | 36 +++++++++++++++----------- megaavr/cores/coreX-corefiles/UART.h | 3 +++ 2 files changed, 24 insertions(+), 15 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index c20a534..6115b99 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -88,7 +88,6 @@ void serialEventRun(void) void UartClass::_tx_data_empty_irq(void) { // Check if tx buffer already empty. - // This interrupt-handler can be called "manually" from flush(); if (_tx_buffer_head == _tx_buffer_tail) { // Buffer empty, so disable "data register empty" interrupt (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); @@ -119,6 +118,24 @@ void UartClass::_tx_data_empty_irq(void) } } +// To invoke data empty "interrupt" via a call, use this method +void UartClass::_poll_tx_data_empty(void) +{ + if ( (!(SREG & CPU_I_bm)) || (!((*_hwserial_module).CTRLA & USART_DREIE_bm)) ) { + // Interrupts are disabled either globally or for data register empty, + // so we'll have to poll the "data register empty" flag ourselves. + // If it is set, pretend an interrupt has happened and call the handler + // to free up space for us. + + // Invoke interrupt handler only if conditions data register is empty + if ((*_hwserial_module).STATUS & USART_DREIF_bm) { + _tx_data_empty_irq(); + } + } + // In case interrupts are enabled, the interrupt routine will be invoked by itself +} + + // Public Methods ////////////////////////////////////////////////////////////// void UartClass::begin(unsigned long baud, uint16_t config) @@ -292,9 +309,7 @@ void UartClass::flush() // If interrupts are globally disabled or the and DR empty interrupt is disabled, // poll the "data register empty" interrupt flag to prevent deadlock - if ( (!(SREG & CPU_I_bm)) || (!((*_hwserial_module).CTRLA & USART_DREIE_bm)) ) { - _tx_data_empty_irq(); - } + _poll_tx_data_empty(); } // If we get here, nothing is queued anymore (DREIE is disabled) and // the hardware finished transmission (TXCIF is set). @@ -333,18 +348,9 @@ size_t UartClass::write(uint8_t c) tx_buffer_index_t i = (_tx_buffer_head + 1) % SERIAL_TX_BUFFER_SIZE; //If the output buffer is full, there's nothing for it other than to - //wait for the interrupt handler to empty it a bit + //wait for the interrupt handler to empty it a bit (or emulate interrupts) while (i == _tx_buffer_tail) { - if ( ( !(SREG & CPU_I_bm) ) || ( !((*_hwserial_module).CTRLA & USART_DREIE_bm) ) ) { - // Interrupts are disabled either globally or for data register empty, - // so we'll have to poll the "data register empty" flag ourselves. - // If it is set, pretend an interrupt has happened and call the handler - //to free up space for us. - - _tx_data_empty_irq(); - } else { - // nop, the interrupt handler will free up space for us - } + _poll_tx_data_empty(); } _tx_buffer[_tx_buffer_head] = c; diff --git a/megaavr/cores/coreX-corefiles/UART.h b/megaavr/cores/coreX-corefiles/UART.h index 4ae9c06..66c650d 100644 --- a/megaavr/cores/coreX-corefiles/UART.h +++ b/megaavr/cores/coreX-corefiles/UART.h @@ -173,6 +173,9 @@ class UartClass : public HardwareSerial // Interrupt handlers - Not intended to be called externally inline void _rx_complete_irq(void); void _tx_data_empty_irq(void); + + private: + void _poll_tx_data_empty(void); }; #if defined(HWSERIAL0) From 917f6cc212402a224271186c3487a3d16d5d8799 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Sep 2019 21:26:42 +0200 Subject: [PATCH 016/351] Change tool path --- megaavr/platform.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 7d43fc8..f7c945a 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -18,7 +18,7 @@ compiler.warning_flags.more=-Wall compiler.warning_flags.all=-Wall -Wextra # Default "compiler.path" is correct, change only if you want to override the initial value -compiler.path={runtime.tools.avr-gcc-5.4.0-atmel3.6.1-arduino2.path}/bin/ +compiler.path={runtime.tools.avr-gcc.path}/bin/ compiler.c.cmd=avr-gcc compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto -fno-fat-lto-objects compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin -Wl,--gc-sections @@ -102,7 +102,7 @@ tools.avrdude.upload.params.quiet=-q -q # tools.avrdude.upload.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value tools.avrdude.upload.verify= tools.avrdude.upload.params.noverify=-V -tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} -Pusb -b{upload.speed} -e -D "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {upload.extra_params} -b{upload.speed} -e -D "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q From 0a8606852327541328265249a8ea46eb60d421f3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Sep 2019 22:54:55 +0200 Subject: [PATCH 017/351] Change millis timer Caused microcontroller to hang when TCB PWM outputs were modified. Closes #11 --- megaavr/variants/28pin-standard/pins_arduino.h | 2 +- megaavr/variants/32pin-standard/pins_arduino.h | 2 +- megaavr/variants/48pin-standard/pins_arduino.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 743772e..80ac3e2 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -29,7 +29,7 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB0 // Use timerb0 for millis generation +#define MILLIS_USE_TIMERB3 #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 45b95df..bd8ce96 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -29,7 +29,7 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB0 // Use timerb0 for millis generation +#define MILLIS_USE_TIMERB3 #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 9150e7d..7e14b8c 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -34,7 +34,7 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 22) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB0 // Use timerb0 for millis generation +#define MILLIS_USE_TIMERB3 #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) From db592bf156fa7bd9f6a30304021ec321c7d11630 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Sep 2019 23:29:54 +0200 Subject: [PATCH 018/351] Update Readme Remove part about pin swap, since it's not implemented yet. --- README.md | 53 ++++++----------------------------------------------- 1 file changed, 6 insertions(+), 47 deletions(-) diff --git a/README.md b/README.md index 3fb9189..b9c7f88 100644 --- a/README.md +++ b/README.md @@ -24,7 +24,6 @@ An Arduino core for the new megaAVR series! * [BOD option](#bod-option) * [Reset pin](#reset-pin) * [Pinout](#pinout) -* [Pin swaps](#pin-swaps) * [PWM output](#pwm-output) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) @@ -107,55 +106,15 @@ Please have a look at the pins_arduino.h files for detailed info.

|
|







| -## Pin swaps -The megaAVR-0 microcontrollers has some capabilities to swap pins for some of the built in devices. -This is specified by invoking the `pins()` method before the `begin()`. -The `pins()` method will return `true` if the pin combination is supported. -For `Serial` the method is `pins(tx,rx)`. This is the same pin sequence as used for the -ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses. -For `Wire` the method is `pins(sda,scl)`, and for `SPI` it is `pins(mosi,miso,scl,ss)`. - -Available pin swaps for the *48 pin standard* pinout are: - -| Device | Default | Alternative 1 | Alternative 2 | -|-----------|----------------------|----------------------|----------------------| -| `Serial` | `pins(0,1)` | `pins(4,5)` | | -| `Wire` | `pins(2,3)` | `pins(16,17)` | | -| `SPI` | `pins(4,5,6,7)` | `pins(14,15,16,17)` | `pins(30,31,32,33)` | -| `Serial3` | `pins(8,9)` | `pins(12,13)` | | -| `Serial1` | `pins(12,13)` | `pins(14,15)` | | -| `Serial2` | `pins(32,35)` | `pins(38,39)` | | - -Available pin swaps for the *28 pin* and *32 pin standard* pinouts are: - -| Device | Default | Alternative | -|-----------|----------------------|----------------------| -| `Serial` | `pins(0,1)` | `pins(4,5)` | -| `Wire` | `pins(2,3)` | `pins(10,11)` | -| `SPI` | `pins(4,5,6,7)` | `pins(8,9,10,11)` | -| `Serial1` | `pins(8,9)` | | -| `Serial2` | `pins(20,21)` | `pins(24,25)` | - -Available pin swaps for the *Uno WiFi* pinout are: - -| Device | Default | Alternative | -|-----------|----------------------|----------------------| -| `Serial1` | `pins(1,0)` | `pins(32,33)` | -| `Wire` | `pins(20,21)` | | -| `Serial2` | `pins(24,23)` | `pins(2,7)` | -| `Serial` | `pins(27,26)` | `pins(9,10)` | -| `SPI` | `pins(32,33,34,10)` | | - - ## PWM output PWM output, `analogWrite()`, is available for the following pins: -| Pinout | Available PWM pins | -|-------------------|-------------------------| -| *28 pin standard* | 8,9,10,11 | -| *32 pin standard* | 8,9,10,11,24,25 | -| *48 pin standard* | 14,15,16,17,18,19,38,39 | -| *Uno WiFi* | 3,5,6,9,10 | +| Pinout | Number of PWM pins | Available PWM pins | +|-------------------|--------------------|--------------------------------| +| *28 pin standard* | 4 | 8, 9, 10, 11 | +| *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | +| *48 pin standard* | 8 | 14, 15, 16, 17, 18, 19, 38, 39 | +| *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | ## How to install From d4d67831093862e9683ce63994dc20f27f56c3b3 Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 11 Sep 2019 00:16:57 +0200 Subject: [PATCH 019/351] Add new pinout diagrams --- README.md | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index b9c7f88..cd360d7 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,6 @@ An Arduino core for the new megaAVR series! **TODO:** * ~~UART pin swap inegraion~~ **DONE! use Serial.swap()** * ~~Add printf to print class~~ **DONE! use Serial.printf()** -* Get rid of nasty compiler warning when compiling a blank sketch (or any sketch really..) * Steal 20 MHz accurate timing from MCUdude_corefiles * SPI pin swap integration in libraries * I2C pin swap integration in libraries @@ -93,17 +92,17 @@ None of the megaAVR-0 microcontrollers needs the reset line in order to be repro ## Pinout This core provides several different Arduino pin mappings based on your current hardware -- **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much more clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. - **32 pin standard**: This is the pinout for the 32 pin version of the ATmega3208/4808. Again, it will not be compatible with shields or anything like that, but it's clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. Will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. +- **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: -| **MegaCoreX ATmega3209/4809 pinout** | **MegaCoreX ATmega3208/4808 pinout** | -|-------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------| -|
|







| +| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | +|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------| +|

|







| ## PWM output @@ -137,16 +136,16 @@ Click to enlarge: [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. Use the `LED_BUILTIN` macro to control the onboard LED. Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Use the `LED_BUILTIN` macro to control the onboard LED marked with *WIFI*. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + ### ATmega4809 Xplained Pro [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. Recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + From 76a16556002b87b46e4e75026487fbf109873b51 Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 11 Sep 2019 00:18:58 +0200 Subject: [PATCH 020/351] Formatting --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index cd360d7..e0d2bbc 100644 --- a/README.md +++ b/README.md @@ -100,9 +100,9 @@ This core provides several different Arduino pin mappings based on your current Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: -| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | -|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|







| +| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | +|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +|

|




















| ## PWM output From 0d406ab9f394936edaecbff03915e82c7bb905da Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 11 Sep 2019 00:35:44 +0200 Subject: [PATCH 021/351] Change lables --- megaavr/boards.txt | 450 ++++++++++++++++++++++----------------------- 1 file changed, 225 insertions(+), 225 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index b548e9f..ed0371a 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -28,11 +28,11 @@ menu.resetpin=Reset pin 4809.bootloader.LOCKBIT=0xC5 # Pinouts +4809.menu.pinout.48pin_standard=40/48 pin standard +4809.menu.pinout.48pin_standard.build.variant=48pin-standard 4809.menu.pinout.uno_wifi=Uno WiFi 4809.menu.pinout.uno_wifi.build.variant=uno-wifi 4809.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE -4809.menu.pinout.48pin_standard=48 pin standard -4809.menu.pinout.48pin_standard.build.variant=48pin-standard # Reset pin 4809.menu.resetpin.reset=Reset @@ -61,35 +61,35 @@ menu.resetpin=Reset pin 4809.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -4809.menu.clock.16MHz=16 MHz -4809.menu.clock.16MHz.upload.speed=115200 -4809.menu.clock.16MHz.bootloader.OSCCFG=0x01 -4809.menu.clock.16MHz.build.f_cpu=16000000L - -4809.menu.clock.20MHz=20 MHz -4809.menu.clock.20MHz.upload.speed=115200 -4809.menu.clock.20MHz.bootloader.OSCCFG=0x02 -4809.menu.clock.20MHz.build.f_cpu=20000000L - -4809.menu.clock.8MHz_div=8 MHz (divided) -4809.menu.clock.8MHz_div.upload.speed=115200 -4809.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.8MHz_div.build.f_cpu=8000000L - -4809.menu.clock.4MHz_div=4 MHz (divided) -4809.menu.clock.4MHz_div.upload.speed=115200 -4809.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.4MHz_div.build.f_cpu=4000000L - -4809.menu.clock.2MHz_div=2 MHz (divided) -4809.menu.clock.2MHz_div.upload.speed=115200 -4809.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.2MHz_div.build.f_cpu=2000000L - -4809.menu.clock.1MHz_div=1 MHz (divided) -4809.menu.clock.1MHz_div.upload.speed=115200 -4809.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.1MHz_div.build.f_cpu=1000000L +4809.menu.clock.internal_16MHz=Internal 16 MHz +4809.menu.clock.internal_16MHz.upload.speed=115200 +4809.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_16MHz.build.f_cpu=16000000L + +4809.menu.clock.internal_20MHz=Internal 20 MHz +4809.menu.clock.internal_20MHz.upload.speed=115200 +4809.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_20MHz.build.f_cpu=20000000L + +4809.menu.clock.internal_8MHz_div=Internal 8 MHz +4809.menu.clock.internal_8MHz_div.upload.speed=115200 +4809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L + +4809.menu.clock.internal_4MHz_div=Internal 4 MHz +4809.menu.clock.internal_4MHz_div.upload.speed=115200 +4809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L + +4809.menu.clock.internal_2MHz_div=Internal 2 MHz +4809.menu.clock.internal_2MHz_div.upload.speed=115200 +4809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L + +4809.menu.clock.internal_1MHz_div=Internal 1 MHz +4809.menu.clock.internal_1MHz_div.upload.speed=115200 +4809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L # ATmega328 emulation #4809.menu.emulation.false=No @@ -154,35 +154,35 @@ menu.resetpin=Reset pin 4808.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -4808.menu.clock.16MHz=16 MHz -4808.menu.clock.16MHz.upload.speed=115200 -4808.menu.clock.16MHz.bootloader.OSCCFG=0x01 -4808.menu.clock.16MHz.build.f_cpu=16000000L +4808.menu.clock.internal_16MHz=Internal 16 MHz +4808.menu.clock.internal_16MHz.upload.speed=115200 +4808.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_16MHz.build.f_cpu=16000000L -4808.menu.clock.20MHz=20 MHz -4808.menu.clock.20MHz.upload.speed=115200 -4808.menu.clock.20MHz.bootloader.OSCCFG=0x02 -4808.menu.clock.20MHz.build.f_cpu=20000000L +4808.menu.clock.internal_20MHz=Internal 20 MHz +4808.menu.clock.internal_20MHz.upload.speed=115200 +4808.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_20MHz.build.f_cpu=20000000L -4808.menu.clock.8MHz_div=8 MHz (divided) -4808.menu.clock.8MHz_div.upload.speed=115200 -4808.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.8MHz_div.build.f_cpu=8000000L +4808.menu.clock.internal_8MHz_div=Internal 8 MHz +4808.menu.clock.internal_8MHz_div.upload.speed=115200 +4808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L -4808.menu.clock.4MHz_div=4 MHz (divided) -4808.menu.clock.4MHz_div.upload.speed=115200 -4808.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.4MHz_div.build.f_cpu=4000000L +4808.menu.clock.internal_4MHz_div=Internal 4 MHz +4808.menu.clock.internal_4MHz_div.upload.speed=115200 +4808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L -4808.menu.clock.2MHz_div=2 MHz (divided) -4808.menu.clock.2MHz_div.upload.speed=115200 -4808.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.2MHz_div.build.f_cpu=2000000L +4808.menu.clock.internal_2MHz_div=Internal 2 MHz +4808.menu.clock.internal_2MHz_div.upload.speed=115200 +4808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L -4808.menu.clock.1MHz_div=1 MHz (divided) -4808.menu.clock.1MHz_div.upload.speed=115200 -4808.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.1MHz_div.build.f_cpu=1000000L +4808.menu.clock.internal_1MHz_div=Internal 1 MHz +4808.menu.clock.internal_1MHz_div.upload.speed=115200 +4808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L @@ -210,11 +210,11 @@ menu.resetpin=Reset pin 3209.bootloader.LOCKBIT=0xC5 # Pinouts +3209.menu.pinout.48pin_standard=48 pin standard +3209.menu.pinout.48pin_standard.build.variant=48pin-standard 3209.menu.pinout.uno_wifi=Uno WiFi 3209.menu.pinout.uno_wifi.build.variant=uno-wifi 3209.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE -3209.menu.pinout.48pin_standard=48 pin standard -3209.menu.pinout.48pin_standard.build.variant=48pin-standard # Reset pin 3209.menu.resetpin.reset=Reset @@ -243,35 +243,35 @@ menu.resetpin=Reset pin 3209.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -3209.menu.clock.16MHz=16 MHz -3209.menu.clock.16MHz.upload.speed=115200 -3209.menu.clock.16MHz.bootloader.OSCCFG=0x01 -3209.menu.clock.16MHz.build.f_cpu=16000000L - -3209.menu.clock.20MHz=20 MHz -3209.menu.clock.20MHz.upload.speed=115200 -3209.menu.clock.20MHz.bootloader.OSCCFG=0x02 -3209.menu.clock.20MHz.build.f_cpu=20000000L - -3209.menu.clock.8MHz_div=8 MHz (divided) -3209.menu.clock.8MHz_div.upload.speed=115200 -3209.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.8MHz_div.build.f_cpu=8000000L - -3209.menu.clock.4MHz_div=4 MHz (divided) -3209.menu.clock.4MHz_div.upload.speed=115200 -3209.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.4MHz_div.build.f_cpu=4000000L - -3209.menu.clock.2MHz_div=2 MHz (divided) -3209.menu.clock.2MHz_div.upload.speed=115200 -3209.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.2MHz_div.build.f_cpu=2000000L - -3209.menu.clock.1MHz_div=1 MHz (divided) -3209.menu.clock.1MHz_div.upload.speed=115200 -3209.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.1MHz_div.build.f_cpu=1000000L +3209.menu.clock.internal_16MHz=Internal 16 MHz +3209.menu.clock.internal_16MHz.upload.speed=115200 +3209.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_16MHz.build.f_cpu=16000000L + +3209.menu.clock.internal_20MHz=Internal 20 MHz +3209.menu.clock.internal_20MHz.upload.speed=115200 +3209.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_20MHz.build.f_cpu=20000000L + +3209.menu.clock.internal_8MHz_div=Internal 8 MHz +3209.menu.clock.internal_8MHz_div.upload.speed=115200 +3209.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_8MHz_div.build.f_cpu=8000000L + +3209.menu.clock.internal_4MHz_div=Internal 4 MHz +3209.menu.clock.internal_4MHz_div.upload.speed=115200 +3209.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_4MHz_div.build.f_cpu=4000000L + +3209.menu.clock.internal_2MHz_div=Internal 2 MHz +3209.menu.clock.internal_2MHz_div.upload.speed=115200 +3209.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_2MHz_div.build.f_cpu=2000000L + +3209.menu.clock.internal_1MHz_div=Internal 1 MHz +3209.menu.clock.internal_1MHz_div.upload.speed=115200 +3209.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_1MHz_div.build.f_cpu=1000000L # ATmega328 emulation 3209.menu.emulation.false=No @@ -336,35 +336,35 @@ menu.resetpin=Reset pin 3208.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -3208.menu.clock.16MHz=16 MHz -3208.menu.clock.16MHz.upload.speed=115200 -3208.menu.clock.16MHz.bootloader.OSCCFG=0x01 -3208.menu.clock.16MHz.build.f_cpu=16000000L +3208.menu.clock.internal_16MHz=Internal 16 MHz +3208.menu.clock.internal_16MHz.upload.speed=115200 +3208.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_16MHz.build.f_cpu=16000000L -3208.menu.clock.20MHz=20 MHz -3208.menu.clock.20MHz.upload.speed=115200 -3208.menu.clock.20MHz.bootloader.OSCCFG=0x02 -3208.menu.clock.20MHz.build.f_cpu=20000000L +3208.menu.clock.internal_20MHz=Internal 20 MHz +3208.menu.clock.internal_20MHz.upload.speed=115200 +3208.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_20MHz.build.f_cpu=20000000L -3208.menu.clock.8MHz_div=8 MHz (divided) -3208.menu.clock.8MHz_div.upload.speed=115200 -3208.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.8MHz_div.build.f_cpu=8000000L +3208.menu.clock.internal_8MHz_div=Internal 8 MHz +3208.menu.clock.internal_8MHz_div.upload.speed=115200 +3208.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_8MHz_div.build.f_cpu=8000000L -3208.menu.clock.4MHz_div=4 MHz (divided) -3208.menu.clock.4MHz_div.upload.speed=115200 -3208.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.4MHz_div.build.f_cpu=4000000L +3208.menu.clock.internal_4MHz_div=Internal 4 MHz +3208.menu.clock.internal_4MHz_div.upload.speed=115200 +3208.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_4MHz_div.build.f_cpu=4000000L -3208.menu.clock.2MHz_div=2 MHz (divided) -3208.menu.clock.2MHz_div.upload.speed=115200 -3208.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.2MHz_div.build.f_cpu=2000000L +3208.menu.clock.internal_2MHz_div=Internal 2 MHz +3208.menu.clock.internal_2MHz_div.upload.speed=115200 +3208.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_2MHz_div.build.f_cpu=2000000L -3208.menu.clock.1MHz_div=1 MHz (divided) -3208.menu.clock.1MHz_div.upload.speed=115200 -3208.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.1MHz_div.build.f_cpu=1000000L +3208.menu.clock.internal_1MHz_div=Internal 1 MHz +3208.menu.clock.internal_1MHz_div.upload.speed=115200 +3208.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_1MHz_div.build.f_cpu=1000000L @@ -392,11 +392,11 @@ menu.resetpin=Reset pin 1609.bootloader.LOCKBIT=0xC5 # Pinouts +1609.menu.pinout.48pin_standard=48 pin standard +1609.menu.pinout.48pin_standard.build.variant=48pin-standard 1609.menu.pinout.uno_wifi=Uno WiFi 1609.menu.pinout.uno_wifi.build.variant=uno-wifi 1609.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE -1609.menu.pinout.48pin_standard=48 pin standard -1609.menu.pinout.48pin_standard.build.variant=48pin-standard # Reset pin 1609.menu.resetpin.reset=Reset @@ -425,35 +425,35 @@ menu.resetpin=Reset pin 1609.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -1609.menu.clock.16MHz=16 MHz -1609.menu.clock.16MHz.upload.speed=115200 -1609.menu.clock.16MHz.bootloader.OSCCFG=0x01 -1609.menu.clock.16MHz.build.f_cpu=16000000L - -1609.menu.clock.20MHz=20 MHz -1609.menu.clock.20MHz.upload.speed=115200 -1609.menu.clock.20MHz.bootloader.OSCCFG=0x02 -1609.menu.clock.20MHz.build.f_cpu=20000000L - -1609.menu.clock.8MHz_div=8 MHz (divided) -1609.menu.clock.8MHz_div.upload.speed=115200 -1609.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.8MHz_div.build.f_cpu=8000000L - -1609.menu.clock.4MHz_div=4 MHz (divided) -1609.menu.clock.4MHz_div.upload.speed=115200 -1609.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.4MHz_div.build.f_cpu=4000000L - -1609.menu.clock.2MHz_div=2 MHz (divided) -1609.menu.clock.2MHz_div.upload.speed=115200 -1609.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.2MHz_div.build.f_cpu=2000000L - -1609.menu.clock.1MHz_div=1 MHz (divided) -1609.menu.clock.1MHz_div.upload.speed=115200 -1609.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.1MHz_div.build.f_cpu=1000000L +1609.menu.clock.internal_16MHz=Internal 16 MHz +1609.menu.clock.internal_16MHz.upload.speed=115200 +1609.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_16MHz.build.f_cpu=16000000L + +1609.menu.clock.internal_20MHz=Internal 20 MHz +1609.menu.clock.internal_20MHz.upload.speed=115200 +1609.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_20MHz.build.f_cpu=20000000L + +1609.menu.clock.internal_8MHz_div=Internal 8 MHz +1609.menu.clock.internal_8MHz_div.upload.speed=115200 +1609.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_8MHz_div.build.f_cpu=8000000L + +1609.menu.clock.internal_4MHz_div=Internal 4 MHz +1609.menu.clock.internal_4MHz_div.upload.speed=115200 +1609.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_4MHz_div.build.f_cpu=4000000L + +1609.menu.clock.internal_2MHz_div=Internal 2 MHz +1609.menu.clock.internal_2MHz_div.upload.speed=115200 +1609.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_2MHz_div.build.f_cpu=2000000L + +1609.menu.clock.internal_1MHz_div=Internal 1 MHz +1609.menu.clock.internal_1MHz_div.upload.speed=115200 +1609.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_1MHz_div.build.f_cpu=1000000L # ATmega328 emulation 1609.menu.emulation.false=No @@ -518,35 +518,35 @@ menu.resetpin=Reset pin 1608.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -1608.menu.clock.16MHz=16 MHz -1608.menu.clock.16MHz.upload.speed=115200 -1608.menu.clock.16MHz.bootloader.OSCCFG=0x01 -1608.menu.clock.16MHz.build.f_cpu=16000000L +1608.menu.clock.internal_16MHz=Internal 16 MHz +1608.menu.clock.internal_16MHz.upload.speed=115200 +1608.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_16MHz.build.f_cpu=16000000L -1608.menu.clock.20MHz=20 MHz -1608.menu.clock.20MHz.upload.speed=115200 -1608.menu.clock.20MHz.bootloader.OSCCFG=0x02 -1608.menu.clock.20MHz.build.f_cpu=20000000L +1608.menu.clock.internal_20MHz=Internal 20 MHz +1608.menu.clock.internal_20MHz.upload.speed=115200 +1608.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_20MHz.build.f_cpu=20000000L -1608.menu.clock.8MHz_div=8 MHz (divided) -1608.menu.clock.8MHz_div.upload.speed=115200 -1608.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.8MHz_div.build.f_cpu=8000000L +1608.menu.clock.internal_8MHz_div=Internal 8 MHz +1608.menu.clock.internal_8MHz_div.upload.speed=115200 +1608.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_8MHz_div.build.f_cpu=8000000L -1608.menu.clock.4MHz_div=4 MHz (divided) -1608.menu.clock.4MHz_div.upload.speed=115200 -1608.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.4MHz_div.build.f_cpu=4000000L +1608.menu.clock.internal_4MHz_div=Internal 4 MHz +1608.menu.clock.internal_4MHz_div.upload.speed=115200 +1608.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_4MHz_div.build.f_cpu=4000000L -1608.menu.clock.2MHz_div=2 MHz (divided) -1608.menu.clock.2MHz_div.upload.speed=115200 -1608.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.2MHz_div.build.f_cpu=2000000L +1608.menu.clock.internal_2MHz_div=Internal 2 MHz +1608.menu.clock.internal_2MHz_div.upload.speed=115200 +1608.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_2MHz_div.build.f_cpu=2000000L -1608.menu.clock.1MHz_div=1 MHz (divided) -1608.menu.clock.1MHz_div.upload.speed=115200 -1608.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.1MHz_div.build.f_cpu=1000000L +1608.menu.clock.internal_1MHz_div=Internal 1 MHz +1608.menu.clock.internal_1MHz_div.upload.speed=115200 +1608.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_1MHz_div.build.f_cpu=1000000L @@ -574,11 +574,11 @@ menu.resetpin=Reset pin 809.bootloader.LOCKBIT=0xC5 # Pinouts +809.menu.pinout.48pin_standard=48 pin standard +809.menu.pinout.48pin_standard.build.variant=48pin-standard 809.menu.pinout.uno_wifi=Uno WiFi 809.menu.pinout.uno_wifi.build.variant=uno-wifi 809.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE -809.menu.pinout.48pin_standard=48 pin standard -809.menu.pinout.48pin_standard.build.variant=48pin-standard # Reset pin 809.menu.resetpin.reset=Reset @@ -607,35 +607,35 @@ menu.resetpin=Reset pin 809.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -809.menu.clock.16MHz=16 MHz -809.menu.clock.16MHz.upload.speed=115200 -809.menu.clock.16MHz.bootloader.OSCCFG=0x01 -809.menu.clock.16MHz.build.f_cpu=16000000L - -809.menu.clock.20MHz=20 MHz -809.menu.clock.20MHz.upload.speed=115200 -809.menu.clock.20MHz.bootloader.OSCCFG=0x02 -809.menu.clock.20MHz.build.f_cpu=20000000L - -809.menu.clock.8MHz_div=8 MHz (divided) -809.menu.clock.8MHz_div.upload.speed=115200 -809.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.8MHz_div.build.f_cpu=8000000L - -809.menu.clock.4MHz_div=4 MHz (divided) -809.menu.clock.4MHz_div.upload.speed=115200 -809.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.4MHz_div.build.f_cpu=4000000L - -809.menu.clock.2MHz_div=2 MHz (divided) -809.menu.clock.2MHz_div.upload.speed=115200 -809.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.2MHz_div.build.f_cpu=2000000L - -809.menu.clock.1MHz_div=1 MHz (divided) -809.menu.clock.1MHz_div.upload.speed=115200 -809.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.1MHz_div.build.f_cpu=1000000L +809.menu.clock.internal_16MHz=Internal 16 MHz +809.menu.clock.internal_16MHz.upload.speed=115200 +809.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_16MHz.build.f_cpu=16000000L + +809.menu.clock.internal_20MHz=Internal 20 MHz +809.menu.clock.internal_20MHz.upload.speed=115200 +809.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +809.menu.clock.internal_20MHz.build.f_cpu=20000000L + +809.menu.clock.internal_8MHz_div=Internal 8 MHz +809.menu.clock.internal_8MHz_div.upload.speed=115200 +809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L + +809.menu.clock.internal_4MHz_div=Internal 4 MHz +809.menu.clock.internal_4MHz_div.upload.speed=115200 +809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L + +809.menu.clock.internal_2MHz_div=Internal 2 MHz +809.menu.clock.internal_2MHz_div.upload.speed=115200 +809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L + +809.menu.clock.internal_1MHz_div=Internal 1 MHz +809.menu.clock.internal_1MHz_div.upload.speed=115200 +809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L # ATmega328 emulation 809.menu.emulation.false=No @@ -700,32 +700,32 @@ menu.resetpin=Reset pin 808.menu.BOD.disabled.bootloader.BODCFG=0x00 # Clock -808.menu.clock.16MHz=16 MHz -808.menu.clock.16MHz.upload.speed=115200 -808.menu.clock.16MHz.bootloader.OSCCFG=0x01 -808.menu.clock.16MHz.build.f_cpu=16000000L - -808.menu.clock.20MHz=20 MHz -808.menu.clock.20MHz.upload.speed=115200 -808.menu.clock.20MHz.bootloader.OSCCFG=0x02 -808.menu.clock.20MHz.build.f_cpu=20000000L - -808.menu.clock.8MHz_div=8 MHz (divided) -808.menu.clock.8MHz_div.upload.speed=115200 -808.menu.clock.8MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.8MHz_div.build.f_cpu=8000000L - -808.menu.clock.4MHz_div=4 MHz (divided) -808.menu.clock.4MHz_div.upload.speed=115200 -808.menu.clock.4MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.4MHz_div.build.f_cpu=4000000L - -808.menu.clock.2MHz_div=2 MHz (divided) -808.menu.clock.2MHz_div.upload.speed=115200 -808.menu.clock.2MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.2MHz_div.build.f_cpu=2000000L - -808.menu.clock.1MHz_div=1 MHz (divided) -808.menu.clock.1MHz_div.upload.speed=115200 -808.menu.clock.1MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.1MHz_div.build.f_cpu=1000000L +808.menu.clock.internal_16MHz=Internal 16 MHz +808.menu.clock.internal_16MHz.upload.speed=115200 +808.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_16MHz.build.f_cpu=16000000L + +808.menu.clock.internal_20MHz=Internal 20 MHz +808.menu.clock.internal_20MHz.upload.speed=115200 +808.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +808.menu.clock.internal_20MHz.build.f_cpu=20000000L + +808.menu.clock.internal_8MHz_div=Internal 8 MHz +808.menu.clock.internal_8MHz_div.upload.speed=115200 +808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L + +808.menu.clock.internal_4MHz_div=Internal 4 MHz +808.menu.clock.internal_4MHz_div.upload.speed=115200 +808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L + +808.menu.clock.internal_2MHz_div=Internal 2 MHz +808.menu.clock.internal_2MHz_div.upload.speed=115200 +808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L + +808.menu.clock.internal_1MHz_div=Internal 1 MHz +808.menu.clock.internal_1MHz_div.upload.speed=115200 +808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L From 4a80924969b27624dcdfce7d6f9acab393f83327 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 11 Sep 2019 00:53:01 +0200 Subject: [PATCH 022/351] Fix unset fuse warning This warning appears only on the microUPDI/mEDBG. No idea why. Closes #32 --- megaavr/boards.txt | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index ed0371a..ee4a249 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -38,7 +38,7 @@ menu.resetpin=Reset pin 4809.menu.resetpin.reset=Reset 4809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 4809.menu.resetpin.gpio=GPIO -4809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +4809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 4809.menu.BOD.2v6=BOD 2.6V @@ -129,9 +129,9 @@ menu.resetpin=Reset pin # Reset pin 4808.menu.resetpin.reset=Reset -4808.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +4808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 4808.menu.resetpin.gpio=GPIO -4808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +4808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 4808.menu.BOD.2v6=BOD 2.6V @@ -218,9 +218,9 @@ menu.resetpin=Reset pin # Reset pin 3209.menu.resetpin.reset=Reset -3209.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +3209.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 3209.menu.resetpin.gpio=GPIO -3209.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +3209.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 3209.menu.BOD.2v6=BOD 2.6V @@ -311,9 +311,9 @@ menu.resetpin=Reset pin # Reset pin 3208.menu.resetpin.reset=Reset -3208.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +3208.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 3208.menu.resetpin.gpio=GPIO -3208.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +3208.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 3208.menu.BOD.2v6=BOD 2.6V @@ -400,9 +400,9 @@ menu.resetpin=Reset pin # Reset pin 1609.menu.resetpin.reset=Reset -1609.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +1609.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 1609.menu.resetpin.gpio=GPIO -1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 1609.menu.BOD.2v6=BOD 2.6V @@ -493,9 +493,9 @@ menu.resetpin=Reset pin # Reset pin 1608.menu.resetpin.reset=Reset -1608.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +1608.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 1608.menu.resetpin.gpio=GPIO -1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 1608.menu.BOD.2v6=BOD 2.6V @@ -582,9 +582,9 @@ menu.resetpin=Reset pin # Reset pin 809.menu.resetpin.reset=Reset -809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +809.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 809.menu.resetpin.gpio=GPIO -809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 809.menu.BOD.2v6=BOD 2.6V @@ -675,9 +675,9 @@ menu.resetpin=Reset pin # Reset pin 808.menu.resetpin.reset=Reset -808.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 808.menu.resetpin.gpio=GPIO -808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 # Brown out detection 808.menu.BOD.2v6=BOD 2.6V From 8cad31dae99fdf6ee27176606bb0fcf7641d668a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 11 Sep 2019 01:00:53 +0200 Subject: [PATCH 023/351] Fix millis timer issue ATmega808/1608/3208/4808 doesn't have TCB3 --- megaavr/variants/28pin-standard/pins_arduino.h | 6 ++++-- megaavr/variants/32pin-standard/pins_arduino.h | 6 ++++-- megaavr/variants/48pin-standard/pins_arduino.h | 2 ++ 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 6b8fbbe..77c7134 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -16,7 +16,7 @@ #include #include "timers.h" -#define DEFAULT_48PIN_PINOUT +#define DEFAULT_28PIN_PINOUT #define NUM_DIGITAL_PINS 23 #define NUM_ANALOG_INPUTS 8 @@ -29,7 +29,9 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB3 +#if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) +#define MILLIS_USE_TIMERB2 +#endif #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 83a05ea..89a79eb 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -16,7 +16,7 @@ #include #include "timers.h" -#define DEFAULT_48PIN_PINOUT +#define DEFAULT_32PIN_PINOUT #define NUM_DIGITAL_PINS 27 #define NUM_ANALOG_INPUTS 12 @@ -29,7 +29,9 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB3 +#if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) +#define MILLIS_USE_TIMERB2 +#endif #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index f23ddaf..85a3260 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -34,7 +34,9 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 22) // The user will have to use A0 - A15, NOT 0 - 15 +#if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) || !defined(MILLIS_USE_TIMERB3) #define MILLIS_USE_TIMERB3 +#endif #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) From b8017c3615590498ac38efb43e4c41c9e4ab6da1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 14:18:58 +0200 Subject: [PATCH 024/351] Fix analog pin related macros and constants the digitalPinToAnalogInput was outright wrong for the 32 and 48 pin standard pinouts. --- megaavr/variants/28pin-standard/pins_arduino.h | 10 ++++++---- megaavr/variants/32pin-standard/pins_arduino.h | 18 ++++++++++++++---- megaavr/variants/48pin-standard/pins_arduino.h | 10 ++++++---- 3 files changed, 26 insertions(+), 12 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 77c7134..bdf5081 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -5,6 +5,8 @@ | COMPATIBLE WITH: | | ATmega4808 | | ATmega3208 | +| ATmega1608 | +| ATmega808 | | | | Note that PWM output pins are swapped by default | | | @@ -20,14 +22,14 @@ #define NUM_DIGITAL_PINS 23 #define NUM_ANALOG_INPUTS 8 -#define NUM_RESERVED_PINS 0 // With great power comes great responsibility -#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 #define NUM_I2C_PINS 2 // (SDA / SCL) #define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 0 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 +#define ANALOG_INPUT_OFFSET 12 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 89a79eb..4ed6ccc 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -5,6 +5,8 @@ | COMPATIBLE WITH: | | ATmega4808 | | ATmega3208 | +| ATmega1608 | +| ATmega808 | | | | Note that PWM output pins are swapped by default | | | @@ -20,14 +22,14 @@ #define NUM_DIGITAL_PINS 27 #define NUM_ANALOG_INPUTS 12 -#define NUM_RESERVED_PINS 0 // With great power comes great responsibility -#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 #define NUM_I2C_PINS 2 // (SDA / SCL) #define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 0 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) // The user will have to use A0 - A15, NOT 0 - 15 +#define ANALOG_INPUT_OFFSET 11 +#define digitalPinToAnalogInput3(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 @@ -121,6 +123,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_A5 (17) #define PIN_A6 (18) #define PIN_A7 (19) +#define PIN_A8 (22) +#define PIN_A9 (23) +#define PIN_A10 (24) +#define PIN_A11 (25) #define PIN_A12 (22) #define PIN_A13 (23) #define PIN_A14 (24) @@ -134,6 +140,10 @@ static const uint8_t A4 = PIN_A4; static const uint8_t A5 = PIN_A5; static const uint8_t A6 = PIN_A6; static const uint8_t A7 = PIN_A7; +static const uint8_t A8 = PIN_A8; +static const uint8_t A9 = PIN_A9; +static const uint8_t A10 = PIN_A10; +static const uint8_t A11 = PIN_A11 static const uint8_t A12 = PIN_A12; static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 85a3260..6715613 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -5,6 +5,8 @@ | COMPATIBLE WITH: | | ATmega4809 | | ATmega3209 | +| ATmega1609 | +| ATmega809 | | | | Note that this pinout is not directly compatible | | with the UNO Wifi Rev2 hardware without performing | @@ -25,14 +27,14 @@ #define NUM_DIGITAL_PINS 41 #define NUM_ANALOG_INPUTS 16 -#define NUM_RESERVED_PINS 0 // With great power comes great responsibility -#define NUM_INTERNALLY_USED_PINS 0 // (2 x Chip select + 2 x UART + 4 x IO + LED_BUILTIN + 1 unused pin) +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 #define NUM_I2C_PINS 2 // (SDA / SCL) #define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 0 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 22) // The user will have to use A0 - A15, NOT 0 - 15 +#define ANALOG_INPUT_OFFSET 22 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= 22 && (p) <= 33) ? ((p) - 22) : ((p) >= 36 && (p) <=39) ? ((p) - 24) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) || !defined(MILLIS_USE_TIMERB3) #define MILLIS_USE_TIMERB3 From f51073953f992884a031140034f8c8308e71f5fc Mon Sep 17 00:00:00 2001 From: Hans Date: Thu, 12 Sep 2019 18:40:06 +0200 Subject: [PATCH 025/351] Change 32-pin pinout We now have analog pins A0 - A11 instead of A0-A7 + A11-15 --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index e0d2bbc..afae1b8 100644 --- a/README.md +++ b/README.md @@ -100,9 +100,9 @@ This core provides several different Arduino pin mappings based on your current Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: -| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | -|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|




















| +| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | +|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +|

|



<



















| ## PWM output From a31231920b5322e063dcf14b940171269d02e062 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 19:44:58 +0200 Subject: [PATCH 026/351] Remove cpu_freq variable wasn't used anyways --- megaavr/cores/coreX-corefiles/wiring.c | 48 ++++---------------------- 1 file changed, 7 insertions(+), 41 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index ef0d24d..05d6074 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -293,58 +293,24 @@ void init() /******************************** CLOCK STUFF *********************************/ - /* We assume 5V operating frequency and FUSE.OSCCFG -> 16MHz */ - - int64_t cpu_freq; - #if (F_CPU == 20000000) - cpu_freq = 20000000; - + #if (F_CPU == 20000000) /* No division on clock */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - - #elif (F_CPU == 16000000) - cpu_freq = 16000000; - + #elif (F_CPU == 16000000) /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - - #elif (F_CPU == 8000000) - cpu_freq = 8000000; - + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); + #elif (F_CPU == 8000000) /* Clock DIV2 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); - - #elif (F_CPU == 4000000) - cpu_freq = 4000000; - + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); + #elif (F_CPU == 4000000) /* Clock DIV4 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); - - #elif (F_CPU == 2000000) - cpu_freq = 2000000; - + #elif (F_CPU == 2000000) /* Clock DIV8 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); - #else - - #ifndef F_CPU - # warning "F_CPU not defined" - #define F_CPU 16000000 - #endif - - # warning "F_CPU defined as an invalid value - may cause undefined behavior" - - /* Default value is 16MHz */ - cpu_freq = 16000000; - - /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); #endif - /* Apply calculated value to F_CPU_CORRECTED */ - F_CPU_CORRECTED = (uint32_t)cpu_freq; - /********************************* ADC ****************************************/ From b3ccee3bc54efb1399b1e81b86e0c63ecdaa3582 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 19:54:41 +0200 Subject: [PATCH 027/351] Move timers.h from variants to core files folder --- .../coreX-corefiles}/timers.h | 0 megaavr/variants/32pin-standard/timers.h | 12 ------------ megaavr/variants/48pin-standard/timers.h | 12 ------------ megaavr/variants/uno-wifi/timers.h | 12 ------------ 4 files changed, 36 deletions(-) rename megaavr/{variants/28pin-standard => cores/coreX-corefiles}/timers.h (100%) delete mode 100644 megaavr/variants/32pin-standard/timers.h delete mode 100644 megaavr/variants/48pin-standard/timers.h delete mode 100644 megaavr/variants/uno-wifi/timers.h diff --git a/megaavr/variants/28pin-standard/timers.h b/megaavr/cores/coreX-corefiles/timers.h similarity index 100% rename from megaavr/variants/28pin-standard/timers.h rename to megaavr/cores/coreX-corefiles/timers.h diff --git a/megaavr/variants/32pin-standard/timers.h b/megaavr/variants/32pin-standard/timers.h deleted file mode 100644 index 438e79f..0000000 --- a/megaavr/variants/32pin-standard/timers.h +++ /dev/null @@ -1,12 +0,0 @@ -#ifndef __TIMERS_H__ -#define __TIMERS_H__ - -#define TIME_TRACKING_TIMER_PERIOD 0xFF -#define TIME_TRACKING_TICKS_PER_OVF (TIME_TRACKING_TIMER_PERIOD + 1) // Timer ticks per overflow of TCB3 -#define TIME_TRACKING_TIMER_DIVIDER 64 // Clock divider for TCB0 -#define TIME_TRACKING_CYCLES_PER_OVF (TIME_TRACKING_TICKS_PER_OVF * TIME_TRACKING_TIMER_DIVIDER) - -#define PWM_TIMER_PERIOD 0xFF // For frequency -#define PWM_TIMER_COMPARE 0x80 // For duty cycle - -#endif \ No newline at end of file diff --git a/megaavr/variants/48pin-standard/timers.h b/megaavr/variants/48pin-standard/timers.h deleted file mode 100644 index 438e79f..0000000 --- a/megaavr/variants/48pin-standard/timers.h +++ /dev/null @@ -1,12 +0,0 @@ -#ifndef __TIMERS_H__ -#define __TIMERS_H__ - -#define TIME_TRACKING_TIMER_PERIOD 0xFF -#define TIME_TRACKING_TICKS_PER_OVF (TIME_TRACKING_TIMER_PERIOD + 1) // Timer ticks per overflow of TCB3 -#define TIME_TRACKING_TIMER_DIVIDER 64 // Clock divider for TCB0 -#define TIME_TRACKING_CYCLES_PER_OVF (TIME_TRACKING_TICKS_PER_OVF * TIME_TRACKING_TIMER_DIVIDER) - -#define PWM_TIMER_PERIOD 0xFF // For frequency -#define PWM_TIMER_COMPARE 0x80 // For duty cycle - -#endif \ No newline at end of file diff --git a/megaavr/variants/uno-wifi/timers.h b/megaavr/variants/uno-wifi/timers.h deleted file mode 100644 index 438e79f..0000000 --- a/megaavr/variants/uno-wifi/timers.h +++ /dev/null @@ -1,12 +0,0 @@ -#ifndef __TIMERS_H__ -#define __TIMERS_H__ - -#define TIME_TRACKING_TIMER_PERIOD 0xFF -#define TIME_TRACKING_TICKS_PER_OVF (TIME_TRACKING_TIMER_PERIOD + 1) // Timer ticks per overflow of TCB3 -#define TIME_TRACKING_TIMER_DIVIDER 64 // Clock divider for TCB0 -#define TIME_TRACKING_CYCLES_PER_OVF (TIME_TRACKING_TICKS_PER_OVF * TIME_TRACKING_TIMER_DIVIDER) - -#define PWM_TIMER_PERIOD 0xFF // For frequency -#define PWM_TIMER_COMPARE 0x80 // For duty cycle - -#endif \ No newline at end of file From 8e0a7f9b31c60e923968b334da02d440585ec7ea Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 20:00:19 +0200 Subject: [PATCH 028/351] Fix analog related macros --- megaavr/cores/coreX-corefiles/Arduino.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 1892a7a..4fba657 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -117,9 +117,9 @@ bool isDoubleBondedActive(uint8_t pin); #define digitalPinToPort(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_port + pin) : NOT_A_PIN ) #define digitalPinToBitPosition(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_bit_position + pin) : NOT_A_PIN ) -#define analogPinToBitPosition(pin) ( (pin < NUM_ANALOG_INPUTS) ? pgm_read_byte(digital_pin_to_bit_position + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) +#define analogPinToBitPosition(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? pgm_read_byte(digital_pin_to_bit_position + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) #define digitalPinToBitMask(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_bit_mask + pin) : NOT_A_PIN ) -#define analogPinToBitMask(pin) ( (pin < NUM_ANALOG_INPUTS) ? pgm_read_byte(digital_pin_to_bit_mask + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) +#define analogPinToBitMask(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? pgm_read_byte(digital_pin_to_bit_mask + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) #define digitalPinToTimer(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_timer + pin) : NOT_ON_TIMER ) #define portToPortStruct(port) ( (port < NUM_TOTAL_PORTS) ? ((PORT_t *)&PORTA + port) : NULL) From 93d09ed53068bb3b495726e218b8aa19003fc3b6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 22:34:13 +0200 Subject: [PATCH 029/351] Fix typos --- megaavr/variants/32pin-standard/pins_arduino.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 4ed6ccc..717fc16 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -29,7 +29,7 @@ #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) #define ANALOG_INPUT_OFFSET 11 -#define digitalPinToAnalogInput3(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) +#define digitalPinToAnalogInput(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 @@ -143,7 +143,7 @@ static const uint8_t A7 = PIN_A7; static const uint8_t A8 = PIN_A8; static const uint8_t A9 = PIN_A9; static const uint8_t A10 = PIN_A10; -static const uint8_t A11 = PIN_A11 +static const uint8_t A11 = PIN_A11; static const uint8_t A12 = PIN_A12; static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; From c4d127972d516da26b462ef9bee6ed543036fcb6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 22:34:33 +0200 Subject: [PATCH 030/351] Add external clock option --- README.md | 11 +- megaavr/boards.txt | 331 +++++++++++++++++++++++-- megaavr/cores/coreX-corefiles/wiring.c | 53 ++-- 3 files changed, 349 insertions(+), 46 deletions(-) diff --git a/README.md b/README.md index afae1b8..df49ca9 100644 --- a/README.md +++ b/README.md @@ -66,9 +66,14 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol | 4 MHz | Internal oscillator | Derived from 16 MHz osc. | | 2 MHz | Internal oscillator | Derived from 16 MHz osc. | | 1 MHz | Internal oscillator | Derived from 16 MHz osc. | - -Note that unlike other AVRs none of these chips are able to drive an external crystal or resonator. If you need an external oscillator it has to be one with a driven clock output. - +| 20 MHz | External clock | | +| 16 MHz | External clock | | +| 12 MHz | External clock | | +| 8 MHz | External clock | | +| 1 MHz | External clock | | + +Note that unlike other AVRs none of these chips are able to drive an external crystal or resonator. If you need an external oscillator it has to be one with a driven clock output. +The microcontroller will freeze if the external clock suddenly drops out. If not present on boot, it will automatically choose the 16 MHz internal oscillator instead. ## BOD option Brown out detection, or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brown out setting. Below is a table that shows the available BOD options: diff --git a/megaavr/boards.txt b/megaavr/boards.txt index ee4a249..b11db88 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -18,6 +18,7 @@ menu.resetpin=Reset pin 4809.build.core=coreX-corefiles 4809.build.board=AVR_ATmega4809 4809.build.mcu=atmega4809 +4809.build.extra_flags={build.oscillator} {build.compat} # Fuses we don't need to modify in the tools menu 4809.bootloader.WDTCFG=0x00 @@ -30,9 +31,10 @@ menu.resetpin=Reset pin # Pinouts 4809.menu.pinout.48pin_standard=40/48 pin standard 4809.menu.pinout.48pin_standard.build.variant=48pin-standard +4809.menu.pinout.48pin_standard.build.compat= 4809.menu.pinout.uno_wifi=Uno WiFi 4809.menu.pinout.uno_wifi.build.variant=uno-wifi -4809.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +4809.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE # Reset pin 4809.menu.resetpin.reset=Reset @@ -64,37 +66,74 @@ menu.resetpin=Reset pin 4809.menu.clock.internal_16MHz=Internal 16 MHz 4809.menu.clock.internal_16MHz.upload.speed=115200 4809.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_16MHz.build.oscillator= 4809.menu.clock.internal_16MHz.build.f_cpu=16000000L 4809.menu.clock.internal_20MHz=Internal 20 MHz 4809.menu.clock.internal_20MHz.upload.speed=115200 4809.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_20MHz.build.oscillator= 4809.menu.clock.internal_20MHz.build.f_cpu=20000000L 4809.menu.clock.internal_8MHz_div=Internal 8 MHz 4809.menu.clock.internal_8MHz_div.upload.speed=115200 4809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_8MHz_div.build.oscillator= 4809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 4809.menu.clock.internal_4MHz_div=Internal 4 MHz 4809.menu.clock.internal_4MHz_div.upload.speed=115200 4809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_4MHz_div.build.oscillator= 4809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 4809.menu.clock.internal_2MHz_div=Internal 2 MHz 4809.menu.clock.internal_2MHz_div.upload.speed=115200 4809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_2MHz_div.build.oscillator= 4809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 4809.menu.clock.internal_1MHz_div=Internal 1 MHz 4809.menu.clock.internal_1MHz_div.upload.speed=115200 4809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_1MHz_div.build.oscillator= 4809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L -# ATmega328 emulation -#4809.menu.emulation.false=No -#4809.menu.emulation.true=Yes -#4809.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE +4809.menu.clock.external_20MHz=External 20 MHz +4809.menu.clock.external_20MHz.upload.speed=115200 +4809.menu.clock.external_20MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_20MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_20MHz.build.f_cpu=20000000L + +4809.menu.clock.external_16MHz=External 16 MHz +4809.menu.clock.external_16MHz.upload.speed=115200 +4809.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_16MHz.build.f_cpu=16000000L + +4809.menu.clock.external_12MHz=External 12 MHz +4809.menu.clock.external_12MHz.upload.speed=115200 +4809.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_12MHz.build.f_cpu=12000000L + +4809.menu.clock.external_8MHz=External 8 MHz +4809.menu.clock.external_8MHz.upload.speed=115200 +4809.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_8MHz.build.f_cpu=8000000L + +4809.menu.clock.external_4MHz=External 4 MHz +4809.menu.clock.external_4MHz.upload.speed=115200 +4809.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_4MHz.build.f_cpu=4000000L + +4809.menu.clock.external_1MHz=External 1 MHz +4809.menu.clock.external_1MHz.upload.speed=115200 +4809.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4809.menu.clock.external_1MHz.build.f_cpu=1000000L @@ -112,6 +151,7 @@ menu.resetpin=Reset pin 4808.build.core=coreX-corefiles 4808.build.board=AVR_ATmega4808 4808.build.mcu=atmega4808 +4808.build.extra_flags={build.oscillator} # Fuses we don't need to modify in the tools menu 4808.bootloader.WDTCFG=0x00 @@ -157,34 +197,68 @@ menu.resetpin=Reset pin 4808.menu.clock.internal_16MHz=Internal 16 MHz 4808.menu.clock.internal_16MHz.upload.speed=115200 4808.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_16MHz.build.oscillator= 4808.menu.clock.internal_16MHz.build.f_cpu=16000000L 4808.menu.clock.internal_20MHz=Internal 20 MHz 4808.menu.clock.internal_20MHz.upload.speed=115200 4808.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_20MHz.build.oscillator= 4808.menu.clock.internal_20MHz.build.f_cpu=20000000L 4808.menu.clock.internal_8MHz_div=Internal 8 MHz 4808.menu.clock.internal_8MHz_div.upload.speed=115200 4808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_8MHz_div.build.oscillator= 4808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 4808.menu.clock.internal_4MHz_div=Internal 4 MHz 4808.menu.clock.internal_4MHz_div.upload.speed=115200 4808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_4MHz_div.build.oscillator= 4808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 4808.menu.clock.internal_2MHz_div=Internal 2 MHz 4808.menu.clock.internal_2MHz_div.upload.speed=115200 4808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_2MHz_div.build.oscillator= 4808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 4808.menu.clock.internal_1MHz_div=Internal 1 MHz 4808.menu.clock.internal_1MHz_div.upload.speed=115200 4808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_1MHz_div.build.oscillator= 4808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L - +4808.menu.clock.external_16MHz=External 16 MHz +4808.menu.clock.external_16MHz.upload.speed=115200 +4808.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4808.menu.clock.external_16MHz.build.f_cpu=16000000L + +4808.menu.clock.external_12MHz=External 12 MHz +4808.menu.clock.external_12MHz.upload.speed=115200 +4808.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4808.menu.clock.external_12MHz.build.f_cpu=12000000L + +4808.menu.clock.external_8MHz=External 8 MHz +4808.menu.clock.external_8MHz.upload.speed=115200 +4808.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4808.menu.clock.external_8MHz.build.f_cpu=8000000L + +4808.menu.clock.external_4MHz=External 4 MHz +4808.menu.clock.external_4MHz.upload.speed=115200 +4808.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4808.menu.clock.external_4MHz.build.f_cpu=4000000L + +4808.menu.clock.external_1MHz=External 1 MHz +4808.menu.clock.external_1MHz.upload.speed=115200 +4808.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +4808.menu.clock.external_1MHz.build.f_cpu=1000000L ##################### #### ATmega3209 #### @@ -200,6 +274,8 @@ menu.resetpin=Reset pin 3209.build.core=coreX-corefiles 3209.build.board=AVR_ATmega3209 3209.build.mcu=atmega3209 +3209.build.extra_flags={build.oscillator} {build.compat} + # Fuses we don't need to modify in the tools menu 3209.bootloader.WDTCFG=0x00 @@ -210,11 +286,13 @@ menu.resetpin=Reset pin 3209.bootloader.LOCKBIT=0xC5 # Pinouts -3209.menu.pinout.48pin_standard=48 pin standard +3209.menu.pinout.48pin_standard=40/48 pin standard 3209.menu.pinout.48pin_standard.build.variant=48pin-standard +3209.menu.pinout.48pin_standard.build.compat= 3209.menu.pinout.uno_wifi=Uno WiFi 3209.menu.pinout.uno_wifi.build.variant=uno-wifi -3209.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +3209.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE + # Reset pin 3209.menu.resetpin.reset=Reset @@ -246,37 +324,68 @@ menu.resetpin=Reset pin 3209.menu.clock.internal_16MHz=Internal 16 MHz 3209.menu.clock.internal_16MHz.upload.speed=115200 3209.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_16MHz.build.oscillator= 3209.menu.clock.internal_16MHz.build.f_cpu=16000000L 3209.menu.clock.internal_20MHz=Internal 20 MHz 3209.menu.clock.internal_20MHz.upload.speed=115200 3209.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_20MHz.build.oscillator= 3209.menu.clock.internal_20MHz.build.f_cpu=20000000L 3209.menu.clock.internal_8MHz_div=Internal 8 MHz 3209.menu.clock.internal_8MHz_div.upload.speed=115200 3209.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_8MHz_div.build.oscillator= 3209.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 3209.menu.clock.internal_4MHz_div=Internal 4 MHz 3209.menu.clock.internal_4MHz_div.upload.speed=115200 3209.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_4MHz_div.build.oscillator= 3209.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 3209.menu.clock.internal_2MHz_div=Internal 2 MHz 3209.menu.clock.internal_2MHz_div.upload.speed=115200 3209.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_2MHz_div.build.oscillator= 3209.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 3209.menu.clock.internal_1MHz_div=Internal 1 MHz 3209.menu.clock.internal_1MHz_div.upload.speed=115200 3209.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_1MHz_div.build.oscillator= 3209.menu.clock.internal_1MHz_div.build.f_cpu=1000000L -# ATmega328 emulation -3209.menu.emulation.false=No -3209.menu.emulation.true=Yes -3209.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE +3209.menu.clock.external_16MHz=External 16 MHz +3209.menu.clock.external_16MHz.upload.speed=115200 +3209.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3209.menu.clock.external_16MHz.build.f_cpu=16000000L + +3209.menu.clock.external_12MHz=External 12 MHz +3209.menu.clock.external_12MHz.upload.speed=115200 +3209.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3209.menu.clock.external_12MHz.build.f_cpu=12000000L + +3209.menu.clock.external_8MHz=External 8 MHz +3209.menu.clock.external_8MHz.upload.speed=115200 +3209.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3209.menu.clock.external_8MHz.build.f_cpu=8000000L + +3209.menu.clock.external_4MHz=External 4 MHz +3209.menu.clock.external_4MHz.upload.speed=115200 +3209.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3209.menu.clock.external_4MHz.build.f_cpu=4000000L + +3209.menu.clock.external_1MHz=External 1 MHz +3209.menu.clock.external_1MHz.upload.speed=115200 +3209.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3209.menu.clock.external_1MHz.build.f_cpu=1000000L @@ -294,6 +403,7 @@ menu.resetpin=Reset pin 3208.build.core=coreX-corefiles 3208.build.board=AVR_ATmega3208 3208.build.mcu=atmega3208 +3208.build.extra_flags={build.oscillator} # Fuses we don't need to modify in the tools menu 3208.bootloader.WDTCFG=0x00 @@ -339,33 +449,69 @@ menu.resetpin=Reset pin 3208.menu.clock.internal_16MHz=Internal 16 MHz 3208.menu.clock.internal_16MHz.upload.speed=115200 3208.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_16MHz.build.oscillator= 3208.menu.clock.internal_16MHz.build.f_cpu=16000000L 3208.menu.clock.internal_20MHz=Internal 20 MHz 3208.menu.clock.internal_20MHz.upload.speed=115200 3208.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_20MHz.build.oscillator= 3208.menu.clock.internal_20MHz.build.f_cpu=20000000L 3208.menu.clock.internal_8MHz_div=Internal 8 MHz 3208.menu.clock.internal_8MHz_div.upload.speed=115200 3208.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_8MHz_div.build.oscillator= 3208.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 3208.menu.clock.internal_4MHz_div=Internal 4 MHz 3208.menu.clock.internal_4MHz_div.upload.speed=115200 3208.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_4MHz_div.build.oscillator= 3208.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 3208.menu.clock.internal_2MHz_div=Internal 2 MHz 3208.menu.clock.internal_2MHz_div.upload.speed=115200 3208.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_2MHz_div.build.oscillator= 3208.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 3208.menu.clock.internal_1MHz_div=Internal 1 MHz 3208.menu.clock.internal_1MHz_div.upload.speed=115200 3208.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_1MHz_div.build.oscillator= 3208.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +3208.menu.clock.external_16MHz=External 16 MHz +3208.menu.clock.external_16MHz.upload.speed=115200 +3208.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3208.menu.clock.external_16MHz.build.f_cpu=16000000L + +3208.menu.clock.external_12MHz=External 12 MHz +3208.menu.clock.external_12MHz.upload.speed=115200 +3208.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3208.menu.clock.external_12MHz.build.f_cpu=12000000L + +3208.menu.clock.external_8MHz=External 8 MHz +3208.menu.clock.external_8MHz.upload.speed=115200 +3208.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3208.menu.clock.external_8MHz.build.f_cpu=8000000L + +3208.menu.clock.external_4MHz=External 4 MHz +3208.menu.clock.external_4MHz.upload.speed=115200 +3208.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3208.menu.clock.external_4MHz.build.f_cpu=4000000L + +3208.menu.clock.external_1MHz=External 1 MHz +3208.menu.clock.external_1MHz.upload.speed=115200 +3208.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +3208.menu.clock.external_1MHz.build.f_cpu=1000000L + ##################### @@ -382,6 +528,7 @@ menu.resetpin=Reset pin 1609.build.core=coreX-corefiles 1609.build.board=AVR_ATmega1609 1609.build.mcu=atmega1609 +1609.build.extra_flags={build.oscillator} {build.compat} # Fuses we don't need to modify in the tools menu 1609.bootloader.WDTCFG=0x00 @@ -392,11 +539,12 @@ menu.resetpin=Reset pin 1609.bootloader.LOCKBIT=0xC5 # Pinouts -1609.menu.pinout.48pin_standard=48 pin standard +1609.menu.pinout.48pin_standard=40/48 pin standard 1609.menu.pinout.48pin_standard.build.variant=48pin-standard +1609.menu.pinout.48pin_standard.build.compat= 1609.menu.pinout.uno_wifi=Uno WiFi 1609.menu.pinout.uno_wifi.build.variant=uno-wifi -1609.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +1609.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE # Reset pin 1609.menu.resetpin.reset=Reset @@ -428,33 +576,69 @@ menu.resetpin=Reset pin 1609.menu.clock.internal_16MHz=Internal 16 MHz 1609.menu.clock.internal_16MHz.upload.speed=115200 1609.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_16MHz.build.oscillator= 1609.menu.clock.internal_16MHz.build.f_cpu=16000000L 1609.menu.clock.internal_20MHz=Internal 20 MHz 1609.menu.clock.internal_20MHz.upload.speed=115200 1609.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_20MHz.build.oscillator= 1609.menu.clock.internal_20MHz.build.f_cpu=20000000L 1609.menu.clock.internal_8MHz_div=Internal 8 MHz 1609.menu.clock.internal_8MHz_div.upload.speed=115200 1609.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_8MHz_div.build.oscillator= 1609.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 1609.menu.clock.internal_4MHz_div=Internal 4 MHz 1609.menu.clock.internal_4MHz_div.upload.speed=115200 1609.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_4MHz_div.build.oscillator= 1609.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 1609.menu.clock.internal_2MHz_div=Internal 2 MHz 1609.menu.clock.internal_2MHz_div.upload.speed=115200 1609.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_2MHz_div.build.oscillator= 1609.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 1609.menu.clock.internal_1MHz_div=Internal 1 MHz 1609.menu.clock.internal_1MHz_div.upload.speed=115200 1609.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_1MHz_div.build.oscillator= 1609.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +1609.menu.clock.external_16MHz=External 16 MHz +1609.menu.clock.external_16MHz.upload.speed=115200 +1609.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1609.menu.clock.external_16MHz.build.f_cpu=16000000L + +1609.menu.clock.external_12MHz=External 12 MHz +1609.menu.clock.external_12MHz.upload.speed=115200 +1609.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1609.menu.clock.external_12MHz.build.f_cpu=12000000L + +1609.menu.clock.external_8MHz=External 8 MHz +1609.menu.clock.external_8MHz.upload.speed=115200 +1609.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1609.menu.clock.external_8MHz.build.f_cpu=8000000L + +1609.menu.clock.external_4MHz=External 4 MHz +1609.menu.clock.external_4MHz.upload.speed=115200 +1609.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1609.menu.clock.external_4MHz.build.f_cpu=4000000L + +1609.menu.clock.external_1MHz=External 1 MHz +1609.menu.clock.external_1MHz.upload.speed=115200 +1609.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1609.menu.clock.external_1MHz.build.f_cpu=1000000L + # ATmega328 emulation 1609.menu.emulation.false=No 1609.menu.emulation.true=Yes @@ -476,6 +660,7 @@ menu.resetpin=Reset pin 1608.build.core=coreX-corefiles 1608.build.board=AVR_ATmega1608 1608.build.mcu=atmega1608 +1608.build.extra_flags={build.oscillator} # Fuses we don't need to modify in the tools menu 1608.bootloader.WDTCFG=0x00 @@ -521,33 +706,69 @@ menu.resetpin=Reset pin 1608.menu.clock.internal_16MHz=Internal 16 MHz 1608.menu.clock.internal_16MHz.upload.speed=115200 1608.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_16MHz.build.oscillator= 1608.menu.clock.internal_16MHz.build.f_cpu=16000000L 1608.menu.clock.internal_20MHz=Internal 20 MHz 1608.menu.clock.internal_20MHz.upload.speed=115200 1608.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_20MHz.build.oscillator= 1608.menu.clock.internal_20MHz.build.f_cpu=20000000L 1608.menu.clock.internal_8MHz_div=Internal 8 MHz 1608.menu.clock.internal_8MHz_div.upload.speed=115200 1608.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_8MHz_div.build.oscillator= 1608.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 1608.menu.clock.internal_4MHz_div=Internal 4 MHz 1608.menu.clock.internal_4MHz_div.upload.speed=115200 1608.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_4MHz_div.build.oscillator= 1608.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 1608.menu.clock.internal_2MHz_div=Internal 2 MHz 1608.menu.clock.internal_2MHz_div.upload.speed=115200 1608.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_2MHz_div.build.oscillator= 1608.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 1608.menu.clock.internal_1MHz_div=Internal 1 MHz 1608.menu.clock.internal_1MHz_div.upload.speed=115200 1608.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_1MHz_div.build.oscillator= 1608.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +1608.menu.clock.external_16MHz=External 16 MHz +1608.menu.clock.external_16MHz.upload.speed=115200 +1608.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1608.menu.clock.external_16MHz.build.f_cpu=16000000L + +1608.menu.clock.external_12MHz=External 12 MHz +1608.menu.clock.external_12MHz.upload.speed=115200 +1608.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1608.menu.clock.external_12MHz.build.f_cpu=12000000L + +1608.menu.clock.external_8MHz=External 8 MHz +1608.menu.clock.external_8MHz.upload.speed=115200 +1608.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1608.menu.clock.external_8MHz.build.f_cpu=8000000L + +1608.menu.clock.external_4MHz=External 4 MHz +1608.menu.clock.external_4MHz.upload.speed=115200 +1608.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1608.menu.clock.external_4MHz.build.f_cpu=4000000L + +1608.menu.clock.external_1MHz=External 1 MHz +1608.menu.clock.external_1MHz.upload.speed=115200 +1608.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +1608.menu.clock.external_1MHz.build.f_cpu=1000000L + ################### @@ -564,6 +785,7 @@ menu.resetpin=Reset pin 809.build.core=coreX-corefiles 809.build.board=AVR_ATmega809 809.build.mcu=atmega809 +809.build.extra_flags={build.oscillator} {build.compat} # Fuses we don't need to modify in the tools menu 809.bootloader.WDTCFG=0x00 @@ -574,11 +796,12 @@ menu.resetpin=Reset pin 809.bootloader.LOCKBIT=0xC5 # Pinouts -809.menu.pinout.48pin_standard=48 pin standard +809.menu.pinout.48pin_standard=40/48 pin standard 809.menu.pinout.48pin_standard.build.variant=48pin-standard +809.menu.pinout.48pin_standard.build.compat= 809.menu.pinout.uno_wifi=Uno WiFi 809.menu.pinout.uno_wifi.build.variant=uno-wifi -809.menu.pinout.uno_wifi.build.extra_flags=-DUNO_WIFI_REV2_328MODE +809.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE # Reset pin 809.menu.resetpin.reset=Reset @@ -610,37 +833,68 @@ menu.resetpin=Reset pin 809.menu.clock.internal_16MHz=Internal 16 MHz 809.menu.clock.internal_16MHz.upload.speed=115200 809.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_16MHz.build.oscillator= 809.menu.clock.internal_16MHz.build.f_cpu=16000000L 809.menu.clock.internal_20MHz=Internal 20 MHz 809.menu.clock.internal_20MHz.upload.speed=115200 809.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +809.menu.clock.internal_20MHz.build.oscillator= 809.menu.clock.internal_20MHz.build.f_cpu=20000000L 809.menu.clock.internal_8MHz_div=Internal 8 MHz 809.menu.clock.internal_8MHz_div.upload.speed=115200 809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_8MHz_div.build.oscillator= 809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 809.menu.clock.internal_4MHz_div=Internal 4 MHz 809.menu.clock.internal_4MHz_div.upload.speed=115200 809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_4MHz_div.build.oscillator= 809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 809.menu.clock.internal_2MHz_div=Internal 2 MHz 809.menu.clock.internal_2MHz_div.upload.speed=115200 809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_2MHz_div.build.oscillator= 809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 809.menu.clock.internal_1MHz_div=Internal 1 MHz 809.menu.clock.internal_1MHz_div.upload.speed=115200 809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +809.menu.clock.internal_1MHz_div.build.oscillator= 809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L -# ATmega328 emulation -809.menu.emulation.false=No -809.menu.emulation.true=Yes -809.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE +809.menu.clock.external_16MHz=External 16 MHz +809.menu.clock.external_16MHz.upload.speed=115200 +809.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +809.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +809.menu.clock.external_16MHz.build.f_cpu=16000000L + +809.menu.clock.external_12MHz=External 12 MHz +809.menu.clock.external_12MHz.upload.speed=115200 +809.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +809.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +809.menu.clock.external_12MHz.build.f_cpu=12000000L + +809.menu.clock.external_8MHz=External 8 MHz +809.menu.clock.external_8MHz.upload.speed=115200 +809.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +809.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +809.menu.clock.external_8MHz.build.f_cpu=8000000L + +809.menu.clock.external_4MHz=External 4 MHz +809.menu.clock.external_4MHz.upload.speed=115200 +809.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +809.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +809.menu.clock.external_4MHz.build.f_cpu=4000000L + +809.menu.clock.external_1MHz=External 1 MHz +809.menu.clock.external_1MHz.upload.speed=115200 +809.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +809.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +809.menu.clock.external_1MHz.build.f_cpu=1000000L @@ -658,6 +912,7 @@ menu.resetpin=Reset pin 808.build.core=coreX-corefiles 808.build.board=AVR_ATmega808 808.build.mcu=atmega808 +808.build.extra_flags={build.oscillator} # Fuses we don't need to modify in the tools menu 808.bootloader.WDTCFG=0x00 @@ -703,29 +958,65 @@ menu.resetpin=Reset pin 808.menu.clock.internal_16MHz=Internal 16 MHz 808.menu.clock.internal_16MHz.upload.speed=115200 808.menu.clock.internal_16MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_16MHz.build.oscillator= 808.menu.clock.internal_16MHz.build.f_cpu=16000000L 808.menu.clock.internal_20MHz=Internal 20 MHz 808.menu.clock.internal_20MHz.upload.speed=115200 808.menu.clock.internal_20MHz.bootloader.OSCCFG=0x02 +808.menu.clock.internal_20MHz.build.oscillator= 808.menu.clock.internal_20MHz.build.f_cpu=20000000L 808.menu.clock.internal_8MHz_div=Internal 8 MHz 808.menu.clock.internal_8MHz_div.upload.speed=115200 808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_8MHz_div.build.oscillator= 808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L 808.menu.clock.internal_4MHz_div=Internal 4 MHz 808.menu.clock.internal_4MHz_div.upload.speed=115200 808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_4MHz_div.build.oscillator= 808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L 808.menu.clock.internal_2MHz_div=Internal 2 MHz 808.menu.clock.internal_2MHz_div.upload.speed=115200 808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_2MHz_div.build.oscillator= 808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L 808.menu.clock.internal_1MHz_div=Internal 1 MHz 808.menu.clock.internal_1MHz_div.upload.speed=115200 808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 +808.menu.clock.internal_1MHz_div.build.oscillator= 808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L + +808.menu.clock.external_16MHz=External 16 MHz +808.menu.clock.external_16MHz.upload.speed=115200 +808.menu.clock.external_16MHz.bootloader.OSCCFG=0x01 +808.menu.clock.external_16MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +808.menu.clock.external_16MHz.build.f_cpu=16000000L + +808.menu.clock.external_12MHz=External 12 MHz +808.menu.clock.external_12MHz.upload.speed=115200 +808.menu.clock.external_12MHz.bootloader.OSCCFG=0x01 +808.menu.clock.external_12MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +808.menu.clock.external_12MHz.build.f_cpu=12000000L + +808.menu.clock.external_8MHz=External 8 MHz +808.menu.clock.external_8MHz.upload.speed=115200 +808.menu.clock.external_8MHz.bootloader.OSCCFG=0x01 +808.menu.clock.external_8MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +808.menu.clock.external_8MHz.build.f_cpu=8000000L + +808.menu.clock.external_4MHz=External 4 MHz +808.menu.clock.external_4MHz.upload.speed=115200 +808.menu.clock.external_4MHz.bootloader.OSCCFG=0x01 +808.menu.clock.external_4MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +808.menu.clock.external_4MHz.build.f_cpu=4000000L + +808.menu.clock.external_1MHz=External 1 MHz +808.menu.clock.external_1MHz.upload.speed=115200 +808.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 +808.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR +808.menu.clock.external_1MHz.build.f_cpu=1000000L diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 05d6074..203060c 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -293,42 +293,49 @@ void init() /******************************** CLOCK STUFF *********************************/ - - #if (F_CPU == 20000000) - /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU == 16000000) - /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU == 8000000) - /* Clock DIV2 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); - #elif (F_CPU == 4000000) - /* Clock DIV4 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); - #elif (F_CPU == 2000000) - /* Clock DIV8 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); + // Use external oscillator if already defined (in boards.txt, platformio.ini) + #if defined(USE_EXTERNAL_OSCILLATOR) + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLA, CLKCTRL_CLKSEL_EXTCLK_gc); + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); // Fallback to 16 MHz internal if no EXTCLK + + // Use internal oscillator if not defined. No need to manipulate the MCLKCTRLA register here + // because it's already done in the SYSCFG0 fuse byte + #else + #if (F_CPU == 20000000L) + /* No division on clock */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); + #elif (F_CPU == 16000000L) + /* No division on clock */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); + #elif (F_CPU == 8000000L) + /* Clock DIV2 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); + #elif (F_CPU == 4000000L) + /* Clock DIV4 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); + #elif (F_CPU == 2000000L) + /* Clock DIV8 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); + #endif #endif - /********************************* ADC ****************************************/ #if defined(ADC0) /* ADC clock between 50-200 kHz */ - #if F_CPU >= 20000000 // 20 MHz / 128 = 156.250 kHz + #if (F_CPU >= 20000000L) // 20 MHz / 128 = 156.250 kHz ADC0.CTRLC |= ADC_PRESC_DIV128_gc; - #elif F_CPU >= 16000000 // 16 MHz / 128 = 125 kHz + #elif (F_CPU >= 16000000L) // 16 MHz / 128 = 125 kHz ADC0.CTRLC |= ADC_PRESC_DIV128_gc; - #elif F_CPU >= 8000000 // 8 MHz / 64 = 125 kHz + #elif (F_CPU >= 8000000L) // 8 MHz / 64 = 125 kHz ADC0.CTRLC |= ADC_PRESC_DIV64_gc; - #elif F_CPU >= 4000000 // 4 MHz / 32 = 125 kHz + #elif (F_CPU >= 4000000L) // 4 MHz / 32 = 125 kHz ADC0.CTRLC |= ADC_PRESC_DIV32_gc; - #elif F_CPU >= 2000000 // 2 MHz / 16 = 125 kHz + #elif (F_CPU >= 2000000L) // 2 MHz / 16 = 125 kHz ADC0.CTRLC |= ADC_PRESC_DIV16_gc; - #elif F_CPU >= 1000000 // 1 MHz / 8 = 125 kHz + #elif (F_CPU >= 1000000L) // 1 MHz / 8 = 125 kHz ADC0.CTRLC |= ADC_PRESC_DIV8_gc; #else // 128 kHz / 2 = 64 kHz -> This is the closest you can get, the prescaler is 2 ADC0.CTRLC |= ADC_PRESC_DIV2_gc; From 6480da146e8b87f5772a7bf3616c97eb2c31c907 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 12 Sep 2019 22:35:03 +0200 Subject: [PATCH 031/351] Add label --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index df49ca9..f5a4b37 100644 --- a/README.md +++ b/README.md @@ -78,7 +78,7 @@ The microcontroller will freeze if the external clock suddenly drops out. If not ## BOD option Brown out detection, or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brown out setting. Below is a table that shows the available BOD options: -| | +| BOD threshold | |--------------------------------| | 4.2 V | | 4.0 V | From ffc607f647206192a6aabf86aa694fc5cbe0e7ac Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 13 Sep 2019 14:29:29 +0200 Subject: [PATCH 032/351] cast BAUD value to uint16_t. No SIGROW correction on external oscillators By casting to uint16_t instead of int16_t we gain some more resolution. More discussion about this in #27 --- megaavr/cores/coreX-corefiles/UART.cpp | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index 6115b99..ef98d56 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -169,16 +169,21 @@ void UartClass::begin(unsigned long baud, uint16_t config) digitalWrite(_hwserial_tx_pin, HIGH); pinMode(_hwserial_tx_pin, OUTPUT); -#if F_CPU == 20000000L - // BUG: should also differentiate between 5V and 3V - int8_t sigrow_val = SIGROW.OSC20ERR5V; -#else - int8_t sigrow_val = SIGROW.OSC16ERR5V; + int8_t sigrow_val = 0; + +// Use error compensation if internal oscillator is used +#if !defined(USE_EXTERNAL_OSCILLATOR) + #if F_CPU == 20000000L + sigrow_val = SIGROW.OSC20ERR5V; + #else + sigrow_val = SIGROW.OSC16ERR5V; + #endif #endif + baud_setting += (baud_setting * sigrow_val) / 1024; // assign the baud_setting, a.k.a. BAUD (USART Baud Rate Register) - (*_hwserial_module).BAUD = (int16_t) baud_setting; + (*_hwserial_module).BAUD = (uint16_t)baud_setting; // Set USART mode of operation (*_hwserial_module).CTRLC = config; From b09bd68c33f91dab861d9bd91b5bf376b31ec150 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 14 Sep 2019 17:33:02 +0200 Subject: [PATCH 033/351] Add minimal setup schematics --- README.md | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index f5a4b37..7ab9d6a 100644 --- a/README.md +++ b/README.md @@ -4,12 +4,10 @@ An Arduino core for the new megaAVR series! **TODO:** * ~~UART pin swap inegraion~~ **DONE! use Serial.swap()** -* ~~Add printf to print class~~ **DONE! use Serial.printf()** * Steal 20 MHz accurate timing from MCUdude_corefiles * SPI pin swap integration in libraries * I2C pin swap integration in libraries * Example (library?) for using the 32.768kHz cystal that can be found on Uno Wifi Rev2 and Curiosity Nano 4809 -* Add ArduinoAPI as subtree for easy maintainance (just need to get some PRs such as printf functionality merged first) * Readme - Need some good intro text at the beginning - Minimal setup schematics @@ -32,6 +30,7 @@ An Arduino core for the new megaAVR series! - [Curiosity Nano](#curiosity-nano) - [AVR-IOT-WG](#avr-iot-wg) - [4809 Xplained Pro](#atmega4809-xplained-pro) +* [Minimal setup](#minimal-setup) ## Supported microcontrollers @@ -154,3 +153,11 @@ Click to enlarge: Click to enlarge: + +## Minimal setup +Here's some simple schematics that shows a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. +Click to enlarge:
+ +| 48-pin (TQFP48) *ATmega809/1609/3209/4809* | 32-pin (TQFP32) *ATmega808/1608/3208/4808* | +|-------------------------------------------------------|-------------------------------------------------------| +||| From fb9672292cfdf753a229f019e08ae35b38cba370 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 14 Sep 2019 22:22:38 +0200 Subject: [PATCH 034/351] Move minimal setup section + add DIP-40 minimal setup --- README.md | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 7ab9d6a..b9b18ee 100644 --- a/README.md +++ b/README.md @@ -25,12 +25,12 @@ An Arduino core for the new megaAVR series! * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) +* [Minimal setup](#minimal-setup) * [Getting your hardware working](#getting-your-hardware-working) - [Arduino Uno WiFi Rev2](#arduino-uno-wifi-rev2) - [Curiosity Nano](#curiosity-nano) - [AVR-IOT-WG](#avr-iot-wg) - [4809 Xplained Pro](#atmega4809-xplained-pro) -* [Minimal setup](#minimal-setup) ## Supported microcontrollers @@ -106,7 +106,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|



<



















| +|

|























| ## PWM output @@ -129,6 +129,14 @@ Click on the "Download ZIP" button. Extract the ZIP file, and move the extracted Open Arduino IDE, and a new category in the boards menu called "MightyCoreX" will show up. +## Minimal setup +Here's some simple schematics that shows a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. +Click to enlarge:
+ +| 48-pin *ATmega809/1609/3209/4809* | 40-pin *ATmega4809* | 32-pin *ATmega808/1608/3208/4808* | +|-------------------------------------------------------|-------------------------------------------------------|-------------------------------------------------------| +|||| + ## Getting your hardware working ### Arduino Uno WiFi Rev2 [The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with, because it's officially supported by Arduino. It uses an ATmega4809, and recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer in order to upload code. For more information about this board please see the product page and its schematic. @@ -153,11 +161,3 @@ Click to enlarge: Click to enlarge: - -## Minimal setup -Here's some simple schematics that shows a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. -Click to enlarge:
- -| 48-pin (TQFP48) *ATmega809/1609/3209/4809* | 32-pin (TQFP32) *ATmega808/1608/3208/4808* | -|-------------------------------------------------------|-------------------------------------------------------| -||| From 5ded48e92912396f858a23d6501304af3d21a061 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 14 Sep 2019 22:48:52 +0200 Subject: [PATCH 035/351] Add accurate delayMicroseconds for 4 and 2 MHz clock --- megaavr/cores/coreX-corefiles/wiring.c | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 203060c..8269b0a 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -261,6 +261,27 @@ void delayMicroseconds(unsigned int us) // us is at least 6 so we can substract 4 us -= 4; // = 2 cycles +#elif F_CPU >= 4000000L + // The overhead of the function call is 14 (16) cycles which is 4 us + if (us <= 2) + return; + + // Subtract microseconds that were wasted in this function + us -= 2; + + // We don't need to multiply here because one request microsecond is exactly one loop cycle + +#elif F_CPU >= 2000000L + // The overhead of the function call is 14 (16) cycles which is 8.68 us + // Plus the if-statement that takes 3 cycles (4 when true): ~11us + if (us <= 13) + return; + + // Subtract microseconds that were wasted in this function + us -= 11; // 2 cycles + + us = (us >> 1); // 3 cycles + #else // for the 1 MHz internal clock (default settings for common Atmega microcontrollers) From e4438ca642fb3629f9d4b624f803d8c3932df599 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 15 Sep 2019 21:00:18 +0200 Subject: [PATCH 036/351] Improve millis/micros for all clocks I'm still having issues with periodic jitter. Didn't have this issue on older AVRs. It may be comiler (optimization + LTO) related, but I'm not sure. Issue #33 still stands though. --- megaavr/cores/coreX-corefiles/wiring.c | 41 +++++++++++++++++--------- 1 file changed, 27 insertions(+), 14 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 8269b0a..aabd389 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -91,9 +91,8 @@ static volatile TCB_t* _timer = m += millis_inc; f += fract_inc; if (f >= FRACT_MAX) { - f -= FRACT_MAX; - m += 1; + m++; } timer_fract = f; @@ -119,32 +118,46 @@ unsigned long millis() return m; } -unsigned long micros() { - unsigned long overflows, microseconds; - uint8_t ticks; +unsigned long micros() { + uint32_t m; + uint8_t t; /* Save current state and disable interrupts */ uint8_t status = SREG; cli(); /* Get current number of overflows and timer count */ - overflows = timer_overflow_count; - ticks = _timer->CNTL; + m = timer_overflow_count; + t = _timer->CNTL; /* If the timer overflow flag is raised, we just missed it, increment to account for it, & read new ticks */ if(_timer->INTFLAGS & TCB_CAPT_bm){ - overflows++; - ticks = _timer->CNTL; + m++; + t = _timer->CNTL; } - /* Restore state */ + // Restore SREG SREG = status; - /* Return microseconds of up time (resets every ~70mins) */ - microseconds = ((overflows * microseconds_per_timer_overflow) - + (ticks * microseconds_per_timer_tick)); - return microseconds; +#if F_CPU >= 24000000L && F_CPU < 32000000L + // m needs to be multiplied by 682.67 + // and t by 2.67 + m = (m << 8) + t; + return (m << 1) + (m >> 1) + (m >> 3) + (m >> 4); // Multiply by 2.6875 +#elif F_CPU == 20000000L + // m needs to be multiplied by 819.2 + // t needs to be multiplied by 3.2 + m = (m << 8) + t; + return m + (m << 1) + (m >> 2) - (m >> 4); // Multiply by 3.1875 +#elif F_CPU == 12000000L + // m needs to be multiplied by 1365.33 + // and t by 5.33 + m = (m << 8) + t; + return m + (m << 2) + (m >> 2) + (m >> 3) - (m >> 4) + (m >> 5); // Multiply by 5.3437 +#else // 16 MHz, 8 MHz, 4 MHz, 2 MHz, 1 MHz + return ((m << 8) + t) * (64 / clockCyclesPerMicrosecond()); +#endif } void delay(unsigned long ms) From 9e15072f26e5aa5011118c4008d4760b65cf178e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 15 Sep 2019 22:39:27 +0200 Subject: [PATCH 037/351] Move UART pins initialization to the very end of begin() This prevents the UART receiver (a USB to serial chip in my case) from receiving garbage characters when the UART port is initialized --- megaavr/cores/coreX-corefiles/UART.cpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index ef98d56..c1d138a 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -162,13 +162,6 @@ void UartClass::begin(unsigned long baud, uint16_t config) _written = false; - //Set up the rx pin - pinMode(_hwserial_rx_pin, INPUT_PULLUP); - - //Set up the tx pin - digitalWrite(_hwserial_tx_pin, HIGH); - pinMode(_hwserial_tx_pin, OUTPUT); - int8_t sigrow_val = 0; // Use error compensation if internal oscillator is used @@ -193,6 +186,13 @@ void UartClass::begin(unsigned long baud, uint16_t config) (*_hwserial_module).CTRLA |= USART_RXCIE_bm; + //Set up the rx pin + pinMode(_hwserial_rx_pin, INPUT_PULLUP); + + //Set up the tx pin + digitalWrite(_hwserial_tx_pin, HIGH); + pinMode(_hwserial_tx_pin, OUTPUT); + // Restore SREG content SREG = oldSREG; } From fe0da95d61ee9f47f7665d9649a065e4ed0158b9 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 16 Sep 2019 10:46:44 +0200 Subject: [PATCH 038/351] Fix interrupt issue Interrupts didn't work on some pins due to the way attachInterrupt is designed. This commit uses the same approach as th official megaavr core does --- megaavr/variants/28pin-standard/pins_arduino.h | 2 +- megaavr/variants/32pin-standard/pins_arduino.h | 2 +- megaavr/variants/48pin-standard/pins_arduino.h | 2 +- megaavr/variants/uno-wifi/pins_arduino.h | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index bdf5081..10f6df7 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -35,7 +35,7 @@ #define MILLIS_USE_TIMERB2 #endif -#define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) +#define EXTERNAL_NUM_INTERRUPTS (47) #define digitalPinHasPWM(p) ((p) >= 8 && (p) <= 11) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 717fc16..79b452f 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -35,7 +35,7 @@ #define MILLIS_USE_TIMERB2 #endif -#define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) +#define EXTERNAL_NUM_INTERRUPTS (47) #define digitalPinHasPWM(p) (((p) >= 8 && (p) <= 11) || (p) == 24 || (p) == 25) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 6715613..0872dd7 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -40,7 +40,7 @@ #define MILLIS_USE_TIMERB3 #endif -#define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) +#define EXTERNAL_NUM_INTERRUPTS (47) #define digitalPinHasPWM(p) (((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index fbdb9d9..021b02e 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -42,7 +42,7 @@ #define MILLIS_USE_TIMERB3 // Use timerb3 for millis generation -#define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) +#define EXTERNAL_NUM_INTERRUPTS (47) #define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10) From 2e99faae89600634e6ab8f12f51d2d2c592f8710 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 16 Sep 2019 11:40:06 +0200 Subject: [PATCH 039/351] Redefine F() as no-op megaAVR 0-series have a unified address space so forcing a const string in flash just increases flash occupation with no benefit on RAM usage. --- megaavr/cores/coreX-corefiles/Arduino.h | 3 +++ 1 file changed, 3 insertions(+) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 4fba657..810608e 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -26,6 +26,9 @@ #include #include +#undef F +#define F(str) (str) + #ifdef __cplusplus extern "C"{ #endif From 2239073562d9d29264e9d23a91fcd04947f200aa Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 16 Sep 2019 12:29:16 +0200 Subject: [PATCH 040/351] Fix Wire endTransmission() return convention --- megaavr/libraries/Wire/src/utility/twi.c | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 71e5d1b..9dc4a7e 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -269,8 +269,11 @@ uint8_t TWI_MasterRead(uint8_t slave_address, * \param bytesToWrite Number of bytes to write. * \param bytesToRead Number of bytes to read. * - * \retval true If transaction could be started. - * \retval false If transaction could not be started. + * \retval 0:success + * \retval 1:data too long to fit in transmit buffer + * \retval 2:received NACK on transmit of address + * \retval 3:received NACK on transmit of data + * \retval 4:other error */ uint8_t TWI_MasterWriteRead(uint8_t slave_address, uint8_t *write_data, @@ -334,8 +337,21 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, // return bytes really read ret = master_bytesRead; } else { - // return 0 if success, >0 otherwise - ret = (master_result == TWIM_RESULT_OK ? 0 : 1); + // return 0 if success, >0 otherwise (follow classic AVR conventions) + switch (master_result) { + case TWIM_RESULT_OK: + ret = 0; + break; + case TWIM_RESULT_BUFFER_OVERFLOW: + ret = 1; + break; + case TWIM_RESULT_NACK_RECEIVED: + ret = 3; + break; + default: + ret = 4; + break; + } } return ret; From ad4fa16ea2852689c8c8d6d72efb6e7108c565a2 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 16 Sep 2019 20:43:16 +0200 Subject: [PATCH 041/351] remove PROGMEM attributes and pgm_read_byte readouts --- megaavr/cores/coreX-corefiles/Arduino.h | 20 +++++++++---------- .../variants/28pin-standard/pins_arduino.h | 8 ++++---- .../variants/32pin-standard/pins_arduino.h | 8 ++++---- .../variants/48pin-standard/pins_arduino.h | 8 ++++---- megaavr/variants/uno-wifi/pins_arduino.h | 8 ++++---- 5 files changed, 26 insertions(+), 26 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 810608e..f8d499c 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -86,10 +86,10 @@ unsigned long microsecondsToClockCycles(unsigned long microseconds); // Get the bit location within the hardware port of the given virtual pin. // This comes from the pins_*.c file for the active board configuration. -extern const uint8_t PROGMEM digital_pin_to_port[]; -extern const uint8_t PROGMEM digital_pin_to_bit_mask[]; -extern const uint8_t PROGMEM digital_pin_to_bit_position[]; -extern const uint8_t PROGMEM digital_pin_to_timer[]; +extern const uint8_t digital_pin_to_port[]; +extern const uint8_t digital_pin_to_bit_mask[]; +extern const uint8_t digital_pin_to_bit_position[]; +extern const uint8_t digital_pin_to_timer[]; // Get the bit location within the hardware port of the given virtual pin. // This comes from the pins_*.c file for the active board configuration. @@ -118,12 +118,12 @@ extern const uint8_t PROGMEM digital_pin_to_timer[]; void setup_timers(); bool isDoubleBondedActive(uint8_t pin); -#define digitalPinToPort(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_port + pin) : NOT_A_PIN ) -#define digitalPinToBitPosition(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_bit_position + pin) : NOT_A_PIN ) -#define analogPinToBitPosition(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? pgm_read_byte(digital_pin_to_bit_position + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) -#define digitalPinToBitMask(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_bit_mask + pin) : NOT_A_PIN ) -#define analogPinToBitMask(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? pgm_read_byte(digital_pin_to_bit_mask + pin + ANALOG_INPUT_OFFSET) : NOT_A_PIN ) -#define digitalPinToTimer(pin) ( (pin < NUM_TOTAL_PINS) ? pgm_read_byte(digital_pin_to_timer + pin) : NOT_ON_TIMER ) +#define digitalPinToPort(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_port[pin] : NOT_A_PIN ) +#define digitalPinToBitPosition(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_bit_position[pin] : NOT_A_PIN ) +#define digitalPinToBitMask(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_bit_mask[pin] : NOT_A_PIN ) +#define digitalPinToTimer(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_timer[pin] : NOT_ON_TIMER ) +#define analogPinToBitPosition(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? digital_pin_to_bit_position[pin + ANALOG_INPUT_OFFSET] : NOT_A_PIN ) +#define analogPinToBitMask(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? digital_pin_to_bit_mask[pin + ANALOG_INPUT_OFFSET] : NOT_A_PIN ) #define portToPortStruct(port) ( (port < NUM_TOTAL_PORTS) ? ((PORT_t *)&PORTA + port) : NULL) #define digitalPinToPortStruct(pin) ( (pin < NUM_TOTAL_PINS) ? ((PORT_t *)&PORTA + digitalPinToPort(pin)) : NULL) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 10f6df7..1de0838 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -137,7 +137,7 @@ static const uint8_t A7 = PIN_A7; #ifdef ARDUINO_MAIN -const uint8_t PROGMEM digital_pin_to_port[] = { +const uint8_t digital_pin_to_port[] = { PA, // 0 PA0/USART0_Tx/CLKIN PA, // 1 PA1/USART0_Rx PA, // 2 PA2/SDA @@ -164,7 +164,7 @@ const uint8_t PROGMEM digital_pin_to_port[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_position[] = { +const uint8_t digital_pin_to_bit_position[] = { PIN0_bp, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bp, // 1 PA1/USART0_Rx PIN2_bp, // 2 PA2/SDA @@ -191,7 +191,7 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_mask[] = { +const uint8_t digital_pin_to_bit_mask[] = { PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bm, // 1 PA1/USART0_Rx PIN2_bm, // 2 PA2/SDA @@ -217,7 +217,7 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN6_bm // 22 PF6 RESET }; -const uint8_t PROGMEM digital_pin_to_timer[] = { +const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx NOT_ON_TIMER, // 2 PA2/SDA diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 79b452f..ba1da79 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -153,7 +153,7 @@ static const uint8_t A15 = PIN_A15; #ifdef ARDUINO_MAIN -const uint8_t PROGMEM digital_pin_to_port[] = { +const uint8_t digital_pin_to_port[] = { PA, // 0 PA0/USART0_Tx/CLKIN PA, // 1 PA1/USART0_Rx PA, // 2 PA2/SDA @@ -184,7 +184,7 @@ const uint8_t PROGMEM digital_pin_to_port[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_position[] = { +const uint8_t digital_pin_to_bit_position[] = { PIN0_bp, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bp, // 1 PA1/USART0_Rx PIN2_bp, // 2 PA2/SDA @@ -215,7 +215,7 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_mask[] = { +const uint8_t digital_pin_to_bit_mask[] = { PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bm, // 1 PA1/USART0_Rx PIN2_bm, // 2 PA2/SDA @@ -245,7 +245,7 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN6_bm // 26 PF6 RESET }; -const uint8_t PROGMEM digital_pin_to_timer[] = { +const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx NOT_ON_TIMER, // 2 PA2/SDA diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 0872dd7..3a98e56 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -172,7 +172,7 @@ static const uint8_t A15 = PIN_A15; #ifdef ARDUINO_MAIN -const uint8_t PROGMEM digital_pin_to_port[] = { +const uint8_t digital_pin_to_port[] = { PA, // 0 PA0/USART0_Tx/CLKIN PA, // 1 PA1/USART0_Rx PA, // 2 PA2/SDA @@ -217,7 +217,7 @@ const uint8_t PROGMEM digital_pin_to_port[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_position[] = { +const uint8_t digital_pin_to_bit_position[] = { PIN0_bp, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bp, // 1 PA1/USART0_Rx PIN2_bp, // 2 PA2/SDA @@ -262,7 +262,7 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_mask[] = { +const uint8_t digital_pin_to_bit_mask[] = { PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN PIN1_bm, // 1 PA1/USART0_Rx PIN2_bm, // 2 PA2/SDA @@ -306,7 +306,7 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; -const uint8_t PROGMEM digital_pin_to_timer[] = { +const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx NOT_ON_TIMER, // 2 PA2/SDA diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 021b02e..0a0924a 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -179,7 +179,7 @@ static const uint8_t A5 = PIN_A5; // -const uint8_t PROGMEM digital_pin_to_port[] = { +const uint8_t digital_pin_to_port[] = { PC, // 0 PC5/USART1_Rx PC, // 1 PC4/USART1_Tx PA, // 2 PA0 @@ -224,7 +224,7 @@ const uint8_t PROGMEM digital_pin_to_port[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_position[] = { +const uint8_t digital_pin_to_bit_position[] = { PIN5_bp, // 0 PC5/USART1_Rx PIN4_bp, // 1 PC4/USART1_Tx PIN0_bp, // 2 PA0 @@ -269,7 +269,7 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { }; /* Use this for accessing PINnCTRL register */ -const uint8_t PROGMEM digital_pin_to_bit_mask[] = { +const uint8_t digital_pin_to_bit_mask[] = { PIN5_bm, // 0 PC5/USART1_Rx PIN4_bm, // 1 PC4/USART1_Tx PIN0_bm, // 2 PA0 @@ -313,7 +313,7 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; -const uint8_t PROGMEM digital_pin_to_timer[] = { +const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PC5/USART1_Rx NOT_ON_TIMER, // 1 PC4/USART1_Tx NOT_ON_TIMER, // 2 PA0 From 88dcabcece3bf3c23f4b4d0c4606500fec5cfd25 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 17 Sep 2019 09:20:43 +0200 Subject: [PATCH 042/351] Fix analogPinToBit* macros analogPinToBitPosition and analogPinToBitMask didn't match the custom pinouts this core provides. Created digitalOrAnalogPinToDigital for each pinout to fix this --- megaavr/cores/coreX-corefiles/Arduino.h | 4 ++-- .../variants/28pin-standard/pins_arduino.h | 21 ++++++++++--------- .../variants/32pin-standard/pins_arduino.h | 21 ++++++++++--------- .../variants/48pin-standard/pins_arduino.h | 21 ++++++++++--------- megaavr/variants/uno-wifi/pins_arduino.h | 21 ++++++++++--------- 5 files changed, 46 insertions(+), 42 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index f8d499c..b7e3955 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -122,8 +122,8 @@ bool isDoubleBondedActive(uint8_t pin); #define digitalPinToBitPosition(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_bit_position[pin] : NOT_A_PIN ) #define digitalPinToBitMask(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_bit_mask[pin] : NOT_A_PIN ) #define digitalPinToTimer(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_timer[pin] : NOT_ON_TIMER ) -#define analogPinToBitPosition(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? digital_pin_to_bit_position[pin + ANALOG_INPUT_OFFSET] : NOT_A_PIN ) -#define analogPinToBitMask(pin) ( (digitalPinToAnalogInput(pin) != NOT_A_PIN) ? digital_pin_to_bit_mask[pin + ANALOG_INPUT_OFFSET] : NOT_A_PIN ) +#define analogPinToBitPosition(pin) ( (digitalOrAnalogPinToDigital(pin) != NOT_A_PIN) ? digital_pin_to_bit_position[digitalOrAnalogPinToDigital(pin)] : NOT_A_PIN ) +#define analogPinToBitMask(pin) ( (digitalOrAnalogPinToDigital(pin) != NOT_A_PIN) ? digital_pin_to_bit_mask[digitalOrAnalogPinToDigital(pin)] : NOT_A_PIN ) #define portToPortStruct(port) ( (port < NUM_TOTAL_PORTS) ? ((PORT_t *)&PORTA + port) : NULL) #define digitalPinToPortStruct(pin) ( (pin < NUM_TOTAL_PINS) ? ((PORT_t *)&PORTA + digitalPinToPort(pin)) : NULL) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 1de0838..601be34 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -20,16 +20,17 @@ #define DEFAULT_28PIN_PINOUT -#define NUM_DIGITAL_PINS 23 -#define NUM_ANALOG_INPUTS 8 -#define NUM_RESERVED_PINS 0 -#define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 12 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) +#define NUM_DIGITAL_PINS 23 +#define NUM_ANALOG_INPUTS 8 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define ANALOG_INPUT_OFFSET 12 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) +#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 12 && (p) <= 19) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index ba1da79..36e8170 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -20,16 +20,17 @@ #define DEFAULT_32PIN_PINOUT -#define NUM_DIGITAL_PINS 27 -#define NUM_ANALOG_INPUTS 12 -#define NUM_RESERVED_PINS 0 -#define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 11 -#define digitalPinToAnalogInput(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) +#define NUM_DIGITAL_PINS 27 +#define NUM_ANALOG_INPUTS 12 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define ANALOG_INPUT_OFFSET 12 +#define digitalPinToAnalogInput(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 8 && (p) <= 11) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 12 && (p) <= 19) || ((p) >= 22 && (p) <= 25)) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 3a98e56..fec378d 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -25,16 +25,17 @@ #define DEFAULT_48PIN_PINOUT -#define NUM_DIGITAL_PINS 41 -#define NUM_ANALOG_INPUTS 16 -#define NUM_RESERVED_PINS 0 -#define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 22 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= 22 && (p) <= 33) ? ((p) - 22) : ((p) >= 36 && (p) <=39) ? ((p) - 24) : NOT_A_PIN) +#define NUM_DIGITAL_PINS 41 +#define NUM_ANALOG_INPUTS 16 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define ANALOG_INPUT_OFFSET 22 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= 22 && (p) <= 33) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= 36 && (p) <=39) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) ((p <= 11) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) <= 15) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 22 && (p) <= 33) || ((p) >= 36 && (p) <= 39)) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) || !defined(MILLIS_USE_TIMERB3) #define MILLIS_USE_TIMERB3 diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 0a0924a..88b086e 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -29,16 +29,17 @@ #define UNO_WIFI_REV2_PINOUT #define UNO2018_PINOUT -#define NUM_DIGITAL_PINS 20 // (14 on digital headers + 6 on analog headers) -#define NUM_ANALOG_INPUTS 6 -#define NUM_RESERVED_PINS 6 // (TOSC1/2, VREF, RESET, DEBUG USART Rx/Tx) -#define NUM_INTERNALLY_USED_PINS 10 // (2 x Chip select + 2 x UART + 4 x IO + LED_BUILTIN + 1 unused pin) -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) -#define ANALOG_INPUT_OFFSET 14 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - ANALOG_INPUT_OFFSET) +#define NUM_DIGITAL_PINS 20 // (14 on digital headers + 6 on analog headers) +#define NUM_ANALOG_INPUTS 6 +#define NUM_RESERVED_PINS 6 // (TOSC1/2, VREF, RESET, DEBUG USART Rx/Tx) +#define NUM_INTERNALLY_USED_PINS 10 // (2 x Chip select + 2 x UART + 4 x IO + LED_BUILTIN + 1 unused pin) +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) +#define ANALOG_INPUT_OFFSET 14 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - ANALOG_INPUT_OFFSET) +#define digitalOrAnalogPinToDigital(p) ((p <= 5) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 14 && (p) <= 19) ? (p) : NOT_A_PIN) #define MILLIS_USE_TIMERB3 // Use timerb3 for millis generation From 8268451a7759c22ca4f43fe5eb99ed49ee321944 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 17 Sep 2019 18:11:38 +0200 Subject: [PATCH 043/351] Changed operator bool to explicit rather than implicit conversion in Serial --- megaavr/cores/coreX-corefiles/UART.h | 2 +- megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.h b/megaavr/cores/coreX-corefiles/UART.h index 66c650d..d4e5043 100644 --- a/megaavr/cores/coreX-corefiles/UART.h +++ b/megaavr/cores/coreX-corefiles/UART.h @@ -168,7 +168,7 @@ class UartClass : public HardwareSerial inline size_t write(unsigned int n) { return write((uint8_t)n); } inline size_t write(int n) { return write((uint8_t)n); } using Print::write; // pull in write(str) and write(buf, size) from Print - operator bool() { return true; } + explicit operator bool() { return true; } // Interrupt handlers - Not intended to be called externally inline void _rx_complete_irq(void); diff --git a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h index b1a37c4..edcf760 100644 --- a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h +++ b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h @@ -103,7 +103,7 @@ class SoftwareSerial : public Stream virtual int read(); virtual int available(); virtual void flush(); - operator bool() { return true; } + explicit operator bool() { return true; } using Print::write; From 1f93a162581bf9c8d3bde27db6627ab801cc5a4f Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 22 Sep 2019 12:46:09 +0200 Subject: [PATCH 044/351] For 48 pin variant, also support PWM output on Arduino pins 12 and 13 --- README.md | 12 ++++++------ megaavr/variants/48pin-standard/pins_arduino.h | 16 ++++++++-------- megaavr/variants/48pin-standard/variant.c | 7 +++++++ 3 files changed, 21 insertions(+), 14 deletions(-) diff --git a/README.md b/README.md index 0cf25a8..9853517 100644 --- a/README.md +++ b/README.md @@ -151,12 +151,12 @@ Available pin swaps for the *Uno WiFi* pinout are: ## PWM output PWM output, `analogWrite()`, is available for the following pins: -| Pinout | Available PWM pins | -|-------------------|-------------------------| -| *28 pin standard* | 8,9,10,11 | -| *32 pin standard* | 8,9,10,11,24,25 | -| *48 pin standard* | 14,15,16,17,18,19,38,39 | -| *Uno WiFi* | 3,5,6,9,10 | +| Pinout | Available PWM pins | +|-------------------|-------------------------------| +| *28 pin standard* | 8,9,10,11 | +| *32 pin standard* | 8,9,10,11,24,25 | +| *48 pin standard* | 12,13,14,15,16,17,18,19,38,39 | +| *Uno WiFi* | 3,5,6,9,10 | ## How to install diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 262d8d0..672bec9 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -181,8 +181,8 @@ const uint8_t PROGMEM digital_pin_to_port[] = { PB, // 9 PB1/USART3_Rx PB, // 10 PB2 PB, // 11 PB3 - PB, // 12 PB4 - PB, // 13 PB5 + PB, // 12 PB4/TCB2 PWM + PB, // 13 PB5/TCB3 PWM PC, // 14 PC0/USART1_Tx/TCA0 PWM PC, // 15 PC1/USART1_Rx/TCA0 PWM PC, // 16 PC2/TCA0 PWM @@ -226,8 +226,8 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { PIN1_bp, // 9 PB1/USART3_Rx PIN2_bp, // 10 PB2 PIN3_bp, // 11 PB3 - PIN4_bp, // 12 PB4 - PIN5_bp, // 13 PB5 + PIN4_bp, // 12 PB4/TCB2 PWM + PIN5_bp, // 13 PB5/TCB2 PWM PIN0_bp, // 14 PC0/USART1_Tx/TCA0 PWM PIN1_bp, // 15 PC1/USART1_Rx/TCA0 PWM PIN2_bp, // 16 PC2/TCA0 PWM @@ -271,8 +271,8 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN1_bm, // 9 PB1/USART3_Rx PIN2_bm, // 10 PB2 PIN3_bm, // 11 PB3 - PIN4_bm, // 12 PB4 - PIN5_bm, // 13 PB5 + PIN4_bm, // 12 PB4/TCB2 PWM + PIN5_bm, // 13 PB5/TCB3 PWM PIN0_bm, // 14 PC0/USART1_Tx/TCA0 PWM PIN1_bm, // 15 PC1/USART1_Rx/TCA0 PWM PIN2_bm, // 16 PC2/TCA0 PWM @@ -315,8 +315,8 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 9 PB1/USART3_Rx NOT_ON_TIMER, // 10 PB2 NOT_ON_TIMER, // 11 PB3 - NOT_ON_TIMER, // 12 PB4 - NOT_ON_TIMER, // 13 PB5 + TIMERB2, // 12 PB4/TCB2 PWM + TIMERB3, // 13 PB5/TCB3 PWM TIMERA0, // 14 PC0/USART1_Tx/TCA0 PWM TIMERA0, // 15 PC1/USART1_Rx/TCA0 PWM TIMERA0, // 16 PC2/TCA0 PWM diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index 5f7e9a8..1f523c6 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -42,6 +42,13 @@ void setup_timers() { PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 #endif + // Setup TCB2 routing + #if defined(TCB2) + PORTMUX.TCBROUTEA |= PORTMUX_TCB2_bm; // Route signal to PB4 instead of PC0 + #endif + + // For TCB3 routing, default B5 is used, alternative is PC1 + // Start with TCB0 TCB_t *timer_B = (TCB_t *)&TCB0; From fe0837b5a6dd75f1d71232ff145116a78dc38453 Mon Sep 17 00:00:00 2001 From: egil Date: Sun, 22 Sep 2019 12:55:19 +0200 Subject: [PATCH 045/351] Save a little bit code --- megaavr/variants/48pin-standard/variant.c | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index 1f523c6..cc5b6e8 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -32,22 +32,19 @@ void setup_timers() { // TYPE B TIMERS - // Setup TCB0 routing + // Set up routing + PORTMUX.TCBROUTEA = 0 #if defined(TCB0) - PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 + | PORTMUX_TCB0_bm // Route signal to PF4 instead of PA2 #endif - - // Setup TCB1 routing #if defined(TCB1) - PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 + | PORTMUX_TCB1_bm // Route signal to PF5 instead of PA3 #endif - - // Setup TCB2 routing #if defined(TCB2) - PORTMUX.TCBROUTEA |= PORTMUX_TCB2_bm; // Route signal to PB4 instead of PC0 + | PORTMUX_TCB2_bm // Route signal to PB4 instead of PC0 #endif - // For TCB3 routing, default B5 is used, alternative is PC1 + ; // Start with TCB0 TCB_t *timer_B = (TCB_t *)&TCB0; From db73134eb36c97040e30adb083f858aaecf5ed84 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 22 Sep 2019 20:22:51 +0200 Subject: [PATCH 046/351] Fix Avrdude path --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index f7c945a..12b2a88 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -91,7 +91,7 @@ recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} { # AVR Uploader/Programmers tools # ------------------------------ -tools.avrdude.path={runtime.tools.avrdude-6.3.0-arduino16.path} +tools.avrdude.path={runtime.tools.avrdude.path} tools.avrdude.cmd.path={path}/bin/avrdude tools.avrdude.config.path={runtime.platform.path}/avrdude.conf From 192ee9810b27a6811688ae830a5ed5177b745ea3 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 10:04:27 +0200 Subject: [PATCH 047/351] We cannot support PWM on the same timer that we use for micros/millis. Also change to TCB2 for standard timer. --- README.md | 12 ++++----- .../variants/48pin-standard/pins_arduino.h | 26 +++++++++++++++---- megaavr/variants/48pin-standard/variant.c | 2 +- 3 files changed, 28 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 9853517..d417b8c 100644 --- a/README.md +++ b/README.md @@ -151,12 +151,12 @@ Available pin swaps for the *Uno WiFi* pinout are: ## PWM output PWM output, `analogWrite()`, is available for the following pins: -| Pinout | Available PWM pins | -|-------------------|-------------------------------| -| *28 pin standard* | 8,9,10,11 | -| *32 pin standard* | 8,9,10,11,24,25 | -| *48 pin standard* | 12,13,14,15,16,17,18,19,38,39 | -| *Uno WiFi* | 3,5,6,9,10 | +| Pinout | Available PWM pins | +|-------------------|----------------------------| +| *28 pin standard* | 8,9,10,11 | +| *32 pin standard* | 8,9,10,11,24,25 | +| *48 pin standard* | 13,14,15,16,17,18,19,38,39 | +| *Uno WiFi* | 3,5,6,9,10 | ## How to install diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 672bec9..8669fef 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -34,7 +34,7 @@ #define ANALOG_INPUT_OFFSET 0 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 22) // The user will have to use A0 - A15, NOT 0 - 15 -#define MILLIS_USE_TIMERB0 // Use timerb0 for millis generation +#define MILLIS_USE_TIMERB2 // Use TCB2 for millis generation #define EXTERNAL_NUM_INTERRUPTS (NUM_TOTAL_PINS) @@ -181,7 +181,7 @@ const uint8_t PROGMEM digital_pin_to_port[] = { PB, // 9 PB1/USART3_Rx PB, // 10 PB2 PB, // 11 PB3 - PB, // 12 PB4/TCB2 PWM + PB, // 12 PB4/(TCB2 PWM) PB, // 13 PB5/TCB3 PWM PC, // 14 PC0/USART1_Tx/TCA0 PWM PC, // 15 PC1/USART1_Rx/TCA0 PWM @@ -226,8 +226,8 @@ const uint8_t PROGMEM digital_pin_to_bit_position[] = { PIN1_bp, // 9 PB1/USART3_Rx PIN2_bp, // 10 PB2 PIN3_bp, // 11 PB3 - PIN4_bp, // 12 PB4/TCB2 PWM - PIN5_bp, // 13 PB5/TCB2 PWM + PIN4_bp, // 12 PB4/(TCB2 PWM) + PIN5_bp, // 13 PB5/TCB3 PWM PIN0_bp, // 14 PC0/USART1_Tx/TCA0 PWM PIN1_bp, // 15 PC1/USART1_Rx/TCA0 PWM PIN2_bp, // 16 PC2/TCA0 PWM @@ -271,7 +271,7 @@ const uint8_t PROGMEM digital_pin_to_bit_mask[] = { PIN1_bm, // 9 PB1/USART3_Rx PIN2_bm, // 10 PB2 PIN3_bm, // 11 PB3 - PIN4_bm, // 12 PB4/TCB2 PWM + PIN4_bm, // 12 PB4/(TCB2 PWM) PIN5_bm, // 13 PB5/TCB3 PWM PIN0_bm, // 14 PC0/USART1_Tx/TCA0 PWM PIN1_bm, // 15 PC1/USART1_Rx/TCA0 PWM @@ -315,8 +315,16 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 9 PB1/USART3_Rx NOT_ON_TIMER, // 10 PB2 NOT_ON_TIMER, // 11 PB3 +#ifdef MILLIS_USE_TIMERB2 + NOT_ON_TIMER, // 12 PB4 +#else TIMERB2, // 12 PB4/TCB2 PWM +#endif +#ifdef MILLIS_USE_TIMERB3 + NOT_ON_TIMER, // 13 PB5 +#else TIMERB3, // 13 PB5/TCB3 PWM +#endif TIMERA0, // 14 PC0/USART1_Tx/TCA0 PWM TIMERA0, // 15 PC1/USART1_Rx/TCA0 PWM TIMERA0, // 16 PC2/TCA0 PWM @@ -341,8 +349,16 @@ const uint8_t PROGMEM digital_pin_to_timer[] = { NOT_ON_TIMER, // 35 PF1/USART2_Rx/TOSC2 NOT_ON_TIMER, // 36 PF2/AIN12 NOT_ON_TIMER, // 37 PF3/AIN13 +#ifdef MILLIS_USE_TIMERB0 + NOT_ON_TIMER, // 38 PF4/AIN14 +#else TIMERB0, // 38 PF4/AIN14/TCB0 PWM +#endif +#ifdef MILLIS_USE_TIMERB1 + NOT_ON_TIMER, // 39 PF5/AIN15/LED_BUILTIN +#else TIMERB1, // 39 PF5/AIN15/TCB1 PWM/LED_BUILTIN +#endif NOT_ON_TIMER // 40 PF6 RESET }; diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index cc5b6e8..7739f4d 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -43,7 +43,7 @@ void setup_timers() { #if defined(TCB2) | PORTMUX_TCB2_bm // Route signal to PB4 instead of PC0 #endif - // For TCB3 routing, default B5 is used, alternative is PC1 + // For TCB3 routing, default PB5 is used, alternative is PC1 ; // Start with TCB0 From 298601ba1c0cf83d1ee26130d7afed0f27a51b9d Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 17:16:58 +0200 Subject: [PATCH 048/351] Substantial rewrite of timer for timing to use a dedicated timer that timeouts exactly every millisecond(). This really improves everything, it simpifies the code a lot, makes the timer much more accurate (micros() will be super accurate) and also makes the timing timer fully independent of the PWM stuff. --- megaavr/cores/coreX-corefiles/Tone.cpp | 3 + megaavr/cores/coreX-corefiles/timers.h | 9 +- megaavr/cores/coreX-corefiles/wiring.c | 119 ++++++------------------- 3 files changed, 36 insertions(+), 95 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Tone.cpp b/megaavr/cores/coreX-corefiles/Tone.cpp index 1102462..4797686 100644 --- a/megaavr/cores/coreX-corefiles/Tone.cpp +++ b/megaavr/cores/coreX-corefiles/Tone.cpp @@ -66,6 +66,9 @@ static volatile TCB_t* _timer = #if defined(USE_TIMERB2) &TCB2; #endif +#if defined(USE_TIMERB3) +&TCB3; +#endif static int _pin = NOT_A_PIN; diff --git a/megaavr/cores/coreX-corefiles/timers.h b/megaavr/cores/coreX-corefiles/timers.h index 438e79f..d31d86b 100644 --- a/megaavr/cores/coreX-corefiles/timers.h +++ b/megaavr/cores/coreX-corefiles/timers.h @@ -1,12 +1,11 @@ #ifndef __TIMERS_H__ #define __TIMERS_H__ -#define TIME_TRACKING_TIMER_PERIOD 0xFF -#define TIME_TRACKING_TICKS_PER_OVF (TIME_TRACKING_TIMER_PERIOD + 1) // Timer ticks per overflow of TCB3 -#define TIME_TRACKING_TIMER_DIVIDER 64 // Clock divider for TCB0 -#define TIME_TRACKING_CYCLES_PER_OVF (TIME_TRACKING_TICKS_PER_OVF * TIME_TRACKING_TIMER_DIVIDER) +// The assumption is that we have a 16 bit timer fully available for timing purposes. +#define TIME_TRACKING_TIMER_DIVIDER 2 // Timer F_CPU Clock divider (can be 1 or 2) +#define TIME_TRACKING_TIMER_COUNT (F_CPU/(1000*TIME_TRACKING_TIMER_DIVIDER)) // Should correspond to exactly 1 ms, i.e. millis() #define PWM_TIMER_PERIOD 0xFF // For frequency #define PWM_TIMER_COMPARE 0x80 // For duty cycle -#endif \ No newline at end of file +#endif diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index aabd389..9dfaed0 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -1,5 +1,5 @@ /* - wiring.c - Partial implementation of the Wiring API for the ATmega8. + wiring.c Part of Arduino - http://www.arduino.cc/ Copyright (c) 2005-2006 David A. Mellis @@ -18,45 +18,20 @@ Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + + Substantially rewritten by Egil Kvaleberg, 23 Sep 2019, to + use a dedicated 16 bit TSB timer for all timing purposes. This + cleans up a lot of things, and makes the code much simpler and + faster. The TCB timers have limitations making it impossible to + use the same timer for both PWM and timing, so this is no loss. + */ #include "wiring_private.h" -// the prescaler is set so that timer ticks every 64 clock cycles, and the -// the overflow handler is called every 256 ticks. -volatile uint16_t microseconds_per_timer_overflow; -volatile uint16_t microseconds_per_timer_tick; - uint32_t F_CPU_CORRECTED = F_CPU; -// the whole number of milliseconds per timer overflow -uint16_t millis_inc; - -// the fractional number of milliseconds per timer overflow -uint16_t fract_inc; -#define FRACT_MAX (1000) - -// whole number of microseconds per timer tick - -volatile uint32_t timer_overflow_count = 0; volatile uint32_t timer_millis = 0; -static uint16_t timer_fract = 0; - -inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk){ - return ( (clk) / 1000000L ); -} - -inline uint16_t clockCyclesPerMicrosecond(){ - return clockCyclesPerMicrosecondComp(F_CPU_CORRECTED); -} - -inline unsigned long clockCyclesToMicroseconds(unsigned long cycles){ - return ( cycles / clockCyclesPerMicrosecond() ); -} - -inline unsigned long microsecondsToClockCycles(unsigned long microseconds){ - return ( microseconds * clockCyclesPerMicrosecond() ); -} static volatile TCB_t* _timer = #if defined(MILLIS_USE_TIMERB0) @@ -65,10 +40,8 @@ static volatile TCB_t* _timer = &TCB1; #elif defined(MILLIS_USE_TIMERB2) &TCB2; -#elif defined(MILLIS_USE_TIMERB3) - &TCB3; -#else - &TCB0; //TCB0 fallback +#else // fallback or defined(MILLIS_USE_TIMERB3) + &TCB3; //TCB3 fallback #endif #if defined(MILLIS_USE_TIMERB0) @@ -77,27 +50,11 @@ static volatile TCB_t* _timer = ISR(TCB1_INT_vect) #elif defined(MILLIS_USE_TIMERB2) ISR(TCB2_INT_vect) -#elif defined(MILLIS_USE_TIMERB3) +#else // fallback or defined(MILLIS_USE_TIMERB3) ISR(TCB3_INT_vect) -#else //TCB0 fallback - ISR(TCB0_INT_vect) #endif { - // copy these to local variables so they can be stored in registers - // (volatile variables must be read from memory on every access) - uint32_t m = timer_millis; - uint16_t f = timer_fract; - - m += millis_inc; - f += fract_inc; - if (f >= FRACT_MAX) { - f -= FRACT_MAX; - m++; - } - - timer_fract = f; - timer_millis = m; - timer_overflow_count++; + timer_millis++; /* Clear flag */ _timer->INTFLAGS = TCB_CAPT_bm; @@ -108,9 +65,10 @@ unsigned long millis() unsigned long m; // disable interrupts while we read timer0_millis or we might get an - // inconsistent value (e.g. in the middle of a write to timer0_millis) + // inconsistent value (e.g. in the middle of a write to timer_millis) uint8_t status = SREG; cli(); + m = timer_millis; SREG = status; @@ -120,44 +78,27 @@ unsigned long millis() unsigned long micros() { uint32_t m; - uint8_t t; + uint16_t t; /* Save current state and disable interrupts */ uint8_t status = SREG; cli(); - /* Get current number of overflows and timer count */ - m = timer_overflow_count; - t = _timer->CNTL; + /* Get current number of millis (i.e. overflows) and timer count */ + m = timer_millis; + t = _timer->CNT; /* If the timer overflow flag is raised, we just missed it, increment to account for it, & read new ticks */ if(_timer->INTFLAGS & TCB_CAPT_bm){ m++; - t = _timer->CNTL; + t = _timer->CNT; } // Restore SREG SREG = status; -#if F_CPU >= 24000000L && F_CPU < 32000000L - // m needs to be multiplied by 682.67 - // and t by 2.67 - m = (m << 8) + t; - return (m << 1) + (m >> 1) + (m >> 3) + (m >> 4); // Multiply by 2.6875 -#elif F_CPU == 20000000L - // m needs to be multiplied by 819.2 - // t needs to be multiplied by 3.2 - m = (m << 8) + t; - return m + (m << 1) + (m >> 2) - (m >> 4); // Multiply by 3.1875 -#elif F_CPU == 12000000L - // m needs to be multiplied by 1365.33 - // and t by 5.33 - m = (m << 8) + t; - return m + (m << 2) + (m >> 2) + (m >> 3) - (m >> 4) + (m >> 5); // Multiply by 5.3437 -#else // 16 MHz, 8 MHz, 4 MHz, 2 MHz, 1 MHz - return ((m << 8) + t) * (64 / clockCyclesPerMicrosecond()); -#endif + return (m * 1000L) + (t / (TIME_TRACKING_TIMER_COUNT / 1000)); } void delay(unsigned long ms) @@ -178,6 +119,7 @@ void delay(unsigned long ms) } /* Delay for the given number of microseconds. Assumes a 1, 8, 12, 16, 20 or 24 MHz clock. */ +// BUG: should really be implemented using _timer instead!!!!!!!!!! void delayMicroseconds(unsigned int us) { // call = 4 cycles + 2 to 4 cycles to init us(2 for constant delay, 4 for variable) @@ -387,22 +329,19 @@ void init() /********************* TCB for system time tracking **************************/ - /* Calculate relevant time tracking values */ - microseconds_per_timer_overflow = clockCyclesToMicroseconds(TIME_TRACKING_CYCLES_PER_OVF); - microseconds_per_timer_tick = microseconds_per_timer_overflow/TIME_TRACKING_TIMER_PERIOD; + // BUG: we can compensate for F_CPU_CORRECTED by fine tuning value of TIME_TRACKING_TIMER_COUNT - millis_inc = microseconds_per_timer_overflow / 1000; - fract_inc = ((microseconds_per_timer_overflow % 1000)); + /* Select vanilla 16 bit periodic interrupt mode */ + _timer->CTRLB = TCB_CNTMODE_INT_gc; - /* Default Periodic Interrupt Mode */ - /* TOP value for overflow every 1024 clock cycles */ - _timer->CCMP = TIME_TRACKING_TIMER_PERIOD; + /* TOP value for overflow every N clock cycles */ + _timer->CCMP = TIME_TRACKING_TIMER_COUNT - 1; /* Enable TCB interrupt */ _timer->INTCTRL |= TCB_CAPT_bm; - /* Clock selection -> same as TCA (F_CPU/64 -- 250kHz) */ - _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; + /* Clock selection is F_CPU/2 -- ~8 MHz -- which is independent of TCA */ + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; /* Enable & start */ _timer->CTRLA |= TCB_ENABLE_bm; /* Keep this last before enabling interrupts to ensure tracking as accurate as possible */ @@ -412,4 +351,4 @@ void init() sei(); } -void setup_timers(void) __attribute__((weak)); \ No newline at end of file +void setup_timers(void) __attribute__((weak)); From 93822b61cd8748fb23329ad961a8ad9ea1cb5a7f Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 17:24:07 +0200 Subject: [PATCH 049/351] Nine PWM pins --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index afc1e26..12fe719 100644 --- a/README.md +++ b/README.md @@ -116,7 +116,7 @@ PWM output, `analogWrite()`, is available for the following pins: |-------------------|--------------------|------------------------------------| | *28 pin standard* | 4 | 8, 9, 10, 11 | | *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | -| *48 pin standard* | 8 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | +| *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | From c8a04adb4f12e2e16d7920d050c1af9eb4e35ac3 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 18:08:45 +0200 Subject: [PATCH 050/351] Re-insert some timing related functions that while they are no longer needed internally, may be used by others. --- megaavr/cores/coreX-corefiles/wiring.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 9dfaed0..5402b6c 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -33,6 +33,22 @@ uint32_t F_CPU_CORRECTED = F_CPU; volatile uint32_t timer_millis = 0; +inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk){ + return ( (clk) / 1000000L ); +} + +inline uint16_t clockCyclesPerMicrosecond(){ + return clockCyclesPerMicrosecondComp(F_CPU_CORRECTED); +} + +inline unsigned long clockCyclesToMicroseconds(unsigned long cycles){ + return ( cycles / clockCyclesPerMicrosecond() ); +} + +inline unsigned long microsecondsToClockCycles(unsigned long microseconds){ + return ( microseconds * clockCyclesPerMicrosecond() ); +} + static volatile TCB_t* _timer = #if defined(MILLIS_USE_TIMERB0) &TCB0; From f2ff1b274ef53e87c2a8c07829f9dd996b7092ed Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 19:03:55 +0200 Subject: [PATCH 051/351] Made function for setting PWM repeat period. Since other Arduino functions seems to relate to microseconds, this function has the repeat period in microseconds as an argument. It will make a best effort to find the best match. void analogWriteRepeat(unsigned int us); --- megaavr/cores/coreX-corefiles/api/Common.h | 3 ++- megaavr/cores/coreX-corefiles/wiring_analog.c | 24 +++++++++++++++++++ 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 302be4c..51a3366 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -106,6 +106,7 @@ PinStatus digitalRead(pin_size_t pinNumber); int analogRead(pin_size_t pinNumber); void analogReference(uint8_t mode); void analogWrite(pin_size_t pinNumber, int value); +void analogWriteRepeat(unsigned int us); unsigned long millis(void); unsigned long micros(void); @@ -147,4 +148,4 @@ long random(long, long); void randomSeed(unsigned long); long map(long, long, long, long, long); -#endif // __cplusplus \ No newline at end of file +#endif // __cplusplus diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 4720523..f720263 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -197,3 +197,27 @@ void analogWrite(uint8_t pin, int val) } } } + +// Set PWM repeat period for all PWM outputs with +// hardware support. +// The argument is the desired period in us. A +// best effort will be made to find something that matches. +// +void analogWriteRepeat(unsigned int us) { + byte index = 0; + static const byte index2setting[] = { + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // 1024 us: ~1 kHz PWM, ~250kHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // 512 us is not possible + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // 256 us: ~4 kHz PWM, ~1MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // 128 us: ~8 kHz PWM, ~2MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // 64 us: ~16 kHz PWM, ~4MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // 32 us: ~32 kHz PWM, ~8MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // 16 us: ~64 kHz PWM, ~16MHz clock + }; + + while (us < 700) { // find approximate match + us *= 2; + if (++index >= sizeof(index2setting) - 1) break; + } + TCA0.SPLIT.CTRLA = index2setting[index]; +} From acad382067a40031f1251172d6b9dc127fd6d9cc Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 19:29:13 +0200 Subject: [PATCH 052/351] It may be more conventional to specify the PWM repeat frequency instead, with 1 as the default value. The new function is analogWriteFrequency(uint8_t kHz) --- README.md | 2 ++ megaavr/cores/coreX-corefiles/api/Common.h | 2 +- megaavr/cores/coreX-corefiles/wiring_analog.c | 26 +++++++++---------- 3 files changed, 16 insertions(+), 14 deletions(-) diff --git a/README.md b/README.md index 12fe719..445d125 100644 --- a/README.md +++ b/README.md @@ -119,6 +119,8 @@ PWM output, `analogWrite()`, is available for the following pins: | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | +The repeat frequency for all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)', where +`kHz' values of 1(default), 4, 8, 16, 32 and 64 are supported. ## How to install #### Boards Manager Installation diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 51a3366..db6feba 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -106,7 +106,7 @@ PinStatus digitalRead(pin_size_t pinNumber); int analogRead(pin_size_t pinNumber); void analogReference(uint8_t mode); void analogWrite(pin_size_t pinNumber, int value); -void analogWriteRepeat(unsigned int us); +void analogWriteFrequency(uint8_t kHz); unsigned long millis(void); unsigned long micros(void); diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index f720263..6c133b6 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -198,25 +198,25 @@ void analogWrite(uint8_t pin, int val) } } -// Set PWM repeat period for all PWM outputs with +// Set PWM repeat frequency for all PWM outputs with // hardware support. -// The argument is the desired period in us. A +// The argument is the desired frequency in kHz. A // best effort will be made to find something that matches. // -void analogWriteRepeat(unsigned int us) { - byte index = 0; +void analogWriteFrequency(uint8_t kHz) { static const byte index2setting[] = { - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // 1024 us: ~1 kHz PWM, ~250kHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // 512 us is not possible - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // 256 us: ~4 kHz PWM, ~1MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // 128 us: ~8 kHz PWM, ~2MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // 64 us: ~16 kHz PWM, ~4MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // 32 us: ~32 kHz PWM, ~8MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // 16 us: ~64 kHz PWM, ~16MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // ~1 kHz PWM, ~250kHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // ~16 kHz PWM, ~4MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // ~32 kHz PWM, ~8MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // ~64 kHz PWM, ~16MHz clock }; + uint8_t index = 0; - while (us < 700) { // find approximate match - us *= 2; + while (kHz > 1) { // find approximate match + kHz >>= 1; if (++index >= sizeof(index2setting) - 1) break; } TCA0.SPLIT.CTRLA = index2setting[index]; From 13aebdfa4202e4b2c9edf9d3a1c48e92c2f1cd98 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 19:47:04 +0200 Subject: [PATCH 053/351] Fix README markup --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 445d125..36245dd 100644 --- a/README.md +++ b/README.md @@ -119,8 +119,8 @@ PWM output, `analogWrite()`, is available for the following pins: | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | -The repeat frequency for all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)', where -`kHz' values of 1(default), 4, 8, 16, 32 and 64 are supported. +The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where +`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. ## How to install #### Boards Manager Installation From 828c6114d2a180f5cb4dcb649e4e4944653a47b1 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 22:29:04 +0200 Subject: [PATCH 054/351] Increase timer speed to full CPU clock to facilitate 1 MHz CPU clock. Also try to maintain PWM at around 1 kHz. BEWARE: This code is not tested --- megaavr/cores/coreX-corefiles/timers.h | 2 +- megaavr/cores/coreX-corefiles/wiring.c | 10 ++++++++-- megaavr/variants/28pin-standard/variant.c | 11 +++++++++++ megaavr/variants/32pin-standard/variant.c | 11 +++++++++++ megaavr/variants/48pin-standard/variant.c | 11 +++++++++++ megaavr/variants/uno-wifi/variant.c | 11 +++++++++++ 6 files changed, 53 insertions(+), 3 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/timers.h b/megaavr/cores/coreX-corefiles/timers.h index d31d86b..5030896 100644 --- a/megaavr/cores/coreX-corefiles/timers.h +++ b/megaavr/cores/coreX-corefiles/timers.h @@ -2,7 +2,7 @@ #define __TIMERS_H__ // The assumption is that we have a 16 bit timer fully available for timing purposes. -#define TIME_TRACKING_TIMER_DIVIDER 2 // Timer F_CPU Clock divider (can be 1 or 2) +#define TIME_TRACKING_TIMER_DIVIDER 1 // Timer F_CPU Clock divider (can be 1 or 2) #define TIME_TRACKING_TIMER_COUNT (F_CPU/(1000*TIME_TRACKING_TIMER_DIVIDER)) // Should correspond to exactly 1 ms, i.e. millis() #define PWM_TIMER_PERIOD 0xFF // For frequency diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 5402b6c..23574a1 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -356,8 +356,14 @@ void init() /* Enable TCB interrupt */ _timer->INTCTRL |= TCB_CAPT_bm; - /* Clock selection is F_CPU/2 -- ~8 MHz -- which is independent of TCA */ - _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; + /* Clock selection is F_CPU/N -- which is independent of TCA */ +#if TIME_TRACKING_TIMER_DIVIDER==1 + _timer->CTRLA = TCB_CLKSEL_CLKDIV1_gc; /* F_CPU */ +#elif TIME_TRACKING_TIMER_DIVIDER==2 + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; /* F_CPU/2 */ +#else +#assert "TIME_TRACKING_TIMER_DIVIDER not supported" +#endif /* Enable & start */ _timer->CTRLA |= TCB_ENABLE_bm; /* Keep this last before enabling interrupts to ensure tracking as accurate as possible */ diff --git a/megaavr/variants/28pin-standard/variant.c b/megaavr/variants/28pin-standard/variant.c index ec4c3f2..be4d73c 100644 --- a/megaavr/variants/28pin-standard/variant.c +++ b/megaavr/variants/28pin-standard/variant.c @@ -27,8 +27,19 @@ void setup_timers() { TCA0.SPLIT.HCMP1 = TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 4000000L + // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif // TYPE B TIMERS diff --git a/megaavr/variants/32pin-standard/variant.c b/megaavr/variants/32pin-standard/variant.c index ec4c3f2..be4d73c 100644 --- a/megaavr/variants/32pin-standard/variant.c +++ b/megaavr/variants/32pin-standard/variant.c @@ -27,8 +27,19 @@ void setup_timers() { TCA0.SPLIT.HCMP1 = TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 4000000L + // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif // TYPE B TIMERS diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index 7739f4d..1cd04e1 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -27,8 +27,19 @@ void setup_timers() { TCA0.SPLIT.HCMP1 = TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 4000000L + // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif // TYPE B TIMERS diff --git a/megaavr/variants/uno-wifi/variant.c b/megaavr/variants/uno-wifi/variant.c index d185de7..0b8123b 100644 --- a/megaavr/variants/uno-wifi/variant.c +++ b/megaavr/variants/uno-wifi/variant.c @@ -27,8 +27,19 @@ void setup_timers() { TCA0.SPLIT.HCMP1 = TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 4000000L + // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif // TYPE B TIMERS From 147eebd7048e6b63ddfb46e4b61fd8e057c6ba6f Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 23:00:29 +0200 Subject: [PATCH 055/351] Make analogWriteFrequency() adapt to the actual F_CPU frequency in a more meaningful way. --- README.md | 3 ++- megaavr/cores/coreX-corefiles/wiring_analog.c | 8 ++++++++ 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 36245dd..2ffa297 100644 --- a/README.md +++ b/README.md @@ -120,7 +120,8 @@ PWM output, `analogWrite()`, is available for the following pins: | *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where -`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. +`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within +the constraints of the hardware will be made to match the request. ## How to install #### Boards Manager Installation diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 6c133b6..72e068c 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -205,10 +205,18 @@ void analogWrite(uint8_t pin, int val) // void analogWriteFrequency(uint8_t kHz) { static const byte index2setting[] = { +#if F_CPU > 8000000L TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // ~1 kHz PWM, ~250kHz clock +#if F_CPU > 4000000L TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 +#if F_CPU > 2000000L TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock +#if F_CPU > 1000000L TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock +#endif +#endif +#endif +#endif TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // ~16 kHz PWM, ~4MHz clock TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // ~32 kHz PWM, ~8MHz clock TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // ~64 kHz PWM, ~16MHz clock From 4620ac847af20f324ee3a818141d610575bdb00c Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 23:22:09 +0200 Subject: [PATCH 056/351] Support 1MHz internal CPU clock --- megaavr/cores/coreX-corefiles/wiring.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 23574a1..930cc16 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -296,18 +296,23 @@ void init() #if (F_CPU == 20000000L) /* No division on clock */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU == 16000000L) + #elif (F_CPU >= 16000000L) /* No division on clock */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU == 8000000L) + #elif (F_CPU >= 8000000L) /* Clock DIV2 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); - #elif (F_CPU == 4000000L) + #elif (F_CPU >= 4000000L) /* Clock DIV4 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); - #elif (F_CPU == 2000000L) + #elif (F_CPU >= 2000000L) /* Clock DIV8 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); + #elif (F_CPU >= 1000000L) + /* Clock DIV16 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_16X_gc)); + #else + #assert "This internal CPU clock is not supported" #endif #endif From 423eec4906aa145d5bb6ae7fd35882e9a2b760ea Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 23:48:53 +0200 Subject: [PATCH 057/351] Default to 2 kHz PWM for 8 MHz CPU clock. 1 kHz is not possible since a suitable scale factor is not available. --- megaavr/variants/28pin-standard/variant.c | 2 +- megaavr/variants/32pin-standard/variant.c | 2 +- megaavr/variants/48pin-standard/variant.c | 10 +++++----- megaavr/variants/uno-wifi/variant.c | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/megaavr/variants/28pin-standard/variant.c b/megaavr/variants/28pin-standard/variant.c index be4d73c..175cf87 100644 --- a/megaavr/variants/28pin-standard/variant.c +++ b/megaavr/variants/28pin-standard/variant.c @@ -33,7 +33,7 @@ void setup_timers() { #elif F_CPU <= 2000000L // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 4000000L +#elif F_CPU <= 8000000L // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); #else diff --git a/megaavr/variants/32pin-standard/variant.c b/megaavr/variants/32pin-standard/variant.c index be4d73c..175cf87 100644 --- a/megaavr/variants/32pin-standard/variant.c +++ b/megaavr/variants/32pin-standard/variant.c @@ -33,7 +33,7 @@ void setup_timers() { #elif F_CPU <= 2000000L // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 4000000L +#elif F_CPU <= 8000000L // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); #else diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index 1cd04e1..c3c577e 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -28,16 +28,16 @@ void setup_timers() { TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; #if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + // Use DIV4 prescaler (giving 250kHz clock on 1MHz), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); #elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + // Use DIV8 prescaler (giving 250kHz clock on 2MHz), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 4000000L - // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer +#elif F_CPU <= 8000000L + // Use DIV16 prescaler (giving 250kHz clocke on 4MHz, 500kHz clock on 8MHz), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); #else - // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer + // Use DIV64 prescaler (giving 250kHz clock on 16MHz), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); #endif diff --git a/megaavr/variants/uno-wifi/variant.c b/megaavr/variants/uno-wifi/variant.c index 0b8123b..e738e81 100644 --- a/megaavr/variants/uno-wifi/variant.c +++ b/megaavr/variants/uno-wifi/variant.c @@ -33,7 +33,7 @@ void setup_timers() { #elif F_CPU <= 2000000L // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 4000000L +#elif F_CPU <= 8000000L // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); #else From 88b11219949b4c602d70b7bdcf590632c5046446 Mon Sep 17 00:00:00 2001 From: egil Date: Mon, 23 Sep 2019 23:53:48 +0200 Subject: [PATCH 058/351] Fix for problem that analogWriteFrequency(1); did not work for intermediate frequecies. --- megaavr/cores/coreX-corefiles/wiring_analog.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 72e068c..76f4717 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -205,17 +205,17 @@ void analogWrite(uint8_t pin, int val) // void analogWriteFrequency(uint8_t kHz) { static const byte index2setting[] = { +#if F_CPU > 1000000L +#if F_CPU > 2000000L +#if F_CPU > 4000000L #if F_CPU > 8000000L TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // ~1 kHz PWM, ~250kHz clock -#if F_CPU > 4000000L - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 -#if F_CPU > 2000000L - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock -#if F_CPU > 1000000L - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock #endif + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 #endif + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock #endif + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock #endif TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // ~16 kHz PWM, ~4MHz clock TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // ~32 kHz PWM, ~8MHz clock From 14298b29f7029d4c7455f84ecf7f1b17009ef3bb Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 24 Sep 2019 10:06:42 +0200 Subject: [PATCH 059/351] Do some housekeeping and cleanup on timer B defintions. Plus offer an extra PWM pin on the Uno. --- README.md | 2 +- megaavr/variants/28pin-standard/pins_arduino.h | 2 +- megaavr/variants/32pin-standard/pins_arduino.h | 2 +- megaavr/variants/48pin-standard/pins_arduino.h | 10 +++++++++- megaavr/variants/uno-wifi/pins_arduino.h | 6 +++++- 5 files changed, 17 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 2ffa297..c531430 100644 --- a/README.md +++ b/README.md @@ -117,7 +117,7 @@ PWM output, `analogWrite()`, is available for the following pins: | *28 pin standard* | 4 | 8, 9, 10, 11 | | *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | -| *Uno WiFi* | 5 | 3, 5, 6, 9, 10 | +| *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where `kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 601be34..81c0154 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -33,7 +33,7 @@ #define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 12 && (p) <= 19) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) -#define MILLIS_USE_TIMERB2 +#define MILLIS_USE_TIMERB2 // use TCB2 #endif #define EXTERNAL_NUM_INTERRUPTS (47) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 36e8170..dccb132 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -33,7 +33,7 @@ #define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 8 && (p) <= 11) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 12 && (p) <= 19) || ((p) >= 22 && (p) <= 25)) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) -#define MILLIS_USE_TIMERB2 +#define MILLIS_USE_TIMERB2 // use TCB2 #endif #define EXTERNAL_NUM_INTERRUPTS (47) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 77da59e..b793e9b 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -43,7 +43,15 @@ #define EXTERNAL_NUM_INTERRUPTS (47) -#define digitalPinHasPWM(p) (((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) +#if defined(MILLIS_USE_TIMERB0) + #define digitalPinHasPWM(p) (((p) >= 12 && (p) <= 19) || (p) == 39) +#elif defined(MILLIS_USE_TIMERB1) + #define digitalPinHasPWM(p) (((p) >= 12 && (p) <= 19) || (p) == 38) +#elif defined(MILLIS_USE_TIMERB2) + #define digitalPinHasPWM(p) (((p) >= 13 && (p) <= 19) || (p) == 38 || (p) == 39) +#else // default to MILLIS_USE_TIMERB3 + #define digitalPinHasPWM(p) ((p) == 12 || ((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) +#endif // SPI 0 // No pinswap enabled by default diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 88b086e..5b99117 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -41,7 +41,7 @@ #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - ANALOG_INPUT_OFFSET) #define digitalOrAnalogPinToDigital(p) ((p <= 5) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 14 && (p) <= 19) ? (p) : NOT_A_PIN) -#define MILLIS_USE_TIMERB3 // Use timerb3 for millis generation +#define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation #define EXTERNAL_NUM_INTERRUPTS (47) @@ -342,7 +342,11 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 24 PA4/NINA RX NOT_ON_TIMER, // 25 PD6/LED_BUILTIN NOT_ON_TIMER, // 26 PB5/USART3_Rx +#ifdef MILLIS_USE_TIMERB2 NOT_ON_TIMER, // 27 PB4/USART3_Tx +#else + TIMERB2, // 27 PB4/USART3_Tx/TCB2 PWM +#endif NOT_ON_TIMER, // 28 PA6/NINA GPIO0 NOT_ON_TIMER, // 29 PA7/NINA RST NOT_ON_TIMER, // 30 PB3/IMU CS From ad88b02182a56c092a81435529639f9b876b489d Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 24 Sep 2019 11:06:04 +0200 Subject: [PATCH 060/351] Do the necessary changes to tone() so that it now works with the new analogWriteFrequency() function. --- .gitignore | 1 + megaavr/cores/coreX-corefiles/Tone.cpp | 52 ++++++++++++++----- megaavr/cores/coreX-corefiles/wiring_analog.c | 2 + 3 files changed, 41 insertions(+), 14 deletions(-) diff --git a/.gitignore b/.gitignore index e43b0f9..538c8c5 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ .DS_Store +*~ diff --git a/megaavr/cores/coreX-corefiles/Tone.cpp b/megaavr/cores/coreX-corefiles/Tone.cpp index 4797686..42353cf 100644 --- a/megaavr/cores/coreX-corefiles/Tone.cpp +++ b/megaavr/cores/coreX-corefiles/Tone.cpp @@ -44,17 +44,17 @@ */ #define AVAILABLE_TONE_PINS 1 -#define USE_TIMERB1 // interferes with PWM on pin 3 +#define USE_TIMERB1 // interferes with TCB1 PWM /* -#define USE_TIMERB2 // interferes with PWM on pin 11 -#define USE_TIMERB0 // interferes with PWM on pin 6 +#define USE_TIMERB2 // interferes with TCB2 PWM, and timer in many configurations +#define USE_TIMERB0 // interferes with TCB0 PWM */ -#if !defined(USE_TIMERB1) && !defined(USE_TIMERB2) && !defined(USE_TIMERB0) +#if !defined(USE_TIMERB0) && !defined(USE_TIMERB1) && !defined(USE_TIMERB2) && !defined(USE_TIMERB3) # error "No timers allowed for tone()" /* Please uncomment a timer above and rebuild */ #endif -// Can't use TIMERB3 -- used for application time tracking +// Can't use timer assigned for application time tracking (usually TIMERB2 or TIMERB3) // Using TIMERA0 NOT RECOMMENDED -- all other timers use its clock! static volatile TCB_t* _timer = #if defined(USE_TIMERB0) @@ -83,6 +83,7 @@ volatile uint8_t timer_bit_mask; // helper functions static void disableTimer(); +static byte timerPrescaler(); // frequency (in hertz) and duration (in milliseconds). void tone(uint8_t pin, unsigned int frequency, unsigned long duration) @@ -105,14 +106,15 @@ void tone(uint8_t pin, unsigned int frequency, unsigned long duration) frequency = 1; } - // Calculate compare value - compare_val = F_CPU_CORRECTED / frequency / 2 - 1; + // Calculate compare value, assuming F_CPU/2 used as clock + compare_val = F_CPU_CORRECTED / frequency / 4 - 1; // If compare larger than 16bits, need to prescale (will be DIV64) - uint8_t prescaler_needed = 0; + uint8_t prescaler = 0; if (compare_val > 0xFFFF){ - // recalculate with new prescaler - compare_val = F_CPU_CORRECTED / frequency / 2 / 64 - 1; - prescaler_needed = 1; + // recalculate with new prescaler + prescaler = timerPrescaler(); + compare_val = F_CPU_CORRECTED / frequency / 2 / prescaler - 1; + if (compare_val > 0xFFFF) compare_val = 0xFFFF; // request lower frequency than supported } // Calculate the toggle count @@ -126,14 +128,15 @@ void tone(uint8_t pin, unsigned int frequency, unsigned long duration) uint8_t status = SREG; cli(); - // Disable for now, set clk according to 'prescaler_needed' + // Disable for now, set clk according to whether 'prescaler' is zero // (Prescaled clock will come from TCA -- // by default it should have a prescaler of 64 (250kHz clock) + // but this may have changed with analogWriteFrequency() // TCA default initialization is in wiring.c -- init() ) - if(prescaler_needed){ + if(prescaler != 0){ _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; } else { - _timer->CTRLA = TCB_CLKSEL_CLKDIV1_gc; + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; } // Timer to Periodic interrupt mode @@ -168,6 +171,27 @@ void noTone(uint8_t pin) } } +// helper function for noTone() +// find which timer prescaler is currently used +static byte timerPrescaler() +{ + byte clksel = (TCA0.SPLIT.CTRLA & TCA_SPLIT_CLKSEL_gm) >> TCA_SPLIT_CLKSEL_gp; + + // the next five lines may have been a #if, + // but alas the C preprocessor does not understand enums + // they should produce no real code, though + if ((TCA_SPLIT_CLKSEL_DIV1_gc>>TCA_SPLIT_CLKSEL_gp) == 0 + && (TCA_SPLIT_CLKSEL_DIV2_gc>>TCA_SPLIT_CLKSEL_gp) == 1 + && (TCA_SPLIT_CLKSEL_DIV4_gc>>TCA_SPLIT_CLKSEL_gp) == 2 + && (TCA_SPLIT_CLKSEL_DIV8_gc>>TCA_SPLIT_CLKSEL_gp) == 3 + && (TCA_SPLIT_CLKSEL_DIV16_gc>>TCA_SPLIT_CLKSEL_gp) == 4 + && clksel <= (TCA_SPLIT_CLKSEL_DIV16_gc>>TCA_SPLIT_CLKSEL_gp)) { + // non-standard TCA clock selection is used + return 1 << clksel; + } + return 64; +} + // helper function for noTone() /* Works for all timers -- the timer being disabled will go back to the configuration it had to output PWM for analogWrite() */ diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 76f4717..d9a0cf3 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -228,4 +228,6 @@ void analogWriteFrequency(uint8_t kHz) { if (++index >= sizeof(index2setting) - 1) break; } TCA0.SPLIT.CTRLA = index2setting[index]; + + // note that this setting also influences Tone.cpp } From 9df76727eda53daf77ef8c57a34e877d58cc490c Mon Sep 17 00:00:00 2001 From: egil Date: Tue, 24 Sep 2019 11:10:22 +0200 Subject: [PATCH 061/351] Add note about interference between tone() and PWM. --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index c531430..375475c 100644 --- a/README.md +++ b/README.md @@ -123,6 +123,8 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n `kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within the constraints of the hardware will be made to match the request. +Note also that tone() will use TCB1 so the corresponding PWM output is not available if it is used. + ## How to install #### Boards Manager Installation *Not yet implemented* From 01ac1f3920a4c21db187ad9d49f54c06857ec559 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 24 Sep 2019 22:14:36 +0200 Subject: [PATCH 062/351] Update Readme New pinout pics + remove some text --- README.md | 16 ++++++---------- 1 file changed, 6 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 375475c..63903e8 100644 --- a/README.md +++ b/README.md @@ -3,15 +3,10 @@ An Arduino core for the new megaAVR series! **TODO:** -* ~~UART pin swap inegraion~~ **DONE! use Serial.swap()** -* Steal 20 MHz accurate timing from MCUdude_corefiles * SPI pin swap integration in libraries * I2C pin swap integration in libraries -* Example (library?) for using the 32.768kHz cystal that can be found on Uno Wifi Rev2 and Curiosity Nano 4809 * Readme - Need some good intro text at the beginning - - Minimal setup schematics -* Proper testing with updated toolchain (I'm experiencing trouble with the 32kB chips) # Table of contents @@ -32,6 +27,7 @@ An Arduino core for the new megaAVR series! - [AVR-IOT-WG](#avr-iot-wg) - [4809 Xplained Pro](#atmega4809-xplained-pro) + ## Supported microcontrollers | | ATmega4809 | ATmega4808 | ATmega3209 | ATmega3208 | ATmega1609 | ATmega1608 | ATmega809 | ATmega808 | @@ -106,7 +102,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## PWM output @@ -123,7 +119,7 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n `kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within the constraints of the hardware will be made to match the request. -Note also that tone() will use TCB1 so the corresponding PWM output is not available if it is used. +Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. ## How to install #### Boards Manager Installation @@ -147,13 +143,13 @@ Here's some simple schematics that shows a minimal setup. The straight 6-pin hea [The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with, because it's officially supported by Arduino. It uses an ATmega4809, and recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer in order to upload code. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. Use the `LED_BUILTIN` macro to control the onboard LED. Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Use the `LED_BUILTIN` macro to control the onboard LED marked with *WIFI*. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. @@ -165,4 +161,4 @@ Click to enlarge: [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. Recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + From 40a59cb35a2840e1106d1acb83385a8f29e1a427 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 28 Sep 2019 14:14:58 +0200 Subject: [PATCH 063/351] Improve UART pin swap Sightly modified implementation of @egilkv's PR #22. Documentation and implementation is now greatly improved! --- README.md | 48 +++++++++++ megaavr/cores/coreX-corefiles/UART.cpp | 85 +++++++++---------- megaavr/cores/coreX-corefiles/UART.h | 21 +++-- megaavr/cores/coreX-corefiles/UART_private.h | 10 +-- .../coreX-corefiles/api/HardwareSerial.h | 2 + megaavr/variants/uno-wifi/pins_arduino.h | 14 +-- 6 files changed, 114 insertions(+), 66 deletions(-) diff --git a/README.md b/README.md index 63903e8..40a4d35 100644 --- a/README.md +++ b/README.md @@ -17,6 +17,7 @@ An Arduino core for the new megaAVR series! * [Reset pin](#reset-pin) * [Pinout](#pinout) * [PWM output](#pwm-output) +* [Alternative pins](#alternative-pins) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) @@ -121,6 +122,53 @@ the constraints of the hardware will be made to match the request. Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. + +## Alternative pins +The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. +This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. +The `swap()` or `pins()` method will return `true` if that swap or pin combination is supported. +For `Serial` peripherals the method is `pins(tx,rx)`. +(Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) + +Note that `swap()` and `pins()` does the exact same thing, but `swap()` is MUX position oriented, while `pins()` is pin oriented. + +If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral. +Note that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. + +`swap()` or `pins()` are called like this. **Use either `swap()` or `pins()`, not both!** + +``` c++ +// UART pin swapping +Serial3.swap(1); +Serial3.begin(9600); +``` + +Available pin combinations for the *48 pin standard* pinout are: + +| Peripheral | Default | Alternative | +|------------|-------------------------------|------------------------------| +| `Serial` | `swap(0)`
`pins(0,1)` | `swap(1)`
`pins(4,5)` | +| `Serial1` | `swap(0)`
`pins(12,13)` | `swap(1)`
`pins(14,15)` | +| `Serial2` | `swap(0)`
`pins(32,35)` | `swap(1)`
`pins(38,39)` | +| `Serial3` | `swap(0)`
`pins(8,9)` | `swap(1)`
`pins(12,13)` | + +Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: + +| Peripheral | Default | Alternative | +|------------|-------------------------------|------------------------------| +| `Serial` | `swap(0)`
`pins(0,1)` | `swap(1)`
`pins(4,5)` | +| `Serial1` | `swap(0)`
`pins(8,9)` | [No swap available] | +| `Serial2` | `swap(0)`
`pins(20,21)` | `swap(1)`
`pins(24,25)` | + +Available pin combinations for the *Uno WiFi* pinout are: + +| Peripheral | Default | Alternative | +|------------|------------------------------|------------------------------| +| `Serial` | `swap(0)`
`pins(27,26)` | `swap(1)`
`pins(9,10)` | +| `Serial1` | `swap(0)`
`pins(1,0)` | `swap(1)`
`pins(32,33)` | +| `Serial2` | `swap(0)`
`pins(24,23)` | `swap(1)`
`pins(2,7)` | + + ## How to install #### Boards Manager Installation *Not yet implemented* diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index c1d138a..23002d4 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -138,6 +138,38 @@ void UartClass::_poll_tx_data_empty(void) // Public Methods ////////////////////////////////////////////////////////////// +// Invoke this function before 'begin' to define the pins used +bool UartClass::pins(uint8_t tx, uint8_t rx) +{ + for (_pin_set = 0; _pin_set < SERIAL_PIN_SETS; ++_pin_set) { + if (tx == _hw_set[_pin_set].tx_pin && rx == _hw_set[_pin_set].rx_pin) { + // We are good, this set of pins is supported + return true; + } + } + _pin_set = 0; // Default to standard + return false; +} + +bool UartClass::swap(uint8_t state) +{ + if(state == 1) // Use alternative pin position + { + _pin_set = state; + return true; + } + else if(state == 0) // Use default pin position + { + _pin_set = 0; + return true; + } + else // Invalid swap value. Use default position + { + _pin_set = 0; + return false; + } +} + void UartClass::begin(unsigned long baud, uint16_t config) { // Make sure no transmissions are ongoing and USART is disabled in case begin() is called by accident @@ -146,8 +178,7 @@ void UartClass::begin(unsigned long baud, uint16_t config) this->end(); } - // Setup default port mux - PORTMUX.USARTROUTEA |= _uart_mux; + struct UartPinSet *set = &_hw_set[_pin_set]; int32_t baud_setting = 0; @@ -186,54 +217,19 @@ void UartClass::begin(unsigned long baud, uint16_t config) (*_hwserial_module).CTRLA |= USART_RXCIE_bm; - //Set up the rx pin - pinMode(_hwserial_rx_pin, INPUT_PULLUP); - //Set up the tx pin - digitalWrite(_hwserial_tx_pin, HIGH); - pinMode(_hwserial_tx_pin, OUTPUT); + // Let PORTMUX point to alternative UART pins as requested + PORTMUX.USARTROUTEA = set->mux | (PORTMUX.USARTROUTEA & ~_hw_set[1].mux); + + // Set pin state for swapped UART pins + pinMode(set->rx_pin, INPUT_PULLUP); + digitalWrite(set->tx_pin, HIGH); + pinMode(set->tx_pin, OUTPUT); // Restore SREG content SREG = oldSREG; } -void UartClass::swap(uint8_t shouldSwap) -{ - if(shouldSwap == true) - { - // Let PORTMUX pont to alternative UART pins - if(_uart_mux_swap > 0) - PORTMUX.USARTROUTEA |= _uart_mux; - else - PORTMUX.USARTROUTEA &= ~_uart_mux; - - // Set pin state for alternative UART pins - pinMode(_hwserial_rx_pin_swap, INPUT_PULLUP); - digitalWrite(_hwserial_tx_pin_swap, HIGH); - pinMode(_hwserial_tx_pin_swap, OUTPUT); - - // Set previous pins to high Z - pinMode(_hwserial_rx_pin, INPUT); - pinMode(_hwserial_tx_pin, INPUT); - } - else //if(shouldSwap == false) - { - if(_uart_mux > 0) - PORTMUX.USARTROUTEA |= _uart_mux; - else - PORTMUX.USARTROUTEA &= ~_uart_mux; - - // Set pin state for default UART pins - pinMode(_hwserial_rx_pin, INPUT_PULLUP); - digitalWrite(_hwserial_tx_pin, HIGH); - pinMode(_hwserial_tx_pin, OUTPUT); - - // Set previous pins to high Z - pinMode(_hwserial_rx_pin_swap, INPUT); - pinMode(_hwserial_tx_pin_swap, INPUT); - } -} - void UartClass::end() { // wait for transmission of outgoing data @@ -247,6 +243,7 @@ void UartClass::end() // clear any received data _rx_buffer_head = _rx_buffer_tail; + // Note: Does not change output pins _written = false; } diff --git a/megaavr/cores/coreX-corefiles/UART.h b/megaavr/cores/coreX-corefiles/UART.h index d4e5043..a1147d6 100644 --- a/megaavr/cores/coreX-corefiles/UART.h +++ b/megaavr/cores/coreX-corefiles/UART.h @@ -120,18 +120,20 @@ typedef uint8_t rx_buffer_index_t; #define SERIAL_7O2 (USART_CMODE_ASYNCHRONOUS_gc | USART_CHSIZE_7BIT_gc | USART_PMODE_ODD_gc | USART_SBMODE_2BIT_gc) #define SERIAL_8O2 (USART_CMODE_ASYNCHRONOUS_gc | USART_CHSIZE_8BIT_gc | USART_PMODE_ODD_gc | USART_SBMODE_2BIT_gc) +#define SERIAL_PIN_SETS 2 + class UartClass : public HardwareSerial { protected: volatile USART_t * const _hwserial_module; - volatile uint8_t const _hwserial_rx_pin; - volatile uint8_t const _hwserial_tx_pin; - volatile uint8_t const _hwserial_rx_pin_swap; - volatile uint8_t const _hwserial_tx_pin_swap; + struct UartPinSet { + uint8_t const rx_pin; + uint8_t const tx_pin; + uint8_t const mux; + } _hw_set[SERIAL_PIN_SETS]; - volatile uint8_t const _uart_mux; - volatile uint8_t const _uart_mux_swap; + uint8_t _pin_set; // Has any byte been written to the UART since begin() bool _written; @@ -148,14 +150,15 @@ class UartClass : public HardwareSerial // Don't put any members after these buffers, since only the first // 32 bytes of this struct can be accessed quickly using the ldd // instruction. - unsigned char _rx_buffer[SERIAL_RX_BUFFER_SIZE]; - unsigned char _tx_buffer[SERIAL_TX_BUFFER_SIZE]; + volatile unsigned char _rx_buffer[SERIAL_RX_BUFFER_SIZE]; + volatile unsigned char _tx_buffer[SERIAL_TX_BUFFER_SIZE]; public: inline UartClass(volatile USART_t *hwserial_module, uint8_t hwserial_rx_pin, uint8_t hwserial_tx_pin, uint8_t hwserial_rx_pin_swap, uint8_t hwserial_tx_pin_swap, uint8_t dre_vect_num, uint8_t uart_mux, uint8_t uart_mux_swap); + bool pins(uint8_t tx, uint8_t rx); + bool swap(uint8_t state = 1); void begin(unsigned long baud) { begin(baud, SERIAL_8N1); } void begin(unsigned long, uint16_t); - void swap(uint8_t shouldSwap = true); void end(); virtual int available(void); virtual int peek(void); diff --git a/megaavr/cores/coreX-corefiles/UART_private.h b/megaavr/cores/coreX-corefiles/UART_private.h index a7b6664..5e8e1f1 100644 --- a/megaavr/cores/coreX-corefiles/UART_private.h +++ b/megaavr/cores/coreX-corefiles/UART_private.h @@ -39,12 +39,10 @@ UartClass::UartClass( volatile uint8_t uart_mux, volatile uint8_t uart_mux_swap) : _hwserial_module(hwserial_module), - _hwserial_rx_pin(hwserial_rx_pin), - _hwserial_tx_pin(hwserial_tx_pin), - _hwserial_rx_pin_swap(hwserial_rx_pin_swap), - _hwserial_tx_pin_swap(hwserial_tx_pin_swap), - _uart_mux(uart_mux), - _uart_mux_swap(uart_mux_swap), + _hw_set { { hwserial_rx_pin, hwserial_tx_pin, uart_mux }, + { hwserial_rx_pin_swap, hwserial_tx_pin_swap, uart_mux_swap } }, + _pin_set(0), + _written(false), _rx_buffer_head(0), _rx_buffer_tail(0), _tx_buffer_head(0), _tx_buffer_tail(0), _hwserial_dre_interrupt_vect_num(hwserial_dre_interrupt_vect_num), diff --git a/megaavr/cores/coreX-corefiles/api/HardwareSerial.h b/megaavr/cores/coreX-corefiles/api/HardwareSerial.h index e3b0b27..734be67 100644 --- a/megaavr/cores/coreX-corefiles/api/HardwareSerial.h +++ b/megaavr/cores/coreX-corefiles/api/HardwareSerial.h @@ -85,6 +85,8 @@ class HardwareSerial : public Stream { public: + virtual bool pins(uint8_t tx, uint8_t rx) = 0; + virtual bool swap(uint8_t state) = 0; virtual void begin(unsigned long) = 0; virtual void begin(unsigned long baudrate, uint16_t config) = 0; virtual void end() = 0; diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 5b99117..69c405d 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -75,12 +75,12 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_RX (0) #define PIN_WIRE_HWSERIAL1_TX (1) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (33) +#define PIN_WIRE_HWSERIAL1_RX (0) #define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (32) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (33) -// Uno2 Debug USART (not available on headers, only via the EDGB virtual COM port) +// Uno2 Debug USART (not available on headers, only via the mEDGB virtual COM port) // USART3 on mega4809 (alternative pins) // Mapped to HWSERIAL1 in Serial library #define HWSERIAL0 (&USART3) @@ -89,10 +89,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL0_RX (26) #define PIN_WIRE_HWSERIAL0_TX (27) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) +#define PIN_WIRE_HWSERIAL0_RX (26) #define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (9) +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) // Uno2 Spare USART available on testpoints // USART0 on mega4809 (alternative pins) @@ -103,10 +103,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) #define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) #define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL2_RX (23) #define PIN_WIRE_HWSERIAL2_TX (24) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) +#define PIN_WIRE_HWSERIAL2_RX (23) #define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (2) +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) #define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) #define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) //PORTMUX_TWI0_ALT1_gc From db5ecb8e63ee27fdff2a7dd492cd4b5f47b61558 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 29 Sep 2019 13:44:36 +0200 Subject: [PATCH 064/351] Add i2c pin swap Uses @egilkv's implementation from PR #22 --- README.md | 39 +- megaavr/libraries/Wire/keywords.txt | 2 + megaavr/libraries/Wire/src/Wire.cpp | 55 +- megaavr/libraries/Wire/src/Wire.h | 3 +- megaavr/libraries/Wire/src/utility/twi.c | 1572 +++++++++++----------- megaavr/libraries/Wire/src/utility/twi.h | 254 ++-- megaavr/variants/uno-wifi/pins_arduino.h | 2 +- 7 files changed, 999 insertions(+), 928 deletions(-) diff --git a/README.md b/README.md index 40a4d35..bee780c 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,6 @@ An Arduino core for the new megaAVR series! **TODO:** * SPI pin swap integration in libraries -* I2C pin swap integration in libraries * Readme - Need some good intro text at the beginning @@ -71,6 +70,7 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol Note that unlike other AVRs none of these chips are able to drive an external crystal or resonator. If you need an external oscillator it has to be one with a driven clock output. The microcontroller will freeze if the external clock suddenly drops out. If not present on boot, it will automatically choose the 16 MHz internal oscillator instead. + ## BOD option Brown out detection, or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brown out setting. Below is a table that shows the available BOD options: @@ -126,14 +126,14 @@ Note also that tone() will use TCB1, so the corresponding PWM output is not avai ## Alternative pins The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. -The `swap()` or `pins()` method will return `true` if that swap or pin combination is supported. -For `Serial` peripherals the method is `pins(tx,rx)`. +They will return `true` if that swap or pin combination is supported. +For `Serial` peripherals the method is `pins(tx,rx)`, and for `Wire` it's `pins(sda,scl)`. (Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) -Note that `swap()` and `pins()` does the exact same thing, but `swap()` is MUX position oriented, while `pins()` is pin oriented. +Note that `swap()` and `pins()` does the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. -If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral. -Note that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. +If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral, +mote that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. `swap()` or `pins()` are called like this. **Use either `swap()` or `pins()`, not both!** @@ -141,32 +141,39 @@ Note that the proper way to switch is first to invoke `end()` to cleanly shut do // UART pin swapping Serial3.swap(1); Serial3.begin(9600); + +// Wire pin swapping +Wire.swap(1); +Wire.begin(); ``` Available pin combinations for the *48 pin standard* pinout are: | Peripheral | Default | Alternative | |------------|-------------------------------|------------------------------| -| `Serial` | `swap(0)`
`pins(0,1)` | `swap(1)`
`pins(4,5)` | -| `Serial1` | `swap(0)`
`pins(12,13)` | `swap(1)`
`pins(14,15)` | -| `Serial2` | `swap(0)`
`pins(32,35)` | `swap(1)`
`pins(38,39)` | -| `Serial3` | `swap(0)`
`pins(8,9)` | `swap(1)`
`pins(12,13)` | +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | +| Serial1 | swap(0) **or** pins(12,13) | swap(1) **or** pins(14,15) | +| Serial2 | swap(0) **or** pins(32,35) | swap(1) **or** pins(38,39) | +| Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: | Peripheral | Default | Alternative | |------------|-------------------------------|------------------------------| -| `Serial` | `swap(0)`
`pins(0,1)` | `swap(1)`
`pins(4,5)` | -| `Serial1` | `swap(0)`
`pins(8,9)` | [No swap available] | -| `Serial2` | `swap(0)`
`pins(20,21)` | `swap(1)`
`pins(24,25)` | +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | +| Serial1 | swap(0) **or** pins(8,9) | [No swap available] | +| Serial2 | swap(0) **or** pins(20,21) | swap(1) **or** pins(24,25) | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | Available pin combinations for the *Uno WiFi* pinout are: | Peripheral | Default | Alternative | |------------|------------------------------|------------------------------| -| `Serial` | `swap(0)`
`pins(27,26)` | `swap(1)`
`pins(9,10)` | -| `Serial1` | `swap(0)`
`pins(1,0)` | `swap(1)`
`pins(32,33)` | -| `Serial2` | `swap(0)`
`pins(24,23)` | `swap(1)`
`pins(2,7)` | +| Serial | swap(0) **or** pins(27,26) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) | +| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | +| Wire | swap(0) **or** pins(20,21) | [No swap available] | ## How to install diff --git a/megaavr/libraries/Wire/keywords.txt b/megaavr/libraries/Wire/keywords.txt index 5e3d2b1..5ad6fce 100644 --- a/megaavr/libraries/Wire/keywords.txt +++ b/megaavr/libraries/Wire/keywords.txt @@ -11,6 +11,8 @@ ####################################### begin KEYWORD2 +pins KEYWORD2 +swap KEYWORD2 setClock KEYWORD2 beginTransmission KEYWORD2 endTransmission KEYWORD2 diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index 060e92a..b8922fd 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -54,6 +54,60 @@ TwoWire::TwoWire() // Public Methods ////////////////////////////////////////////////////////////// +// Special for megaAVR 0-series: Select which pins to use for I2C interface +// True if pin specification actually exists +// Note that we do not currently support the dual TWI mode +bool TwoWire::pins(uint8_t sda_pin, uint8_t scl_pin) +{ +#if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) + if (sda_pin == PIN_WIRE_SDA_PINSWAP_1 && scl_pin == PIN_WIRE_SCL_PINSWAP_1) + { + // Use pin swap + PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return true; + } + else if(sda_pin == PIN_WIRE_SDA && scl_pin == PIN_WIRE_SCL) + { + // Use default configuration + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return true; + } + else + { + // Assume default configuration + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return false; + } + + +#endif +} + +bool TwoWire::swap(uint8_t state) +{ +#if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) + if(state == 1) + { + // Use pin swap + PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return true; + } + else if(state == 0) + { + // Use default configuration + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return true; + } + else + { + // Assume default configuration + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + return true; + } +#endif + return false; +} + void TwoWire::begin(void) { rxBufferIndex = 0; @@ -77,7 +131,6 @@ void TwoWire::begin(uint8_t address) TWI_attachSlaveTxEvent(onRequestService, txBuffer); // default callback must exist TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, BUFFER_LENGTH); // default callback must exist - } void TwoWire::begin(int address) diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index 0cc157c..8c30eae 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -28,7 +28,6 @@ // WIRE_HAS_END means Wire has end() #define WIRE_HAS_END 1 - class TwoWire : public HardwareI2C { private: @@ -48,6 +47,8 @@ class TwoWire : public HardwareI2C static void onReceiveService(int); public: TwoWire(); + bool pins(uint8_t sda_pin, uint8_t scl_pin); + bool swap(uint8_t state = 1); void begin(); void begin(uint8_t); void begin(int); diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 9dc4a7e..0bdfd87 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -1,783 +1,791 @@ -/****************************************************************************** -* (c) 2018 Microchip Technology Inc. and its subsidiaries. -* -* Subject to your compliance with these terms, you may use Microchip software -* and any derivatives exclusively with Microchip products. It is your -* responsibility to comply with third party license terms applicable to your -* use of third party software (including open source software) that may -* accompany Microchip software. -* -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER -* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED -* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR -* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, -* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY -* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP -* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE -* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN -* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, -* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. -* - *****************************************************************************/ - -#include "twi.h" -#include "Arduino.h" - -/* Master variables */ -static register8_t master_slaveAddress; /*!< Slave address */ -static register8_t* master_writeData; /*!< Data to write */ -static register8_t* master_readData; /*!< Read data */ -static register8_t master_bytesToWrite; /*!< Number of bytes to write */ -static register8_t master_bytesToRead; /*!< Number of bytes to read */ -static register8_t master_bytesWritten; /*!< Number of bytes written */ -static register8_t master_bytesRead; /*!< Number of bytes read */ -static register8_t master_sendStop; /*!< To send a stop at the end of the transaction or not */ -static register8_t master_trans_status; /*!< Status of transaction */ -static register8_t master_result; /*!< Result of transaction */ - -/* Slave variables */ -static uint8_t (*TWI_onSlaveTransmit)(void) __attribute__((unused)); -static void (*TWI_onSlaveReceive)(int) __attribute__((unused)); -static register8_t* slave_writeData; -static register8_t* slave_readData; -static register8_t slave_bytesToWrite; -static register8_t slave_bytesWritten; -static register8_t slave_bytesToRead; -static register8_t slave_bytesRead; -static register8_t slave_trans_status; -static register8_t slave_result; -static register8_t slave_callUserReceive; -static register8_t slave_callUserRequest; - -/* TWI module mode */ -static volatile TWI_MODE_t twi_mode; - -/*! \brief Initialize the TWI module as a master. - * - * TWI master initialization function. - * Enables master read and write interrupts. - * Remember to enable interrupts globally from the main application. - * - * \param frequency The required baud. - */ -void TWI_MasterInit(uint32_t frequency) -{ - if(twi_mode != TWI_MODE_UNKNOWN) return; - - // Enable pullups just in case, should have external ones though - //pinMode(PIN_WIRE_SDA, INPUT_PULLUP); - //pinMode(PIN_WIRE_SCL, INPUT_PULLUP); - - PORTMUX.TWISPIROUTEA |= TWI_MUX; - - twi_mode = TWI_MODE_MASTER; - - master_bytesRead = 0; - master_bytesWritten = 0; - master_trans_status = TWIM_STATUS_READY; - master_result = TWIM_RESULT_UNKNOWN; - - TWI0.MCTRLA = TWI_RIEN_bm | TWI_WIEN_bm | TWI_ENABLE_bm; - TWI_MasterSetBaud(frequency); - TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; -} - -/*! \brief Initialize the TWI module as a slave. - * - * TWI slave initialization function. - * Enables slave address/stop and data interrupts. - * Assigns slave's own address. - * Remember to enable interrupts globally from the main application. - * - * \param address The TWI Slave's own address. - */ -void TWI_SlaveInit(uint8_t address) -{ - if(twi_mode != TWI_MODE_UNKNOWN) return; - - twi_mode = TWI_MODE_SLAVE; - - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_trans_status = TWIS_STATUS_READY; - slave_result = TWIS_RESULT_UNKNOWN; - slave_callUserRequest = 0; - slave_callUserReceive = 0; - - TWI0.SADDR = address << 1; - TWI0.SCTRLA = TWI_DIEN_bm | TWI_APIEN_bm | TWI_PIEN_bm | TWI_ENABLE_bm; - - /* Bus Error Detection circuitry needs Master enabled to work */ - TWI0.MCTRLA = TWI_ENABLE_bm; -} - -void TWI_Flush(void){ - TWI0.MCTRLB |= TWI_FLUSH_bm; -} - -/*! \brief Disable the TWI module. - * - * TWI module disable function. - * Disables both master and slave modes - * - * \param frequency The required baud. - */ -void TWI_Disable(void) -{ - TWI0.MCTRLA = 0x00; - TWI0.MBAUD = 0x00; - TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; - TWI0.SADDR = 0x00; - TWI0.SCTRLA = 0x00; - - twi_mode = TWI_MODE_UNKNOWN; -} - -/*! \brief Returns the TWI bus state. - * - * Returns the TWI bus state (type defined in device headerfile), - * unknown, idle, owner or busy. - * - * \param twi The TWI_Master_t struct instance. - * - * \retval TWI_MASTER_BUSSTATE_UNKNOWN_gc Bus state is unknown. - * \retval TWI_MASTER_BUSSTATE_IDLE_gc Bus state is idle. - * \retval TWI_MASTER_BUSSTATE_OWNER_gc Bus state is owned by the master. - * \retval TWI_MASTER_BUSSTATE_BUSY_gc Bus state is busy. - */ -TWI_BUSSTATE_t TWI_MasterState(void) -{ - TWI_BUSSTATE_t twi_status; - twi_status = (TWI_BUSSTATE_t) (TWI0.MSTATUS & TWI_BUSSTATE_gm); - return twi_status; -} - - -/*! \brief Returns true if transaction is ready. - * - * This function returns a boolean whether the TWI Master is ready - * for a new transaction. - * - * \param twi The TWI_Master_t struct instance. - * - * \retval true If transaction could be started. - * \retval false If transaction could not be started. - */ -uint8_t TWI_MasterReady(void) -{ - uint8_t twi_status = (master_trans_status & TWIM_STATUS_READY); - return twi_status; -} - -/*! \brief Set the TWI baud rate. - * - * Sets the baud rate used by TWI Master. - * - * \param frequency The required baud. - */ -void TWI_MasterSetBaud(uint32_t frequency){ - -// Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; -// Where T_RISE varies depending on operating frequency... -// From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz - - uint16_t t_rise; - - if(frequency < 200000){ - frequency = 100000; - t_rise = 1000; - - } else if (frequency < 800000){ - frequency = 400000; - t_rise = 300; - - } else if (frequency < 1200000){ - frequency = 1000000; - t_rise = 120; - - } else { - frequency = 100000; - t_rise = 1000; - } - - uint32_t baud = ((F_CPU_CORRECTED/frequency) - (((F_CPU_CORRECTED*t_rise)/1000)/1000)/1000 - 10)/2; - TWI0.MBAUD = (uint8_t)baud; - -} - -/*! \brief TWI write transaction. - * - * This function is TWI Master wrapper for a write-only transaction. - * - * \param twi The TWI_Master_t struct instance. - * \param address Slave address. - * \param writeData Pointer to data to write. - * \param bytesToWrite Number of data bytes to write. - * - * \retval true If transaction could be started. - * \retval false If transaction could not be started. - */ -uint8_t TWI_MasterWrite(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t send_stop) -{ - return TWI_MasterWriteRead(slave_address, - write_data, - bytes_to_write, - 0, - send_stop); -} - - -/*! \brief TWI read transaction. - * - * This function is a TWI Master wrapper for read-only transaction. - * - * \param twi The TWI_Master_t struct instance. - * \param address The slave address. - * \param bytesToRead The number of bytes to read. - * - * \retval true If transaction could be started. - * \retval false If transaction could not be started. - */ -uint8_t TWI_MasterRead(uint8_t slave_address, - uint8_t* read_data, - uint8_t bytes_to_read, - uint8_t send_stop) -{ - master_readData = read_data; - - uint8_t bytes_read = TWI_MasterWriteRead(slave_address, - 0, - 0, - bytes_to_read, - send_stop); - return bytes_read; -} - - -/*! \brief TWI write and/or read transaction. - * - * This function is a TWI Master write and/or read transaction. The function - * can be used to both write and/or read bytes to/from the TWI Slave in one - * transaction. - * - * \param twi The TWI_Master_t struct instance. - * \param address The slave address. - * \param writeData Pointer to data to write. - * \param bytesToWrite Number of bytes to write. - * \param bytesToRead Number of bytes to read. - * - * \retval 0:success - * \retval 1:data too long to fit in transmit buffer - * \retval 2:received NACK on transmit of address - * \retval 3:received NACK on transmit of data - * \retval 4:other error - */ -uint8_t TWI_MasterWriteRead(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t bytes_to_read, - uint8_t send_stop) -{ - if(twi_mode != TWI_MODE_MASTER) return false; - - /*Initiate transaction if bus is ready. */ - if (master_trans_status == TWIM_STATUS_READY) { - - master_trans_status = TWIM_STATUS_BUSY; - master_result = TWIM_RESULT_UNKNOWN; - - master_writeData = write_data; - - master_bytesToWrite = bytes_to_write; - master_bytesToRead = bytes_to_read; - master_bytesWritten = 0; - master_bytesRead = 0; - master_sendStop = send_stop; - master_slaveAddress = slave_address<<1; - -trigger_action: - - /* If write command, send the START condition + Address + - * 'R/_W = 0' - */ - if (master_bytesToWrite > 0) { - twi_mode = TWI_MODE_MASTER_TRANSMIT; - uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); - TWI0.MADDR = writeAddress; - } - - /* If read command, send the START condition + Address + - * 'R/_W = 1' - */ - else if (master_bytesToRead > 0) { - twi_mode = TWI_MODE_MASTER_RECEIVE; - uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); - TWI0.MADDR = readAddress; - } - - else if (master_bytesToWrite == 0 && master_bytesToRead == 0) { - twi_mode = TWI_MODE_MASTER_TRANSMIT; - uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); - TWI0.MADDR = writeAddress; - } - - /* Arduino requires blocking function */ - while(master_result == TWIM_RESULT_UNKNOWN) {} - - // in case of arbitration lost, retry sending - if (master_result == TWIM_RESULT_ARBITRATION_LOST) { - goto trigger_action; - } - - uint8_t ret = 0; - if (master_bytesToRead > 0) { - // return bytes really read - ret = master_bytesRead; - } else { - // return 0 if success, >0 otherwise (follow classic AVR conventions) - switch (master_result) { - case TWIM_RESULT_OK: - ret = 0; - break; - case TWIM_RESULT_BUFFER_OVERFLOW: - ret = 1; - break; - case TWIM_RESULT_NACK_RECEIVED: - ret = 3; - break; - default: - ret = 4; - break; - } - } - - return ret; - } else { - return 1; - } -} - - -/*! \brief Common TWI master interrupt service routine. - * - * Check current status and calls the appropriate handler. - * - */ -void TWI_MasterInterruptHandler() -{ - uint8_t currentStatus = TWI0.MSTATUS; - - /* If arbitration lost or bus error. */ - if ((currentStatus & TWI_ARBLOST_bm) || - (currentStatus & TWI_BUSERR_bm)) { - - TWI_MasterArbitrationLostBusErrorHandler(); - } - - /* If master write interrupt. */ - else if (currentStatus & TWI_WIF_bm) { - TWI_MasterWriteHandler(); - } - - /* If master read interrupt. */ - else if (currentStatus & TWI_RIF_bm) { - TWI_MasterReadHandler(); - } - - /* If unexpected state. */ - else { - TWI_MasterTransactionFinished(TWIM_RESULT_FAIL); - } -} - -/*! \brief TWI master arbitration lost and bus error interrupt handler. - * - * Handles TWI responses to lost arbitration and bus error. - * - */ -void TWI_MasterArbitrationLostBusErrorHandler() -{ - uint8_t currentStatus = TWI0.MSTATUS; - - /* If bus error. */ - if (currentStatus & TWI_BUSERR_bm) { - master_result = TWIM_RESULT_BUS_ERROR; - } - /* If arbitration lost. */ - else { - master_result = TWIM_RESULT_ARBITRATION_LOST; - } - - /* Clear all flags, abort operation */ - TWI0.MSTATUS = currentStatus; - - /* Wait for a new operation */ - twi_mode = TWI_MODE_MASTER; - master_trans_status = TWIM_STATUS_READY; -} - - -/*! \brief TWI master write interrupt handler. - * - * Handles TWI transactions (master write) and responses to (N)ACK. - * - */ -void TWI_MasterWriteHandler() -{ - /* Local variables used in if tests to avoid compiler warning. */ - uint8_t bytesToWrite = master_bytesToWrite; - uint8_t bytesToRead = master_bytesToRead; - - /* If NOT acknowledged (NACK) by slave cancel the transaction. */ - if (TWI0.MSTATUS & TWI_RXACK_bm) { - if(master_sendStop){ - TWI0.MCTRLB = TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; - - } - TWI_MasterTransactionFinished(TWIM_RESULT_NACK_RECEIVED); - } - - /* If more bytes to write, send data. */ - else if (master_bytesWritten < bytesToWrite) { - uint8_t data = master_writeData[master_bytesWritten]; - TWI0.MDATA = data; - master_bytesWritten++; - } - - /* If bytes to read, send START condition + Address + - * 'R/_W = 1' - */ - else if (master_bytesRead < bytesToRead) { - twi_mode = TWI_MODE_MASTER_RECEIVE; - uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); - TWI0.MADDR = readAddress; - } - - /* If transaction finished, send ACK/STOP condition if instructed and set RESULT OK. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; - } - TWI_MasterTransactionFinished(TWIM_RESULT_OK); - } -} - - -/*! \brief TWI master read interrupt handler. - * - * This is the master read interrupt handler that takes care of - * reading bytes from the TWI slave. - * - * \param twi The TWI_Master_t struct instance. - */ -void TWI_MasterReadHandler() -{ - /* Fetch data if bytes to be read. */ - if (master_bytesRead < master_bytesToRead) { - uint8_t data = TWI0.MDATA; - master_readData[master_bytesRead] = data; - master_bytesRead++; - } - - /* If buffer overflow, issue NACK/STOP and BUFFER_OVERFLOW condition. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; - } - - TWI_MasterTransactionFinished(TWIM_RESULT_BUFFER_OVERFLOW); - master_bytesToRead = 0; - return; - } - - /* Local variable used in if test to avoid compiler warning. */ - uint8_t bytesToRead = master_bytesToRead; - - /* If more bytes to read, issue ACK and start a byte read. */ - if (master_bytesRead < bytesToRead) { - TWI0.MCTRLB = TWI_MCMD_RECVTRANS_gc; - } - - /* If transaction finished, issue NACK and STOP condition if instructed. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; - } - - TWI_MasterTransactionFinished(TWIM_RESULT_OK); - } -} - - -/*! \brief TWI transaction finished handler. - * - * Prepares module for new transaction. - * - * \param result The result of the operation. - */ -void TWI_MasterTransactionFinished(uint8_t result) -{ - master_result = result; - master_trans_status = TWIM_STATUS_READY; - twi_mode = TWI_MODE_MASTER; -} - - -/*! \brief Common TWI slave interrupt service routine. - * - * Check current status and calls the appropriate handler. - * - */ -void TWI_SlaveInterruptHandler(){ - uint8_t currentStatus = TWI0.SSTATUS; - - /* If bus error */ - if(currentStatus & TWI_BUSERR_bm){ - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_bytesToWrite = 0; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUS_ERROR); - } - - /* If Address or Stop */ - else if(currentStatus & TWI_APIF_bm){ - - /* Call user onReceive function if end of Master Write/Slave Read. - * This should be hit when there is a STOP or REPSTART - */ - if(slave_callUserReceive == 1){ - TWI_onSlaveReceive(slave_bytesRead); - slave_callUserReceive = 0; - } - - /* If address match */ - if(currentStatus & TWI_AP_bm){ - TWI_SlaveAddressMatchHandler(); - } - - /* If stop */ - else { - TWI_SlaveStopHandler(); - - /* If CLKHOLD is high, we have missed an address match - from a fast start after stop. - Because the flag is shared we need to handle this here. - */ - if(TWI0.SSTATUS & TWI_CLKHOLD_bm){ - - /* CLKHOLD will be cleared by servicing the address match */ - TWI_SlaveAddressMatchHandler(); - } - } - } - - /* If Data Interrupt */ - else if (currentStatus & TWI_DIF_bm){ - - /* If collision flag is raised, slave transmit unsuccessful */ - if (currentStatus & TWI_COLL_bm){ - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_bytesToWrite = 0; - TWI_SlaveTransactionFinished(TWIS_RESULT_TRANSMIT_COLLISION); - } - - /* Otherwise, normal data interrupt */ - else { - TWI_SlaveDataHandler(); - } - } - - /* If unexpected state */ - else { - TWI_SlaveTransactionFinished(TWIS_RESULT_FAIL); - } -} - -/*! \brief TWI slave address interrupt handler. - * - * This is the slave address match handler that takes care of responding to - * being addressed by a master - * - */ -void TWI_SlaveAddressMatchHandler(){ - slave_trans_status = TWIS_STATUS_BUSY; - slave_result = TWIS_RESULT_UNKNOWN; - - /* Send ACK, wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - - /* If Master Read/Slave Write */ - if(TWI0.SSTATUS & TWI_DIR_bm){ - slave_bytesWritten = 0; - /* Call user function */ - slave_bytesToWrite = TWI_onSlaveTransmit(); - twi_mode = TWI_MODE_SLAVE_TRANSMIT; - } - /* If Master Write/Slave Read */ - else { - slave_bytesRead = 0; - slave_callUserReceive = 1; - twi_mode = TWI_MODE_SLAVE_RECEIVE; - } - - /* Data interrupt to follow... */ -} - -/*! \brief TWI slave stop interrupt handler. - * - */ -void TWI_SlaveStopHandler(){ - - /* Clear APIF, don't ACK or NACK */ - TWI0.SSTATUS = TWI_APIF_bm; - - TWI_SlaveTransactionFinished(TWIS_RESULT_OK); - -} - -/*! \brief TWI slave data interrupt handler. - * - * This is the slave data handler that takes care of sending data to or - * receiving data from a master - * - */ -void TWI_SlaveDataHandler(){ - - /* Enable stop interrupt */ - TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); - - /* If Master Read/Slave Write */ - if(TWI0.SSTATUS & TWI_DIR_bm){ - - TWI_SlaveWriteHandler(); - } - - /* If Master Write/Slave Read */ - else { - TWI_SlaveReadHandler(); - } - - -} - -/*! \brief TWI slave data write interrupt handler. - * - * This is the slave data handler that takes care of sending data to a master - * - */ -void TWI_SlaveWriteHandler(){ - - /* If NACK, slave write transaction finished */ - if((slave_bytesWritten > 0) && (TWI0.SSTATUS & TWI_RXACK_bm)){ - - TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_OK); - } - - /* If ACK, master expects more data */ - else { - - if(slave_bytesWritten < slave_bytesToWrite){ - uint8_t data = slave_writeData[slave_bytesWritten]; - TWI0.SDATA = data; - slave_bytesWritten++; - - /* Send data, wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - - } - - /* If buffer overflow */ - else { - TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); - - } - - - } -} - -/*! \brief TWI slave data read interrupt handler. - * - * This is the slave data handler that takes care of receiving data from a master - * - */ -void TWI_SlaveReadHandler(){ - - /* If free space in buffer */ - if(slave_bytesRead < slave_bytesToRead){ - - /* Fetch data */ - uint8_t data = TWI0.SDATA; - slave_readData[slave_bytesRead] = data; - slave_bytesRead++; - - /* Send ACK and wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - } - /* If buffer overflow, send NACK and wait for next START. - Set result buffer overflow */ - else { - TWI0.SCTRLB = TWI_ACKACT_bm | TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); - } -} - -/* - * Function twi_attachSlaveRxEvent - * Desc sets function called before a slave read operation - * Input function: callback function to use - * Output none - */ -void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ){ - TWI_onSlaveReceive = function; - slave_readData = read_data; - slave_bytesToRead = bytes_to_read; -} - -/* - * Function twi_attachSlaveTxEvent - * Desc sets function called before a slave write operation - * Input function: callback function to use - * Output none - */ -void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t* write_data ){ - TWI_onSlaveTransmit = function; - slave_writeData = write_data; -} - - -/*! \brief TWI slave transaction finished handler. - * - * Prepares module for new transaction. - * - * \param result The result of the operation. - */ -void TWI_SlaveTransactionFinished(uint8_t result) -{ - TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); - twi_mode = TWI_MODE_SLAVE; - slave_result = result; - slave_trans_status = TWIM_STATUS_READY; -} - -ISR(TWI0_TWIM_vect){ - TWI_MasterInterruptHandler(); -} - -ISR(TWI0_TWIS_vect){ - TWI_SlaveInterruptHandler(); +/****************************************************************************** +* (c) 2018 Microchip Technology Inc. and its subsidiaries. +* +* Subject to your compliance with these terms, you may use Microchip software +* and any derivatives exclusively with Microchip products. It is your +* responsibility to comply with third party license terms applicable to your +* use of third party software (including open source software) that may +* accompany Microchip software. +* +* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER +* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED +* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR +* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, +* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY +* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP +* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE +* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN +* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, +* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. +* + *****************************************************************************/ + +#include "twi.h" +#include "Arduino.h" + +/* Master variables */ +static register8_t master_slaveAddress; /*!< Slave address */ +static register8_t* master_writeData; /*!< Data to write */ +static register8_t* master_readData; /*!< Read data */ +static register8_t master_bytesToWrite; /*!< Number of bytes to write */ +static register8_t master_bytesToRead; /*!< Number of bytes to read */ +static register8_t master_bytesWritten; /*!< Number of bytes written */ +static register8_t master_bytesRead; /*!< Number of bytes read */ +static register8_t master_sendStop; /*!< To send a stop at the end of the transaction or not */ +static register8_t master_trans_status; /*!< Status of transaction */ +static register8_t master_result; /*!< Result of transaction */ + +/* Slave variables */ +static uint8_t (*TWI_onSlaveTransmit)(void) __attribute__((unused)); +static void (*TWI_onSlaveReceive)(int) __attribute__((unused)); +static register8_t* slave_writeData; +static register8_t* slave_readData; +static register8_t slave_bytesToWrite; +static register8_t slave_bytesWritten; +static register8_t slave_bytesToRead; +static register8_t slave_bytesRead; +static register8_t slave_trans_status; +static register8_t slave_result; +static register8_t slave_callUserReceive; +static register8_t slave_callUserRequest; + +/* TWI module mode */ +static volatile TWI_MODE_t twi_mode; + +/*! \brief Initialize the TWI module as a master. + * + * TWI master initialization function. + * Enables master read and write interrupts. + * Remember to enable interrupts globally from the main application. + * + * \param frequency The required baud. + */ +void TWI_MasterInit(uint32_t frequency) +{ + if(twi_mode != TWI_MODE_UNKNOWN) return; + + // Enable input pullup for the default or pin swapped pin position + if((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) + { + pinMode(PIN_WIRE_SDA, INPUT_PULLUP); + pinMode(PIN_WIRE_SCL, INPUT_PULLUP); + } +#if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) + else if((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX_PINSWAP) + { + pinMode(PIN_WIRE_SDA_PINSWAP_1, INPUT_PULLUP); + pinMode(PIN_WIRE_SCL_PINSWAP_1, INPUT_PULLUP); + } +#endif + + twi_mode = TWI_MODE_MASTER; + + master_bytesRead = 0; + master_bytesWritten = 0; + master_trans_status = TWIM_STATUS_READY; + master_result = TWIM_RESULT_UNKNOWN; + + TWI0.MCTRLA = TWI_RIEN_bm | TWI_WIEN_bm | TWI_ENABLE_bm; + TWI_MasterSetBaud(frequency); + TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; +} + +/*! \brief Initialize the TWI module as a slave. + * + * TWI slave initialization function. + * Enables slave address/stop and data interrupts. + * Assigns slave's own address. + * Remember to enable interrupts globally from the main application. + * + * \param address The TWI Slave's own address. + */ +void TWI_SlaveInit(uint8_t address) +{ + if(twi_mode != TWI_MODE_UNKNOWN) return; + + twi_mode = TWI_MODE_SLAVE; + + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_trans_status = TWIS_STATUS_READY; + slave_result = TWIS_RESULT_UNKNOWN; + slave_callUserRequest = 0; + slave_callUserReceive = 0; + + TWI0.SADDR = address << 1; + TWI0.SCTRLA = TWI_DIEN_bm | TWI_APIEN_bm | TWI_PIEN_bm | TWI_ENABLE_bm; + + /* Bus Error Detection circuitry needs Master enabled to work */ + TWI0.MCTRLA = TWI_ENABLE_bm; +} + +void TWI_Flush(void){ + TWI0.MCTRLB |= TWI_FLUSH_bm; +} + +/*! \brief Disable the TWI module. + * + * TWI module disable function. + * Disables both master and slave modes + * + * \param frequency The required baud. + */ +void TWI_Disable(void) +{ + TWI0.MCTRLA = 0x00; + TWI0.MBAUD = 0x00; + TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; + TWI0.SADDR = 0x00; + TWI0.SCTRLA = 0x00; + + twi_mode = TWI_MODE_UNKNOWN; +} + +/*! \brief Returns the TWI bus state. + * + * Returns the TWI bus state (type defined in device headerfile), + * unknown, idle, owner or busy. + * + * \param twi The TWI_Master_t struct instance. + * + * \retval TWI_MASTER_BUSSTATE_UNKNOWN_gc Bus state is unknown. + * \retval TWI_MASTER_BUSSTATE_IDLE_gc Bus state is idle. + * \retval TWI_MASTER_BUSSTATE_OWNER_gc Bus state is owned by the master. + * \retval TWI_MASTER_BUSSTATE_BUSY_gc Bus state is busy. + */ +TWI_BUSSTATE_t TWI_MasterState(void) +{ + TWI_BUSSTATE_t twi_status; + twi_status = (TWI_BUSSTATE_t) (TWI0.MSTATUS & TWI_BUSSTATE_gm); + return twi_status; +} + + +/*! \brief Returns true if transaction is ready. + * + * This function returns a boolean whether the TWI Master is ready + * for a new transaction. + * + * \param twi The TWI_Master_t struct instance. + * + * \retval true If transaction could be started. + * \retval false If transaction could not be started. + */ +uint8_t TWI_MasterReady(void) +{ + uint8_t twi_status = (master_trans_status & TWIM_STATUS_READY); + return twi_status; +} + +/*! \brief Set the TWI baud rate. + * + * Sets the baud rate used by TWI Master. + * + * \param frequency The required baud. + */ +void TWI_MasterSetBaud(uint32_t frequency){ + +// Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; +// Where T_RISE varies depending on operating frequency... +// From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz + + uint16_t t_rise; + + if(frequency < 200000){ + frequency = 100000; + t_rise = 1000; + + } else if (frequency < 800000){ + frequency = 400000; + t_rise = 300; + + } else if (frequency < 1200000){ + frequency = 1000000; + t_rise = 120; + + } else { + frequency = 100000; + t_rise = 1000; + } + + uint32_t baud = ((F_CPU_CORRECTED/frequency) - (((F_CPU_CORRECTED*t_rise)/1000)/1000)/1000 - 10)/2; + TWI0.MBAUD = (uint8_t)baud; + +} + +/*! \brief TWI write transaction. + * + * This function is TWI Master wrapper for a write-only transaction. + * + * \param twi The TWI_Master_t struct instance. + * \param address Slave address. + * \param writeData Pointer to data to write. + * \param bytesToWrite Number of data bytes to write. + * + * \retval true If transaction could be started. + * \retval false If transaction could not be started. + */ +uint8_t TWI_MasterWrite(uint8_t slave_address, + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t send_stop) +{ + return TWI_MasterWriteRead(slave_address, + write_data, + bytes_to_write, + 0, + send_stop); +} + + +/*! \brief TWI read transaction. + * + * This function is a TWI Master wrapper for read-only transaction. + * + * \param twi The TWI_Master_t struct instance. + * \param address The slave address. + * \param bytesToRead The number of bytes to read. + * + * \retval true If transaction could be started. + * \retval false If transaction could not be started. + */ +uint8_t TWI_MasterRead(uint8_t slave_address, + uint8_t* read_data, + uint8_t bytes_to_read, + uint8_t send_stop) +{ + master_readData = read_data; + + uint8_t bytes_read = TWI_MasterWriteRead(slave_address, + 0, + 0, + bytes_to_read, + send_stop); + return bytes_read; +} + + +/*! \brief TWI write and/or read transaction. + * + * This function is a TWI Master write and/or read transaction. The function + * can be used to both write and/or read bytes to/from the TWI Slave in one + * transaction. + * + * \param twi The TWI_Master_t struct instance. + * \param address The slave address. + * \param writeData Pointer to data to write. + * \param bytesToWrite Number of bytes to write. + * \param bytesToRead Number of bytes to read. + * + * \retval 0:success + * \retval 1:data too long to fit in transmit buffer + * \retval 2:received NACK on transmit of address + * \retval 3:received NACK on transmit of data + * \retval 4:other error + */ +uint8_t TWI_MasterWriteRead(uint8_t slave_address, + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t bytes_to_read, + uint8_t send_stop) +{ + if(twi_mode != TWI_MODE_MASTER) return false; + + /*Initiate transaction if bus is ready. */ + if (master_trans_status == TWIM_STATUS_READY) { + + master_trans_status = TWIM_STATUS_BUSY; + master_result = TWIM_RESULT_UNKNOWN; + + master_writeData = write_data; + + master_bytesToWrite = bytes_to_write; + master_bytesToRead = bytes_to_read; + master_bytesWritten = 0; + master_bytesRead = 0; + master_sendStop = send_stop; + master_slaveAddress = slave_address<<1; + +trigger_action: + + /* If write command, send the START condition + Address + + * 'R/_W = 0' + */ + if (master_bytesToWrite > 0) { + twi_mode = TWI_MODE_MASTER_TRANSMIT; + uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); + TWI0.MADDR = writeAddress; + } + + /* If read command, send the START condition + Address + + * 'R/_W = 1' + */ + else if (master_bytesToRead > 0) { + twi_mode = TWI_MODE_MASTER_RECEIVE; + uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); + TWI0.MADDR = readAddress; + } + + else if (master_bytesToWrite == 0 && master_bytesToRead == 0) { + twi_mode = TWI_MODE_MASTER_TRANSMIT; + uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); + TWI0.MADDR = writeAddress; + } + + /* Arduino requires blocking function */ + while(master_result == TWIM_RESULT_UNKNOWN) {} + + // in case of arbitration lost, retry sending + if (master_result == TWIM_RESULT_ARBITRATION_LOST) { + goto trigger_action; + } + + uint8_t ret = 0; + if (master_bytesToRead > 0) { + // return bytes really read + ret = master_bytesRead; + } else { + // return 0 if success, >0 otherwise (follow classic AVR conventions) + switch (master_result) { + case TWIM_RESULT_OK: + ret = 0; + break; + case TWIM_RESULT_BUFFER_OVERFLOW: + ret = 1; + break; + case TWIM_RESULT_NACK_RECEIVED: + ret = 3; + break; + default: + ret = 4; + break; + } + } + + return ret; + } else { + return 1; + } +} + + +/*! \brief Common TWI master interrupt service routine. + * + * Check current status and calls the appropriate handler. + * + */ +void TWI_MasterInterruptHandler() +{ + uint8_t currentStatus = TWI0.MSTATUS; + + /* If arbitration lost or bus error. */ + if ((currentStatus & TWI_ARBLOST_bm) || + (currentStatus & TWI_BUSERR_bm)) { + + TWI_MasterArbitrationLostBusErrorHandler(); + } + + /* If master write interrupt. */ + else if (currentStatus & TWI_WIF_bm) { + TWI_MasterWriteHandler(); + } + + /* If master read interrupt. */ + else if (currentStatus & TWI_RIF_bm) { + TWI_MasterReadHandler(); + } + + /* If unexpected state. */ + else { + TWI_MasterTransactionFinished(TWIM_RESULT_FAIL); + } +} + +/*! \brief TWI master arbitration lost and bus error interrupt handler. + * + * Handles TWI responses to lost arbitration and bus error. + * + */ +void TWI_MasterArbitrationLostBusErrorHandler() +{ + uint8_t currentStatus = TWI0.MSTATUS; + + /* If bus error. */ + if (currentStatus & TWI_BUSERR_bm) { + master_result = TWIM_RESULT_BUS_ERROR; + } + /* If arbitration lost. */ + else { + master_result = TWIM_RESULT_ARBITRATION_LOST; + } + + /* Clear all flags, abort operation */ + TWI0.MSTATUS = currentStatus; + + /* Wait for a new operation */ + twi_mode = TWI_MODE_MASTER; + master_trans_status = TWIM_STATUS_READY; +} + + +/*! \brief TWI master write interrupt handler. + * + * Handles TWI transactions (master write) and responses to (N)ACK. + * + */ +void TWI_MasterWriteHandler() +{ + /* Local variables used in if tests to avoid compiler warning. */ + uint8_t bytesToWrite = master_bytesToWrite; + uint8_t bytesToRead = master_bytesToRead; + + /* If NOT acknowledged (NACK) by slave cancel the transaction. */ + if (TWI0.MSTATUS & TWI_RXACK_bm) { + if(master_sendStop){ + TWI0.MCTRLB = TWI_MCMD_STOP_gc; + } else { + TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; + + } + TWI_MasterTransactionFinished(TWIM_RESULT_NACK_RECEIVED); + } + + /* If more bytes to write, send data. */ + else if (master_bytesWritten < bytesToWrite) { + uint8_t data = master_writeData[master_bytesWritten]; + TWI0.MDATA = data; + master_bytesWritten++; + } + + /* If bytes to read, send START condition + Address + + * 'R/_W = 1' + */ + else if (master_bytesRead < bytesToRead) { + twi_mode = TWI_MODE_MASTER_RECEIVE; + uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); + TWI0.MADDR = readAddress; + } + + /* If transaction finished, send ACK/STOP condition if instructed and set RESULT OK. */ + else { + if(master_sendStop){ + TWI0.MCTRLB = TWI_MCMD_STOP_gc; + } else { + TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; + } + TWI_MasterTransactionFinished(TWIM_RESULT_OK); + } +} + + +/*! \brief TWI master read interrupt handler. + * + * This is the master read interrupt handler that takes care of + * reading bytes from the TWI slave. + * + * \param twi The TWI_Master_t struct instance. + */ +void TWI_MasterReadHandler() +{ + /* Fetch data if bytes to be read. */ + if (master_bytesRead < master_bytesToRead) { + uint8_t data = TWI0.MDATA; + master_readData[master_bytesRead] = data; + master_bytesRead++; + } + + /* If buffer overflow, issue NACK/STOP and BUFFER_OVERFLOW condition. */ + else { + if(master_sendStop){ + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; + } else { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; + } + + TWI_MasterTransactionFinished(TWIM_RESULT_BUFFER_OVERFLOW); + master_bytesToRead = 0; + return; + } + + /* Local variable used in if test to avoid compiler warning. */ + uint8_t bytesToRead = master_bytesToRead; + + /* If more bytes to read, issue ACK and start a byte read. */ + if (master_bytesRead < bytesToRead) { + TWI0.MCTRLB = TWI_MCMD_RECVTRANS_gc; + } + + /* If transaction finished, issue NACK and STOP condition if instructed. */ + else { + if(master_sendStop){ + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; + } else { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; + } + + TWI_MasterTransactionFinished(TWIM_RESULT_OK); + } +} + + +/*! \brief TWI transaction finished handler. + * + * Prepares module for new transaction. + * + * \param result The result of the operation. + */ +void TWI_MasterTransactionFinished(uint8_t result) +{ + master_result = result; + master_trans_status = TWIM_STATUS_READY; + twi_mode = TWI_MODE_MASTER; +} + + +/*! \brief Common TWI slave interrupt service routine. + * + * Check current status and calls the appropriate handler. + * + */ +void TWI_SlaveInterruptHandler(){ + uint8_t currentStatus = TWI0.SSTATUS; + + /* If bus error */ + if(currentStatus & TWI_BUSERR_bm){ + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_bytesToWrite = 0; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUS_ERROR); + } + + /* If Address or Stop */ + else if(currentStatus & TWI_APIF_bm){ + + /* Call user onReceive function if end of Master Write/Slave Read. + * This should be hit when there is a STOP or REPSTART + */ + if(slave_callUserReceive == 1){ + TWI_onSlaveReceive(slave_bytesRead); + slave_callUserReceive = 0; + } + + /* If address match */ + if(currentStatus & TWI_AP_bm){ + TWI_SlaveAddressMatchHandler(); + } + + /* If stop */ + else { + TWI_SlaveStopHandler(); + + /* If CLKHOLD is high, we have missed an address match + from a fast start after stop. + Because the flag is shared we need to handle this here. + */ + if(TWI0.SSTATUS & TWI_CLKHOLD_bm){ + + /* CLKHOLD will be cleared by servicing the address match */ + TWI_SlaveAddressMatchHandler(); + } + } + } + + /* If Data Interrupt */ + else if (currentStatus & TWI_DIF_bm){ + + /* If collision flag is raised, slave transmit unsuccessful */ + if (currentStatus & TWI_COLL_bm){ + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_bytesToWrite = 0; + TWI_SlaveTransactionFinished(TWIS_RESULT_TRANSMIT_COLLISION); + } + + /* Otherwise, normal data interrupt */ + else { + TWI_SlaveDataHandler(); + } + } + + /* If unexpected state */ + else { + TWI_SlaveTransactionFinished(TWIS_RESULT_FAIL); + } +} + +/*! \brief TWI slave address interrupt handler. + * + * This is the slave address match handler that takes care of responding to + * being addressed by a master + * + */ +void TWI_SlaveAddressMatchHandler(){ + slave_trans_status = TWIS_STATUS_BUSY; + slave_result = TWIS_RESULT_UNKNOWN; + + /* Send ACK, wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + + /* If Master Read/Slave Write */ + if(TWI0.SSTATUS & TWI_DIR_bm){ + slave_bytesWritten = 0; + /* Call user function */ + slave_bytesToWrite = TWI_onSlaveTransmit(); + twi_mode = TWI_MODE_SLAVE_TRANSMIT; + } + /* If Master Write/Slave Read */ + else { + slave_bytesRead = 0; + slave_callUserReceive = 1; + twi_mode = TWI_MODE_SLAVE_RECEIVE; + } + + /* Data interrupt to follow... */ +} + +/*! \brief TWI slave stop interrupt handler. + * + */ +void TWI_SlaveStopHandler(){ + + /* Clear APIF, don't ACK or NACK */ + TWI0.SSTATUS = TWI_APIF_bm; + + TWI_SlaveTransactionFinished(TWIS_RESULT_OK); + +} + +/*! \brief TWI slave data interrupt handler. + * + * This is the slave data handler that takes care of sending data to or + * receiving data from a master + * + */ +void TWI_SlaveDataHandler(){ + + /* Enable stop interrupt */ + TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); + + /* If Master Read/Slave Write */ + if(TWI0.SSTATUS & TWI_DIR_bm){ + + TWI_SlaveWriteHandler(); + } + + /* If Master Write/Slave Read */ + else { + TWI_SlaveReadHandler(); + } + + +} + +/*! \brief TWI slave data write interrupt handler. + * + * This is the slave data handler that takes care of sending data to a master + * + */ +void TWI_SlaveWriteHandler(){ + + /* If NACK, slave write transaction finished */ + if((slave_bytesWritten > 0) && (TWI0.SSTATUS & TWI_RXACK_bm)){ + + TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_OK); + } + + /* If ACK, master expects more data */ + else { + + if(slave_bytesWritten < slave_bytesToWrite){ + uint8_t data = slave_writeData[slave_bytesWritten]; + TWI0.SDATA = data; + slave_bytesWritten++; + + /* Send data, wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + + } + + /* If buffer overflow */ + else { + TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); + + } + + + } +} + +/*! \brief TWI slave data read interrupt handler. + * + * This is the slave data handler that takes care of receiving data from a master + * + */ +void TWI_SlaveReadHandler(){ + + /* If free space in buffer */ + if(slave_bytesRead < slave_bytesToRead){ + + /* Fetch data */ + uint8_t data = TWI0.SDATA; + slave_readData[slave_bytesRead] = data; + slave_bytesRead++; + + /* Send ACK and wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + } + /* If buffer overflow, send NACK and wait for next START. + Set result buffer overflow */ + else { + TWI0.SCTRLB = TWI_ACKACT_bm | TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); + } +} + +/* + * Function twi_attachSlaveRxEvent + * Desc sets function called before a slave read operation + * Input function: callback function to use + * Output none + */ +void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ){ + TWI_onSlaveReceive = function; + slave_readData = read_data; + slave_bytesToRead = bytes_to_read; +} + +/* + * Function twi_attachSlaveTxEvent + * Desc sets function called before a slave write operation + * Input function: callback function to use + * Output none + */ +void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t* write_data ){ + TWI_onSlaveTransmit = function; + slave_writeData = write_data; +} + + +/*! \brief TWI slave transaction finished handler. + * + * Prepares module for new transaction. + * + * \param result The result of the operation. + */ +void TWI_SlaveTransactionFinished(uint8_t result) +{ + TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); + twi_mode = TWI_MODE_SLAVE; + slave_result = result; + slave_trans_status = TWIM_STATUS_READY; +} + +ISR(TWI0_TWIM_vect){ + TWI_MasterInterruptHandler(); +} + +ISR(TWI0_TWIS_vect){ + TWI_SlaveInterruptHandler(); } \ No newline at end of file diff --git a/megaavr/libraries/Wire/src/utility/twi.h b/megaavr/libraries/Wire/src/utility/twi.h index 9895ba7..401f118 100644 --- a/megaavr/libraries/Wire/src/utility/twi.h +++ b/megaavr/libraries/Wire/src/utility/twi.h @@ -1,127 +1,127 @@ -/****************************************************************************** -* (c) 2018 Microchip Technology Inc. and its subsidiaries. -* -* Subject to your compliance with these terms, you may use Microchip software -* and any derivatives exclusively with Microchip products. It is your -* responsibility to comply with third party license terms applicable to your -* use of third party software (including open source software) that may -* accompany Microchip software. -* -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER -* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED -* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR -* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, -* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY -* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP -* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE -* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN -* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, -* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. -* - *****************************************************************************/ - -#ifndef TWI_DRIVER_H -#define TWI_DRIVER_H - -#include "avr/io.h" - -/*! Transaction status defines. */ -#define TWIM_STATUS_READY 0 -#define TWIM_STATUS_BUSY 1 - -/* Transaction status defines.*/ -#define TWIS_STATUS_READY 0 -#define TWIS_STATUS_BUSY 1 - -/*! Transaction result enumeration. */ -typedef enum TWIM_RESULT_enum { - TWIM_RESULT_UNKNOWN = (0x00<<0), - TWIM_RESULT_OK = (0x01<<0), - TWIM_RESULT_BUFFER_OVERFLOW = (0x02<<0), - TWIM_RESULT_ARBITRATION_LOST = (0x03<<0), - TWIM_RESULT_BUS_ERROR = (0x04<<0), - TWIM_RESULT_NACK_RECEIVED = (0x05<<0), - TWIM_RESULT_FAIL = (0x06<<0), -} TWIM_RESULT_t; - -/* Transaction result enumeration */ -typedef enum TWIS_RESULT_enum { - TWIS_RESULT_UNKNOWN = (0x00<<0), - TWIS_RESULT_OK = (0x01<<0), - TWIS_RESULT_BUFFER_OVERFLOW = (0x02<<0), - TWIS_RESULT_TRANSMIT_COLLISION = (0x03<<0), - TWIS_RESULT_BUS_ERROR = (0x04<<0), - TWIS_RESULT_FAIL = (0x05<<0), - TWIS_RESULT_ABORTED = (0x06<<0), -} TWIS_RESULT_t; - -/*! TWI Modes */ -typedef enum TWI_MODE_enum { - TWI_MODE_UNKNOWN = 0, - TWI_MODE_MASTER = 1, - TWI_MODE_SLAVE = 2, - TWI_MODE_MASTER_TRANSMIT = 3, - TWI_MODE_MASTER_RECEIVE = 4, - TWI_MODE_SLAVE_TRANSMIT = 5, - TWI_MODE_SLAVE_RECEIVE = 6 -} TWI_MODE_t; - -/*! For adding R/_W bit to address */ -#define ADD_READ_BIT(address) (address | 0x01) -#define ADD_WRITE_BIT(address) (address & ~0x01) - -void TWI_MasterInit(uint32_t frequency); -void TWI_SlaveInit(uint8_t address); -void TWI_Flush(void); -void TWI_Disable(void); -TWI_BUSSTATE_t TWI_MasterState(void); -uint8_t TWI_MasterReady(void); -void TWI_MasterSetBaud(uint32_t frequency); -uint8_t TWI_MasterWrite(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t send_stop); -uint8_t TWI_MasterRead(uint8_t slave_address, - uint8_t* read_data, - uint8_t bytes_to_read, - uint8_t send_stop); -uint8_t TWI_MasterWriteRead(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t bytes_to_read, - uint8_t send_stop); -void TWI_MasterInterruptHandler(void); -void TWI_MasterArbitrationLostBusErrorHandler(void); -void TWI_MasterWriteHandler(void); -void TWI_MasterReadHandler(void); -void TWI_MasterTransactionFinished(uint8_t result); - -void TWI_SlaveInterruptHandler(void); -void TWI_SlaveAddressMatchHandler(void); -void TWI_SlaveStopHandler(void); -void TWI_SlaveDataHandler(void); -void TWI_SlaveWriteHandler(void); -void TWI_SlaveReadHandler(void); -void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ); -void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t *write_data ); -void TWI_SlaveTransactionFinished(uint8_t result); -/*! TWI master interrupt service routine. - * - * Interrupt service routine for the TWI master. Copy the needed vectors - * into your code. - * - - - ISR(TWI0_TWIM_vect){ - TWI_MasterInterruptHandler(); - } - - ISR(TWI0_TWIS_vect){ - TWI_SlaveInterruptHandler(); - } - - * - */ - - -#endif /* TWI_DRIVER_H */ +/****************************************************************************** +* (c) 2018 Microchip Technology Inc. and its subsidiaries. +* +* Subject to your compliance with these terms, you may use Microchip software +* and any derivatives exclusively with Microchip products. It is your +* responsibility to comply with third party license terms applicable to your +* use of third party software (including open source software) that may +* accompany Microchip software. +* +* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER +* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED +* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR +* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, +* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY +* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP +* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE +* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN +* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, +* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. +* + *****************************************************************************/ + +#ifndef TWI_DRIVER_H +#define TWI_DRIVER_H + +#include "avr/io.h" + +/*! Transaction status defines. */ +#define TWIM_STATUS_READY 0 +#define TWIM_STATUS_BUSY 1 + +/* Transaction status defines.*/ +#define TWIS_STATUS_READY 0 +#define TWIS_STATUS_BUSY 1 + +/*! Transaction result enumeration. */ +typedef enum TWIM_RESULT_enum { + TWIM_RESULT_UNKNOWN = (0x00<<0), + TWIM_RESULT_OK = (0x01<<0), + TWIM_RESULT_BUFFER_OVERFLOW = (0x02<<0), + TWIM_RESULT_ARBITRATION_LOST = (0x03<<0), + TWIM_RESULT_BUS_ERROR = (0x04<<0), + TWIM_RESULT_NACK_RECEIVED = (0x05<<0), + TWIM_RESULT_FAIL = (0x06<<0), +} TWIM_RESULT_t; + +/* Transaction result enumeration */ +typedef enum TWIS_RESULT_enum { + TWIS_RESULT_UNKNOWN = (0x00<<0), + TWIS_RESULT_OK = (0x01<<0), + TWIS_RESULT_BUFFER_OVERFLOW = (0x02<<0), + TWIS_RESULT_TRANSMIT_COLLISION = (0x03<<0), + TWIS_RESULT_BUS_ERROR = (0x04<<0), + TWIS_RESULT_FAIL = (0x05<<0), + TWIS_RESULT_ABORTED = (0x06<<0), +} TWIS_RESULT_t; + +/*! TWI Modes */ +typedef enum TWI_MODE_enum { + TWI_MODE_UNKNOWN = 0, + TWI_MODE_MASTER = 1, + TWI_MODE_SLAVE = 2, + TWI_MODE_MASTER_TRANSMIT = 3, + TWI_MODE_MASTER_RECEIVE = 4, + TWI_MODE_SLAVE_TRANSMIT = 5, + TWI_MODE_SLAVE_RECEIVE = 6 +} TWI_MODE_t; + +/*! For adding R/_W bit to address */ +#define ADD_READ_BIT(address) (address | 0x01) +#define ADD_WRITE_BIT(address) (address & ~0x01) + +void TWI_MasterInit(uint32_t frequency); +void TWI_SlaveInit(uint8_t address); +void TWI_Flush(void); +void TWI_Disable(void); +TWI_BUSSTATE_t TWI_MasterState(void); +uint8_t TWI_MasterReady(void); +void TWI_MasterSetBaud(uint32_t frequency); +uint8_t TWI_MasterWrite(uint8_t slave_address, + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t send_stop); +uint8_t TWI_MasterRead(uint8_t slave_address, + uint8_t* read_data, + uint8_t bytes_to_read, + uint8_t send_stop); +uint8_t TWI_MasterWriteRead(uint8_t slave_address, + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t bytes_to_read, + uint8_t send_stop); +void TWI_MasterInterruptHandler(void); +void TWI_MasterArbitrationLostBusErrorHandler(void); +void TWI_MasterWriteHandler(void); +void TWI_MasterReadHandler(void); +void TWI_MasterTransactionFinished(uint8_t result); + +void TWI_SlaveInterruptHandler(void); +void TWI_SlaveAddressMatchHandler(void); +void TWI_SlaveStopHandler(void); +void TWI_SlaveDataHandler(void); +void TWI_SlaveWriteHandler(void); +void TWI_SlaveReadHandler(void); +void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ); +void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t *write_data ); +void TWI_SlaveTransactionFinished(uint8_t result); +/*! TWI master interrupt service routine. + * + * Interrupt service routine for the TWI master. Copy the needed vectors + * into your code. + * + + + ISR(TWI0_TWIM_vect){ + TWI_MasterInterruptHandler(); + } + + ISR(TWI0_TWIS_vect){ + TWI_SlaveInterruptHandler(); + } + + * + */ + + +#endif /* TWI_DRIVER_H */ diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 69c405d..c50a97c 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -60,9 +60,9 @@ static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; static const uint8_t SCK = PIN_SPI_SCK; +// No pinswap available #define PIN_WIRE_SDA (20) #define PIN_WIRE_SCL (21) - static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; From 2f94e7b7cc0ff7f6d5e846e430068c43279f2fc3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 29 Sep 2019 22:32:22 +0200 Subject: [PATCH 065/351] Add modified Servo library Uses other timers than the default one. Timers can also be overrided --- megaavr/libraries/Servo/README.adoc | 25 +++ .../libraries/Servo/examples/Knob/Knob.ino | 27 +++ .../libraries/Servo/examples/Sweep/Sweep.ino | 32 +++ megaavr/libraries/Servo/keywords.txt | 24 ++ megaavr/libraries/Servo/library.properties | 9 + megaavr/libraries/Servo/src/Servo.h | 111 +++++++++ megaavr/libraries/Servo/src/megaavr/Servo.cpp | 212 ++++++++++++++++++ .../libraries/Servo/src/megaavr/ServoTimers.h | 56 +++++ 8 files changed, 496 insertions(+) create mode 100644 megaavr/libraries/Servo/README.adoc create mode 100644 megaavr/libraries/Servo/examples/Knob/Knob.ino create mode 100644 megaavr/libraries/Servo/examples/Sweep/Sweep.ino create mode 100644 megaavr/libraries/Servo/keywords.txt create mode 100644 megaavr/libraries/Servo/library.properties create mode 100644 megaavr/libraries/Servo/src/Servo.h create mode 100644 megaavr/libraries/Servo/src/megaavr/Servo.cpp create mode 100644 megaavr/libraries/Servo/src/megaavr/ServoTimers.h diff --git a/megaavr/libraries/Servo/README.adoc b/megaavr/libraries/Servo/README.adoc new file mode 100644 index 0000000..dd3f0ba --- /dev/null +++ b/megaavr/libraries/Servo/README.adoc @@ -0,0 +1,25 @@ += Servo Library for Arduino = + +This library allows an Arduino board to control RC (hobby) servo motors. + +For more information about this library please visit us at +http://www.arduino.cc/en/Reference/Servo + +== License == + +Copyright (c) 2013 Arduino LLC. All right reserved. +Copyright (c) 2009 Michael Margolis. All right reserved. + +This library is free software; you can redistribute it and/or +modify it under the terms of the GNU Lesser General Public +License as published by the Free Software Foundation; either +version 2.1 of the License, or (at your option) any later version. + +This library 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 +Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public +License along with this library; if not, write to the Free Software +Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA diff --git a/megaavr/libraries/Servo/examples/Knob/Knob.ino b/megaavr/libraries/Servo/examples/Knob/Knob.ino new file mode 100644 index 0000000..0db8770 --- /dev/null +++ b/megaavr/libraries/Servo/examples/Knob/Knob.ino @@ -0,0 +1,27 @@ +/* + Controlling a servo position using a potentiometer (variable resistor) + by Michal Rinott + + modified on 8 Nov 2013 + by Scott Fitzgerald + http://www.arduino.cc/en/Tutorial/Knob +*/ + +#include + +Servo myservo; // create servo object to control a servo + +int potpin = 0; // analog pin used to connect the potentiometer +int val; // variable to read the value from the analog pin + +void setup() { + myservo.attach(9); // attaches the servo on pin 9 to the servo object +} + +void loop() { + val = analogRead(potpin); // reads the value of the potentiometer (value between 0 and 1023) + val = map(val, 0, 1023, 0, 180); // scale it to use it with the servo (value between 0 and 180) + myservo.write(val); // sets the servo position according to the scaled value + delay(15); // waits for the servo to get there +} + diff --git a/megaavr/libraries/Servo/examples/Sweep/Sweep.ino b/megaavr/libraries/Servo/examples/Sweep/Sweep.ino new file mode 100644 index 0000000..df904af --- /dev/null +++ b/megaavr/libraries/Servo/examples/Sweep/Sweep.ino @@ -0,0 +1,32 @@ +/* Sweep + by BARRAGAN + This example code is in the public domain. + + modified 8 Nov 2013 + by Scott Fitzgerald + http://www.arduino.cc/en/Tutorial/Sweep +*/ + +#include + +Servo myservo; // create servo object to control a servo +// twelve servo objects can be created on most boards + +int pos = 0; // variable to store the servo position + +void setup() { + myservo.attach(9); // attaches the servo on pin 9 to the servo object +} + +void loop() { + for (pos = 0; pos <= 180; pos += 1) { // goes from 0 degrees to 180 degrees + // in steps of 1 degree + myservo.write(pos); // tell servo to go to position in variable 'pos' + delay(15); // waits 15ms for the servo to reach the position + } + for (pos = 180; pos >= 0; pos -= 1) { // goes from 180 degrees to 0 degrees + myservo.write(pos); // tell servo to go to position in variable 'pos' + delay(15); // waits 15ms for the servo to reach the position + } +} + diff --git a/megaavr/libraries/Servo/keywords.txt b/megaavr/libraries/Servo/keywords.txt new file mode 100644 index 0000000..0a7ca1e --- /dev/null +++ b/megaavr/libraries/Servo/keywords.txt @@ -0,0 +1,24 @@ +####################################### +# Syntax Coloring Map Servo +####################################### + +####################################### +# Datatypes (KEYWORD1) +####################################### + +Servo KEYWORD1 Servo + +####################################### +# Methods and Functions (KEYWORD2) +####################################### +attach KEYWORD2 +detach KEYWORD2 +write KEYWORD2 +read KEYWORD2 +attached KEYWORD2 +writeMicroseconds KEYWORD2 +readMicroseconds KEYWORD2 + +####################################### +# Constants (LITERAL1) +####################################### diff --git a/megaavr/libraries/Servo/library.properties b/megaavr/libraries/Servo/library.properties new file mode 100644 index 0000000..6fd2324 --- /dev/null +++ b/megaavr/libraries/Servo/library.properties @@ -0,0 +1,9 @@ +name=Servo +version=1.1.5 +author=MCUdude based on work by Michael Margolis, Arduino +maintainer=MCUdude +sentence=Allows megaAVR0 chips to control a variety of servo motors. +paragraph=This library can control a great number of servos.
It makes careful use of timers: the library can control 12 servos using only 1 timer.
On the Arduino Due you can control up to 60 servos.
+category=Device Control +url=http://www.arduino.cc/en/Reference/Servo +architectures=megaavr diff --git a/megaavr/libraries/Servo/src/Servo.h b/megaavr/libraries/Servo/src/Servo.h new file mode 100644 index 0000000..4a58550 --- /dev/null +++ b/megaavr/libraries/Servo/src/Servo.h @@ -0,0 +1,111 @@ +/* + Servo.h - Interrupt driven Servo library for Arduino using 16 bit timers- Version 2 + Copyright (c) 2009 Michael Margolis. All right reserved. + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +*/ + +/* + A servo is activated by creating an instance of the Servo class passing + the desired pin to the attach() method. + The servos are pulsed in the background using the value most recently + written using the write() method. + + Note that analogWrite of PWM on pins associated with the timer are + disabled when the first servo is attached. + Timers are seized as needed in groups of 12 servos - 24 servos use two + timers, 48 servos will use four. + The sequence used to sieze timers is defined in timers.h + + The methods are: + + Servo - Class for manipulating servo motors connected to Arduino pins. + + attach(pin ) - Attaches a servo motor to an i/o pin. + attach(pin, min, max ) - Attaches to a pin setting min and max values in microseconds + default min is 544, max is 2400 + + write() - Sets the servo angle in degrees. (invalid angle that is valid as pulse in microseconds is treated as microseconds) + writeMicroseconds() - Sets the servo pulse width in microseconds + read() - Gets the last written servo pulse width as an angle between 0 and 180. + readMicroseconds() - Gets the last written servo pulse width in microseconds. (was read_us() in first release) + attached() - Returns true if there is a servo attached. + detach() - Stops an attached servos from pulsing its i/o pin. + */ + +#ifndef Servo_h +#define Servo_h + +#include + +/* + * Defines for 16 bit timers used with Servo library + * + * If _useTimerX is defined then TimerX is a 16 bit timer on the current board + * timer16_Sequence_t enumerates the sequence that the timers should be allocated + * _Nbr_16timers indicates how many 16 bit timers are available. + */ + +// Architecture specific include +#if defined(ARDUINO_ARCH_MEGAAVR) + #include "megaavr/ServoTimers.h" + #if (F_CPU==1000000L) + #warning "Running at 1MHz results in unstable servo signal." + #endif +#else + #error "This library only supports boards with a megaAVR0 processor." +#endif + +#define Servo_VERSION 2 // software version of this library + +#define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo +#define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo +#define DEFAULT_PULSE_WIDTH 1500 // default pulse width when servo is attached +#define REFRESH_INTERVAL 20000 // minumim time to refresh servos in microseconds + +#define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer +#define MAX_SERVOS (_Nbr_16timers * SERVOS_PER_TIMER) + +#define INVALID_SERVO 255 // flag indicating an invalid servo index + +typedef struct { + uint8_t nbr :6 ; // a pin number from 0 to 63 + uint8_t isActive :1 ; // true if this channel is enabled, pin not pulsed if false +} ServoPin_t ; + +typedef struct { + ServoPin_t Pin; + volatile unsigned int ticks; +} servo_t; + +class Servo +{ +public: + Servo(); + uint8_t attach(int pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure + uint8_t attach(int pin, int min, int max); // as above but also sets min and max values for writes. + void detach(); + void write(int value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds + void writeMicroseconds(int value); // Write pulse width in microseconds + int read(); // returns current pulse width as an angle between 0 and 180 degrees + int readMicroseconds(); // returns current pulse width in microseconds for this servo (was read_us() in first release) + bool attached(); // return true if this servo is attached, otherwise false +private: + uint8_t servoIndex; // index into the channel data for this servo + int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH + int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH +}; + +#endif diff --git a/megaavr/libraries/Servo/src/megaavr/Servo.cpp b/megaavr/libraries/Servo/src/megaavr/Servo.cpp new file mode 100644 index 0000000..bf46c43 --- /dev/null +++ b/megaavr/libraries/Servo/src/megaavr/Servo.cpp @@ -0,0 +1,212 @@ +#if defined(ARDUINO_ARCH_MEGAAVR) + +#include +#include + +#define usToTicks(_us) ((( _us / 16) * clockCyclesPerMicrosecond()) / 4) // converts microseconds to tick +#define ticksToUs(_ticks) (((unsigned) _ticks * 16 * 4) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds + +#define TRIM_DURATION 5 // compensation ticks to trim adjust for digitalWrite delays + +static servo_t servos[MAX_SERVOS]; // static array of servo structures + +uint8_t ServoCount = 0; // the total number of attached servos + +static volatile int8_t currentServoIndex[_Nbr_16timers]; // index for the servo being pulsed for each timer (or -1 if refresh interval) + +// convenience macros +#define SERVO_INDEX_TO_TIMER(_servo_nbr) ((timer16_Sequence_t)(_servo_nbr / SERVOS_PER_TIMER)) // returns the timer controlling this servo +#define SERVO_INDEX_TO_CHANNEL(_servo_nbr) (_servo_nbr % SERVOS_PER_TIMER) // returns the index of the servo on this timer +#define SERVO_INDEX(_timer,_channel) ((_timer*SERVOS_PER_TIMER) + _channel) // macro to access servo index by timer and channel +#define SERVO(_timer,_channel) (servos[SERVO_INDEX(_timer,_channel)]) // macro to access servo class by timer and channel + +#define SERVO_MIN() (MIN_PULSE_WIDTH - this->min * 4) // minimum value in uS for this servo +#define SERVO_MAX() (MAX_PULSE_WIDTH - this->max * 4) // maximum value in uS for this servo + +void ServoHandler(int timer) +{ + if (currentServoIndex[timer] < 0) { + // Write compare register + _timer->CCMP = 0; + } else { + if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { + digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, LOW); // pulse this channel low if activated + } + } + + // Select the next servo controlled by this timer + currentServoIndex[timer]++; + + if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && currentServoIndex[timer] < SERVOS_PER_TIMER) { + if (SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { // check if activated + digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, HIGH); // it's an active channel so pulse it high + } + + // Get the counter value + uint16_t tcCounterValue = 0; //_timer->CCMP; + _timer->CCMP = (uint16_t) (tcCounterValue + SERVO(timer, currentServoIndex[timer]).ticks); + } + else { + // finished all channels so wait for the refresh period to expire before starting over + + // Get the counter value + uint16_t tcCounterValue = _timer->CCMP; + + if (tcCounterValue + 4UL < usToTicks(REFRESH_INTERVAL)) { // allow a few ticks to ensure the next OCR1A not missed + _timer->CCMP = (uint16_t) usToTicks(REFRESH_INTERVAL); + } + else { + _timer->CCMP = (uint16_t) (tcCounterValue + 4UL); // at least REFRESH_INTERVAL has elapsed + } + + currentServoIndex[timer] = -1; // this will get incremented at the end of the refresh period to start again at the first channel + } + + /* Clear flag */ + _timer->INTFLAGS = TCB_CAPT_bm; +} + +#if defined(SERVO_USE_TIMERB0) +ISR(TCB0_INT_vect) +#elif defined(SERVO_USE_TIMERB1) +ISR(TCB1_INT_vect) +#elif defined(SERVO_USE_TIMERB2) +ISR(TCB2_INT_vect) +#elif defined(SERVO_USE_TIMERB3) +ISR(TCB3_INT_vect) +#endif +{ + ServoHandler(0); +} + +static void initISR(__attribute__ ((unused)) timer16_Sequence_t timer) +{ + //TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV16_gc) | (TCA_SINGLE_ENABLE_bm); + _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; + // Timer to Periodic interrupt mode + // This write will also disable any active PWM outputs + _timer->CTRLB = TCB_CNTMODE_INT_gc; + // Enable interrupt + _timer->INTCTRL = TCB_CAPTEI_bm; + // Enable timer + _timer->CTRLA |= TCB_ENABLE_bm; +} + +static void finISR(__attribute__ ((unused)) timer16_Sequence_t timer) +{ + // Disable interrupt + _timer->INTCTRL = 0; +} + +static boolean isTimerActive(timer16_Sequence_t timer) +{ + // returns true if any servo is active on this timer + for(uint8_t channel=0; channel < SERVOS_PER_TIMER; channel++) { + if(SERVO(timer,channel).Pin.isActive == true) + return true; + } + return false; +} + +/****************** end of static functions ******************************/ + +Servo::Servo() +{ + if (ServoCount < MAX_SERVOS) { + this->servoIndex = ServoCount++; // assign a servo index to this instance + servos[this->servoIndex].ticks = usToTicks(DEFAULT_PULSE_WIDTH); // store default values + } else { + this->servoIndex = INVALID_SERVO; // too many servos + } +} + +uint8_t Servo::attach(int pin) +{ + return this->attach(pin, MIN_PULSE_WIDTH, MAX_PULSE_WIDTH); +} + +uint8_t Servo::attach(int pin, int min, int max) +{ + timer16_Sequence_t timer; + + if (this->servoIndex < MAX_SERVOS) { + pinMode(pin, OUTPUT); // set servo pin to output + servos[this->servoIndex].Pin.nbr = pin; + // todo min/max check: abs(min - MIN_PULSE_WIDTH) /4 < 128 + this->min = (MIN_PULSE_WIDTH - min)/4; //resolution of min/max is 4 uS + this->max = (MAX_PULSE_WIDTH - max)/4; + // initialize the timer if it has not already been initialized + timer = SERVO_INDEX_TO_TIMER(servoIndex); + if (isTimerActive(timer) == false) { + initISR(timer); + } + servos[this->servoIndex].Pin.isActive = true; // this must be set after the check for isTimerActive + } + return this->servoIndex; +} + +void Servo::detach() +{ + timer16_Sequence_t timer; + + servos[this->servoIndex].Pin.isActive = false; + timer = SERVO_INDEX_TO_TIMER(servoIndex); + if(isTimerActive(timer) == false) { + finISR(timer); + } +} + +void Servo::write(int value) +{ + // treat values less than 544 as angles in degrees (valid values in microseconds are handled as microseconds) + if (value < MIN_PULSE_WIDTH) + { + if (value < 0) + value = 0; + else if (value > 180) + value = 180; + + value = map(value, 0, 180, SERVO_MIN(), SERVO_MAX()); + } + writeMicroseconds(value); +} + +void Servo::writeMicroseconds(int value) +{ + // calculate and store the values for the given channel + byte channel = this->servoIndex; + if( (channel < MAX_SERVOS) ) // ensure channel is valid + { + if (value < SERVO_MIN()) // ensure pulse width is valid + value = SERVO_MIN(); + else if (value > SERVO_MAX()) + value = SERVO_MAX(); + + value = value - TRIM_DURATION; + value = usToTicks(value); // convert to ticks after compensating for interrupt overhead + servos[channel].ticks = value; + } +} + +int Servo::read() // return the value as degrees +{ + return map(readMicroseconds()+1, SERVO_MIN(), SERVO_MAX(), 0, 180); +} + +int Servo::readMicroseconds() +{ + unsigned int pulsewidth; + if (this->servoIndex != INVALID_SERVO) + pulsewidth = ticksToUs(servos[this->servoIndex].ticks) + TRIM_DURATION; + else + pulsewidth = 0; + + return pulsewidth; +} + +bool Servo::attached() +{ + return servos[this->servoIndex].Pin.isActive; +} + +#endif \ No newline at end of file diff --git a/megaavr/libraries/Servo/src/megaavr/ServoTimers.h b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h new file mode 100644 index 0000000..fe5bdfd --- /dev/null +++ b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h @@ -0,0 +1,56 @@ +/* + Copyright (c) 2018 Arduino LLC. All right reserved. + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +*/ + +/* + * Defines for 16 bit timers used with Servo library + * + */ + +#ifndef __SERVO_TIMERS_H__ +#define __SERVO_TIMERS_H__ + +#if !defined(SERVO_USE_TIMERB0) || !defined(SERVO_USE_TIMERB1) || !defined(SERVO_USE_TIMERB2) || !defined(SERVO_USE_TIMERB3) + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) + #define SERVO_USE_TIMERB1 + #elif defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) + #define SERVO_USE_TIMERB3 + #else + #error "No timers allowed for Servo" + #endif +#endif + +__attribute__ ((used)) static volatile TCB_t* _timer = +#if defined(SERVO_USE_TIMERB0) + &TCB0; +#endif +#if defined(SERVO_USE_TIMERB1) + &TCB1; +#endif +#if defined(SERVO_USE_TIMERB2) + &TCB2; +#endif +#if defined(SERVO_USE_TIMERB3) + &TCB3; +#endif + +typedef enum { + timer0, + _Nbr_16timers } timer16_Sequence_t; + + +#endif /* __SERVO_TIMERS_H__ */ From 5a8ba68cfd8b61770f2d7e5e07a1c27e3173d176 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 30 Sep 2019 14:44:43 +0200 Subject: [PATCH 066/351] Map all analog inputs to Arduino pins Even though only A0 - A5 is marked on the UNO Wifi Rev2 silkscreen, is _has_ more ADC pins. Now you can access them through analogRead() --- megaavr/variants/uno-wifi/pins_arduino.h | 40 ++++++++++++++++++------ 1 file changed, 30 insertions(+), 10 deletions(-) diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index c50a97c..5ac7f49 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -30,7 +30,7 @@ #define UNO2018_PINOUT #define NUM_DIGITAL_PINS 20 // (14 on digital headers + 6 on analog headers) -#define NUM_ANALOG_INPUTS 6 +#define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 6 // (TOSC1/2, VREF, RESET, DEBUG USART Rx/Tx) #define NUM_INTERNALLY_USED_PINS 10 // (2 x Chip select + 2 x UART + 4 x IO + LED_BUILTIN + 1 unused pin) #define NUM_I2C_PINS 2 // (SDA / SCL) @@ -38,8 +38,8 @@ #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) #define ANALOG_INPUT_OFFSET 14 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - ANALOG_INPUT_OFFSET) -#define digitalOrAnalogPinToDigital(p) ((p <= 5) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 14 && (p) <= 19) ? (p) : NOT_A_PIN) +#define digitalPinToAnalogInput(p) (((p) <= 5 && (p) != 3) ? (p) : ((p) >= 14 && (p) <= 19) ? ((p) - 14) : ((p) == 25) ? ((p) - 19) : ((p) == 39) ? ((p) - 32) : ((p) >= 11 && (p) <= 13) ? ((p) - 3) : ((p) == 8) ? ((p) + 3) : ((p) >= 35 && (p) <= 36) ? ((p) - 23) : ((p) == 6) ? ((p) + 8) : ((p) == 3) ? ((p) + 12) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) #define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation @@ -122,13 +122,33 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_A3 (17) #define PIN_A4 (18) #define PIN_A5 (19) - -static const uint8_t A0 = PIN_A0; -static const uint8_t A1 = PIN_A1; -static const uint8_t A2 = PIN_A2; -static const uint8_t A3 = PIN_A3; -static const uint8_t A4 = PIN_A4; -static const uint8_t A5 = PIN_A5; +#define PIN_A6 (25) +#define PIN_A7 (39) +#define PIN_A8 (11) +#define PIN_A9 (12) +#define PIN_A10 (13) +#define PIN_A11 (8) +#define PIN_A12 (35) +#define PIN_A13 (36) +#define PIN_A14 (6) +#define PIN_A15 (3) + +static const uint8_t A0 = PIN_A0; +static const uint8_t A1 = PIN_A1; +static const uint8_t A2 = PIN_A2; +static const uint8_t A3 = PIN_A3; +static const uint8_t A4 = PIN_A4; +static const uint8_t A5 = PIN_A5; +static const uint8_t A6 = PIN_A6; +static const uint8_t A7 = PIN_A7; +static const uint8_t A8 = PIN_A8; +static const uint8_t A9 = PIN_A9; +static const uint8_t A10 = PIN_A10; +static const uint8_t A11 = PIN_A11; +static const uint8_t A12 = PIN_A12; +static const uint8_t A13 = PIN_A13; +static const uint8_t A14 = PIN_A14; +static const uint8_t A15 = PIN_A15; #define PINS_COUNT (40u) From c7cb716d64860882f3eb819375b946692d9fd825 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 30 Sep 2019 19:09:42 +0200 Subject: [PATCH 067/351] Update Uno Wifi Rev2 pinouts --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index bee780c..ff48799 100644 --- a/README.md +++ b/README.md @@ -103,7 +103,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## PWM output @@ -198,7 +198,7 @@ Here's some simple schematics that shows a minimal setup. The straight 6-pin hea [The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with, because it's officially supported by Arduino. It uses an ATmega4809, and recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer in order to upload code. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. Use the `LED_BUILTIN` macro to control the onboard LED. Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. From 9e80ecccd21accdcfec7b08c197a03aaaa046fea Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 30 Sep 2019 23:20:44 +0200 Subject: [PATCH 068/351] Remove register emulation feature Messes with the existing PORTx registers. We don't want that --- megaavr/boards.txt | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index b11db88..bc5f9f1 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -34,7 +34,7 @@ menu.resetpin=Reset pin 4809.menu.pinout.48pin_standard.build.compat= 4809.menu.pinout.uno_wifi=Uno WiFi 4809.menu.pinout.uno_wifi.build.variant=uno-wifi -4809.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE +4809.menu.pinout.uno_wifi.build.compat= # Reset pin 4809.menu.resetpin.reset=Reset @@ -291,7 +291,7 @@ menu.resetpin=Reset pin 3209.menu.pinout.48pin_standard.build.compat= 3209.menu.pinout.uno_wifi=Uno WiFi 3209.menu.pinout.uno_wifi.build.variant=uno-wifi -3209.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE +3209.menu.pinout.uno_wifi.build.compat= # Reset pin @@ -544,7 +544,7 @@ menu.resetpin=Reset pin 1609.menu.pinout.48pin_standard.build.compat= 1609.menu.pinout.uno_wifi=Uno WiFi 1609.menu.pinout.uno_wifi.build.variant=uno-wifi -1609.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE +1609.menu.pinout.uno_wifi.build.compat= # Reset pin 1609.menu.resetpin.reset=Reset @@ -639,11 +639,6 @@ menu.resetpin=Reset pin 1609.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 1609.menu.clock.external_1MHz.build.f_cpu=1000000L -# ATmega328 emulation -1609.menu.emulation.false=No -1609.menu.emulation.true=Yes -1609.menu.emulation.true.build.extra_flags=-DUNO_WIFI_REV2_328MODE - #################### @@ -801,7 +796,7 @@ menu.resetpin=Reset pin 809.menu.pinout.48pin_standard.build.compat= 809.menu.pinout.uno_wifi=Uno WiFi 809.menu.pinout.uno_wifi.build.variant=uno-wifi -809.menu.pinout.uno_wifi.build.compat=-DUNO_WIFI_REV2_328MODE +809.menu.pinout.uno_wifi.build.compat= # Reset pin 809.menu.resetpin.reset=Reset From a7bdb9b75a3e46fd121320a8cf89a54823f15db5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 2 Oct 2019 22:05:05 +0200 Subject: [PATCH 069/351] Add library for interfacing with the Configurable Custom Logic Closes #38 --- .../Five_input_NOR/Five_input_NOR.ino | 56 ++++++ .../Logic/examples/Interrupt/Interrupt.ino | 66 +++++++ .../Three_input_AND/Three_input_AND.ino | 56 ++++++ .../Three_input_NAND/Three_input_NAND.ino | 56 ++++++ .../Three_input_OR/Three_input_OR.ino | 56 ++++++ .../examples/Two_input_AND/Two_input_AND.ino | 57 ++++++ .../Two_input_NAND/Two_input_NAND.ino | 57 ++++++ .../examples/Two_input_OR/Two_input_OR.ino | 57 ++++++ megaavr/libraries/Logic/keywords.txt | 70 +++++++ megaavr/libraries/Logic/library.properties | 9 + megaavr/libraries/Logic/src/Logic.cpp | 143 ++++++++++++++ megaavr/libraries/Logic/src/Logic.h | 185 ++++++++++++++++++ 12 files changed, 868 insertions(+) create mode 100644 megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino create mode 100644 megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino create mode 100644 megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino create mode 100644 megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino create mode 100644 megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino create mode 100644 megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino create mode 100644 megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino create mode 100644 megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino create mode 100644 megaavr/libraries/Logic/keywords.txt create mode 100644 megaavr/libraries/Logic/library.properties create mode 100644 megaavr/libraries/Logic/src/Logic.cpp create mode 100644 megaavr/libraries/Logic/src/Logic.h diff --git a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino new file mode 100644 index 0000000..a9ab15b --- /dev/null +++ b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino @@ -0,0 +1,56 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Five_input_NOR.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use two logic blocks to get five inputs. | +| The output of block 1 is connected to one of the inputs of block 0. | +| With the correct truth tables values we can make the output of | +| block 0 go high when all inputs are low. | +| | +| See Microchip's application note TB3218 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 1 + // Logic block 1 has three inputs, PC0, PC1 and PC2. + // It's output, PC3 is disabled because we connect the output signal to block 0 internally + Logic.block1.enable = true; // Enable logic block 1 + Logic.block1.input0 = in::input_pullup; // Set PC0 as input with pullup + Logic.block1.input1 = in::input_pullup; // Set PC1 as input with pullup + Logic.block1.input2 = in::input_pullup; // Set PC2 as input with pullup + Logic.block1.output = out::disable; // No output on PC3 + Logic.block1.filter = filter::disable; // No output filter enabled + Logic.block1.truth = 0xFE; // Set truth table + + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // input2 is internally connected to the output of block1 (which means PA2 is freed up) + // Block 0 output on PA3 + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic.block0.input2 = in::link; // Route output from block 1 to this input internally + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0x01; // Set truth table + + // Initialize logic block 0 and 1 + Logic.init(Logic.block0); + Logic.init(Logic.block1); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino new file mode 100644 index 0000000..174e3f5 --- /dev/null +++ b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino @@ -0,0 +1,66 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Interrupt.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 3-input NOR gate using logic block 2 on PORT D. | +| We will use input on PD0, PD1 and PD2. Instead of having an output | +| pin the logic block will instead trigger an interrupt that runs a | +| user defined function. | +| | +| 3-input NOR truth table: | +| If we look at the truth table |PD2|PD1|PD0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 1 | | +| be represented as 00000001. | 0 | 0 | 1 | 0 | | +| If we convert this 8-bit | 0 | 1 | 0 | 0 | | +| binary number into hex, we | 0 | 1 | 1 | 0 | | +| get 0x01. | 1 | 0 | 0 | 0 | | +| | 1 | 0 | 1 | 0 | | +| In this example the output is | 1 | 1 | 0 | 0 | | +| true if all inputs are low. | 1 | 1 | 1 | 0 | | +| | +|***********************************************************************/ + +#include + +void setup() +{ + // Modify the serial port to match your hardware + Serial.begin(9600); + + // Initialize logic block 2 + // Logic block 2 has three inputs, PA0, PA1 and PA2. + // It has one output, but this is disabled because we're using an interrupt instead. + Logic.block2.enable = true; // Enable logic block 0 + Logic.block2.input0 = in::input_pullup; // Set PD0 as input with pullup + Logic.block2.input1 = in::input_pullup; // Set PD1 as input with pullup + Logic.block2.input2 = in::input_pullup; // Set PD2 as input with pullup + Logic.block2.output = out::disable; // Disable output on PD3 (we don't have to though) + Logic.block2.filter = filter::disable; // No output filter enabled + Logic.block2.truth = 0x01; // Set truth table + + // Initialize logic block 2 + Logic.init(Logic.block2); + + // Set interrupt (supports RISING, FALLING and CHANGE) + Logic.attachInterrupt(Logic.block2, interruptFunction, RISING); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} + +void interruptFunction() +{ + Serial.println("Output of logic block 2 went high!"); +} diff --git a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino new file mode 100644 index 0000000..54a31c1 --- /dev/null +++ b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino @@ -0,0 +1,56 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Three_input_AND.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 3-input AND gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| Here's how 0x80 turns out to be the correct value to create a 3-input | +| AND gate: | +| 3-input AND truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 0 | | +| be represented as 10000000. | 0 | 0 | 1 | 0 | | +| If we convert this 8-bit | 0 | 1 | 0 | 0 | | +| binary number into hex, we | 0 | 1 | 1 | 0 | | +| get 0x80. | 1 | 0 | 0 | 0 | | +| | 1 | 0 | 1 | 0 | | +| In this example the output pin, | 1 | 1 | 0 | 0 | | +| PA3 will go high if all three | 1 | 1 | 1 | 1 | | +| inputs are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0x80; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino new file mode 100644 index 0000000..c5cb919 --- /dev/null +++ b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino @@ -0,0 +1,56 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Three_input_NAND.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 3-input NAND gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| Here's how 0x7F turns out to be the correct value to create a 3-input | +| NAND gate: | +| 3-input NAND truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 1 | | +| be represented as 01111111. | 0 | 0 | 1 | 1 | | +| If we convert this 8-bit | 0 | 1 | 0 | 1 | | +| binary number into hex, we | 0 | 1 | 1 | 1 | | +| get 0x7F. | 1 | 0 | 0 | 1 | | +| | 1 | 0 | 1 | 1 | | +| In this example the output pin | 1 | 1 | 0 | 1 | | +| PA3 will go low if all three | 1 | 1 | 1 | 0 | | +| inputs are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0x7F; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino new file mode 100644 index 0000000..4a5d75b --- /dev/null +++ b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino @@ -0,0 +1,56 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Three_input_OR.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 3-input OR gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| Here's how 0xFE turns out to be the correct value to create a 3-input | +| OR gate: | +| 3-input OR truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 0 | | +| be represented as 11111110. | 0 | 0 | 1 | 1 | | +| If we convert this 8-bit | 0 | 1 | 0 | 1 | | +| binary number into hex, we | 0 | 1 | 1 | 1 | | +| get 0xFE. | 1 | 0 | 0 | 1 | | +| | 1 | 0 | 1 | 1 | | +| In this example the output pin, | 1 | 1 | 0 | 1 | | +| PA3 will go high if one or more | 1 | 1 | 1 | 1 | | +| inputs are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0xFE; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino new file mode 100644 index 0000000..0f77625 --- /dev/null +++ b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino @@ -0,0 +1,57 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Two_input_AND.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 2-input AND gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| We will only use PA0 and PA1 as inputs. When the last input is | +| disabled it will always be read as 0. | +| Here's how 0x08 turns out to be the correct value to create a 2-input | +| NAND gate: | +| 2-input AND truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 0 | | +| be represented as 00001000. | 0 | 0 | 1 | 0 | | +| If we convert this 8-bit | 0 | 1 | 0 | 0 | | +| binary number into hex, we | 0 | 1 | 1 | 1 | | +| get 0x08. | 1 | 0 | 0 | 0 | PA2 is always 0 | +| | 1 | 0 | 1 | 0 | PA2 is always 0 | +| In this example the output pin, | 1 | 1 | 0 | 0 | PA2 is always 0 | +| PA3 will only go high if the | 1 | 1 | 1 | 0 | PA2 is always 0 | +| two input pins are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0x08; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino new file mode 100644 index 0000000..d88fd91 --- /dev/null +++ b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino @@ -0,0 +1,57 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Two_input_NAND.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 2-input NAND gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| We will only use PA0 and PA1 as inputs. when the last input is | +| disabled it will always be read as 0. | +| Here's how 0xF7 turns out to be the correct value to create a 2-input | +| NAND gate: | +| 2-input NAND truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 1 | | +| be represented as 11110111. | 0 | 0 | 1 | 1 | | +| If we convert this 8-bit | 0 | 1 | 0 | 1 | | +| binary number into hex, we | 0 | 1 | 1 | 0 | | +| get 0xF7. | 1 | 0 | 0 | 1 | PA2 is always 0 | +| | 1 | 0 | 1 | 1 | PA2 is always 0 | +| In this example the output pin, | 1 | 1 | 0 | 1 | PA2 is always 0 | +| PA3 will only go low if the | 1 | 1 | 1 | 1 | PA2 is always 0 | +| two input pins are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0xF7; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino new file mode 100644 index 0000000..d85dc5d --- /dev/null +++ b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino @@ -0,0 +1,57 @@ +/***********************************************************************| +| megaAVR Configurable Custom Logic library | +| | +| Two_input_OR.ino | +| | +| A library for interfacing with the megaAVR Configurable Custom Logic. | +| Developed in 2019 by MCUdude for use with MegaCoreX. | +| https://github.com/MCUdude/MegaCoreX | +| | +| In this example we use the configurable logic peripherals the the | +| megaAVR to create a 2-input OR gate using logic block 0 on PORT A. | +| The example is pretty straight forward, but the truth table value may | +| be a little difficult to understand at first glance. | +| We will only use PA0 and PA1 as inputs. When the last input is | +| disabled it will always be read as 0. | +| Here's how 0xFE turns out to be the correct value to create a 2-input | +| OR gate: | +| 2-input OR truth table: | +| If we look at the truth table |PA2|PA1|PA0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 0 | | +| be represented as 11111110. | 0 | 0 | 1 | 1 | | +| If we convert this 8-bit | 0 | 1 | 0 | 1 | | +| binary number into hex, we | 0 | 1 | 1 | 1 | | +| get 0xFE. | 1 | 0 | 0 | 1 | PA2 is always 0 | +| | 1 | 0 | 1 | 1 | PA2 is always 0 | +| In this example the output pin, | 1 | 1 | 0 | 1 | PA2 is always 0 | +| PA3 will go high if one of | 1 | 1 | 1 | 1 | PA2 is always 0 | +| the input pins are high. | +|***********************************************************************/ + +#include + +void setup() +{ + // Initialize logic block 0 + // Logic block 0 has three inputs, PA0, PA1 and PA2. + // It has one output, PA3, but can be swapped to PA6 if needed + Logic.block0.enable = true; // Enable logic block 0 + Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic.block0.filter = filter::disable; // No output filter enabled + Logic.block0.truth = 0xFE; // Set truth table + + // Initialize logic block 0 + Logic.init(Logic.block0); + + // Start the AVR logic hardware + Logic.start(); +} + +void loop() +{ + // When using configurable custom logic the CPU isn't doing anything! +} diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt new file mode 100644 index 0000000..6cf3094 --- /dev/null +++ b/megaavr/libraries/Logic/keywords.txt @@ -0,0 +1,70 @@ +####################################### +# Syntax Coloring Map For Wire +####################################### + +####################################### +# Datatypes (KEYWORD1) +####################################### + +#masked LITERAL1 +#unused LITERAL1 +#disable LITERAL1 +#feedback LITERAL1 +#link LITERAL1 +#event_a LITERAL1 +#event_b LITERAL1 +#input LITERAL1 +#ac LITERAL1 +#input_pullup LITERAL1 +#usart LITERAL1 +#spi LITERAL1 +#tca0 LITERAL1 +#tcb LITERAL1 + +#disable LITERAL1 +#no_swap LITERAL1 +#enable LITERAL1 +#pin_swap LITERAL1 + +#disable LITERAL1 +#synchronizer LITERAL1 +#filter LITERAL1 + +#disable LITERAL1 +#d_flip_flop LITERAL1 +#jk_flip_flop LITERAL1 +#d_latch LITERAL1 +#sr_latch LITERAL1 +#rs_latch LITERAL1 + + + +####################################### +# Methods and Functions (KEYWORD2) +####################################### + +begin KEYWORD2 +end KEYWORD2 +init KEYWORD2 +attachInterrupt KEYWORD2 +detachInterrupt KEYWORD2 + + +####################################### +# Instances (KEYWORD2) +####################################### + +Logic KEYWORD2 +block0 KEYWORD2 +block1 KEYWORD2 +block2 KEYWORD2 +block3 KEYWORD2 + +####################################### +# Constants (LITERAL1) +####################################### + +in LITERAL1 +out LITERAL1 +filter LITERAL1 +sequencer LITERAL1 diff --git a/megaavr/libraries/Logic/library.properties b/megaavr/libraries/Logic/library.properties new file mode 100644 index 0000000..984a10c --- /dev/null +++ b/megaavr/libraries/Logic/library.properties @@ -0,0 +1,9 @@ +name=Logic +version=1.0.0 +author=MCUdude +maintainer=MCUdude +sentence=A library for interfacing with the customizable logic in megaAVR chips +paragraph= +category=Signal Input/Output +url=https://github.com/MCUdude/MegaCoreX +architectures=megaavr diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp new file mode 100644 index 0000000..e9d75d3 --- /dev/null +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -0,0 +1,143 @@ +#include "Logic.h" + +// Preinstantiate Object +CustomLogic Logic; + +CustomLogic::CustomLogic() +{ +} + +void CustomLogic::start(bool state) +{ + CCL.CTRLA = (state << CCL_ENABLE_bp); +} + + +void CustomLogic::end() +{ + start(false); +} + + +void CustomLogic::init(block_t &block) +{ + // Block input 0 pin dir + if(block.input0 == in::input) + block.PORT->DIR &= ~PIN0_bm; + else if(block.input0 == in::input_pullup) + { + block.PORT->DIR &= ~PIN0_bm; + block.PORT->PIN0CTRL |= PORT_PULLUPEN_bm; + block.input0 = in::input; + } + // Block input 1 pin dir + if(block.input1 == in::input) + block.PORT->DIR &= ~PIN1_bm; + else if(block.input1 == in::input_pullup) + { + block.PORT->DIR &= ~PIN1_bm; + block.PORT->PIN1CTRL |= PORT_PULLUPEN_bm; + block.input1 = in::input; + } + // Block input 2 pin dir + if(block.input2 == in::input) + block.PORT->DIR &= ~PIN2_bm; + else if(block.input2 == in::input_pullup) + { + block.PORT->DIR &= ~PIN2_bm; + block.PORT->PIN2CTRL |= PORT_PULLUPEN_bm; + block.input2 = in::input; + } + + // Set inputs modes + *block.LUTCTRLB = (block.input1 << 4) | block.input0; + *block.LUTCTRLC |= 0xFF & block.input2; + + // Set truth table + *block.TRUTH = block.truth; + + // Set sequencer + *block.SEQCTRL = block.sequencer; + + // Set output pin state and output pin swap + if(block.output == out::enable) + { + if(block.output_swap == out::pin_swap) + { + PORTMUX.CCLROUTEA |= (block.output_swap << block.block_number); + block.PORT->DIR |= PIN6_bm; + } + else if(block.output_swap == out::no_swap) + { + PORTMUX.CCLROUTEA &= (block.output_swap << block.block_number); + block.PORT->DIR |= PIN3_bm; + } + } + + // Set logic output state and output filter + *block.LUTCTRLA = (block.output << 6) | (block.filter << 4) | (block.enable << 0); +} + + +void CustomLogic::attachInterrupt(block_t &block, void (*userFunc)(void), PinStatus mode) +{ + switch (mode) + { + // Set RISING, FALLING or CHANGE interrupt trigger for a block output + case RISING: + CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (1 << (block.block_number * 2)); + break; + case FALLING: + CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (2 << (block.block_number * 2)); + break; + case CHANGE: + CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (3 << (block.block_number * 2)); + break; + default: + // Only RISING, FALLING and CHANGE is supported + return; + } + + // Store function pointer + intFuncCCL[block.block_number] = userFunc; +} + + +void CustomLogic::detachInterrupt(block_t &block) +{ + // Disable interrupt for a given block output + CCL.INTCTRL0 &= ~(0x03 << (block.block_number * 2)); +} + + +// CCL interrupt service routine +// Use attachIntterupt to activate this. +ISR(CCL_CCL_vect) +{ + // Cleck for block 0 interrupt + if(CCL.INTFLAGS & CCL_INT0_bm) + { + // Run user function + intFuncCCL[CCL_INT0_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT0_bm; + } + if(CCL.INTFLAGS & CCL_INT1_bm) + { + intFuncCCL[CCL_INT1_bp](); + CCL.INTFLAGS |= CCL_INT1_bm; + } + if(CCL.INTFLAGS & CCL_INT2_bm) + { + intFuncCCL[CCL_INT2_bp](); + CCL.INTFLAGS |= CCL_INT2_bm; + } + // Cleck for block 3 interrupt + if(CCL.INTFLAGS & CCL_INT3_bm) + { + // Run user function + intFuncCCL[CCL_INT3_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT3_bm; + } +} \ No newline at end of file diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h new file mode 100644 index 0000000..5fb901f --- /dev/null +++ b/megaavr/libraries/Logic/src/Logic.h @@ -0,0 +1,185 @@ +// edge detect + +#ifndef LOGIC_h +#define LOGIC_h + +#include + +// Array for storing ISR function pointers +static volatile voidFuncPtr intFuncCCL[4]; + +//Use in:: when working with logic inputs +namespace in +{ + enum + { + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_a = 0x03, + event_b = 0x04, + input = 0x05, + ac = 0x06, + input_pullup = 0x07, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tcb = 0x0C, + }; +}; + +// Use out:: when working with logic outputs +namespace out +{ + enum + { + disable = 0x00, + no_swap = 0x00, + enable = 0x01, + pin_swap = 0x02, + }; +}; + +// Use filter:: when working with logic output filter +namespace filter +{ + enum + { + disable = 0x00, + synchronizer = 0x01, + filter = 0x02, + }; +}; + +// Use sequencer:: when working with LUT sequencer +namespace sequencer +{ + enum + { + disable = 0x00, + d_flip_flop = 0x01, + jk_flip_flop = 0x02, + d_latch = 0x03, + sr_latch = 0x04, + rs_latch = 0x04, + }; +}; + +class CustomLogic +{ + private: + // Struct that holds all information a single logic block needs + typedef struct + { + const uint8_t block_number; + PORT_t* PORT; + volatile uint8_t* SEQCTRL; + volatile uint8_t* LUTCTRLA; + volatile uint8_t* LUTCTRLB; + volatile uint8_t* LUTCTRLC; + volatile uint8_t* TRUTH; + uint8_t input0; + uint8_t input1; + uint8_t input2; + uint8_t output; + uint8_t enable; + uint8_t truth; + uint8_t output_swap; + uint8_t filter; + uint8_t sequencer; + } block_t; + + public: + CustomLogic(); + void start(bool state = true); + void end(); + void init(block_t &block); + void attachInterrupt(block_t &block, voidFuncPtr callback, PinStatus mode); + void detachInterrupt(block_t &block); + + // Struct object for logic block 0 (IOs connected to PORTA) + block_t block0 = { + .block_number = 0, + .PORT = &PORTA, + .SEQCTRL = &CCL_SEQCTRL0, + .LUTCTRLA = &CCL_LUT0CTRLA, + .LUTCTRLB = &CCL_LUT0CTRLB, + .LUTCTRLC = &CCL_LUT0CTRLC, + .TRUTH = &CCL_TRUTH0, + .input0 = in::masked, + .input1 = in::masked, + .input2 = in::masked, + .output = false, + .enable = false, + .truth = 0x00, + .output_swap = out::no_swap, + .filter = filter::disable, + .sequencer = sequencer::disable, + }; + + // Struct object for logic block 1 (IOs connected to PORTC) + block_t block1 = { + .block_number = 1, + .PORT = &PORTC, + .SEQCTRL = &CCL_SEQCTRL0, + .LUTCTRLA = &CCL_LUT1CTRLA, + .LUTCTRLB = &CCL_LUT1CTRLB, + .LUTCTRLC = &CCL_LUT1CTRLC, + .TRUTH = &CCL_TRUTH1, + .input0 = in::masked, + .input1 = in::masked, + .input2 = in::masked, + .output = out::disable, + .enable = false, + .truth = 0x00, + .output_swap = out::no_swap, + .filter = filter::disable, + .sequencer = sequencer::disable, + }; + + // Struct object for logic block 2 (IOs connected to PORTD) + block_t block2 = { + .block_number = 2, + .PORT = &PORTD, + .SEQCTRL = &CCL_SEQCTRL1, + .LUTCTRLA = &CCL_LUT2CTRLA, + .LUTCTRLB = &CCL_LUT2CTRLB, + .LUTCTRLC = &CCL_LUT2CTRLC, + .TRUTH = &CCL_TRUTH2, + .input0 = in::masked, + .input1 = in::masked, + .input2 = in::masked, + .output = out::disable, + .enable = false, + .truth = 0x00, + .output_swap = out::no_swap, + .filter = filter::disable, + .sequencer = sequencer::disable, + }; + + // Struct object for logic block 3 (IOs connected to PORTF) + block_t block3 = { + .block_number = 3, + .PORT = &PORTF, + .SEQCTRL = &CCL_SEQCTRL1, + .LUTCTRLA = &CCL_LUT3CTRLA, + .LUTCTRLB = &CCL_LUT3CTRLB, + .LUTCTRLC = &CCL_LUT3CTRLC, + .TRUTH = &CCL_TRUTH3, + .input0 = in::masked, + .input1 = in::masked, + .input2 = in::masked, + .output = out::disable, + .enable = false, + .truth = 0x00, + .output_swap = out::no_swap, + .filter = filter::disable, + .sequencer = sequencer::disable, + }; +}; + +extern CustomLogic Logic; + +#endif From ce672c246dda34483c43dd275a2b44081ccd458b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 4 Oct 2019 22:38:01 +0200 Subject: [PATCH 070/351] Fix pin swap value --- megaavr/libraries/Logic/src/Logic.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 5fb901f..54c0df6 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -36,9 +36,9 @@ namespace out enum { disable = 0x00, - no_swap = 0x00, enable = 0x01, - pin_swap = 0x02, + no_swap = 0x00, + pin_swap = 0x01, }; }; From cb9f710824a6b92583dc663ac3a039731e0ad923 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 7 Oct 2019 00:16:10 +0200 Subject: [PATCH 071/351] Pinout diagrams now have CCL pins marked --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index ff48799..2448d18 100644 --- a/README.md +++ b/README.md @@ -103,7 +103,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## PWM output @@ -198,22 +198,22 @@ Here's some simple schematics that shows a minimal setup. The straight 6-pin hea [The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with, because it's officially supported by Arduino. It uses an ATmega4809, and recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer in order to upload code. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. Use the `LED_BUILTIN` macro to control the onboard LED. Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Use the `LED_BUILTIN` macro to control the onboard LED marked with *WIFI*. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + ### ATmega4809 Xplained Pro [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. Recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: - + From 25959eac89c5880577919756805b61b4d5b2f4fe Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 7 Oct 2019 15:09:20 +0200 Subject: [PATCH 072/351] Create Logic library README --- megaavr/libraries/Logic/README.md | 200 ++++++++++++++++++++++++++++++ 1 file changed, 200 insertions(+) create mode 100644 megaavr/libraries/Logic/README.md diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md new file mode 100644 index 0000000..cc288b5 --- /dev/null +++ b/megaavr/libraries/Logic/README.md @@ -0,0 +1,200 @@ +# Logic +A library for interfacing with the CCL (Configurable Custom Logic) peripherals of the megaAVR-0 MCUs. +Developed by MCUdude for use with [MegaCoreX](https://github.com/MCUdude/MegaCoreX). +The megaAVR-0 has four independent internal logic blocks that can be individually customized. +More useful information about CCL can be found in the [Microchip Application Note TB3218](http://ww1.microchip.com/downloads/en/AppNotes/TB3218-Getting-Started-with-CCL-90003218A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). + + +## block_t +Struct for interfacing with the built-in logic block. use the predefined objects `block0`, `block1`, `block2` and `block3`. +Each object contains register pointers for interfacing with the right registers. Some of these variables are available to the user. + + +### enable +Variable for enabling or disabling a logic block. +Accepted values: +```c++ +true; // Enable the current logic block +false; // Disable the current logic block +``` + +##### Usage +```c++ +Logic.block0.enable = true; // Enable logic block 0 +``` + +##### Default state +`Logic.block0.enable` defaults to `false` if not specified in the user program. + + +### input0..input2 +Variable for setting what mode input 0..2 on a logic block should have. +Accepted values: +``` c++ +in::masked; // Pin not in use +in::unused; // Pin not in use +in::disable; // Pin not in use +in::feedback; // Connect output of the logic block to this input +in::link; // Connect output of logic block n+1 to this input +in::event_a; // Connect input to event A +in::event_b; // Connect input to event B +in::input; // Connect input to GPIO +in::ac; // Connect input to the output of the internal analog comparator +in::input_pullup; // Connect input to GPIO and enable the internal pullup resistor +in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX +in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK +in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 +in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO +``` + +##### Usage +``` c++ +Logic.block0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 +Logic.block0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO +Logic.block0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO and enable pullup +``` + +##### Default state +`Logic.blockN.inputN` defaults to `in::unused` if not specified in the user program. + + +### output +Variable for changing the logic block output pin behavior. Note that the output of the logic block still can be used internally if the output pin is disabled. +Accepted values: +```c++ +out::disable; // Disable the output GPIO pin. Useful when triggering an interrupt instead. +out::enable; // Enable the output GPIO pin +``` + +##### Usage +```c++ +Logic.block0.output = out::disable; // Disable the output GPIO pin. +``` + +##### Default state +`Logic.blockN.output` defaults to `out::disable` if not specified in the user program. + + +### output_swap +Variable for pin swapping the physical output pin to its alternative position. See the pinout diagrams in the main MegaCoreX README for detailed info. +Accepted values: +```c++ +out::no_swap; // Use default pin position, pin 2 on the port +out::pin_swap; // Use alternative position, pin 6 on the port +``` + +##### Usage +```c++ +Logic.block0.output_swap = out::no_swap; // No pin swap for output of block0 +``` + +##### Default state +`Logic.blockN.output_swap` defaults to `out::no_swap` if not specified in the user program. + + +### filter +Variable to connecting a filter or synchronizer to the logic block output. Useful when multiple logic blocks are connected internally to prevent logic race. +Accepted values: +```c++ +filter::disable; // No filter used +filter::synchronizer; // Connect synchronizer to output +filter::filter; // Connect filter to output +``` + +##### Usage +```c++ +Logic.block0.filter = filter::filter; // Enable filter on output of block 0 +``` + +##### Default state +`Logic.blockN.filter` defaults to `filter::disable` if not specified in the user program. + + +### sequencer +Variable for connecting a sequencer to the logic block output. +Accepted values: +```c++ +sequencer::disable; // No sequencer connected +sequencer::d_flip_flop; // D flip flop sequencer connected +sequencer::jk_flip_flop; // JK flip flop sequencer connected +sequencer::d_latch; // D latch sequencer connected +sequencer::rs_latch; // RS latch sequencer connected +``` + +##### Usage +```c++ +Logic.block0.sequencer = sequencer::disable; // Disable sequencer +``` + +##### Default state +`Logic.blockN.sequencer` defaults to `sequencer::disable` if not specified in the user program. + + +### truth +Variable to hold the 8-bit truth table value. +Accepted values between 0x00 and 0xFF. + +##### Usage +```c++ +Logic.block0.truth = 0xF0; +``` + +##### Default state +`Logic.blockN.truth` defaults to `0x00` if not specified in the user program. + + + +## init() +Method for initializing a logic block. The logic block object to initialize is passed as an argument. + +##### Usage +```c++ +Logic.init(Logic.block0); // Initialize block 0 +Logic.init(Logic.block1); // Initialize block 1 +``` + + + +## start() +Method for starting the CCL hardware after all registers have been initialized using init(block_t). + +##### Usage +```c++ +Logic.start(); // Start CCL hardware +``` + + + +## end() +Method for stopping the CCL hardware. + +##### Usage +```c++ +Logic.stop(); // Stop CCL +``` + + + +## attachInterrupt() +Method for enabling interrupts for a specific block. +Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. + +##### Usage +```c++ +Logic.attachInterrupt(Logic.block0, blinkLED, RISING); // Runthe blinkLED function when the putput goes high + +void blinkLED() +{ + digitalWrite(myLedPin, CHANGE); +} +``` + + + +## detachInterrupt() +Method for disabling interrupts for a specific block. + +##### Usage +```c++ +Logic.detachInterrupt(Logic.block0); // Disable interrupts for block 0 +``` From 2c283eeb2859ee2a5f6803caaa20fda1ce5f37d4 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 7 Oct 2019 15:19:16 +0200 Subject: [PATCH 073/351] Add section about CCL --- README.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/README.md b/README.md index 2448d18..5d08812 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,7 @@ An Arduino core for the new megaAVR series! * [Reset pin](#reset-pin) * [Pinout](#pinout) * [PWM output](#pwm-output) +* [Configurable Custom Logic](#configurable-custom-logic-ccl) * [Alternative pins](#alternative-pins) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) @@ -123,6 +124,10 @@ the constraints of the hardware will be made to match the request. Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. +## Configurable custom logic (CCL) +The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performence. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from eachother, connected together or generate interrupt for to the CPU. I've made a [light weight, high level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integraion with the CCL hardware. + + ## Alternative pins The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. From ee35b40a0f78b22c1b9de4ab27e1e341ffa550b0 Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Tue, 8 Oct 2019 00:52:55 +0900 Subject: [PATCH 074/351] [Logic] Mark pointers to hardware registers as const --- megaavr/libraries/Logic/src/Logic.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 54c0df6..5dbe630 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -74,12 +74,12 @@ class CustomLogic typedef struct { const uint8_t block_number; - PORT_t* PORT; - volatile uint8_t* SEQCTRL; - volatile uint8_t* LUTCTRLA; - volatile uint8_t* LUTCTRLB; - volatile uint8_t* LUTCTRLC; - volatile uint8_t* TRUTH; + PORT_t* const PORT; + volatile uint8_t* const SEQCTRL; + volatile uint8_t* const LUTCTRLA; + volatile uint8_t* const LUTCTRLB; + volatile uint8_t* const LUTCTRLC; + volatile uint8_t* const TRUTH; uint8_t input0; uint8_t input1; uint8_t input2; From 95150b5167ddcbefa1e15611b5b2d5e8c0419ff6 Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Sat, 5 Oct 2019 00:00:43 +0900 Subject: [PATCH 075/351] [Logic] Fix bit manipulations This CL also utilizes DIRCLR and DIRSET register to manipulate port direction. --- megaavr/libraries/Logic/src/Logic.cpp | 34 +++++++++++++++------------ 1 file changed, 19 insertions(+), 15 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index e9d75d3..9a95a9f 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -23,35 +23,35 @@ void CustomLogic::init(block_t &block) { // Block input 0 pin dir if(block.input0 == in::input) - block.PORT->DIR &= ~PIN0_bm; + block.PORT->DIRCLR = PIN0_bm; else if(block.input0 == in::input_pullup) { - block.PORT->DIR &= ~PIN0_bm; + block.PORT->DIRCLR = PIN0_bm; block.PORT->PIN0CTRL |= PORT_PULLUPEN_bm; block.input0 = in::input; } // Block input 1 pin dir if(block.input1 == in::input) - block.PORT->DIR &= ~PIN1_bm; + block.PORT->DIRCLR = PIN1_bm; else if(block.input1 == in::input_pullup) { - block.PORT->DIR &= ~PIN1_bm; + block.PORT->DIRCLR = PIN1_bm; block.PORT->PIN1CTRL |= PORT_PULLUPEN_bm; block.input1 = in::input; } // Block input 2 pin dir if(block.input2 == in::input) - block.PORT->DIR &= ~PIN2_bm; + block.PORT->DIRCLR = PIN2_bm; else if(block.input2 == in::input_pullup) { - block.PORT->DIR &= ~PIN2_bm; + block.PORT->DIRCLR = PIN2_bm; block.PORT->PIN2CTRL |= PORT_PULLUPEN_bm; block.input2 = in::input; } // Set inputs modes *block.LUTCTRLB = (block.input1 << 4) | block.input0; - *block.LUTCTRLC |= 0xFF & block.input2; + *block.LUTCTRLC = block.input2; // Set truth table *block.TRUTH = block.truth; @@ -64,13 +64,13 @@ void CustomLogic::init(block_t &block) { if(block.output_swap == out::pin_swap) { - PORTMUX.CCLROUTEA |= (block.output_swap << block.block_number); - block.PORT->DIR |= PIN6_bm; + PORTMUX.CCLROUTEA |= (1 << block.block_number); + block.PORT->DIRSET = PIN6_bm; } else if(block.output_swap == out::no_swap) { - PORTMUX.CCLROUTEA &= (block.output_swap << block.block_number); - block.PORT->DIR |= PIN3_bm; + PORTMUX.CCLROUTEA &= ~(1 << block.block_number); + block.PORT->DIRSET = PIN3_bm; } } @@ -81,22 +81,26 @@ void CustomLogic::init(block_t &block) void CustomLogic::attachInterrupt(block_t &block, void (*userFunc)(void), PinStatus mode) { + CCL_INTMODE0_t intmode; switch (mode) { // Set RISING, FALLING or CHANGE interrupt trigger for a block output case RISING: - CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (1 << (block.block_number * 2)); + intmode = CCL_INTMODE0_RISING_gc; break; case FALLING: - CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (2 << (block.block_number * 2)); + intmode = CCL_INTMODE0_FALLING_gc; break; case CHANGE: - CCL.INTCTRL0 |= (0x03 << (block.block_number * 2)) & (3 << (block.block_number * 2)); + intmode = CCL_INTMODE0_BOTH_gc; break; default: // Only RISING, FALLING and CHANGE is supported return; } + const int intmode_bp = block.block_number * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(0x3 << intmode_bp)) + | (intmode << intmode_bp); // Store function pointer intFuncCCL[block.block_number] = userFunc; @@ -140,4 +144,4 @@ ISR(CCL_CCL_vect) // Clear flag CCL.INTFLAGS |= CCL_INT3_bm; } -} \ No newline at end of file +} From e459212570e1cc3cbd1285b82d8b365e2488fcf1 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 7 Oct 2019 23:05:54 +0200 Subject: [PATCH 076/351] Fix incorrect pins on 48-pin pinout Vcc and GND pins were shifted. --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 5d08812..988b36f 100644 --- a/README.md +++ b/README.md @@ -104,7 +104,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## PWM output From c1a0d960e2a53524f8db0353643fce29a1a2c7dc Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Tue, 8 Oct 2019 23:57:25 +0900 Subject: [PATCH 077/351] Fix vector pointers allocation --- megaavr/libraries/Logic/src/Logic.cpp | 3 +++ megaavr/libraries/Logic/src/Logic.h | 3 --- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 9a95a9f..feee510 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -1,5 +1,8 @@ #include "Logic.h" +// Array for storing ISR function pointers +static volatile voidFuncPtr intFuncCCL[4]; + // Preinstantiate Object CustomLogic Logic; diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 5dbe630..81b6e80 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -5,9 +5,6 @@ #include -// Array for storing ISR function pointers -static volatile voidFuncPtr intFuncCCL[4]; - //Use in:: when working with logic inputs namespace in { From 296bc4300adcd2d2fa03e209f2f688ba62ed0270 Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Tue, 8 Oct 2019 17:23:45 +0900 Subject: [PATCH 078/351] [Logic] Separate CCL block instances This CL makes 4 CCL block instances in Logic object separated in Logic0 through Logic3 objects. Thus compiler/linker can optimize out unused block object from a sketch and reduce RAM consumption. --- megaavr/libraries/Logic/README.md | 48 +++--- .../Five_input_NOR/Five_input_NOR.ino | 34 ++--- .../Logic/examples/Interrupt/Interrupt.ino | 20 +-- .../Three_input_AND/Three_input_AND.ino | 20 +-- .../Three_input_NAND/Three_input_NAND.ino | 20 +-- .../Three_input_OR/Three_input_OR.ino | 20 +-- .../examples/Two_input_AND/Two_input_AND.ino | 18 +-- .../Two_input_NAND/Two_input_NAND.ino | 18 +-- .../examples/Two_input_OR/Two_input_OR.ino | 18 +-- megaavr/libraries/Logic/src/Logic.cpp | 117 +++++++++----- megaavr/libraries/Logic/src/Logic.h | 144 +++++------------- 11 files changed, 218 insertions(+), 259 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index cc288b5..20555f4 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -5,8 +5,8 @@ The megaAVR-0 has four independent internal logic blocks that can be individuall More useful information about CCL can be found in the [Microchip Application Note TB3218](http://ww1.microchip.com/downloads/en/AppNotes/TB3218-Getting-Started-with-CCL-90003218A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). -## block_t -Struct for interfacing with the built-in logic block. use the predefined objects `block0`, `block1`, `block2` and `block3`. +## Logic +Class for interfacing with the built-in logic block. use the predefined objects `Logic0`, `Logic1`, `Logic2` and `Logic3`. Each object contains register pointers for interfacing with the right registers. Some of these variables are available to the user. @@ -20,11 +20,11 @@ false; // Disable the current logic block ##### Usage ```c++ -Logic.block0.enable = true; // Enable logic block 0 +Logic0.enable = true; // Enable logic block 0 ``` ##### Default state -`Logic.block0.enable` defaults to `false` if not specified in the user program. +`Logic0.enable` defaults to `false` if not specified in the user program. ### input0..input2 @@ -49,13 +49,13 @@ in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 ##### Usage ``` c++ -Logic.block0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 -Logic.block0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO -Logic.block0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO and enable pullup +Logic0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 +Logic0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO +Logic0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO and enable pullup ``` ##### Default state -`Logic.blockN.inputN` defaults to `in::unused` if not specified in the user program. +`LogicN.inputN` defaults to `in::unused` if not specified in the user program. ### output @@ -68,11 +68,11 @@ out::enable; // Enable the output GPIO pin ##### Usage ```c++ -Logic.block0.output = out::disable; // Disable the output GPIO pin. +Logic0.output = out::disable; // Disable the output GPIO pin. ``` ##### Default state -`Logic.blockN.output` defaults to `out::disable` if not specified in the user program. +`LogicN.output` defaults to `out::disable` if not specified in the user program. ### output_swap @@ -85,11 +85,11 @@ out::pin_swap; // Use alternative position, pin 6 on the port ##### Usage ```c++ -Logic.block0.output_swap = out::no_swap; // No pin swap for output of block0 +Logic0.output_swap = out::no_swap; // No pin swap for output of block0 ``` ##### Default state -`Logic.blockN.output_swap` defaults to `out::no_swap` if not specified in the user program. +`LogicN.output_swap` defaults to `out::no_swap` if not specified in the user program. ### filter @@ -103,11 +103,11 @@ filter::filter; // Connect filter to output ##### Usage ```c++ -Logic.block0.filter = filter::filter; // Enable filter on output of block 0 +Logic0.filter = filter::filter; // Enable filter on output of block 0 ``` ##### Default state -`Logic.blockN.filter` defaults to `filter::disable` if not specified in the user program. +`LogicN.filter` defaults to `filter::disable` if not specified in the user program. ### sequencer @@ -123,11 +123,11 @@ sequencer::rs_latch; // RS latch sequencer connected ##### Usage ```c++ -Logic.block0.sequencer = sequencer::disable; // Disable sequencer +Logic0.sequencer = sequencer::disable; // Disable sequencer ``` ##### Default state -`Logic.blockN.sequencer` defaults to `sequencer::disable` if not specified in the user program. +`LogicN.sequencer` defaults to `sequencer::disable` if not specified in the user program. ### truth @@ -136,11 +136,11 @@ Accepted values between 0x00 and 0xFF. ##### Usage ```c++ -Logic.block0.truth = 0xF0; +Logic0.truth = 0xF0; ``` ##### Default state -`Logic.blockN.truth` defaults to `0x00` if not specified in the user program. +`LogicN.truth` defaults to `0x00` if not specified in the user program. @@ -149,8 +149,8 @@ Method for initializing a logic block. The logic block object to initialize is p ##### Usage ```c++ -Logic.init(Logic.block0); // Initialize block 0 -Logic.init(Logic.block1); // Initialize block 1 +Logic0.init(); // Initialize block 0 +Logic1.init(); // Initialize block 1 ``` @@ -160,7 +160,7 @@ Method for starting the CCL hardware after all registers have been initialized u ##### Usage ```c++ -Logic.start(); // Start CCL hardware +Logic::start(); // Start CCL hardware ``` @@ -170,7 +170,7 @@ Method for stopping the CCL hardware. ##### Usage ```c++ -Logic.stop(); // Stop CCL +Logic::stop(); // Stop CCL ``` @@ -181,7 +181,7 @@ Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. ##### Usage ```c++ -Logic.attachInterrupt(Logic.block0, blinkLED, RISING); // Runthe blinkLED function when the putput goes high +Logic0.attachInterrupt(blinkLED, RISING); // Runthe blinkLED function when the putput goes high void blinkLED() { @@ -196,5 +196,5 @@ Method for disabling interrupts for a specific block. ##### Usage ```c++ -Logic.detachInterrupt(Logic.block0); // Disable interrupts for block 0 +Logic0.detachInterrupt(); // Disable interrupts for block 0 ``` diff --git a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino index a9ab15b..c2200e9 100644 --- a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino +++ b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino @@ -22,32 +22,32 @@ void setup() // Initialize logic block 1 // Logic block 1 has three inputs, PC0, PC1 and PC2. // It's output, PC3 is disabled because we connect the output signal to block 0 internally - Logic.block1.enable = true; // Enable logic block 1 - Logic.block1.input0 = in::input_pullup; // Set PC0 as input with pullup - Logic.block1.input1 = in::input_pullup; // Set PC1 as input with pullup - Logic.block1.input2 = in::input_pullup; // Set PC2 as input with pullup - Logic.block1.output = out::disable; // No output on PC3 - Logic.block1.filter = filter::disable; // No output filter enabled - Logic.block1.truth = 0xFE; // Set truth table + Logic1.enable = true; // Enable logic block 1 + Logic1.input0 = in::input_pullup; // Set PC0 as input with pullup + Logic1.input1 = in::input_pullup; // Set PC1 as input with pullup + Logic1.input2 = in::input_pullup; // Set PC2 as input with pullup + Logic1.output = out::disable; // No output on PC3 + Logic1.filter = filter::disable; // No output filter enabled + Logic1.truth = 0xFE; // Set truth table // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // input2 is internally connected to the output of block1 (which means PA2 is freed up) // Block 0 output on PA3 - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic.block0.input2 = in::link; // Route output from block 1 to this input internally - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0x01; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = in::link; // Route output from block 1 to this input internally + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0x01; // Set truth table // Initialize logic block 0 and 1 - Logic.init(Logic.block0); - Logic.init(Logic.block1); + Logic0.init(); + Logic1.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino index 174e3f5..a48dee7 100644 --- a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino @@ -37,22 +37,22 @@ void setup() // Initialize logic block 2 // Logic block 2 has three inputs, PA0, PA1 and PA2. // It has one output, but this is disabled because we're using an interrupt instead. - Logic.block2.enable = true; // Enable logic block 0 - Logic.block2.input0 = in::input_pullup; // Set PD0 as input with pullup - Logic.block2.input1 = in::input_pullup; // Set PD1 as input with pullup - Logic.block2.input2 = in::input_pullup; // Set PD2 as input with pullup - Logic.block2.output = out::disable; // Disable output on PD3 (we don't have to though) - Logic.block2.filter = filter::disable; // No output filter enabled - Logic.block2.truth = 0x01; // Set truth table + Logic2.enable = true; // Enable logic block 0 + Logic2.input0 = in::input_pullup; // Set PD0 as input with pullup + Logic2.input1 = in::input_pullup; // Set PD1 as input with pullup + Logic2.input2 = in::input_pullup; // Set PD2 as input with pullup + Logic2.output = out::disable; // Disable output on PD3 (we don't have to though) + Logic2.filter = filter::disable; // No output filter enabled + Logic2.truth = 0x01; // Set truth table // Initialize logic block 2 - Logic.init(Logic.block2); + Logic2.init(); // Set interrupt (supports RISING, FALLING and CHANGE) - Logic.attachInterrupt(Logic.block2, interruptFunction, RISING); + Logic2.attachInterrupt(interruptFunction, RISING); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino index 54a31c1..1b1444e 100644 --- a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino @@ -34,20 +34,20 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0x80; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0x80; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino index c5cb919..d9332d3 100644 --- a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino @@ -34,20 +34,20 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0x7F; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0x7F; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino index 4a5d75b..63627af 100644 --- a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino @@ -34,20 +34,20 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic.block0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0xFE; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0xFE; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino index 0f77625..f288bec 100644 --- a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino @@ -36,19 +36,19 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0x08; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0x08; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino index d88fd91..4118180 100644 --- a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino @@ -36,19 +36,19 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0xF7; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0xF7; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino index d85dc5d..bc93cfa 100644 --- a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino @@ -36,19 +36,19 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic.block0.enable = true; // Enable logic block 0 - Logic.block0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic.block0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic.block0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic.block0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic.block0.filter = filter::disable; // No output filter enabled - Logic.block0.truth = 0xFE; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = filter::disable; // No output filter enabled + Logic0.truth = 0xFE; // Set truth table // Initialize logic block 0 - Logic.init(Logic.block0); + Logic0.init(); // Start the AVR logic hardware - Logic.start(); + Logic::start(); } void loop() diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 9a95a9f..b764bdd 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -1,85 +1,120 @@ #include "Logic.h" -// Preinstantiate Object -CustomLogic Logic; +// Preinstantiate Objects -CustomLogic::CustomLogic() +// Object for logic block 0 (IOs connected to PORTA) +Logic Logic0(0, PORTA, CCL_SEQCTRL0, CCL_LUT0CTRLA, CCL_LUT0CTRLB, CCL_LUT0CTRLC, CCL_TRUTH0); + +// Object for logic block 1 (IOs connected to PORTC) +Logic Logic1(1, PORTC, CCL_SEQCTRL0, CCL_LUT1CTRLA, CCL_LUT1CTRLB, CCL_LUT1CTRLC, CCL_TRUTH1); + +// Object for logic block 2 (IOs connected to PORTD) +Logic Logic2(2, PORTD, CCL_SEQCTRL1, CCL_LUT2CTRLA, CCL_LUT2CTRLB, CCL_LUT2CTRLC, CCL_TRUTH2); + +// Object for logic block 3 (IOs connected to PORTF) +Logic Logic3(3, PORTF, CCL_SEQCTRL1, CCL_LUT3CTRLA, CCL_LUT3CTRLB, CCL_LUT3CTRLC, CCL_TRUTH3); + +Logic::Logic( + const uint8_t block_number, + PORT_t& port, + register8_t& seq_ctrl, + register8_t& lut_ctrla, + register8_t& lut_ctrlb, + register8_t& lut_ctrlc, + register8_t& truth) + : PORT(port), + SEQCTRL(seq_ctrl), + LUTCTRLA(lut_ctrla), + LUTCTRLB(lut_ctrlb), + LUTCTRLC(lut_ctrlc), + TRUTH(truth), + input0(in::masked), + input1(in::masked), + input2(in::masked), + output(false), + enable(false), + truth(0x00), + output_swap(out::no_swap), + filter(filter::disable), + sequencer(sequencer::disable) { } -void CustomLogic::start(bool state) +// static +void Logic::start(bool state) { CCL.CTRLA = (state << CCL_ENABLE_bp); } -void CustomLogic::end() +// static +void Logic::end() { start(false); } -void CustomLogic::init(block_t &block) +void Logic::init() { // Block input 0 pin dir - if(block.input0 == in::input) - block.PORT->DIRCLR = PIN0_bm; - else if(block.input0 == in::input_pullup) + if(input0 == in::input) + PORT.DIRCLR = PIN0_bm; + else if(input0 == in::input_pullup) { - block.PORT->DIRCLR = PIN0_bm; - block.PORT->PIN0CTRL |= PORT_PULLUPEN_bm; - block.input0 = in::input; + PORT.DIRCLR = PIN0_bm; + PORT.PIN0CTRL |= PORT_PULLUPEN_bm; + input0 = in::input; } // Block input 1 pin dir - if(block.input1 == in::input) - block.PORT->DIRCLR = PIN1_bm; - else if(block.input1 == in::input_pullup) + if(input1 == in::input) + PORT.DIRCLR = PIN1_bm; + else if(input1 == in::input_pullup) { - block.PORT->DIRCLR = PIN1_bm; - block.PORT->PIN1CTRL |= PORT_PULLUPEN_bm; - block.input1 = in::input; + PORT.DIRCLR = PIN1_bm; + PORT.PIN1CTRL |= PORT_PULLUPEN_bm; + input1 = in::input; } // Block input 2 pin dir - if(block.input2 == in::input) - block.PORT->DIRCLR = PIN2_bm; - else if(block.input2 == in::input_pullup) + if(input2 == in::input) + PORT.DIRCLR = PIN2_bm; + else if(input2 == in::input_pullup) { - block.PORT->DIRCLR = PIN2_bm; - block.PORT->PIN2CTRL |= PORT_PULLUPEN_bm; - block.input2 = in::input; + PORT.DIRCLR = PIN2_bm; + PORT.PIN2CTRL |= PORT_PULLUPEN_bm; + input2 = in::input; } // Set inputs modes - *block.LUTCTRLB = (block.input1 << 4) | block.input0; - *block.LUTCTRLC = block.input2; + LUTCTRLB = (input1 << 4) | input0; + LUTCTRLC = input2; // Set truth table - *block.TRUTH = block.truth; + TRUTH = truth; // Set sequencer - *block.SEQCTRL = block.sequencer; + SEQCTRL = sequencer; // Set output pin state and output pin swap - if(block.output == out::enable) + if(output == out::enable) { - if(block.output_swap == out::pin_swap) + if(output_swap == out::pin_swap) { - PORTMUX.CCLROUTEA |= (1 << block.block_number); - block.PORT->DIRSET = PIN6_bm; + PORTMUX.CCLROUTEA |= (1 << block_number); + PORT.DIRSET = PIN6_bm; } - else if(block.output_swap == out::no_swap) + else if(output_swap == out::no_swap) { - PORTMUX.CCLROUTEA &= ~(1 << block.block_number); - block.PORT->DIRSET = PIN3_bm; + PORTMUX.CCLROUTEA &= ~(1 << block_number); + PORT.DIRSET = PIN3_bm; } } // Set logic output state and output filter - *block.LUTCTRLA = (block.output << 6) | (block.filter << 4) | (block.enable << 0); + LUTCTRLA = (output << 6) | (filter << 4) | (enable << 0); } -void CustomLogic::attachInterrupt(block_t &block, void (*userFunc)(void), PinStatus mode) +void Logic::attachInterrupt(void (*userFunc)(void), PinStatus mode) { CCL_INTMODE0_t intmode; switch (mode) @@ -98,19 +133,19 @@ void CustomLogic::attachInterrupt(block_t &block, void (*userFunc)(void), PinSta // Only RISING, FALLING and CHANGE is supported return; } - const int intmode_bp = block.block_number * 2; + const int intmode_bp = block_number * 2; CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(0x3 << intmode_bp)) | (intmode << intmode_bp); // Store function pointer - intFuncCCL[block.block_number] = userFunc; + intFuncCCL[block_number] = userFunc; } -void CustomLogic::detachInterrupt(block_t &block) +void Logic::detachInterrupt() { // Disable interrupt for a given block output - CCL.INTCTRL0 &= ~(0x03 << (block.block_number * 2)); + CCL.INTCTRL0 &= ~(0x03 << (block_number * 2)); } diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 5dbe630..5324272 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -67,119 +67,43 @@ namespace sequencer }; }; -class CustomLogic +class Logic { - private: - // Struct that holds all information a single logic block needs - typedef struct - { - const uint8_t block_number; - PORT_t* const PORT; - volatile uint8_t* const SEQCTRL; - volatile uint8_t* const LUTCTRLA; - volatile uint8_t* const LUTCTRLB; - volatile uint8_t* const LUTCTRLC; - volatile uint8_t* const TRUTH; - uint8_t input0; - uint8_t input1; - uint8_t input2; - uint8_t output; - uint8_t enable; - uint8_t truth; - uint8_t output_swap; - uint8_t filter; - uint8_t sequencer; - } block_t; - public: - CustomLogic(); - void start(bool state = true); - void end(); - void init(block_t &block); - void attachInterrupt(block_t &block, voidFuncPtr callback, PinStatus mode); - void detachInterrupt(block_t &block); - - // Struct object for logic block 0 (IOs connected to PORTA) - block_t block0 = { - .block_number = 0, - .PORT = &PORTA, - .SEQCTRL = &CCL_SEQCTRL0, - .LUTCTRLA = &CCL_LUT0CTRLA, - .LUTCTRLB = &CCL_LUT0CTRLB, - .LUTCTRLC = &CCL_LUT0CTRLC, - .TRUTH = &CCL_TRUTH0, - .input0 = in::masked, - .input1 = in::masked, - .input2 = in::masked, - .output = false, - .enable = false, - .truth = 0x00, - .output_swap = out::no_swap, - .filter = filter::disable, - .sequencer = sequencer::disable, - }; - - // Struct object for logic block 1 (IOs connected to PORTC) - block_t block1 = { - .block_number = 1, - .PORT = &PORTC, - .SEQCTRL = &CCL_SEQCTRL0, - .LUTCTRLA = &CCL_LUT1CTRLA, - .LUTCTRLB = &CCL_LUT1CTRLB, - .LUTCTRLC = &CCL_LUT1CTRLC, - .TRUTH = &CCL_TRUTH1, - .input0 = in::masked, - .input1 = in::masked, - .input2 = in::masked, - .output = out::disable, - .enable = false, - .truth = 0x00, - .output_swap = out::no_swap, - .filter = filter::disable, - .sequencer = sequencer::disable, - }; - - // Struct object for logic block 2 (IOs connected to PORTD) - block_t block2 = { - .block_number = 2, - .PORT = &PORTD, - .SEQCTRL = &CCL_SEQCTRL1, - .LUTCTRLA = &CCL_LUT2CTRLA, - .LUTCTRLB = &CCL_LUT2CTRLB, - .LUTCTRLC = &CCL_LUT2CTRLC, - .TRUTH = &CCL_TRUTH2, - .input0 = in::masked, - .input1 = in::masked, - .input2 = in::masked, - .output = out::disable, - .enable = false, - .truth = 0x00, - .output_swap = out::no_swap, - .filter = filter::disable, - .sequencer = sequencer::disable, - }; - - // Struct object for logic block 3 (IOs connected to PORTF) - block_t block3 = { - .block_number = 3, - .PORT = &PORTF, - .SEQCTRL = &CCL_SEQCTRL1, - .LUTCTRLA = &CCL_LUT3CTRLA, - .LUTCTRLB = &CCL_LUT3CTRLB, - .LUTCTRLC = &CCL_LUT3CTRLC, - .TRUTH = &CCL_TRUTH3, - .input0 = in::masked, - .input1 = in::masked, - .input2 = in::masked, - .output = out::disable, - .enable = false, - .truth = 0x00, - .output_swap = out::no_swap, - .filter = filter::disable, - .sequencer = sequencer::disable, - }; + static void start(bool state = true); + static void end(); + + Logic(const uint8_t block_number, + PORT_t& port, + register8_t& seq_ctrl, + register8_t& lut_ctrla, + register8_t& lut_ctrlb, + register8_t& lut_ctrlc, + register8_t& truth); + void init(); + void attachInterrupt(voidFuncPtr callback, PinStatus mode); + void detachInterrupt(); + + uint8_t input0; + uint8_t input1; + uint8_t input2; + uint8_t output; + uint8_t enable; + uint8_t truth; + uint8_t output_swap; + uint8_t filter; + uint8_t sequencer; + +private: + const uint8_t block_number; + PORT_t& PORT; + volatile register8_t& SEQCTRL; + volatile register8_t& LUTCTRLA; + volatile register8_t& LUTCTRLB; + volatile register8_t& LUTCTRLC; + volatile register8_t& TRUTH; }; -extern CustomLogic Logic; +extern Logic Logic0, Logic1, Logic2, Logic3; #endif From b874fc29c4a42923e7940024e6d410a97b2bae7c Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Wed, 9 Oct 2019 18:50:10 +0900 Subject: [PATCH 079/351] [Logic] Remove accidentally introduced lines --- megaavr/libraries/Logic/src/Logic.cpp | 3 --- 1 file changed, 3 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 420dce2..b333f54 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -3,9 +3,6 @@ // Array for storing ISR function pointers static volatile voidFuncPtr intFuncCCL[4]; -// Preinstantiate Object -CustomLogic Logic; - // Object for logic block 0 (IOs connected to PORTA) Logic Logic0(0, PORTA, CCL_SEQCTRL0, CCL_LUT0CTRLA, CCL_LUT0CTRLB, CCL_LUT0CTRLC, CCL_TRUTH0); From a1ec749b6d4f822a8e786baab0d9258289d93720 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 9 Oct 2019 18:47:28 +0200 Subject: [PATCH 080/351] Reorder to get rid of compiler warnings --- megaavr/libraries/Logic/src/Logic.cpp | 5 +++-- megaavr/libraries/Logic/src/Logic.h | 20 ++++++++++---------- 2 files changed, 13 insertions(+), 12 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index b333f54..6a6609b 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -16,14 +16,15 @@ Logic Logic2(2, PORTD, CCL_SEQCTRL1, CCL_LUT2CTRLA, CCL_LUT2CTRLB, CCL_LUT2CTRLC Logic Logic3(3, PORTF, CCL_SEQCTRL1, CCL_LUT3CTRLA, CCL_LUT3CTRLB, CCL_LUT3CTRLC, CCL_TRUTH3); Logic::Logic( - const uint8_t block_number, + const uint8_t block, PORT_t& port, register8_t& seq_ctrl, register8_t& lut_ctrla, register8_t& lut_ctrlb, register8_t& lut_ctrlc, register8_t& truth) - : PORT(port), + : block_number(block), + PORT(port), SEQCTRL(seq_ctrl), LUTCTRLA(lut_ctrla), LUTCTRLB(lut_ctrlb), diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 6da047b..768072e 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -1,5 +1,3 @@ -// edge detect - #ifndef LOGIC_h #define LOGIC_h @@ -66,6 +64,15 @@ namespace sequencer class Logic { + private: + const uint8_t block_number; + PORT_t& PORT; + volatile register8_t& SEQCTRL; + volatile register8_t& LUTCTRLA; + volatile register8_t& LUTCTRLB; + volatile register8_t& LUTCTRLC; + volatile register8_t& TRUTH; + public: static void start(bool state = true); static void end(); @@ -91,14 +98,7 @@ class Logic uint8_t filter; uint8_t sequencer; -private: - const uint8_t block_number; - PORT_t& PORT; - volatile register8_t& SEQCTRL; - volatile register8_t& LUTCTRLA; - volatile register8_t& LUTCTRLB; - volatile register8_t& LUTCTRLC; - volatile register8_t& TRUTH; + }; extern Logic Logic0, Logic1, Logic2, Logic3; From 474f9955c161d5957dec6669efd5e4acc7d83cb5 Mon Sep 17 00:00:00 2001 From: "Tadashi G. Takaoka" Date: Thu, 10 Oct 2019 15:19:47 +0900 Subject: [PATCH 081/351] [Logic] Support tinyAVR series --- megaavr/libraries/Logic/README.md | 2 + .../Logic/examples/Interrupt/Interrupt.ino | 2 +- megaavr/libraries/Logic/src/Logic.cpp | 279 +++++++++++++----- megaavr/libraries/Logic/src/Logic.h | 64 ++-- 4 files changed, 246 insertions(+), 101 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index 20555f4..5445a57 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -178,6 +178,7 @@ Logic::stop(); // Stop CCL ## attachInterrupt() Method for enabling interrupts for a specific block. Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. +This method ins't available on tinyAVR series. ##### Usage ```c++ @@ -193,6 +194,7 @@ void blinkLED() ## detachInterrupt() Method for disabling interrupts for a specific block. +This method ins't available on tinyAVR series. ##### Usage ```c++ diff --git a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino index a48dee7..23028c1 100644 --- a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino @@ -37,7 +37,7 @@ void setup() // Initialize logic block 2 // Logic block 2 has three inputs, PA0, PA1 and PA2. // It has one output, but this is disabled because we're using an interrupt instead. - Logic2.enable = true; // Enable logic block 0 + Logic2.enable = true; // Enable logic block 2 Logic2.input0 = in::input_pullup; // Set PD0 as input with pullup Logic2.input1 = in::input_pullup; // Set PD1 as input with pullup Logic2.input2 = in::input_pullup; // Set PD2 as input with pullup diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 6a6609b..b5db234 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -1,51 +1,176 @@ #include "Logic.h" +#if defined(CCL_CCL_vect) // Array for storing ISR function pointers static volatile voidFuncPtr intFuncCCL[4]; +#endif -// Object for logic block 0 (IOs connected to PORTA) -Logic Logic0(0, PORTA, CCL_SEQCTRL0, CCL_LUT0CTRLA, CCL_LUT0CTRLB, CCL_LUT0CTRLC, CCL_TRUTH0); - -// Object for logic block 1 (IOs connected to PORTC) -Logic Logic1(1, PORTC, CCL_SEQCTRL0, CCL_LUT1CTRLA, CCL_LUT1CTRLB, CCL_LUT1CTRLC, CCL_TRUTH1); - -// Object for logic block 2 (IOs connected to PORTD) -Logic Logic2(2, PORTD, CCL_SEQCTRL1, CCL_LUT2CTRLA, CCL_LUT2CTRLB, CCL_LUT2CTRLC, CCL_TRUTH2); - -// Object for logic block 3 (IOs connected to PORTF) -Logic Logic3(3, PORTF, CCL_SEQCTRL1, CCL_LUT3CTRLA, CCL_LUT3CTRLB, CCL_LUT3CTRLC, CCL_TRUTH3); - -Logic::Logic( - const uint8_t block, - PORT_t& port, - register8_t& seq_ctrl, - register8_t& lut_ctrla, - register8_t& lut_ctrlb, - register8_t& lut_ctrlc, - register8_t& truth) - : block_number(block), - PORT(port), - SEQCTRL(seq_ctrl), - LUTCTRLA(lut_ctrla), - LUTCTRLB(lut_ctrlb), - LUTCTRLC(lut_ctrlc), - TRUTH(truth), +struct Logic::CCLBlock +{ + const uint8_t number; + const uint8_t input0_bm; + const uint8_t input1_bm; + const uint8_t input2_bm; + const uint8_t output_bm; + const uint8_t output_alt_bm; + PORT_t& PORT_IN; + PORT_t& PORT_OUT; + PORT_t& PORT_ALT_OUT; + volatile register8_t& SEQCTRL; + volatile register8_t& LUTCTRLA; + volatile register8_t& LUTCTRLB; + volatile register8_t& LUTCTRLC; + volatile register8_t& TRUTH; +}; + +static const struct Logic::CCLBlock blocks[] = { +#if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ + defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ + defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ + defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ + defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ + defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, 0, 0, PIN7_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, +#endif +#if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ + defined(__AVR_ATtiny1606__) || \ + defined(__AVR_ATtiny416__) || defined(__AVR_ATtiny816__) || \ + defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) +#define PORTMUX_CCL PORTMUX.CTRLA +#define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, +#endif +#if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ + defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ + defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) +#define PORTMUX_CCL PORTMUX.CTRLA +#define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, +#endif +#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) +#define PORTMUX_CCL PORTMUX.CCLROUTEA +#define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { // Note: 28-Pin version doesn't have input2 and output_alt. + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, +#endif +#if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) +#define PORTMUX_CCL PORTMUX.CCLROUTEA +#define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { // Note: 40-Pin version doesn't have output_alt. + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, +#endif +}; + +#if defined(CCL_TRUTH0) +Logic Logic0(0); +#endif +#if defined(CCL_TRUTH1) +Logic Logic1(1); +#endif +#if defined(CCL_TRUTH2) +Logic Logic2(2); +#endif +#if defined(CCL_TRUTH3) +Logic Logic3(3); +#endif + +Logic::Logic(const uint8_t block_number) + : enable(false), input0(in::masked), input1(in::masked), input2(in::masked), - output(false), - enable(false), - truth(0x00), + output(out::disable), output_swap(out::no_swap), filter(filter::disable), - sequencer(sequencer::disable) + truth(0x00), + sequencer(sequencer::disable), + block(blocks[block_number]) { } // static void Logic::start(bool state) { - CCL.CTRLA = (state << CCL_ENABLE_bp); + CCL.CTRLA = (state ? CCL_ENABLE_bm : 0); } @@ -55,67 +180,78 @@ void Logic::end() start(false); } +static volatile register8_t& PINCTRL(PORT_t& port, const uint8_t pin_bm) +{ + if(pin_bm == PIN0_bm) return port.PIN0CTRL; + if(pin_bm == PIN1_bm) return port.PIN1CTRL; + if(pin_bm == PIN2_bm) return port.PIN2CTRL; + if(pin_bm == PIN3_bm) return port.PIN3CTRL; + if(pin_bm == PIN4_bm) return port.PIN4CTRL; + if(pin_bm == PIN5_bm) return port.PIN5CTRL; + if(pin_bm == PIN6_bm) return port.PIN6CTRL; + return port.PIN7CTRL; +} -void Logic::init() + +void Logic::initInput(in::input_t& input, PORT_t& port, const uint8_t pin_bm) { - // Block input 0 pin dir - if(input0 == in::input) - PORT.DIRCLR = PIN0_bm; - else if(input0 == in::input_pullup) + if(input == in::input && pin_bm) { - PORT.DIRCLR = PIN0_bm; - PORT.PIN0CTRL |= PORT_PULLUPEN_bm; - input0 = in::input; + port.DIRCLR = pin_bm; + PINCTRL(port, pin_bm) &= ~PORT_PULLUPEN_bm; } - // Block input 1 pin dir - if(input1 == in::input) - PORT.DIRCLR = PIN1_bm; - else if(input1 == in::input_pullup) + else if (input == in::input_pullup && pin_bm) { - PORT.DIRCLR = PIN1_bm; - PORT.PIN1CTRL |= PORT_PULLUPEN_bm; - input1 = in::input; - } - // Block input 2 pin dir - if(input2 == in::input) - PORT.DIRCLR = PIN2_bm; - else if(input2 == in::input_pullup) - { - PORT.DIRCLR = PIN2_bm; - PORT.PIN2CTRL |= PORT_PULLUPEN_bm; - input2 = in::input; + port.DIRCLR = pin_bm; + PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; + input = in::input; } +} + + +void Logic::init() +{ + initInput(input0, block.PORT_IN, block.input0_bm); + initInput(input1, block.PORT_IN, block.input1_bm); + initInput(input2, block.PORT_IN, block.input2_bm); // Set inputs modes - LUTCTRLB = (input1 << 4) | input0; - LUTCTRLC = input2; + block.LUTCTRLB = (input1 << CCL_INSEL1_gp) | (input0 << CCL_INSEL0_gp); + block.LUTCTRLC = (input2 << CCL_INSEL2_gp); // Set truth table - TRUTH = truth; + block.TRUTH = truth; // Set sequencer - SEQCTRL = sequencer; + block.SEQCTRL = sequencer; // Set output pin state and output pin swap if(output == out::enable) { - if(output_swap == out::pin_swap) + if(output_swap == out::pin_swap && block.output_alt_bm) { - PORTMUX.CCLROUTEA |= (1 << block_number); - PORT.DIRSET = PIN6_bm; +#if defined(PORTMUX_CCL) + PORTMUX_CCL |= PORTMUX_ALTOUT_bm; +#endif + block.PORT_OUT.DIRSET = block.output_alt_bm; } - else if(output_swap == out::no_swap) + else if(output_swap == out::no_swap && block.output_bm) { - PORTMUX.CCLROUTEA &= ~(1 << block_number); - PORT.DIRSET = PIN3_bm; +#if defined(PORTMUX_CCL) + PORTMUX_CCL &= ~PORTMUX_ALTOUT_bm; +#endif + block.PORT_ALT_OUT.DIRSET = block.output_bm; } } // Set logic output state and output filter - LUTCTRLA = (output << 6) | (filter << 4) | (enable << 0); + block.LUTCTRLA = (output ? CCL_OUTEN_bm : 0) + | (filter << CCL_FILTSEL_gp) + | (enable ? CCL_ENABLE_bm : 0); } +#if defined(CCL_CCL_vect) void Logic::attachInterrupt(void (*userFunc)(void), PinStatus mode) { CCL_INTMODE0_t intmode; @@ -135,19 +271,19 @@ void Logic::attachInterrupt(void (*userFunc)(void), PinStatus mode) // Only RISING, FALLING and CHANGE is supported return; } - const int intmode_bp = block_number * 2; - CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(0x3 << intmode_bp)) + const int intmode_bp = block.number * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); // Store function pointer - intFuncCCL[block_number] = userFunc; + intFuncCCL[block.number] = userFunc; } void Logic::detachInterrupt() { // Disable interrupt for a given block output - CCL.INTCTRL0 &= ~(0x03 << (block_number * 2)); + CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); } @@ -182,3 +318,4 @@ ISR(CCL_CCL_vect) CCL.INTFLAGS |= CCL_INT3_bm; } } +#endif // CCL_CCL_vect diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 768072e..fd6cf5d 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -6,7 +6,7 @@ //Use in:: when working with logic inputs namespace in { - enum + enum input_t : uint8_t { masked = 0x00, unused = 0x00, @@ -28,10 +28,13 @@ namespace in // Use out:: when working with logic outputs namespace out { - enum + enum output_t : uint8_t { disable = 0x00, enable = 0x01, + }; + enum pinswap_t : uint8_t + { no_swap = 0x00, pin_swap = 0x01, }; @@ -40,7 +43,7 @@ namespace out // Use filter:: when working with logic output filter namespace filter { - enum + enum filter_t : uint8_t { disable = 0x00, synchronizer = 0x01, @@ -51,7 +54,7 @@ namespace filter // Use sequencer:: when working with LUT sequencer namespace sequencer { - enum + enum sequencer_t : uint8_t { disable = 0x00, d_flip_flop = 0x01, @@ -64,43 +67,46 @@ namespace sequencer class Logic { - private: - const uint8_t block_number; - PORT_t& PORT; - volatile register8_t& SEQCTRL; - volatile register8_t& LUTCTRLA; - volatile register8_t& LUTCTRLB; - volatile register8_t& LUTCTRLC; - volatile register8_t& TRUTH; - public: static void start(bool state = true); static void end(); - Logic(const uint8_t block_number, - PORT_t& port, - register8_t& seq_ctrl, - register8_t& lut_ctrla, - register8_t& lut_ctrlb, - register8_t& lut_ctrlc, - register8_t& truth); + Logic(const uint8_t block_number); void init(); +#if defined(CCL_CCL_vect) void attachInterrupt(voidFuncPtr callback, PinStatus mode); void detachInterrupt(); +#endif - uint8_t input0; - uint8_t input1; - uint8_t input2; - uint8_t output; - uint8_t enable; + bool enable; + in::input_t input0; + in::input_t input1; + in::input_t input2; + out::output_t output; + out::pinswap_t output_swap; + filter::filter_t filter; uint8_t truth; - uint8_t output_swap; - uint8_t filter; - uint8_t sequencer; + sequencer::sequencer_t sequencer; + + struct CCLBlock; + private: + const struct CCLBlock& block; + void initInput(in::input_t& input, PORT_t& port, const uint8_t pin_bm); }; -extern Logic Logic0, Logic1, Logic2, Logic3; +#if defined(CCL_TRUTH0) +extern Logic Logic0; +#endif +#if defined(CCL_TRUTH1) +extern Logic Logic1; +#endif +#if defined(CCL_TRUTH2) +extern Logic Logic2; +#endif +#if defined(CCL_TRUTH3) +extern Logic Logic3; +#endif #endif From f9e4090bdc6cea93367c039701bce6ebc0cfeb7a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 11 Oct 2019 20:13:27 +0200 Subject: [PATCH 082/351] Initial bootloader support --- megaavr/boards.txt | 526 +++++++++++++++++- megaavr/bootloaders/empty/empty.hex | 2 + .../optiboot_mega0_UART0_ALT_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART0_DEF_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART1_ALT_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART1_DEF_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART2_ALT_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART2_DEF_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART3_ALT_115200_PA7.hex | 32 ++ .../optiboot_mega0_UART3_DEF_115200_PA7.hex | 32 ++ megaavr/platform.txt | 8 +- 11 files changed, 770 insertions(+), 22 deletions(-) create mode 100644 megaavr/bootloaders/empty/empty.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex create mode 100644 megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex diff --git a/megaavr/boards.txt b/megaavr/boards.txt index bc5f9f1..ec25111 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -2,6 +2,7 @@ menu.clock=Clock menu.BOD=BOD menu.pinout=Pinout menu.resetpin=Reset pin +menu.bootloader=Bootloader #################### @@ -9,7 +10,7 @@ menu.resetpin=Reset pin #################### # General -4809.name=Atmega4809 +4809.name=ATmega4809 4809.upload.tool=avrdude 4809.upload.maximum_size=49152 4809.upload.maximum_data_size=6144 @@ -25,7 +26,6 @@ menu.resetpin=Reset pin 4809.bootloader.TCD0CFG=0x00 4809.bootloader.SYSCFG1=0x06 4809.bootloader.APPEND=0x00 -4809.bootloader.BOOTEND=0x00 4809.bootloader.LOCKBIT=0xC5 # Pinouts @@ -135,6 +135,76 @@ menu.resetpin=Reset pin 4809.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 4809.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +4809.menu.bootloader.no_bootloader=No bootloader +4809.menu.bootloader.no_bootloader.upload.extra_params= +4809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +4809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +4809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +4809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +4809.menu.bootloader.uart0_default.upload.protocol=arduino +4809.menu.bootloader.uart0_default.upload.extra_params= +4809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +4809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +4809.menu.bootloader.uart0_alternative.upload.protocol=arduino +4809.menu.bootloader.uart0_alternative.upload.extra_params= +4809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +4809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +4809.menu.bootloader.uart1_default.upload.protocol=arduino +4809.menu.bootloader.uart1_default.upload.extra_params= +4809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +4809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +4809.menu.bootloader.uart1_alternative.upload.protocol=arduino +4809.menu.bootloader.uart1_alternative.upload.extra_params= +4809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +4809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +4809.menu.bootloader.uart2_default.upload.protocol=arduino +4809.menu.bootloader.uart2_default.upload.extra_params= +4809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +4809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +4809.menu.bootloader.uart2_alternative.upload.protocol=arduino +4809.menu.bootloader.uart2_alternative.upload.extra_params= +4809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +4809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +4809.menu.bootloader.uart3_default.upload.protocol=arduino +4809.menu.bootloader.uart3_default.upload.extra_params= +4809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +4809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 + +4809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +4809.menu.bootloader.uart3_alternative.upload.protocol=arduino +4809.menu.bootloader.uart3_alternative.upload.extra_params= +4809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +4809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 +4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 #################### @@ -142,7 +212,7 @@ menu.resetpin=Reset pin #################### # General -4808.name=Atmega4808 +4808.name=ATmega4808 4808.upload.tool=avrdude 4808.upload.maximum_size=49152 4808.upload.maximum_data_size=6144 @@ -158,7 +228,6 @@ menu.resetpin=Reset pin 4808.bootloader.TCD0CFG=0x00 4808.bootloader.SYSCFG1=0x06 4808.bootloader.APPEND=0x00 -4808.bootloader.BOOTEND=0x00 4808.bootloader.LOCKBIT=0xC5 # Pinouts @@ -260,12 +329,68 @@ menu.resetpin=Reset pin 4808.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 4808.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +4808.menu.bootloader.no_bootloader=No bootloader +4808.menu.bootloader.no_bootloader.upload.extra_params= +4808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +4808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +4808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +4808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +4808.menu.bootloader.uart0_default.upload.protocol=arduino +4808.menu.bootloader.uart0_default.upload.extra_params= +4808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +4808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +4808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +4808.menu.bootloader.uart0_alternative.upload.protocol=arduino +4808.menu.bootloader.uart0_alternative.upload.extra_params= +4808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +4808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +4808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +4808.menu.bootloader.uart1_default.upload.protocol=arduino +4808.menu.bootloader.uart1_default.upload.extra_params= +4808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +4808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +4808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +4808.menu.bootloader.uart1_alternative.upload.protocol=arduino +4808.menu.bootloader.uart1_alternative.upload.extra_params= +4808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +4808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +4808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +4808.menu.bootloader.uart2_default.upload.protocol=arduino +4808.menu.bootloader.uart2_default.upload.extra_params= +4808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +4808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +4808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +4808.menu.bootloader.uart2_alternative.upload.protocol=arduino +4808.menu.bootloader.uart2_alternative.upload.extra_params= +4808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +4808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + + ##################### #### ATmega3209 #### ##################### # General -3209.name=Atmega3209 +3209.name=ATmega3209 3209.upload.tool=avrdude 3209.upload.maximum_size=32768 3209.upload.maximum_data_size=4096 @@ -276,13 +401,11 @@ menu.resetpin=Reset pin 3209.build.mcu=atmega3209 3209.build.extra_flags={build.oscillator} {build.compat} - # Fuses we don't need to modify in the tools menu 3209.bootloader.WDTCFG=0x00 3209.bootloader.TCD0CFG=0x00 3209.bootloader.SYSCFG1=0x06 3209.bootloader.APPEND=0x00 -3209.bootloader.BOOTEND=0x00 3209.bootloader.LOCKBIT=0xC5 # Pinouts @@ -293,7 +416,6 @@ menu.resetpin=Reset pin 3209.menu.pinout.uno_wifi.build.variant=uno-wifi 3209.menu.pinout.uno_wifi.build.compat= - # Reset pin 3209.menu.resetpin.reset=Reset 3209.menu.resetpin.reset.bootloader.SYSCFG0=0xCD @@ -387,6 +509,76 @@ menu.resetpin=Reset pin 3209.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 3209.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +3209.menu.bootloader.no_bootloader=No bootloader +3209.menu.bootloader.no_bootloader.upload.extra_params= +3209.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +3209.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +3209.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +3209.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +3209.menu.bootloader.uart0_default.upload.protocol=arduino +3209.menu.bootloader.uart0_default.upload.extra_params= +3209.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +3209.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +3209.menu.bootloader.uart0_alternative.upload.protocol=arduino +3209.menu.bootloader.uart0_alternative.upload.extra_params= +3209.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +3209.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +3209.menu.bootloader.uart1_default.upload.protocol=arduino +3209.menu.bootloader.uart1_default.upload.extra_params= +3209.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +3209.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +3209.menu.bootloader.uart1_alternative.upload.protocol=arduino +3209.menu.bootloader.uart1_alternative.upload.extra_params= +3209.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +3209.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +3209.menu.bootloader.uart2_default.upload.protocol=arduino +3209.menu.bootloader.uart2_default.upload.extra_params= +3209.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +3209.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +3209.menu.bootloader.uart2_alternative.upload.protocol=arduino +3209.menu.bootloader.uart2_alternative.upload.extra_params= +3209.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +3209.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +3209.menu.bootloader.uart3_default.upload.protocol=arduino +3209.menu.bootloader.uart3_default.upload.extra_params= +3209.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +3209.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 + +3209.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +3209.menu.bootloader.uart3_alternative.upload.protocol=arduino +3209.menu.bootloader.uart3_alternative.upload.extra_params= +3209.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +3209.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 +3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 #################### @@ -394,7 +586,7 @@ menu.resetpin=Reset pin #################### # General -3208.name=Atmega3208 +3208.name=ATmega3208 3208.upload.tool=avrdude 3208.upload.maximum_size=32768 3208.upload.maximum_data_size=4096 @@ -410,7 +602,6 @@ menu.resetpin=Reset pin 3208.bootloader.TCD0CFG=0x00 3208.bootloader.SYSCFG1=0x06 3208.bootloader.APPEND=0x00 -3208.bootloader.BOOTEND=0x00 3208.bootloader.LOCKBIT=0xC5 # Pinouts @@ -512,6 +703,60 @@ menu.resetpin=Reset pin 3208.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 3208.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +3208.menu.bootloader.no_bootloader=No bootloader +3208.menu.bootloader.no_bootloader.upload.extra_params= +3208.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +3208.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +3208.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +3208.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +3208.menu.bootloader.uart0_default.upload.protocol=arduino +3208.menu.bootloader.uart0_default.upload.extra_params= +3208.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +3208.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +3208.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +3208.menu.bootloader.uart0_alternative.upload.protocol=arduino +3208.menu.bootloader.uart0_alternative.upload.extra_params= +3208.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +3208.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +3208.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +3208.menu.bootloader.uart1_default.upload.protocol=arduino +3208.menu.bootloader.uart1_default.upload.extra_params= +3208.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +3208.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +3208.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +3208.menu.bootloader.uart1_alternative.upload.protocol=arduino +3208.menu.bootloader.uart1_alternative.upload.extra_params= +3208.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +3208.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +3208.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +3208.menu.bootloader.uart2_default.upload.protocol=arduino +3208.menu.bootloader.uart2_default.upload.extra_params= +3208.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +3208.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +3208.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +3208.menu.bootloader.uart2_alternative.upload.protocol=arduino +3208.menu.bootloader.uart2_alternative.upload.extra_params= +3208.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +3208.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 ##################### @@ -519,7 +764,7 @@ menu.resetpin=Reset pin ##################### # General -1609.name=Atmega1609 +1609.name=ATmega1609 1609.upload.tool=avrdude 1609.upload.maximum_size=16384 1609.upload.maximum_data_size=2048 @@ -535,7 +780,6 @@ menu.resetpin=Reset pin 1609.bootloader.TCD0CFG=0x00 1609.bootloader.SYSCFG1=0x06 1609.bootloader.APPEND=0x00 -1609.bootloader.BOOTEND=0x00 1609.bootloader.LOCKBIT=0xC5 # Pinouts @@ -639,6 +883,76 @@ menu.resetpin=Reset pin 1609.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 1609.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +1609.menu.bootloader.no_bootloader=No bootloader +1609.menu.bootloader.no_bootloader.upload.extra_params= +1609.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +1609.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +1609.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +1609.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +1609.menu.bootloader.uart0_default.upload.protocol=arduino +1609.menu.bootloader.uart0_default.upload.extra_params= +1609.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +1609.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +1609.menu.bootloader.uart0_alternative.upload.protocol=arduino +1609.menu.bootloader.uart0_alternative.upload.extra_params= +1609.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +1609.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +1609.menu.bootloader.uart1_default.upload.protocol=arduino +1609.menu.bootloader.uart1_default.upload.extra_params= +1609.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +1609.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +1609.menu.bootloader.uart1_alternative.upload.protocol=arduino +1609.menu.bootloader.uart1_alternative.upload.extra_params= +1609.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +1609.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +1609.menu.bootloader.uart2_default.upload.protocol=arduino +1609.menu.bootloader.uart2_default.upload.extra_params= +1609.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +1609.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +1609.menu.bootloader.uart2_alternative.upload.protocol=arduino +1609.menu.bootloader.uart2_alternative.upload.extra_params= +1609.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +1609.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +1609.menu.bootloader.uart3_default.upload.protocol=arduino +1609.menu.bootloader.uart3_default.upload.extra_params= +1609.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +1609.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 + +1609.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +1609.menu.bootloader.uart3_alternative.upload.protocol=arduino +1609.menu.bootloader.uart3_alternative.upload.extra_params= +1609.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +1609.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 +1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 #################### @@ -646,7 +960,7 @@ menu.resetpin=Reset pin #################### # General -1608.name=Atmega1608 +1608.name=ATmega1608 1608.upload.tool=avrdude 1608.upload.maximum_size=16384 1608.upload.maximum_data_size=2048 @@ -662,7 +976,6 @@ menu.resetpin=Reset pin 1608.bootloader.TCD0CFG=0x00 1608.bootloader.SYSCFG1=0x06 1608.bootloader.APPEND=0x00 -1608.bootloader.BOOTEND=0x00 1608.bootloader.LOCKBIT=0xC5 # Pinouts @@ -764,6 +1077,60 @@ menu.resetpin=Reset pin 1608.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 1608.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +1608.menu.bootloader.no_bootloader=No bootloader +1608.menu.bootloader.no_bootloader.upload.extra_params= +1608.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +1608.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +1608.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +1608.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +1608.menu.bootloader.uart0_default.upload.protocol=arduino +1608.menu.bootloader.uart0_default.upload.extra_params= +1608.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +1608.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +1608.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +1608.menu.bootloader.uart0_alternative.upload.protocol=arduino +1608.menu.bootloader.uart0_alternative.upload.extra_params= +1608.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +1608.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +1608.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +1608.menu.bootloader.uart1_default.upload.protocol=arduino +1608.menu.bootloader.uart1_default.upload.extra_params= +1608.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +1608.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +1608.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +1608.menu.bootloader.uart1_alternative.upload.protocol=arduino +1608.menu.bootloader.uart1_alternative.upload.extra_params= +1608.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +1608.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +1608.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +1608.menu.bootloader.uart2_default.upload.protocol=arduino +1608.menu.bootloader.uart2_default.upload.extra_params= +1608.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +1608.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +1608.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +1608.menu.bootloader.uart2_alternative.upload.protocol=arduino +1608.menu.bootloader.uart2_alternative.upload.extra_params= +1608.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +1608.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 ################### @@ -771,7 +1138,7 @@ menu.resetpin=Reset pin ################### # General -809.name=Atmega809 +809.name=ATmega809 809.upload.tool=avrdude 809.upload.maximum_size=8192 809.upload.maximum_data_size=1024 @@ -787,7 +1154,6 @@ menu.resetpin=Reset pin 809.bootloader.TCD0CFG=0x00 809.bootloader.SYSCFG1=0x06 809.bootloader.APPEND=0x00 -809.bootloader.BOOTEND=0x00 809.bootloader.LOCKBIT=0xC5 # Pinouts @@ -891,6 +1257,76 @@ menu.resetpin=Reset pin 809.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 809.menu.clock.external_1MHz.build.f_cpu=1000000L +# Bootloader +809.menu.bootloader.no_bootloader=No bootloader +809.menu.bootloader.no_bootloader.upload.extra_params= +809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +809.menu.bootloader.uart0_default.upload.protocol=arduino +809.menu.bootloader.uart0_default.upload.extra_params= +809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +809.menu.bootloader.uart0_alternative.upload.protocol=arduino +809.menu.bootloader.uart0_alternative.upload.extra_params= +809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +809.menu.bootloader.uart1_default.upload.protocol=arduino +809.menu.bootloader.uart1_default.upload.extra_params= +809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +809.menu.bootloader.uart1_alternative.upload.protocol=arduino +809.menu.bootloader.uart1_alternative.upload.extra_params= +809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +809.menu.bootloader.uart2_default.upload.protocol=arduino +809.menu.bootloader.uart2_default.upload.extra_params= +809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +809.menu.bootloader.uart2_alternative.upload.protocol=arduino +809.menu.bootloader.uart2_alternative.upload.extra_params= +809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +809.menu.bootloader.uart3_default.upload.protocol=arduino +809.menu.bootloader.uart3_default.upload.extra_params= +809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 + +809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +809.menu.bootloader.uart3_alternative.upload.protocol=arduino +809.menu.bootloader.uart3_alternative.upload.extra_params= +809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 +809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 ################### @@ -898,7 +1334,7 @@ menu.resetpin=Reset pin ################### # General -808.name=Atmega808 +808.name=ATmega808 808.upload.tool=avrdude 808.upload.maximum_size=8192 808.upload.maximum_data_size=1024 @@ -914,7 +1350,6 @@ menu.resetpin=Reset pin 808.bootloader.TCD0CFG=0x00 808.bootloader.SYSCFG1=0x06 808.bootloader.APPEND=0x00 -808.bootloader.BOOTEND=0x00 808.bootloader.LOCKBIT=0xC5 # Pinouts @@ -1015,3 +1450,58 @@ menu.resetpin=Reset pin 808.menu.clock.external_1MHz.bootloader.OSCCFG=0x01 808.menu.clock.external_1MHz.build.oscillator=-DUSE_EXTERNAL_OSCILLATOR 808.menu.clock.external_1MHz.build.f_cpu=1000000L + +# Bootloader +808.menu.bootloader.no_bootloader=No bootloader +808.menu.bootloader.no_bootloader.upload.extra_params= +808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 + +808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +808.menu.bootloader.uart0_default.upload.protocol=arduino +808.menu.bootloader.uart0_default.upload.extra_params= +808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 + +808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +808.menu.bootloader.uart0_alternative.upload.protocol=arduino +808.menu.bootloader.uart0_alternative.upload.extra_params= +808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 + +808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +808.menu.bootloader.uart1_default.upload.protocol=arduino +808.menu.bootloader.uart1_default.upload.extra_params= +808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 + +808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +808.menu.bootloader.uart1_alternative.upload.protocol=arduino +808.menu.bootloader.uart1_alternative.upload.extra_params= +808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 + +808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +808.menu.bootloader.uart2_default.upload.protocol=arduino +808.menu.bootloader.uart2_default.upload.extra_params= +808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 + +808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +808.menu.bootloader.uart2_alternative.upload.protocol=arduino +808.menu.bootloader.uart2_alternative.upload.extra_params= +808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 +808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 diff --git a/megaavr/bootloaders/empty/empty.hex b/megaavr/bootloaders/empty/empty.hex new file mode 100644 index 0000000..0bb9243 --- /dev/null +++ b/megaavr/bootloaders/empty/empty.hex @@ -0,0 +1,2 @@ +:0200000002C03C +:00000001FF \ No newline at end of file diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex new file mode 100644 index 0000000..8a36e1f --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0D2C01124809140008093400083FF42 +:1000100004C0282E80E0B0D0F3C0A895049A0C9AB2 +:1000200081E08093E205809182128370813029F50E +:100030008CE590E0809308089093090881E0809314 +:100040000B0883E0809307081092050880EC8093EA +:10005000060888E091D0079A87E0815089F4A89536 +:100060000DE983E0D82E7CD08134F1F479D0182FBB +:100070008CD0123889F480E013C083E790E0DACFA7 +:10008000179A2EEC36E5A8959091040897FDE8CFD5 +:1000900021503109C1F7E1CF89E0113809F083E03F +:1000A00058D080E156D0DFCF823419F484E175D086 +:1000B000F8CF853411F485E0FACF853531F450D08E +:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC +:1000D00064D0D1CF8436B9F443D042D0182F40D069 +:1000E000863479F4D05C3CD0888321961150D9F7BE +:1000F0004CD004BFD0920010809102108370E1F7C1 +:10010000D0CFDC5EF0CF843791F42AD029D0182FDD +:1001100027D0F82E3AD086E4F81207C0D05C888148 +:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 +:1001300051F42BD0809100110CD08091011109D085 +:1001400080910211ADCF813509F0BDCF81E014D08F +:10015000BACF9091040895FFFCCF809302080895D0 +:100160008091040887FFFCCF9091010880910008DE +:1001700092FD01C0A89508959091010190FDFCCFDA +:1001800098ED94BF809300010895EADF803219F062 +:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 +:1001A000C150E9F7CF91F1CF88ED84BF6093000192 +:0A01B000809102108370E1F70895BA +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C6DF0C94000035 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex new file mode 100644 index 0000000..89ac6c9 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0CFC01124809140008093400083FF45 +:1000100004C0282E80E0ADD0F3C0A895009A089ABD +:10002000809182128370813029F58CE590E0809375 +:1000300008089093090881E080930B0883E080937F +:1000400007081092050880EC8093060888E091D09C +:10005000079A87E0815089F4A8950DE983E0D82EAE +:100060007CD08134F1F479D0182F8CD0123889F4F7 +:1000700080E013C083E790E0DACF179A2EEC36E5E4 +:10008000A8959091040897FDE8CF21503109C1F758 +:10009000E1CF89E0113809F083E058D080E156D0F3 +:1000A000DFCF823419F484E175D0F8CF853411F4B0 +:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 +:1000C00061D0ECCF863519F484E064D0D1CF84368A +:1000D000B9F443D042D0182F40D0863479F4D05CA4 +:1000E0003CD0888321961150D9F74CD004BFD092D0 +:1000F0000010809102108370E1F7D0CFDC5EF0CF6A +:10010000843791F42AD029D0182F27D0F82E3AD04E +:1001100086E4F81207C0D05C8881219617D0115070 +:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 +:1001300000110CD08091011109D080910211ADCF36 +:10014000813509F0BDCF81E014D0BACF9091040879 +:1001500095FFFCCF8093020808958091040887FFE3 +:10016000FCCF909101088091000892FD01C0A895F4 +:1001700008959091010190FDFCCF98ED94BF80937C +:1001800000010895EADF803219F081E0F2DFFFCF4D +:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 +:1001A000F1CF88ED84BF60930001809102108370CD +:0401B000E1F70895D6 +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C3DF0C94000038 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex new file mode 100644 index 0000000..a1b4057 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0D2C01124809140008093400083FF42 +:1000100004C0282E80E0B0D0F3C0A895449A4C9A32 +:1000200084E08093E205809182128370813029F50B +:100030008CE590E0809328089093290881E08093D4 +:100040002B0883E0809327081092250880EC80938A +:10005000260888E091D0079A87E0815089F4A89516 +:100060000DE983E0D82E7CD08134F1F479D0182FBB +:100070008CD0123889F480E013C083E790E0DACFA7 +:10008000179A2EEC36E5A8959091240897FDE8CFB5 +:1000900021503109C1F7E1CF89E0113809F083E03F +:1000A00058D080E156D0DFCF823419F484E175D086 +:1000B000F8CF853411F485E0FACF853531F450D08E +:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC +:1000D00064D0D1CF8436B9F443D042D0182F40D069 +:1000E000863479F4D05C3CD0888321961150D9F7BE +:1000F0004CD004BFD0920010809102108370E1F7C1 +:10010000D0CFDC5EF0CF843791F42AD029D0182FDD +:1001100027D0F82E3AD086E4F81207C0D05C888148 +:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 +:1001300051F42BD0809100110CD08091011109D085 +:1001400080910211ADCF813509F0BDCF81E014D08F +:10015000BACF9091240895FFFCCF80932208089590 +:100160008091240887FFFCCF90912108809120087E +:1001700092FD01C0A89508959091010190FDFCCFDA +:1001800098ED94BF809300010895EADF803219F062 +:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 +:1001A000C150E9F7CF91F1CF88ED84BF6093000192 +:0A01B000809102108370E1F70895BA +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C6DF0C94000035 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex new file mode 100644 index 0000000..be8dfc7 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0CFC01124809140008093400083FF45 +:1000100004C0282E80E0ADD0F3C0A895409A489A3D +:10002000809182128370813029F58CE590E0809375 +:1000300028089093290881E080932B0883E080931F +:1000400027081092250880EC8093260888E091D03C +:10005000079A87E0815089F4A8950DE983E0D82EAE +:100060007CD08134F1F479D0182F8CD0123889F4F7 +:1000700080E013C083E790E0DACF179A2EEC36E5E4 +:10008000A8959091240897FDE8CF21503109C1F738 +:10009000E1CF89E0113809F083E058D080E156D0F3 +:1000A000DFCF823419F484E175D0F8CF853411F4B0 +:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 +:1000C00061D0ECCF863519F484E064D0D1CF84368A +:1000D000B9F443D042D0182F40D0863479F4D05CA4 +:1000E0003CD0888321961150D9F74CD004BFD092D0 +:1000F0000010809102108370E1F7D0CFDC5EF0CF6A +:10010000843791F42AD029D0182F27D0F82E3AD04E +:1001100086E4F81207C0D05C8881219617D0115070 +:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 +:1001300000110CD08091011109D080910211ADCF36 +:10014000813509F0BDCF81E014D0BACF9091240859 +:1001500095FFFCCF8093220808958091240887FFA3 +:10016000FCCF909121088091200892FD01C0A895B4 +:1001700008959091010190FDFCCF98ED94BF80937C +:1001800000010895EADF803219F081E0F2DFFFCF4D +:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 +:1001A000F1CF88ED84BF60930001809102108370CD +:0401B000E1F70895D6 +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C3DF0C94000038 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex new file mode 100644 index 0000000..f8be480 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0D2C01124809140008093400083FF42 +:1000100004C0282E80E0B0D0F3C0A895A49AAC9A72 +:1000200080E18093E205809182128370813029F50E +:100030008CE590E0809348089093490881E0809394 +:100040004B0883E0809347081092450880EC80932A +:10005000460888E091D0079A87E0815089F4A895F6 +:100060000DE983E0D82E7CD08134F1F479D0182FBB +:100070008CD0123889F480E013C083E790E0DACFA7 +:10008000179A2EEC36E5A8959091440897FDE8CF95 +:1000900021503109C1F7E1CF89E0113809F083E03F +:1000A00058D080E156D0DFCF823419F484E175D086 +:1000B000F8CF853411F485E0FACF853531F450D08E +:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC +:1000D00064D0D1CF8436B9F443D042D0182F40D069 +:1000E000863479F4D05C3CD0888321961150D9F7BE +:1000F0004CD004BFD0920010809102108370E1F7C1 +:10010000D0CFDC5EF0CF843791F42AD029D0182FDD +:1001100027D0F82E3AD086E4F81207C0D05C888148 +:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 +:1001300051F42BD0809100110CD08091011109D085 +:1001400080910211ADCF813509F0BDCF81E014D08F +:10015000BACF9091440895FFFCCF80934208089550 +:100160008091440887FFFCCF90914108809140081E +:1001700092FD01C0A89508959091010190FDFCCFDA +:1001800098ED94BF809300010895EADF803219F062 +:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 +:1001A000C150E9F7CF91F1CF88ED84BF6093000192 +:0A01B000809102108370E1F70895BA +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C6DF0C94000035 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex new file mode 100644 index 0000000..5d989f3 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0CFC01124809140008093400083FF45 +:1000100004C0282E80E0ADD0F3C0A895A09AA89A7D +:10002000809182128370813029F58CE590E0809375 +:1000300048089093490881E080934B0883E08093BF +:1000400047081092450880EC8093460888E091D0DC +:10005000079A87E0815089F4A8950DE983E0D82EAE +:100060007CD08134F1F479D0182F8CD0123889F4F7 +:1000700080E013C083E790E0DACF179A2EEC36E5E4 +:10008000A8959091440897FDE8CF21503109C1F718 +:10009000E1CF89E0113809F083E058D080E156D0F3 +:1000A000DFCF823419F484E175D0F8CF853411F4B0 +:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 +:1000C00061D0ECCF863519F484E064D0D1CF84368A +:1000D000B9F443D042D0182F40D0863479F4D05CA4 +:1000E0003CD0888321961150D9F74CD004BFD092D0 +:1000F0000010809102108370E1F7D0CFDC5EF0CF6A +:10010000843791F42AD029D0182F27D0F82E3AD04E +:1001100086E4F81207C0D05C8881219617D0115070 +:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 +:1001300000110CD08091011109D080910211ADCF36 +:10014000813509F0BDCF81E014D0BACF9091440839 +:1001500095FFFCCF8093420808958091440887FF63 +:10016000FCCF909141088091400892FD01C0A89574 +:1001700008959091010190FDFCCF98ED94BF80937C +:1001800000010895EADF803219F081E0F2DFFFCF4D +:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 +:1001A000F1CF88ED84BF60930001809102108370CD +:0401B000E1F70895D6 +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C3DF0C94000038 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex new file mode 100644 index 0000000..70bfcaf --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0D2C01124809140008093400083FF42 +:1000100004C0282E80E0B0D0F3C0A895249A2C9A72 +:1000200080E48093E205809182128370813029F50B +:100030008CE590E0809368089093690881E0809354 +:100040006B0883E0809367081092650880EC8093CA +:10005000660888E091D0079A87E0815089F4A895D6 +:100060000DE983E0D82E7CD08134F1F479D0182FBB +:100070008CD0123889F480E013C083E790E0DACFA7 +:10008000179A2EEC36E5A8959091640897FDE8CF75 +:1000900021503109C1F7E1CF89E0113809F083E03F +:1000A00058D080E156D0DFCF823419F484E175D086 +:1000B000F8CF853411F485E0FACF853531F450D08E +:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC +:1000D00064D0D1CF8436B9F443D042D0182F40D069 +:1000E000863479F4D05C3CD0888321961150D9F7BE +:1000F0004CD004BFD0920010809102108370E1F7C1 +:10010000D0CFDC5EF0CF843791F42AD029D0182FDD +:1001100027D0F82E3AD086E4F81207C0D05C888148 +:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 +:1001300051F42BD0809100110CD08091011109D085 +:1001400080910211ADCF813509F0BDCF81E014D08F +:10015000BACF9091640895FFFCCF80936208089510 +:100160008091640887FFFCCF9091610880916008BE +:1001700092FD01C0A89508959091010190FDFCCFDA +:1001800098ED94BF809300010895EADF803219F062 +:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 +:1001A000C150E9F7CF91F1CF88ED84BF6093000192 +:0A01B000809102108370E1F70895BA +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C6DF0C94000035 +:00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex new file mode 100644 index 0000000..6993650 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex @@ -0,0 +1,32 @@ +:1000000001C0CFC01124809140008093400083FF45 +:1000100004C0282E80E0ADD0F3C0A895209A289A7D +:10002000809182128370813029F58CE590E0809375 +:1000300068089093690881E080936B0883E080935F +:1000400067081092650880EC8093660888E091D07C +:10005000079A87E0815089F4A8950DE983E0D82EAE +:100060007CD08134F1F479D0182F8CD0123889F4F7 +:1000700080E013C083E790E0DACF179A2EEC36E5E4 +:10008000A8959091640897FDE8CF21503109C1F7F8 +:10009000E1CF89E0113809F083E058D080E156D0F3 +:1000A000DFCF823419F484E175D0F8CF853411F4B0 +:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 +:1000C00061D0ECCF863519F484E064D0D1CF84368A +:1000D000B9F443D042D0182F40D0863479F4D05CA4 +:1000E0003CD0888321961150D9F74CD004BFD092D0 +:1000F0000010809102108370E1F7D0CFDC5EF0CF6A +:10010000843791F42AD029D0182F27D0F82E3AD04E +:1001100086E4F81207C0D05C8881219617D0115070 +:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 +:1001300000110CD08091011109D080910211ADCF36 +:10014000813509F0BDCF81E014D0BACF9091640819 +:1001500095FFFCCF8093620808958091640887FF23 +:10016000FCCF909161088091600892FD01C0A89534 +:1001700008959091010190FDFCCF98ED94BF80937C +:1001800000010895EADF803219F081E0F2DFFFCF4D +:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 +:1001A000F1CF88ED84BF60930001809102108370CD +:0401B000E1F70895D6 +:0201FE000009F6 +:10020000E0E4F0E0808180838091FE019091FF0125 +:1002100050E040E064E090E080E0C3DF0C94000038 +:00000001FF diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 12b2a88..e454687 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -21,7 +21,7 @@ compiler.warning_flags.all=-Wall -Wextra compiler.path={runtime.tools.avr-gcc.path}/bin/ compiler.c.cmd=avr-gcc compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto -fno-fat-lto-objects -compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin -Wl,--gc-sections +compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin -Wl,--gc-sections -Wl,--section-start={build.text_section_start} compiler.c.elf.cmd=avr-gcc compiler.S.flags=-c -g -x assembler-with-cpp -flto -MMD compiler.cpp.cmd=avr-g++ @@ -102,7 +102,7 @@ tools.avrdude.upload.params.quiet=-q -q # tools.avrdude.upload.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value tools.avrdude.upload.verify= tools.avrdude.upload.params.noverify=-V -tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {upload.extra_params} -b{upload.speed} -e -D "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} -P{serial.port} -b{upload.speed} -D "-Uflash:w:{build.path}/{build.project_name}.hex:i" tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q @@ -113,7 +113,7 @@ tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} { tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q -tools.avrdude.erase.pattern= +tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} -e {program.extra_params} {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} tools.avrdude.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" tools.avrdude.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" @@ -127,7 +127,7 @@ tools.avrdude.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" tools.avrdude.bootloader.params.verbose=-v tools.avrdude.bootloader.params.quiet=-q -q -tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" {bootloader.verbose} -p{build.mcu} -c{protocol} {program.extra_params} {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" tools.avrdude_remote.upload.pattern=/usr/bin/run-avrdude /tmp/sketch.hex {upload.verbose} -p{build.mcu} From a70a2b8d9613f12aada67c8d1019440986927a5e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 11 Oct 2019 20:47:03 +0200 Subject: [PATCH 083/351] Fix duplicate flags --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index e454687..ce45ceb 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -113,7 +113,7 @@ tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} { tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q -tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} -e {program.extra_params} {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} -e {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} tools.avrdude.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" tools.avrdude.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" From a488f06a30c731f334d33a2262252c417c8a204e Mon Sep 17 00:00:00 2001 From: "Spence Konde (aka Dr. Azzy)" Date: Sun, 13 Oct 2019 04:01:59 -0400 Subject: [PATCH 084/351] Fix size output for const variables See https://github.com/SpenceKonde/megaTinyCore/issues/95 --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index ce45ceb..7d964c0 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -77,7 +77,7 @@ recipe.output.save_file={build.project_name}.{build.variant}.hex ## Compute size recipe.size.pattern="{compiler.path}{compiler.size.cmd}" -A "{build.path}/{build.project_name}.elf" -recipe.size.regex=^(?:\.text|\.data|\.bootloader)\s+([0-9]+).* +recipe.size.regex=^(?:\.text|\.data|\.rodata|\.bootloader)\s+([0-9]+).* recipe.size.regex.data=^(?:\.data|\.bss|\.noinit)\s+([0-9]+).* recipe.size.regex.eeprom=^(?:\.eeprom)\s+([0-9]+).* From a300b4e032d7666fae8c3471945aaf30481f4bce Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 13 Oct 2019 18:33:35 +0200 Subject: [PATCH 085/351] Update bootloader files Fix issue where the PINMUX was incorrectly set if the bootloader was changed --- .../optiboot_mega0_UART0_DEF_115200_PA7.hex | 58 +++++++++---------- .../optiboot_mega0_UART1_DEF_115200_PA7.hex | 58 +++++++++---------- .../optiboot_mega0_UART2_DEF_115200_PA7.hex | 58 +++++++++---------- .../optiboot_mega0_UART3_DEF_115200_PA7.hex | 58 +++++++++---------- 4 files changed, 116 insertions(+), 116 deletions(-) diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex index 89ac6c9..5f09d61 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex @@ -1,32 +1,32 @@ -:1000000001C0CFC01124809140008093400083FF45 -:1000100004C0282E80E0ADD0F3C0A895009A089ABD -:10002000809182128370813029F58CE590E0809375 -:1000300008089093090881E080930B0883E080937F -:1000400007081092050880EC8093060888E091D09C -:10005000079A87E0815089F4A8950DE983E0D82EAE -:100060007CD08134F1F479D0182F8CD0123889F4F7 -:1000700080E013C083E790E0DACF179A2EEC36E5E4 -:10008000A8959091040897FDE8CF21503109C1F758 -:10009000E1CF89E0113809F083E058D080E156D0F3 -:1000A000DFCF823419F484E175D0F8CF853411F4B0 -:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 -:1000C00061D0ECCF863519F484E064D0D1CF84368A -:1000D000B9F443D042D0182F40D0863479F4D05CA4 -:1000E0003CD0888321961150D9F74CD004BFD092D0 -:1000F0000010809102108370E1F7D0CFDC5EF0CF6A -:10010000843791F42AD029D0182F27D0F82E3AD04E -:1001100086E4F81207C0D05C8881219617D0115070 -:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 -:1001300000110CD08091011109D080910211ADCF36 -:10014000813509F0BDCF81E014D0BACF9091040879 -:1001500095FFFCCF8093020808958091040887FFE3 -:10016000FCCF909101088091000892FD01C0A895F4 -:1001700008959091010190FDFCCF98ED94BF80937C -:1001800000010895EADF803219F081E0F2DFFFCF4D -:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 -:1001A000F1CF88ED84BF60930001809102108370CD -:0401B000E1F70895D6 +:1000000001C0D1C01124809140008093400083FF43 +:1000100004C0282E80E0AFD0F3C0A895009A089ABB +:100020001092E205809182128370813029F58CE56F +:1000300090E0809308089093090881E080930B0872 +:1000400083E0809307081092050880EC80930608EF +:1000500088E091D0079A87E0815089F4A8950DE94E +:1000600083E0D82E7CD08134F1F479D0182F8CD055 +:10007000123889F480E013C083E790E0DACF179A52 +:100080002EEC36E5A8959091040897FDE8CF215015 +:100090003109C1F7E1CF89E0113809F083E058D088 +:1000A00080E156D0DFCF823419F484E175D0F8CFE7 +:1000B000853411F485E0FACF853531F450D0C82F5E +:1000C0004ED0D82F61D0ECCF863519F484E064D0BF +:1000D000D1CF8436B9F443D042D0182F40D08634E3 +:1000E00079F4D05C3CD0888321961150D9F74CD05C +:1000F00004BFD0920010809102108370E1F7D0CF3E +:10010000DC5EF0CF843791F42AD029D0182F27D085 +:10011000F82E3AD086E4F81207C0D05C8881219688 +:1001200017D01150D9F7BCCFDC5EF8CF853751F42A +:100130002BD0809100110CD08091011109D08091B9 +:100140000211ADCF813509F0BDCF81E014D0BACF17 +:100150009091040895FFFCCF809302080895809148 +:10016000040887FFFCCF909101088091000892FD60 +:1001700001C0A89508959091010190FDFCCF98EDE4 +:1001800094BF809300010895EADF803219F081E086 +:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 +:1001A000E9F7CF91F1CF88ED84BF60930001809192 +:0801B00002108370E1F70895CD :0201FE000009F6 :10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C3DF0C94000038 +:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex index be8dfc7..c996adf 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex @@ -1,32 +1,32 @@ -:1000000001C0CFC01124809140008093400083FF45 -:1000100004C0282E80E0ADD0F3C0A895409A489A3D -:10002000809182128370813029F58CE590E0809375 -:1000300028089093290881E080932B0883E080931F -:1000400027081092250880EC8093260888E091D03C -:10005000079A87E0815089F4A8950DE983E0D82EAE -:100060007CD08134F1F479D0182F8CD0123889F4F7 -:1000700080E013C083E790E0DACF179A2EEC36E5E4 -:10008000A8959091240897FDE8CF21503109C1F738 -:10009000E1CF89E0113809F083E058D080E156D0F3 -:1000A000DFCF823419F484E175D0F8CF853411F4B0 -:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 -:1000C00061D0ECCF863519F484E064D0D1CF84368A -:1000D000B9F443D042D0182F40D0863479F4D05CA4 -:1000E0003CD0888321961150D9F74CD004BFD092D0 -:1000F0000010809102108370E1F7D0CFDC5EF0CF6A -:10010000843791F42AD029D0182F27D0F82E3AD04E -:1001100086E4F81207C0D05C8881219617D0115070 -:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 -:1001300000110CD08091011109D080910211ADCF36 -:10014000813509F0BDCF81E014D0BACF9091240859 -:1001500095FFFCCF8093220808958091240887FFA3 -:10016000FCCF909121088091200892FD01C0A895B4 -:1001700008959091010190FDFCCF98ED94BF80937C -:1001800000010895EADF803219F081E0F2DFFFCF4D -:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 -:1001A000F1CF88ED84BF60930001809102108370CD -:0401B000E1F70895D6 +:1000000001C0D1C01124809140008093400083FF43 +:1000100004C0282E80E0AFD0F3C0A895409A489A3B +:100020001092E205809182128370813029F58CE56F +:1000300090E0809328089093290881E080932B0812 +:1000400083E0809327081092250880EC809326088F +:1000500088E091D0079A87E0815089F4A8950DE94E +:1000600083E0D82E7CD08134F1F479D0182F8CD055 +:10007000123889F480E013C083E790E0DACF179A52 +:100080002EEC36E5A8959091240897FDE8CF2150F5 +:100090003109C1F7E1CF89E0113809F083E058D088 +:1000A00080E156D0DFCF823419F484E175D0F8CFE7 +:1000B000853411F485E0FACF853531F450D0C82F5E +:1000C0004ED0D82F61D0ECCF863519F484E064D0BF +:1000D000D1CF8436B9F443D042D0182F40D08634E3 +:1000E00079F4D05C3CD0888321961150D9F74CD05C +:1000F00004BFD0920010809102108370E1F7D0CF3E +:10010000DC5EF0CF843791F42AD029D0182F27D085 +:10011000F82E3AD086E4F81207C0D05C8881219688 +:1001200017D01150D9F7BCCFDC5EF8CF853751F42A +:100130002BD0809100110CD08091011109D08091B9 +:100140000211ADCF813509F0BDCF81E014D0BACF17 +:100150009091240895FFFCCF809322080895809108 +:10016000240887FFFCCF909121088091200892FD00 +:1001700001C0A89508959091010190FDFCCF98EDE4 +:1001800094BF809300010895EADF803219F081E086 +:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 +:1001A000E9F7CF91F1CF88ED84BF60930001809192 +:0801B00002108370E1F70895CD :0201FE000009F6 :10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C3DF0C94000038 +:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex index 5d989f3..e24ac40 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex @@ -1,32 +1,32 @@ -:1000000001C0CFC01124809140008093400083FF45 -:1000100004C0282E80E0ADD0F3C0A895A09AA89A7D -:10002000809182128370813029F58CE590E0809375 -:1000300048089093490881E080934B0883E08093BF -:1000400047081092450880EC8093460888E091D0DC -:10005000079A87E0815089F4A8950DE983E0D82EAE -:100060007CD08134F1F479D0182F8CD0123889F4F7 -:1000700080E013C083E790E0DACF179A2EEC36E5E4 -:10008000A8959091440897FDE8CF21503109C1F718 -:10009000E1CF89E0113809F083E058D080E156D0F3 -:1000A000DFCF823419F484E175D0F8CF853411F4B0 -:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 -:1000C00061D0ECCF863519F484E064D0D1CF84368A -:1000D000B9F443D042D0182F40D0863479F4D05CA4 -:1000E0003CD0888321961150D9F74CD004BFD092D0 -:1000F0000010809102108370E1F7D0CFDC5EF0CF6A -:10010000843791F42AD029D0182F27D0F82E3AD04E -:1001100086E4F81207C0D05C8881219617D0115070 -:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 -:1001300000110CD08091011109D080910211ADCF36 -:10014000813509F0BDCF81E014D0BACF9091440839 -:1001500095FFFCCF8093420808958091440887FF63 -:10016000FCCF909141088091400892FD01C0A89574 -:1001700008959091010190FDFCCF98ED94BF80937C -:1001800000010895EADF803219F081E0F2DFFFCF4D -:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 -:1001A000F1CF88ED84BF60930001809102108370CD -:0401B000E1F70895D6 +:1000000001C0D1C01124809140008093400083FF43 +:1000100004C0282E80E0AFD0F3C0A895A09AA89A7B +:100020001092E205809182128370813029F58CE56F +:1000300090E0809348089093490881E080934B08B2 +:1000400083E0809347081092450880EC809346082F +:1000500088E091D0079A87E0815089F4A8950DE94E +:1000600083E0D82E7CD08134F1F479D0182F8CD055 +:10007000123889F480E013C083E790E0DACF179A52 +:100080002EEC36E5A8959091440897FDE8CF2150D5 +:100090003109C1F7E1CF89E0113809F083E058D088 +:1000A00080E156D0DFCF823419F484E175D0F8CFE7 +:1000B000853411F485E0FACF853531F450D0C82F5E +:1000C0004ED0D82F61D0ECCF863519F484E064D0BF +:1000D000D1CF8436B9F443D042D0182F40D08634E3 +:1000E00079F4D05C3CD0888321961150D9F74CD05C +:1000F00004BFD0920010809102108370E1F7D0CF3E +:10010000DC5EF0CF843791F42AD029D0182F27D085 +:10011000F82E3AD086E4F81207C0D05C8881219688 +:1001200017D01150D9F7BCCFDC5EF8CF853751F42A +:100130002BD0809100110CD08091011109D08091B9 +:100140000211ADCF813509F0BDCF81E014D0BACF17 +:100150009091440895FFFCCF8093420808958091C8 +:10016000440887FFFCCF909141088091400892FDA0 +:1001700001C0A89508959091010190FDFCCF98EDE4 +:1001800094BF809300010895EADF803219F081E086 +:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 +:1001A000E9F7CF91F1CF88ED84BF60930001809192 +:0801B00002108370E1F70895CD :0201FE000009F6 :10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C3DF0C94000038 +:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex index 6993650..81553f4 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex @@ -1,32 +1,32 @@ -:1000000001C0CFC01124809140008093400083FF45 -:1000100004C0282E80E0ADD0F3C0A895209A289A7D -:10002000809182128370813029F58CE590E0809375 -:1000300068089093690881E080936B0883E080935F -:1000400067081092650880EC8093660888E091D07C -:10005000079A87E0815089F4A8950DE983E0D82EAE -:100060007CD08134F1F479D0182F8CD0123889F4F7 -:1000700080E013C083E790E0DACF179A2EEC36E5E4 -:10008000A8959091640897FDE8CF21503109C1F7F8 -:10009000E1CF89E0113809F083E058D080E156D0F3 -:1000A000DFCF823419F484E175D0F8CF853411F4B0 -:1000B00085E0FACF853531F450D0C82F4ED0D82FF7 -:1000C00061D0ECCF863519F484E064D0D1CF84368A -:1000D000B9F443D042D0182F40D0863479F4D05CA4 -:1000E0003CD0888321961150D9F74CD004BFD092D0 -:1000F0000010809102108370E1F7D0CFDC5EF0CF6A -:10010000843791F42AD029D0182F27D0F82E3AD04E -:1001100086E4F81207C0D05C8881219617D0115070 -:10012000D9F7BCCFDC5EF8CF853751F42BD0809166 -:1001300000110CD08091011109D080910211ADCF36 -:10014000813509F0BDCF81E014D0BACF9091640819 -:1001500095FFFCCF8093620808958091640887FF23 -:10016000FCCF909161088091600892FD01C0A89534 -:1001700008959091010190FDFCCF98ED94BF80937C -:1001800000010895EADF803219F081E0F2DFFFCF4D -:1001900084E1DCCFCF93C82FE0DFC150E9F7CF91E6 -:1001A000F1CF88ED84BF60930001809102108370CD -:0401B000E1F70895D6 +:1000000001C0D1C01124809140008093400083FF43 +:1000100004C0282E80E0AFD0F3C0A895209A289A7B +:100020001092E205809182128370813029F58CE56F +:1000300090E0809368089093690881E080936B0852 +:1000400083E0809367081092650880EC80936608CF +:1000500088E091D0079A87E0815089F4A8950DE94E +:1000600083E0D82E7CD08134F1F479D0182F8CD055 +:10007000123889F480E013C083E790E0DACF179A52 +:100080002EEC36E5A8959091640897FDE8CF2150B5 +:100090003109C1F7E1CF89E0113809F083E058D088 +:1000A00080E156D0DFCF823419F484E175D0F8CFE7 +:1000B000853411F485E0FACF853531F450D0C82F5E +:1000C0004ED0D82F61D0ECCF863519F484E064D0BF +:1000D000D1CF8436B9F443D042D0182F40D08634E3 +:1000E00079F4D05C3CD0888321961150D9F74CD05C +:1000F00004BFD0920010809102108370E1F7D0CF3E +:10010000DC5EF0CF843791F42AD029D0182F27D085 +:10011000F82E3AD086E4F81207C0D05C8881219688 +:1001200017D01150D9F7BCCFDC5EF8CF853751F42A +:100130002BD0809100110CD08091011109D08091B9 +:100140000211ADCF813509F0BDCF81E014D0BACF17 +:100150009091640895FFFCCF809362080895809188 +:10016000640887FFFCCF909161088091600892FD40 +:1001700001C0A89508959091010190FDFCCF98EDE4 +:1001800094BF809300010895EADF803219F081E086 +:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 +:1001A000E9F7CF91F1CF88ED84BF60930001809192 +:0801B00002108370E1F70895CD :0201FE000009F6 :10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C3DF0C94000038 +:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF From 93f2328bbf6dc4427239572f4e99b0e42faf60e5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 13 Oct 2019 19:41:43 +0200 Subject: [PATCH 086/351] Change LED_BUILTIN to 7 --- megaavr/variants/28pin-standard/pins_arduino.h | 9 ++++----- megaavr/variants/32pin-standard/pins_arduino.h | 9 ++++----- megaavr/variants/48pin-standard/pins_arduino.h | 9 ++++----- 3 files changed, 12 insertions(+), 15 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 81c0154..1f60c52 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -24,11 +24,12 @@ #define NUM_ANALOG_INPUTS 8 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 12 +#define ANALOG_INPUT_OFFSET 12 +#define LED_BUILTIN 7 // PA7 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) #define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 12 && (p) <= 19) ? (p) : NOT_A_PIN) @@ -75,8 +76,6 @@ static const uint8_t SCK = PIN_SPI_SCK; static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -#define LED_BUILTIN 15 - // USART 0 // No pinswap by default #define HWSERIAL0 (&USART0) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index dccb132..3ba4d17 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -24,11 +24,12 @@ #define NUM_ANALOG_INPUTS 12 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 12 +#define ANALOG_INPUT_OFFSET 12 +#define LED_BUILTIN 7 // PA7 #define digitalPinToAnalogInput(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 8 && (p) <= 11) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 12 && (p) <= 19) || ((p) >= 22 && (p) <= 25)) ? (p) : NOT_A_PIN) @@ -75,8 +76,6 @@ static const uint8_t SCK = PIN_SPI_SCK; static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -#define LED_BUILTIN 15 - // USART 0 // No pinswap enabled by default #define HWSERIAL0 (&USART0) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index b793e9b..b428112 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -29,11 +29,12 @@ #define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) -#define ANALOG_INPUT_OFFSET 22 +#define ANALOG_INPUT_OFFSET 22 +#define LED_BUILTIN 7 // PA7 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= 22 && (p) <= 33) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= 36 && (p) <=39) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) ((p <= 11) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) <= 15) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 22 && (p) <= 33) || ((p) >= 36 && (p) <= 39)) ? (p) : NOT_A_PIN) @@ -88,8 +89,6 @@ static const uint8_t SCK = PIN_SPI_SCK; static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -#define LED_BUILTIN 39 - // USART 0 // No pinswap by default #define HWSERIAL0 (&USART0) From 90742adfedd89c37615c3eaf7212feb72dc9ff94 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 14 Oct 2019 13:49:41 +0200 Subject: [PATCH 087/351] Reduce maximum flash size vaiable when using a bootloader --- megaavr/boards.txt | 72 ++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 64 insertions(+), 8 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index ec25111..6b2648c 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -12,7 +12,6 @@ menu.bootloader=Bootloader # General 4809.name=ATmega4809 4809.upload.tool=avrdude -4809.upload.maximum_size=49152 4809.upload.maximum_data_size=6144 4809.upload.speed=115200 4809.bootloader.tool=avrdude @@ -137,12 +136,14 @@ menu.bootloader=Bootloader # Bootloader 4809.menu.bootloader.no_bootloader=No bootloader +4809.menu.bootloader.no_bootloader.upload.maximum_size=49152 4809.menu.bootloader.no_bootloader.upload.extra_params= 4809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 4809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 4809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 4809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +4809.menu.bootloader.uart0_default.upload.maximum_size=48640 4809.menu.bootloader.uart0_default.upload.protocol=arduino 4809.menu.bootloader.uart0_default.upload.extra_params= 4809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -151,6 +152,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +4809.menu.bootloader.uart0_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart0_alternative.upload.protocol=arduino 4809.menu.bootloader.uart0_alternative.upload.extra_params= 4809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -159,6 +161,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +4809.menu.bootloader.uart1_default.upload.maximum_size=48640 4809.menu.bootloader.uart1_default.upload.protocol=arduino 4809.menu.bootloader.uart1_default.upload.extra_params= 4809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -167,6 +170,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +4809.menu.bootloader.uart1_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart1_alternative.upload.protocol=arduino 4809.menu.bootloader.uart1_alternative.upload.extra_params= 4809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -175,6 +179,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +4809.menu.bootloader.uart2_default.upload.maximum_size=48640 4809.menu.bootloader.uart2_default.upload.protocol=arduino 4809.menu.bootloader.uart2_default.upload.extra_params= 4809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -183,6 +188,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +4809.menu.bootloader.uart2_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart2_alternative.upload.protocol=arduino 4809.menu.bootloader.uart2_alternative.upload.extra_params= 4809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -191,6 +197,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +4809.menu.bootloader.uart3_default.upload.maximum_size=48640 4809.menu.bootloader.uart3_default.upload.protocol=arduino 4809.menu.bootloader.uart3_default.upload.extra_params= 4809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 @@ -199,6 +206,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +4809.menu.bootloader.uart3_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart3_alternative.upload.protocol=arduino 4809.menu.bootloader.uart3_alternative.upload.extra_params= 4809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 @@ -214,7 +222,6 @@ menu.bootloader=Bootloader # General 4808.name=ATmega4808 4808.upload.tool=avrdude -4808.upload.maximum_size=49152 4808.upload.maximum_data_size=6144 4808.upload.speed=115200 4808.bootloader.tool=avrdude @@ -331,12 +338,14 @@ menu.bootloader=Bootloader # Bootloader 4808.menu.bootloader.no_bootloader=No bootloader +4808.menu.bootloader.no_bootloader.upload.maximum_size=49152 4808.menu.bootloader.no_bootloader.upload.extra_params= 4808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 4808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 4808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 4808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +4808.menu.bootloader.uart0_default.upload.maximum_size=48640 4808.menu.bootloader.uart0_default.upload.protocol=arduino 4808.menu.bootloader.uart0_default.upload.extra_params= 4808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -345,6 +354,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +4808.menu.bootloader.uart0_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart0_alternative.upload.protocol=arduino 4808.menu.bootloader.uart0_alternative.upload.extra_params= 4808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -353,6 +363,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +4808.menu.bootloader.uart1_default.upload.maximum_size=48640 4808.menu.bootloader.uart1_default.upload.protocol=arduino 4808.menu.bootloader.uart1_default.upload.extra_params= 4808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -361,6 +372,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +4808.menu.bootloader.uart1_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart1_alternative.upload.protocol=arduino 4808.menu.bootloader.uart1_alternative.upload.extra_params= 4808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -369,6 +381,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +4808.menu.bootloader.uart2_default.upload.maximum_size=48640 4808.menu.bootloader.uart2_default.upload.protocol=arduino 4808.menu.bootloader.uart2_default.upload.extra_params= 4808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -377,6 +390,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +4808.menu.bootloader.uart2_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart2_alternative.upload.protocol=arduino 4808.menu.bootloader.uart2_alternative.upload.extra_params= 4808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -392,7 +406,6 @@ menu.bootloader=Bootloader # General 3209.name=ATmega3209 3209.upload.tool=avrdude -3209.upload.maximum_size=32768 3209.upload.maximum_data_size=4096 3209.upload.speed=115200 3209.bootloader.tool=avrdude @@ -511,12 +524,14 @@ menu.bootloader=Bootloader # Bootloader 3209.menu.bootloader.no_bootloader=No bootloader +3209.menu.bootloader.no_bootloader.upload.maximum_size=32768 3209.menu.bootloader.no_bootloader.upload.extra_params= 3209.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 3209.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 3209.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 3209.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +3209.menu.bootloader.uart0_default.upload.maximum_size=32256 3209.menu.bootloader.uart0_default.upload.protocol=arduino 3209.menu.bootloader.uart0_default.upload.extra_params= 3209.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -525,6 +540,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +3209.menu.bootloader.uart0_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart0_alternative.upload.protocol=arduino 3209.menu.bootloader.uart0_alternative.upload.extra_params= 3209.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -533,6 +549,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +3209.menu.bootloader.uart1_default.upload.maximum_size=32256 3209.menu.bootloader.uart1_default.upload.protocol=arduino 3209.menu.bootloader.uart1_default.upload.extra_params= 3209.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -541,6 +558,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +3209.menu.bootloader.uart1_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart1_alternative.upload.protocol=arduino 3209.menu.bootloader.uart1_alternative.upload.extra_params= 3209.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -549,6 +567,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +3209.menu.bootloader.uart2_default.upload.maximum_size=32256 3209.menu.bootloader.uart2_default.upload.protocol=arduino 3209.menu.bootloader.uart2_default.upload.extra_params= 3209.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -557,6 +576,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +3209.menu.bootloader.uart2_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart2_alternative.upload.protocol=arduino 3209.menu.bootloader.uart2_alternative.upload.extra_params= 3209.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -565,6 +585,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +3209.menu.bootloader.uart3_default.upload.maximum_size=32256 3209.menu.bootloader.uart3_default.upload.protocol=arduino 3209.menu.bootloader.uart3_default.upload.extra_params= 3209.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 @@ -573,6 +594,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +3209.menu.bootloader.uart3_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart3_alternative.upload.protocol=arduino 3209.menu.bootloader.uart3_alternative.upload.extra_params= 3209.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 @@ -588,7 +610,6 @@ menu.bootloader=Bootloader # General 3208.name=ATmega3208 3208.upload.tool=avrdude -3208.upload.maximum_size=32768 3208.upload.maximum_data_size=4096 3208.upload.speed=115200 3208.bootloader.tool=avrdude @@ -705,12 +726,14 @@ menu.bootloader=Bootloader # Bootloader 3208.menu.bootloader.no_bootloader=No bootloader +3208.menu.bootloader.no_bootloader.upload.maximum_size=32768 3208.menu.bootloader.no_bootloader.upload.extra_params= 3208.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 3208.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 3208.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 3208.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +3208.menu.bootloader.uart0_default.upload.maximum_size=32256 3208.menu.bootloader.uart0_default.upload.protocol=arduino 3208.menu.bootloader.uart0_default.upload.extra_params= 3208.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -719,6 +742,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +3208.menu.bootloader.uart0_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart0_alternative.upload.protocol=arduino 3208.menu.bootloader.uart0_alternative.upload.extra_params= 3208.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -727,6 +751,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +3208.menu.bootloader.uart1_default.upload.maximum_size=32256 3208.menu.bootloader.uart1_default.upload.protocol=arduino 3208.menu.bootloader.uart1_default.upload.extra_params= 3208.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -735,6 +760,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +3208.menu.bootloader.uart1_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart1_alternative.upload.protocol=arduino 3208.menu.bootloader.uart1_alternative.upload.extra_params= 3208.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -743,6 +769,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +3208.menu.bootloader.uart2_default.upload.maximum_size=32256 3208.menu.bootloader.uart2_default.upload.protocol=arduino 3208.menu.bootloader.uart2_default.upload.extra_params= 3208.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -751,6 +778,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +3208.menu.bootloader.uart2_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart2_alternative.upload.protocol=arduino 3208.menu.bootloader.uart2_alternative.upload.extra_params= 3208.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -766,7 +794,6 @@ menu.bootloader=Bootloader # General 1609.name=ATmega1609 1609.upload.tool=avrdude -1609.upload.maximum_size=16384 1609.upload.maximum_data_size=2048 1609.upload.speed=115200 1609.bootloader.tool=avrdude @@ -885,12 +912,14 @@ menu.bootloader=Bootloader # Bootloader 1609.menu.bootloader.no_bootloader=No bootloader +1609.menu.bootloader.no_bootloader.upload.maximum_size=16384 1609.menu.bootloader.no_bootloader.upload.extra_params= 1609.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 1609.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 1609.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 1609.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +1609.menu.bootloader.uart0_default.upload.maximum_size=15872 1609.menu.bootloader.uart0_default.upload.protocol=arduino 1609.menu.bootloader.uart0_default.upload.extra_params= 1609.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -899,6 +928,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +1609.menu.bootloader.uart0_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart0_alternative.upload.protocol=arduino 1609.menu.bootloader.uart0_alternative.upload.extra_params= 1609.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -907,6 +937,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +1609.menu.bootloader.uart1_default.upload.maximum_size=15872 1609.menu.bootloader.uart1_default.upload.protocol=arduino 1609.menu.bootloader.uart1_default.upload.extra_params= 1609.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -915,6 +946,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +1609.menu.bootloader.uart1_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart1_alternative.upload.protocol=arduino 1609.menu.bootloader.uart1_alternative.upload.extra_params= 1609.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -923,6 +955,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +1609.menu.bootloader.uart2_default.upload.maximum_size=15872 1609.menu.bootloader.uart2_default.upload.protocol=arduino 1609.menu.bootloader.uart2_default.upload.extra_params= 1609.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -931,6 +964,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +1609.menu.bootloader.uart2_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart2_alternative.upload.protocol=arduino 1609.menu.bootloader.uart2_alternative.upload.extra_params= 1609.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -939,6 +973,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +1609.menu.bootloader.uart3_default.upload.maximum_size=15872 1609.menu.bootloader.uart3_default.upload.protocol=arduino 1609.menu.bootloader.uart3_default.upload.extra_params= 1609.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 @@ -947,6 +982,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +1609.menu.bootloader.uart3_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart3_alternative.upload.protocol=arduino 1609.menu.bootloader.uart3_alternative.upload.extra_params= 1609.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 @@ -962,7 +998,6 @@ menu.bootloader=Bootloader # General 1608.name=ATmega1608 1608.upload.tool=avrdude -1608.upload.maximum_size=16384 1608.upload.maximum_data_size=2048 1608.upload.speed=115200 1608.bootloader.tool=avrdude @@ -1079,12 +1114,14 @@ menu.bootloader=Bootloader # Bootloader 1608.menu.bootloader.no_bootloader=No bootloader +1608.menu.bootloader.no_bootloader.upload.maximum_size=16384 1608.menu.bootloader.no_bootloader.upload.extra_params= 1608.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 1608.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 1608.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 1608.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +1608.menu.bootloader.uart0_default.upload.maximum_size=15872 1608.menu.bootloader.uart0_default.upload.protocol=arduino 1608.menu.bootloader.uart0_default.upload.extra_params= 1608.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -1093,6 +1130,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +1608.menu.bootloader.uart0_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart0_alternative.upload.protocol=arduino 1608.menu.bootloader.uart0_alternative.upload.extra_params= 1608.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -1101,6 +1139,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +1608.menu.bootloader.uart1_default.upload.maximum_size=15872 1608.menu.bootloader.uart1_default.upload.protocol=arduino 1608.menu.bootloader.uart1_default.upload.extra_params= 1608.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -1109,6 +1148,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +1608.menu.bootloader.uart1_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart1_alternative.upload.protocol=arduino 1608.menu.bootloader.uart1_alternative.upload.extra_params= 1608.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -1117,6 +1157,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +1608.menu.bootloader.uart2_default.upload.maximum_size=15872 1608.menu.bootloader.uart2_default.upload.protocol=arduino 1608.menu.bootloader.uart2_default.upload.extra_params= 1608.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -1125,6 +1166,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +1608.menu.bootloader.uart2_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart2_alternative.upload.protocol=arduino 1608.menu.bootloader.uart2_alternative.upload.extra_params= 1608.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -1140,7 +1182,6 @@ menu.bootloader=Bootloader # General 809.name=ATmega809 809.upload.tool=avrdude -809.upload.maximum_size=8192 809.upload.maximum_data_size=1024 809.upload.speed=115200 809.bootloader.tool=avrdude @@ -1259,12 +1300,14 @@ menu.bootloader=Bootloader # Bootloader 809.menu.bootloader.no_bootloader=No bootloader +809.menu.bootloader.no_bootloader.upload.maximum_size=8192 809.menu.bootloader.no_bootloader.upload.extra_params= 809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +809.menu.bootloader.uart0_default.upload.maximum_size=7680 809.menu.bootloader.uart0_default.upload.protocol=arduino 809.menu.bootloader.uart0_default.upload.extra_params= 809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -1273,6 +1316,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +809.menu.bootloader.uart0_alternative.upload.maximum_size=7680 809.menu.bootloader.uart0_alternative.upload.protocol=arduino 809.menu.bootloader.uart0_alternative.upload.extra_params= 809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -1281,6 +1325,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +809.menu.bootloader.uart1_default.upload.maximum_size=7680 809.menu.bootloader.uart1_default.upload.protocol=arduino 809.menu.bootloader.uart1_default.upload.extra_params= 809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -1289,6 +1334,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +809.menu.bootloader.uart1_alternative.upload.maximum_size=7680 809.menu.bootloader.uart1_alternative.upload.protocol=arduino 809.menu.bootloader.uart1_alternative.upload.extra_params= 809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -1297,6 +1343,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +809.menu.bootloader.uart2_default.upload.maximum_size=7680 809.menu.bootloader.uart2_default.upload.protocol=arduino 809.menu.bootloader.uart2_default.upload.extra_params= 809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -1305,6 +1352,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +809.menu.bootloader.uart2_alternative.upload.maximum_size=7680 809.menu.bootloader.uart2_alternative.upload.protocol=arduino 809.menu.bootloader.uart2_alternative.upload.extra_params= 809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 @@ -1313,6 +1361,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) +809.menu.bootloader.uart3_default.upload.maximum_size=7680 809.menu.bootloader.uart3_default.upload.protocol=arduino 809.menu.bootloader.uart3_default.upload.extra_params= 809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 @@ -1321,6 +1370,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) +809.menu.bootloader.uart3_alternative.upload.maximum_size=7680 809.menu.bootloader.uart3_alternative.upload.protocol=arduino 809.menu.bootloader.uart3_alternative.upload.extra_params= 809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 @@ -1336,7 +1386,6 @@ menu.bootloader=Bootloader # General 808.name=ATmega808 808.upload.tool=avrdude -808.upload.maximum_size=8192 808.upload.maximum_data_size=1024 808.upload.speed=115200 808.bootloader.tool=avrdude @@ -1453,12 +1502,14 @@ menu.bootloader=Bootloader # Bootloader 808.menu.bootloader.no_bootloader=No bootloader +808.menu.bootloader.no_bootloader.upload.maximum_size=8192 808.menu.bootloader.no_bootloader.upload.extra_params= 808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex 808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) +808.menu.bootloader.uart0_default.upload.maximum_size=7680 808.menu.bootloader.uart0_default.upload.protocol=arduino 808.menu.bootloader.uart0_default.upload.extra_params= 808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 @@ -1467,6 +1518,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) +808.menu.bootloader.uart0_alternative.upload.maximum_size=7680 808.menu.bootloader.uart0_alternative.upload.protocol=arduino 808.menu.bootloader.uart0_alternative.upload.extra_params= 808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 @@ -1475,6 +1527,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) +808.menu.bootloader.uart1_default.upload.maximum_size=7680 808.menu.bootloader.uart1_default.upload.protocol=arduino 808.menu.bootloader.uart1_default.upload.extra_params= 808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 @@ -1483,6 +1536,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) +808.menu.bootloader.uart1_alternative.upload.maximum_size=7680 808.menu.bootloader.uart1_alternative.upload.protocol=arduino 808.menu.bootloader.uart1_alternative.upload.extra_params= 808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 @@ -1491,6 +1545,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) +808.menu.bootloader.uart2_default.upload.maximum_size=7680 808.menu.bootloader.uart2_default.upload.protocol=arduino 808.menu.bootloader.uart2_default.upload.extra_params= 808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 @@ -1499,6 +1554,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) +808.menu.bootloader.uart2_alternative.upload.maximum_size=7680 808.menu.bootloader.uart2_alternative.upload.protocol=arduino 808.menu.bootloader.uart2_alternative.upload.extra_params= 808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 From 4104ac3215be5eaf5c34e0c16878f701deb014e7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 14 Oct 2019 22:40:10 +0200 Subject: [PATCH 088/351] Fix object color coding --- megaavr/libraries/Logic/keywords.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt index 6cf3094..398d7e1 100644 --- a/megaavr/libraries/Logic/keywords.txt +++ b/megaavr/libraries/Logic/keywords.txt @@ -55,10 +55,10 @@ detachInterrupt KEYWORD2 ####################################### Logic KEYWORD2 -block0 KEYWORD2 -block1 KEYWORD2 -block2 KEYWORD2 -block3 KEYWORD2 +Logic0 KEYWORD2 +Logic1 KEYWORD2 +Logic2 KEYWORD2 +Logic3 KEYWORD2 ####################################### # Constants (LITERAL1) From ee561c49a2c269057289fd562c6e4ac1d678f38a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Oct 2019 19:26:36 +0200 Subject: [PATCH 089/351] Cleanup --- megaavr/libraries/Logic/keywords.txt | 35 +--------------------------- 1 file changed, 1 insertion(+), 34 deletions(-) diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt index 398d7e1..228be5e 100644 --- a/megaavr/libraries/Logic/keywords.txt +++ b/megaavr/libraries/Logic/keywords.txt @@ -6,50 +6,17 @@ # Datatypes (KEYWORD1) ####################################### -#masked LITERAL1 -#unused LITERAL1 -#disable LITERAL1 -#feedback LITERAL1 -#link LITERAL1 -#event_a LITERAL1 -#event_b LITERAL1 -#input LITERAL1 -#ac LITERAL1 -#input_pullup LITERAL1 -#usart LITERAL1 -#spi LITERAL1 -#tca0 LITERAL1 -#tcb LITERAL1 - -#disable LITERAL1 -#no_swap LITERAL1 -#enable LITERAL1 -#pin_swap LITERAL1 - -#disable LITERAL1 -#synchronizer LITERAL1 -#filter LITERAL1 - -#disable LITERAL1 -#d_flip_flop LITERAL1 -#jk_flip_flop LITERAL1 -#d_latch LITERAL1 -#sr_latch LITERAL1 -#rs_latch LITERAL1 - - ####################################### # Methods and Functions (KEYWORD2) ####################################### -begin KEYWORD2 +start KEYWORD2 end KEYWORD2 init KEYWORD2 attachInterrupt KEYWORD2 detachInterrupt KEYWORD2 - ####################################### # Instances (KEYWORD2) ####################################### From eb5c703adaf88077a76b9f496ce73bd5f43823f4 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Oct 2019 19:27:14 +0200 Subject: [PATCH 090/351] Initial commit --- megaavr/libraries/Comparator/README.md | 2 + megaavr/libraries/Comparator/keywords.txt | 37 +++++ .../libraries/Comparator/library.properties | 9 + .../libraries/Comparator/src/Comparator.cpp | 154 ++++++++++++++++++ megaavr/libraries/Comparator/src/Comparator.h | 91 +++++++++++ 5 files changed, 293 insertions(+) create mode 100644 megaavr/libraries/Comparator/README.md create mode 100644 megaavr/libraries/Comparator/keywords.txt create mode 100644 megaavr/libraries/Comparator/library.properties create mode 100644 megaavr/libraries/Comparator/src/Comparator.cpp create mode 100644 megaavr/libraries/Comparator/src/Comparator.h diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md new file mode 100644 index 0000000..763d71d --- /dev/null +++ b/megaavr/libraries/Comparator/README.md @@ -0,0 +1,2 @@ +# Comparator library + diff --git a/megaavr/libraries/Comparator/keywords.txt b/megaavr/libraries/Comparator/keywords.txt new file mode 100644 index 0000000..eba2e3b --- /dev/null +++ b/megaavr/libraries/Comparator/keywords.txt @@ -0,0 +1,37 @@ +####################################### +# Syntax Coloring Map For Wire +####################################### + +####################################### +# Datatypes (KEYWORD1) +####################################### + + +####################################### +# Methods and Functions (KEYWORD2) +####################################### + +start KEYWORD2 +end KEYWORD2 +init KEYWORD2 +attachInterrupt KEYWORD2 +detachInterrupt KEYWORD2 + +####################################### +# Instances (KEYWORD2) +####################################### + +Comparator KEYWORD2 +Comparator0 KEYWORD2 +Comparator1 KEYWORD2 +Comparator2 KEYWORD2 + +####################################### +# Constants (LITERAL1) +####################################### + +out LITERAL1 +hyst LITERAL1 +in_p LITERAL1 +in_n LITERAL1 +ref LITERAL1 diff --git a/megaavr/libraries/Comparator/library.properties b/megaavr/libraries/Comparator/library.properties new file mode 100644 index 0000000..115b0a8 --- /dev/null +++ b/megaavr/libraries/Comparator/library.properties @@ -0,0 +1,9 @@ +name=Comparator +version=1.0.0 +author=MCUdude +maintainer=MCUdude +sentence=A library for interfacing with the built-in analog comparator +paragraph= +category=Signal Input/Output +url=https://github.com/MCUdude/MegaCoreX +architectures=megaavr diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp new file mode 100644 index 0000000..9016643 --- /dev/null +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -0,0 +1,154 @@ +#include "Comparator.h" + +AnalogComparator Comparator(0, AC0); + +// Array for storing ISR function pointers +#if defined(AC2_AC_vect) +static volatile voidFuncPtr intFuncAC[3]; +#elif defined(AC1_AC_vect) +static volatile voidFuncPtr intFuncAC[2]; +#elif defined(AC0_AC_vect) +static volatile voidFuncPtr intFuncAC[1]; +#else +#error target does not have an analog comparator! +#endif + + +AnalogComparator::AnalogComparator(const uint8_t comp_number, AC_t& ac) : comparator_number(comp_number), AC(ac) +{ +} + +void AnalogComparator::init() +{ + // Set voltage reference + if(reference != ref::disable) + { + VREF.CTRLA = (VREF.CTRLA & ~VREF_AC0REFSEL_AVDD_gc) | reference; + VREF.CTRLB = VREF_AC0REFEN_bm; + } + else + VREF.CTRLB &= ~VREF_AC0REFEN_bm; + + // Set DACREF + AC.DACREF = dacref; + + // Set hysteresis + AC.CTRLA = (AC.CTRLA & ~AC_HYSMODE_gm) | hysteresis; + + // Set inputs + if(input_p == in_p::in0) + PORTD.PIN2CTRL = PORT_ISC_INPUT_DISABLE_gc; + else if(input_p == in_p::in1) + PORTD.PIN4CTRL = PORT_ISC_INPUT_DISABLE_gc; + else if(input_p == in_p::in2) + PORTD.PIN6CTRL = PORT_ISC_INPUT_DISABLE_gc; + else if(input_p == in_p::in3) + PORTD.PIN1CTRL = PORT_ISC_INPUT_DISABLE_gc; + if(input_n == in_n::in0) + PORTD.PIN3CTRL = PORT_ISC_INPUT_DISABLE_gc; + else if(input_n == in_n::in1) + PORTD.PIN5CTRL = PORT_ISC_INPUT_DISABLE_gc; + else if(input_n == in_n::in2) + PORTD.PIN7CTRL = PORT_ISC_INPUT_DISABLE_gc; + AC.MUXCTRLA = (AC.MUXCTRLA & ~0x1B) | (input_p << 3) | input_n; + + // Set output + if(output == out::enable) + { + AC.MUXCTRLA &= ~out::invert; + AC.CTRLA |= out::enable; + PORTA.DIRSET = PIN7_bm; + } + else if(output == out::invert) + { + AC.MUXCTRLA |= out::invert; + AC.CTRLA |= out::enable; + PORTA.DIRSET = PIN7_bm; + } + else if(output == out::disable) + { + AC.MUXCTRLA &= ~out::invert; + AC.CTRLA &= ~out::enable; + PORTA.DIRCLR = PIN7_bm; + } +} + +void AnalogComparator::start(bool state) +{ + if(state) + AC.CTRLA |= AC_ENABLE_bm; + else + AC.CTRLA &= ~AC_ENABLE_bm; +} + +void AnalogComparator::end() +{ + start(false); +} + +void AnalogComparator::attachInterrupt(void (*userFunc)(void), PinStatus mode) +{ + AC_INTMODE_t intmode; + switch (mode) + { + // Set RISING, FALLING or CHANGE interrupt trigger for the comparator output + case RISING: + intmode = AC_INTMODE_POSEDGE_gc; + break; + case FALLING: + intmode = AC_INTMODE_NEGEDGE_gc; + break; + case CHANGE: + intmode = AC_INTMODE_BOTHEDGE_gc; + break; + default: + // Only RISING, FALLING and CHANGE is supported + return; + } + AC.CTRLA = (AC.CTRLA & ~AC_INTMODE_POSEDGE_gc) | intmode; + + // Store function pointer + intFuncAC[comparator_number] = userFunc; + + // Enable interrupt + AC.INTCTRL |= AC_CMP_bm; +} + +void AnalogComparator::detachInterrupt() +{ + // Disable interrupt + AC.INTCTRL &= ~AC_CMP_bm; +} + +#ifdef AC0_AC_vect +ISR(AC0_AC_vect) +{ + // Run user function + intFuncAC[0](); + + // Clear flag + AC0.STATUS = AC_CMP_bm; +} +#endif + +#ifdef AC1_AC_vect +ISR(AC1_AC_vect) +{ + // Run user function + intFuncAC[1](); + + // Clear flag + AC1.STATUS = AC_CMP_bm; +} +#endif + +#ifdef AC2_AC_vect +ISR(AC2_AC_vect) +{ + // Run user function + intFuncAC[2](); + + // Clear flag + AC2.STATUS = AC_CMP_bm; +} +#endif diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h new file mode 100644 index 0000000..70363d0 --- /dev/null +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -0,0 +1,91 @@ +#ifndef COMPARATOR_h +#define COMPARATOR_h + +#include + +namespace out +{ + enum output_t : uint8_t + { + disable = 0x00, + enable = 0x40, + invert = 0x80, + }; +}; + +namespace hyst +{ + enum hysteresis_t : uint8_t + { + disable = 0x00, // No hysteresis + small = 0x02, // 10 mV + medium = 0x04, // 25 mV + large = 0x06, // 50 mV + }; +}; + +namespace in_p +{ + enum inputP_t : uint8_t + { + in0 = 0x00, + in1 = 0x01, + in2 = 0x02, + in3 = 0x03, + }; +}; + +namespace in_n +{ + enum inputN_t : uint8_t + { + in0 = 0x00, + in1 = 0x01, + in2 = 0x02, + dacref = 0x03, + }; +}; + +namespace ref +{ + enum reference_t : uint8_t + { + vref_0v55 = 0x00, // 0.55V + vref_1v1 = 0x01, // 1.1V + vref_1v5 = 0x04, // 1.5V + vref_2v5 = 0x02, // 2.5V + vref_4v3 = 0x03, // 4.3V + vref_avcc = 0x07, // Vcc + disable = 0x08, + }; +}; + +class AnalogComparator +{ + public: + AnalogComparator(const uint8_t comparator_number, AC_t& ac); + void init(); + void start(bool state = true); + void end(); + void attachInterrupt(voidFuncPtr callback, PinStatus mode); + void detachInterrupt(); + + out::output_t output = out::disable; + hyst::hysteresis_t hysteresis = hyst::disable; + in_p::inputP_t input_p = in_p::in0; + in_n::inputN_t input_n = in_n::in0; + ref::reference_t reference = ref::disable; + uint8_t dacref = 0xff; + + private: + const uint8_t comparator_number; + AC_t& AC; + bool enable = false; +}; + +#if defined(AC0_AC_vect) +extern AnalogComparator Comparator0; +#define Comparator Comparator0 +#endif + +#endif From 244acdff5e0baa08395f2406c4c2e5e92310301f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Oct 2019 21:44:12 +0200 Subject: [PATCH 091/351] Edit header in examples The library isn't just for MegaCoreX anymore. It also supports tiny0's and tiny1's --- .../Logic/examples/Five_input_NOR/Five_input_NOR.ino | 4 ++-- megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino | 4 ++-- .../Logic/examples/Three_input_AND/Three_input_AND.ino | 4 ++-- .../Logic/examples/Three_input_NAND/Three_input_NAND.ino | 4 ++-- .../Logic/examples/Three_input_OR/Three_input_OR.ino | 4 ++-- .../libraries/Logic/examples/Two_input_AND/Two_input_AND.ino | 4 ++-- .../Logic/examples/Two_input_NAND/Two_input_NAND.ino | 4 ++-- .../libraries/Logic/examples/Two_input_OR/Two_input_OR.ino | 4 ++-- 8 files changed, 16 insertions(+), 16 deletions(-) diff --git a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino index c2200e9..cf9ef8d 100644 --- a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino +++ b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino @@ -4,8 +4,8 @@ | Five_input_NOR.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use two logic blocks to get five inputs. | | The output of block 1 is connected to one of the inputs of block 0. | diff --git a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino index 23028c1..d381bb9 100644 --- a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino @@ -4,8 +4,8 @@ | Interrupt.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 3-input NOR gate using logic block 2 on PORT D. | diff --git a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino index 1b1444e..fbf2534 100644 --- a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino @@ -4,8 +4,8 @@ | Three_input_AND.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 3-input AND gate using logic block 0 on PORT A. | diff --git a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino index d9332d3..36a39a1 100644 --- a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino @@ -4,8 +4,8 @@ | Three_input_NAND.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 3-input NAND gate using logic block 0 on PORT A. | diff --git a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino index 63627af..1fd8a2f 100644 --- a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino @@ -4,8 +4,8 @@ | Three_input_OR.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 3-input OR gate using logic block 0 on PORT A. | diff --git a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino index f288bec..961f703 100644 --- a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino @@ -4,8 +4,8 @@ | Two_input_AND.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 2-input AND gate using logic block 0 on PORT A. | diff --git a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino index 4118180..3266d2a 100644 --- a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino @@ -4,8 +4,8 @@ | Two_input_NAND.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 2-input NAND gate using logic block 0 on PORT A. | diff --git a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino index bc93cfa..fb5f539 100644 --- a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino @@ -4,8 +4,8 @@ | Two_input_OR.ino | | | | A library for interfacing with the megaAVR Configurable Custom Logic. | -| Developed in 2019 by MCUdude for use with MegaCoreX. | -| https://github.com/MCUdude/MegaCoreX | +| Developed in 2019 by MCUdude. | +| https://github.com/MCUdude/ | | | | In this example we use the configurable logic peripherals the the | | megaAVR to create a 2-input OR gate using logic block 0 on PORT A. | From 0d2126c1a98eb996ae539b4cea519d8fffa3d63a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Oct 2019 23:12:36 +0200 Subject: [PATCH 092/351] Add AC examples Related to #48 --- .../examples/Hysteresis/Hysteresis.ino | 38 +++++++++++++ .../Internal_reference/Internal_reference.ino | 43 ++++++++++++++ .../examples/Interrupt/Interrupt.ino | 57 +++++++++++++++++++ .../Simple_comparator/Simple_comparator.ino | 36 ++++++++++++ 4 files changed, 174 insertions(+) create mode 100644 megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino create mode 100644 megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino create mode 100644 megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino create mode 100644 megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino diff --git a/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino b/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino new file mode 100644 index 0000000..b2255e3 --- /dev/null +++ b/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino @@ -0,0 +1,38 @@ +/***********************************************************************| +| megaAVR analog comparator library | +| | +| Hysteresis.ino | +| | +| A library for interfacing with the megaAVR analog comparator. | +| Developed in 2019 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use the negative and positive input 0 of the | +| comparator. The output goes high if the positive input is higher than | +| the negative input, and low otherwise. We'll also use the built-in | +| hysteresis functionality to prevent false spikes. | +| | +| See Microchip's application note TB3211 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Configure relevant comparator parameters + Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = in_n::in0; // Use negative input 0 (PD3) + Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis + Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + + // Initialize comparator + Comparator.init(); + + // Start comparator + Comparator.start(); +} + +void loop() +{ + +} diff --git a/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino b/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino new file mode 100644 index 0000000..65b13ef --- /dev/null +++ b/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino @@ -0,0 +1,43 @@ +/***********************************************************************| +| megaAVR analog comparator library | +| | +| Internal_reference.ino | +| | +| A library for interfacing with the megaAVR analog comparator. | +| Developed in 2019 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use an internal reference voltage instead of an | +| external one on the negative pin. This eliminates the need for an | +| external voltage divider to generate a reference. Note that the | +| internal reference requires a stable voltage to function properly. | +| | +| This is the formula for the generated voltage: | +| Vdacref = (DACREF / 256) * Vref | +| | +| See Microchip's application note TB3211 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Configure relevant comparator parameters + Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = in_n::dacref; // Connect the negative pin to the DACREF voltage + Comparator.reference = ref::vref_2v5; // Set the DACREF voltage to 2.5V + Comparator.dacref = 127; // Gives us 1.24V -> (127 / 256) * 2.5V = 1.24V + Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis + Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + + // Initialize comparator + Comparator.init(); + + // Start comparator + Comparator.start(); +} + +void loop() +{ + +} diff --git a/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino new file mode 100644 index 0000000..4a5e529 --- /dev/null +++ b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino @@ -0,0 +1,57 @@ +/***********************************************************************| +| megaAVR analog comparator library | +| | +| Interrupt.ino | +| | +| A library for interfacing with the megaAVR analog comparator. | +| Developed in 2019 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use an internal reference voltage instead of an | +| external one on the negative pin. This eliminates the need for an | +| external voltage divider to generate a reference. Note that the | +| internal reference requires a stable voltage to function properly. | +| Instead of using a physical output pin we're instead triggering an | +| interrupt that will run a user defined function. | +| | +| This is the formula for the generated voltage: | +| Vdacref = (DACREF / 256) * Vref | +| | +| See Microchip's application note TB3211 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Configure serial port + Serial3.begin(9600); + + // Configure relevant comparator parameters + Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = in_n::dacref; // Connect the negative pin to the DACREF voltage + Comparator.reference = ref::vref_2v5; // Set the DACREF voltage to 2.5V + Comparator.dacref = 255; // Gives us 2.5V -> (255 / 256) * 2.5V = 2.5V + Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis + Comparator.output = out::disable; // Use interrupt trigger instead of output pin + + // Initialize comparator + Comparator.init(); + + // Set interrupt (supports RISING, FALLING and CHANGE) + Comparator.attachInterrupt(interruptFunction, RISING); + + // Start comparator + Comparator.start(); +} + +void loop() +{ + +} + +// This function runs when an interrupt occurs +void interruptFunction() +{ + Serial3.println("Output of analog comparator went high!"); +} diff --git a/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino b/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino new file mode 100644 index 0000000..8fc2d85 --- /dev/null +++ b/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino @@ -0,0 +1,36 @@ +/***********************************************************************| +| megaAVR analog comparator library | +| | +| Simple_comparator.ino | +| | +| A library for interfacing with the megaAVR analog comparator. | +| Developed in 2019 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use the negative and positive input 0 of the | +| comparator. The output goes high if the positive input is higher than | +| the negative input, and low otherwise. | +| | +| See Microchip's application note TB3211 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Configure relevant comparator parameters + Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = in_n::in0; // Use negative input 0 (PD3) + Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + + // Initialize comparator + Comparator.init(); + + // Start comparator + Comparator.start(); +} + +void loop() +{ + +} From b1a2a241a5f00281f6ba7fc61b7d48e255a0d29b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 19 Oct 2019 19:50:47 +0200 Subject: [PATCH 093/351] Rename end() to stop() --- megaavr/libraries/Logic/README.md | 2 +- megaavr/libraries/Logic/keywords.txt | 2 +- megaavr/libraries/Logic/src/Logic.cpp | 2 +- megaavr/libraries/Logic/src/Logic.h | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index 5445a57..4d754e0 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -165,7 +165,7 @@ Logic::start(); // Start CCL hardware -## end() +## stop() Method for stopping the CCL hardware. ##### Usage diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt index 228be5e..720da20 100644 --- a/megaavr/libraries/Logic/keywords.txt +++ b/megaavr/libraries/Logic/keywords.txt @@ -12,7 +12,7 @@ ####################################### start KEYWORD2 -end KEYWORD2 +stop KEYWORD2 init KEYWORD2 attachInterrupt KEYWORD2 detachInterrupt KEYWORD2 diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index b5db234..7201662 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -175,7 +175,7 @@ void Logic::start(bool state) // static -void Logic::end() +void Logic::stop() { start(false); } diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index fd6cf5d..212b80e 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -69,7 +69,7 @@ class Logic { public: static void start(bool state = true); - static void end(); + static void stop(); Logic(const uint8_t block_number); void init(); From 1eb1fd5fc93ea04a12a152c699b1e4289e2a5a28 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 19 Oct 2019 19:51:51 +0200 Subject: [PATCH 094/351] Rename end() to stop() --- megaavr/libraries/Comparator/keywords.txt | 2 +- megaavr/libraries/Comparator/src/Comparator.cpp | 2 +- megaavr/libraries/Comparator/src/Comparator.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/libraries/Comparator/keywords.txt b/megaavr/libraries/Comparator/keywords.txt index eba2e3b..a8332fe 100644 --- a/megaavr/libraries/Comparator/keywords.txt +++ b/megaavr/libraries/Comparator/keywords.txt @@ -12,7 +12,7 @@ ####################################### start KEYWORD2 -end KEYWORD2 +stop KEYWORD2 init KEYWORD2 attachInterrupt KEYWORD2 detachInterrupt KEYWORD2 diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index 9016643..2d88189 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -81,7 +81,7 @@ void AnalogComparator::start(bool state) AC.CTRLA &= ~AC_ENABLE_bm; } -void AnalogComparator::end() +void AnalogComparator::stop() { start(false); } diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 70363d0..663866c 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -66,7 +66,7 @@ class AnalogComparator AnalogComparator(const uint8_t comparator_number, AC_t& ac); void init(); void start(bool state = true); - void end(); + void stop(); void attachInterrupt(voidFuncPtr callback, PinStatus mode); void detachInterrupt(); From 07e52a4d46119809f3b8eb354cfbaedc8be32c64 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 19 Oct 2019 21:30:56 +0200 Subject: [PATCH 095/351] Update README.md --- megaavr/libraries/Comparator/README.md | 170 ++++++++++++++++++++++++- 1 file changed, 169 insertions(+), 1 deletion(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index 763d71d..c389366 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -1,2 +1,170 @@ -# Comparator library +# Comparator +A library for interfacing with the analog comparator peripheral in the megaAVR-0 series MCUs. +Developed by [MCUdude](https://github.com/MCUdude/). +The megaAVR-0 has one comparator where four positive and three negative pins are available for use. An alternative for the negative pin is to use an internally generated reference voltage instead. +More useful information about the analog comparator can be found in the [Microchip Application Note TB3211](http://ww1.microchip.com/downloads/en/AppNotes/TB3211-Getting-Started-with-AC-90003211A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). + +## Comparator +Class for interfacing with the built-in comparator. use the predefined objects `Comparator` or `Comparator0`. + + +### input_p +Variable for setting what input pin the positive input of the comparator should be connected to +Accepted values: +``` c++ +in_p::in0; // Use positive input pin 0 (PD2) as input +in_p::in1; // Use positive input pin 1 (PD4) as input +in_p::in2; // Use positive input pin 2 (PD6) as input +in_p::in3; // Use positive input pin 3 (PD1) as input +``` + +##### Usage +``` c++ +Comparator.input_p = in_p::in0; // Connect positive input pin 0 to the positive pin of the comparator +``` + +##### Default state +`Comparator.input_p` defaults to `in_p::in0` if not specified in the user program. + + +### input_n +Variable for setting what input pin the negative input of the comparator should be connected to +Accepted values: +``` c++ +in_n::in0; // Use positive input pin 0 (PD3) as input +in_n::in1; // Use positive input pin 1 (PD5) as input +in_n::in2; // Use positive input pin 2 (PD7) as input +in_p::dacref; // Use DACREF as input +``` + +##### Usage +``` c++ +Comparator.input_n = in_n::in0; // Connect negative input pin 0 to the negative pin of the comparator +``` + +##### Default state +`Comparator.input_n` defaults to `in_n::in0` if not specified in the user program. + + +### reference +Variable for setting what reference voltage the DACREF should use. This voltage is internally generated. +Accepted values: +``` c++ +ref::disable; // Do not use any reference +ref::vref_0v55; // 0.55V internal voltage +ref::vref_1v1; // 1.1V internal voltage +ref::vref_1v5; // 1.5V internal voltage +ref::vref_2v5; // 2.5V internal voltage +ref::vref_4v3; // 4.3V internal voltage +ref::vref_avcc; // Use voltage on AVCC pin +``` + +##### Usage +``` c++ +Comparator.reference = ref::vref_2v5; // Use the internal 2.5V reference for the DACREF +``` + +##### Default state +`Comparator.reference` defaults to `ref::disable` if not specified in the user program. + + +### dacref +Variable for setting the DACREF value. The DACREF voltage is the voltage that the comparator uses as it's reference. +This is the formula for the DACREF output voltage: + + + +##### Usage +``` c++ +Comparator.dacref = 127; // Divide the reference voltage by two +``` + +##### Default state +`Comparator.dacref` defaults to `255` if not specified in the user program. + + +### hysteresis +Variable for setting the comparator input hysteresis. Useful for eliminating "bouncing". +Accepted values: +``` c++ +hyst::disable; // No hysteresis +hyst::small; // 10mV hysteresis (±5mV) +hyst::medium; // 25mV hysteresis (±12.5mV) +hyst::large; // 50mV hysteresis (±25mV) +``` + +##### Usage +``` c++ +Comparator.hysteresis = hyst::large; // Use 50V hysteresis +``` + +##### Default state +`Comparator.hysteresis` defaults to `hyst::disable` if not specified in the user program. + + +### output +Variable for setting the comparator output pin (PA7). +Accepted values: +``` c++ +out::disable; // No output pin +out::enable; // Enable output pin (PA7) +out::invert; // Invert output pin (PA7) +``` + +##### Usage +``` c++ +Comparator.output = out::enable; // Enable output pin (PA7) +``` + +##### Default state +`Comparator.output` defaults to `out::disable` if not specified in the user program. + + +## init() +Method for initializing the comparator. + +##### Usage +```c++ +Comparator.init(); // Initialize comparator +``` + +## start() +Method for starting the analog comparator. +##### Usage +```c++ +Comparator.start(); // Start comparator +``` + + +## stop() +Method for stopping the analog comparator. + +##### Usage +```c++ +Comparator.stop(); // Stop comparator +``` + + +## attachInterrupt() +Method for enabling analog comparator interrupt. The interrupt will trigger when the the comparator output changes. +Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. + +##### Usage +```c++ +Comparator.attachInterrupt(blinkLED, RISING); // Run the blinkLED function when the comparator output goes high + +void blinkLED() +{ + digitalWrite(myLedPin, CHANGE); +} +``` + + +## detachInterrupt() +Method for disabling analog comparator interrupt. + +##### Usage +```c++ +Comparator.detachInterrupt(); // Disable interrupt +``` From a3dd55a8f8f1f50102e47179fa60834cffa6da2f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 20 Oct 2019 22:45:02 +0200 Subject: [PATCH 096/351] Implement SPI pin swap Closes #22 --- README.md | 49 +++++---- megaavr/libraries/SPI/keywords.txt | 2 + megaavr/libraries/SPI/src/SPI.cpp | 99 ++++++++++++++++--- megaavr/libraries/SPI/src/SPI.h | 6 +- .../variants/28pin-standard/pins_arduino.h | 6 +- .../variants/32pin-standard/pins_arduino.h | 5 - megaavr/variants/uno-wifi/pins_arduino.h | 2 - 7 files changed, 120 insertions(+), 49 deletions(-) diff --git a/README.md b/README.md index 988b36f..c053924 100644 --- a/README.md +++ b/README.md @@ -132,7 +132,7 @@ The megaAVR-0 microcontrollers are equipped with four independent configurable l The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. They will return `true` if that swap or pin combination is supported. -For `Serial` peripherals the method is `pins(tx,rx)`, and for `Wire` it's `pins(sda,scl)`. +For `Serial` peripherals the method is `pins(tx,rx)`, for `Wire` it's `pins(sda,scl)` and for `SPI` it's `pins(mosi,miso,sck,ss)`. (Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) Note that `swap()` and `pins()` does the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. @@ -150,36 +150,43 @@ Serial3.begin(9600); // Wire pin swapping Wire.swap(1); Wire.begin(); + +// SPI pin swapping +SPI.swap(1); +SPI.begin(); ``` Available pin combinations for the *48 pin standard* pinout are: -| Peripheral | Default | Alternative | -|------------|-------------------------------|------------------------------| -| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | -| Serial1 | swap(0) **or** pins(12,13) | swap(1) **or** pins(14,15) | -| Serial2 | swap(0) **or** pins(32,35) | swap(1) **or** pins(38,39) | -| Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | -| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | +| Peripheral | Default | Alternative 1 | Alternative 2 | +|------------|------------------------------- |------------------------------------|------------------------------------| +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | | +| Serial1 | swap(0) **or** pins(12,13) | swap(1) **or** pins(14,15) | | +| Serial2 | swap(0) **or** pins(32,35) | swap(1) **or** pins(38,39) | | +| Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | | +| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(14,15,16,17) | swap(2) **or** pins(30,31,32,33) | + Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: -| Peripheral | Default | Alternative | -|------------|-------------------------------|------------------------------| -| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | -| Serial1 | swap(0) **or** pins(8,9) | [No swap available] | -| Serial2 | swap(0) **or** pins(20,21) | swap(1) **or** pins(24,25) | -| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | +| Peripheral | Default | Alternative | +|------------|--------------------------------|----------------------------------| +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | +| Serial1 | swap(0) **or** pins(8,9) | | +| Serial2 | swap(0) **or** pins(20,21) | swap(1) **or** pins(24,25) | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | +| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(8,9,10,11) | Available pin combinations for the *Uno WiFi* pinout are: -| Peripheral | Default | Alternative | -|------------|------------------------------|------------------------------| -| Serial | swap(0) **or** pins(27,26) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) | -| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | -| Wire | swap(0) **or** pins(20,21) | [No swap available] | - +| Peripheral | Default | Alternative | +|------------|------------------------------------|------------------------------| +| Serial | swap(0) **or** pins(27,26) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) | +| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | +| Wire | swap(0) **or** pins(20,21) | | +| SPI | swap(0) **or** pins(32,33,34,10) | | ## How to install #### Boards Manager Installation diff --git a/megaavr/libraries/SPI/keywords.txt b/megaavr/libraries/SPI/keywords.txt index fa76165..efb6175 100644 --- a/megaavr/libraries/SPI/keywords.txt +++ b/megaavr/libraries/SPI/keywords.txt @@ -13,6 +13,8 @@ SPI KEYWORD1 ####################################### begin KEYWORD2 end KEYWORD2 +swap KEYWORD2 +pins KEYWORD2 transfer KEYWORD2 setBitOrder KEYWORD2 setDataMode KEYWORD2 diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index fbc6ac8..61601e3 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -26,30 +26,101 @@ const SPISettings DEFAULT_SPI_SETTINGS = SPISettings(); -SPIClass::SPIClass(uint8_t uc_pinMISO, uint8_t uc_pinSCK, uint8_t uc_pinMOSI, uint8_t uc_pinSS, uint8_t uc_mux) +SPIClass::SPIClass() { initialized = false; - // pins - _uc_mux = uc_mux; - _uc_pinMiso = uc_pinMISO; - _uc_pinSCK = uc_pinSCK; - _uc_pinMosi = uc_pinMOSI; - _uc_pinSS = uc_pinSS; + // Default mux setting + #if defined(SPI_MUX) + _uc_mux = SPI_MUX; + #endif +} + +bool SPIClass::pins(uint8_t pinMOSI, uint8_t pinMISO, uint8_t pinSCK, uint8_t pinSS) +{ +#if defined(SPI_MUX) + #if defined(SPI_MUX_PINSWAP_1) || defined(SPI_MUX_PINSWAP_2) + + _uc_mux = SPI_MUX; + #if defined(SPI_MUX_PINSWAP_1) && defined(PIN_SPI_MOSI_PINSWAP_1) + if(pinMOSI == PIN_SPI_MOSI_PINSWAP_1 && pinMISO == PIN_SPI_MISO_PINSWAP_1 && pinSCK == PIN_SPI_SCK_PINSWAP_1 && pinSS == PIN_SPI_SS_PINSWAP_1) + { + _uc_mux = SPI_MUX_PINSWAP_1; + } + #endif + #if defined(SPI_MUX_PINSWAP_2) && defined(PIN_SPI_MOSI_PINSWAP_2) + if(pinMOSI == PIN_SPI_MOSI_PINSWAP_2 && pinMISO == PIN_SPI_MISO_PINSWAP_2 && pinSCK == PIN_SPI_SCK_PINSWAP_2 && pinSS == PIN_SPI_SS_PINSWAP_2) + { + _uc_mux = SPI_MUX_PINSWAP_2; + } + #endif + + if(_uc_mux != SPI_MUX) + return true; + + #endif + + return pinMOSI == PIN_SPI_MOSI && pinMISO == PIN_SPI_MISO && pinSCK == PIN_SPI_SCK && pinSS == PIN_SPI_SS; +#else + return false; +#endif +} + +bool SPIClass::swap(uint8_t state) +{ + if(state == 0) + { + pins(PIN_SPI_MOSI, PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_SS); + return true; + } + #if defined(SPI_MUX_PINSWAP_1) + else if(state == 1) + { + pins(PIN_SPI_MOSI_PINSWAP_1, PIN_SPI_MISO_PINSWAP_1, PIN_SPI_SCK_PINSWAP_1, PIN_SPI_SS_PINSWAP_1); + return true; + } + #endif + #if defined(SPI_MUX_PINSWAP_2) + else if(state == 2) + { + pins(PIN_SPI_MOSI_PINSWAP_2, PIN_SPI_MISO_PINSWAP_2, PIN_SPI_SCK_PINSWAP_2, PIN_SPI_SS_PINSWAP_2); + return true; + } + #endif + else + return false; } void SPIClass::begin() { init(); - PORTMUX.TWISPIROUTEA |= _uc_mux; + PORTMUX.TWISPIROUTEA = _uc_mux | (PORTMUX.TWISPIROUTEA & ~3); - // We don't need HW SS since slave/master mode is selected via registers, so make it simply INPUT - pinMode(_uc_pinSS, INPUT); - pinMode(_uc_pinMosi, OUTPUT); - pinMode(_uc_pinSCK, OUTPUT); // MISO is set to input by the controller - + if(_uc_mux == SPI_MUX) + { + pinMode(PIN_SPI_SS, INPUT); + pinMode(PIN_SPI_MOSI, OUTPUT); + pinMode(PIN_SPI_SCK, OUTPUT); + } + #if defined(SPI_MUX_PINSWAP_1) + else if(_uc_mux == SPI_MUX_PINSWAP_1) + { + pinMode(PIN_SPI_SS_PINSWAP_1, INPUT); + pinMode(PIN_SPI_MOSI_PINSWAP_1, OUTPUT); + pinMode(PIN_SPI_SCK_PINSWAP_1, OUTPUT); + } + #endif + #if defined(SPI_MUX_PINSWAP_2) + else if(_uc_mux == SPI_MUX_PINSWAP_2) + { + pinMode(PIN_SPI_SS_PINSWAP_2, INPUT); + pinMode(PIN_SPI_MOSI_PINSWAP_2, OUTPUT); + pinMode(PIN_SPI_SCK_PINSWAP_2, OUTPUT); + } + #endif + SPI0.CTRLB |= (SPI_SSD_bm); SPI0.CTRLA |= (SPI_ENABLE_bm | SPI_MASTER_bm); @@ -264,5 +335,5 @@ void SPIClass::transfer(void *buf, size_t count) } #if SPI_INTERFACES_COUNT > 0 - SPIClass SPI (PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_MOSI, PIN_SPI_SS, SPI_MUX); + SPIClass SPI; #endif diff --git a/megaavr/libraries/SPI/src/SPI.h b/megaavr/libraries/SPI/src/SPI.h index dd427e1..7947930 100644 --- a/megaavr/libraries/SPI/src/SPI.h +++ b/megaavr/libraries/SPI/src/SPI.h @@ -145,7 +145,7 @@ class SPISettings { class SPIClass { public: - SPIClass(uint8_t uc_pinMISO, uint8_t uc_pinSCK, uint8_t uc_pinMOSI, uint8_t uc_pinSS, uint8_t uc_mux); + SPIClass(); byte transfer(uint8_t data); uint16_t transfer16(uint16_t data); @@ -156,7 +156,9 @@ class SPIClass { void notUsingInterrupt(int interruptNumber); void beginTransaction(SPISettings settings); void endTransaction(void); - + + bool pins(uint8_t pinMOSI, uint8_t pinMISO, uint8_t pinSCK, uint8_t pinSS); + bool swap(uint8_t state = 1); void begin(); void end(); diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 1f60c52..c7e7df3 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -47,7 +47,6 @@ #define SPI_INTERFACES_COUNT 1 #define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) #define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_DEFAULT_gc) #define PIN_SPI_MISO (5) #define PIN_SPI_SCK (6) #define PIN_SPI_MOSI (4) @@ -56,10 +55,7 @@ #define PIN_SPI_SCK_PINSWAP_1 (10) #define PIN_SPI_MOSI_PINSWAP_1 (8) #define PIN_SPI_SS_PINSWAP_1 (11) -#define PIN_SPI_MISO_PINSWAP_2 (5) -#define PIN_SPI_SCK_PINSWAP_2 (6) -#define PIN_SPI_MOSI_PINSWAP_2 (4) -#define PIN_SPI_SS_PINSWAP_2 (7) + static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 3ba4d17..817ecad 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -47,7 +47,6 @@ #define SPI_INTERFACES_COUNT 1 #define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) #define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_DEFAULT_gc) #define PIN_SPI_MISO (5) #define PIN_SPI_SCK (6) #define PIN_SPI_MOSI (4) @@ -56,10 +55,6 @@ #define PIN_SPI_SCK_PINSWAP_1 (10) #define PIN_SPI_MOSI_PINSWAP_1 (8) #define PIN_SPI_SS_PINSWAP_1 (11) -#define PIN_SPI_MISO_PINSWAP_2 (5) -#define PIN_SPI_SCK_PINSWAP_2 (6) -#define PIN_SPI_MOSI_PINSWAP_2 (4) -#define PIN_SPI_SS_PINSWAP_2 (7) static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 5ac7f49..df2b39c 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -48,8 +48,6 @@ #define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10) #define SPI_MUX (PORTMUX_SPI0_ALT1_gc) -#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT2_gc) -#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_DEFAULT_gc) #define PIN_SPI_MISO (33) #define PIN_SPI_SCK (34) #define PIN_SPI_MOSI (32) From 90dd18fab384327e923918928995a46883987186 Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 20 Oct 2019 23:15:44 +0200 Subject: [PATCH 097/351] Add analog comparator section --- README.md | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index c053924..2e609de 100644 --- a/README.md +++ b/README.md @@ -3,9 +3,9 @@ An Arduino core for the new megaAVR series! **TODO:** -* SPI pin swap integration in libraries * Readme - Need some good intro text at the beginning + - Bootloader info # Table of contents @@ -16,7 +16,8 @@ An Arduino core for the new megaAVR series! * [Reset pin](#reset-pin) * [Pinout](#pinout) * [PWM output](#pwm-output) -* [Configurable Custom Logic](#configurable-custom-logic-ccl) +* [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) +* [Analog Comparator (AC)](#analog-comparator-ac) * [Alternative pins](#alternative-pins) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) @@ -46,9 +47,9 @@ An Arduino core for the new megaAVR series! ## Programming -Programming must be done with a UPDI compatible programmer, such as the JTAGICE 3 or any of the new EDBG chips that can be found on newer AVR explained and curoisity boards. +Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) or an official Atmel/Microchip UPDI compatible programmer. -Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained pro board you'll have to choose mEDBG, nEDBG or EDBG. +Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. ## Supported clock frequencies @@ -118,16 +119,20 @@ PWM output, `analogWrite()`, is available for the following pins: | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where -`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within -the constraints of the hardware will be made to match the request. +`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within the constraints of the hardware will be made to match the request. Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. -## Configurable custom logic (CCL) +## Configurable Custom Logic (CCL) The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performence. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from eachother, connected together or generate interrupt for to the CPU. I've made a [light weight, high level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integraion with the CCL hardware. +## Analog Comparator (AC) +The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. +Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. + + ## Alternative pins The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. From 0ce59b03c412cad300f37b29b5674a51a9483247 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 21 Oct 2019 14:44:33 +0200 Subject: [PATCH 098/351] Add bootloader info --- README.md | 28 ++++++++++++++++------------ 1 file changed, 16 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 2e609de..9b518bd 100644 --- a/README.md +++ b/README.md @@ -5,12 +5,13 @@ An Arduino core for the new megaAVR series! **TODO:** * Readme - Need some good intro text at the beginning - - Bootloader info # Table of contents * [Supported microcontrollers](#supported-microcontrollers) * [Programming](#programming) + - [Using a UPDI programmer](#using-a-updi-programmer) + - [Using a bootloader](#using-a-bootloader) * [Supported clock frequencies](#supported-clock-frequencies) * [BOD option](#bod-option) * [Reset pin](#reset-pin) @@ -32,25 +33,28 @@ An Arduino core for the new megaAVR series! ## Supported microcontrollers -| | ATmega4809 | ATmega4808 | ATmega3209 | ATmega3208 | ATmega1609 | ATmega1608 | ATmega809 | ATmega808 | -|------------------------|----------------------------|-----------------------------|------------------|-----------------------------|------------------|-----------------------------|------------------|-----------------------------| -| **Flash** | 48 kB | 48 kB | 32 kB | 32 kB | 16 kB | 16 kB | 8 kB | 8 kB | -| **RAM** | 6 kB | 6 kB | 4 kB | 4 kB | 2 kB | 2 kB | 1 kB | 1 kB | -| **EEPROM** | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | -| **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | -| **IO pins** | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | 40/41* | 26/27*
23†/24†† | -| **Available packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | +| | Mega4809 | Mega4808 | Mega3209 | Mega3208 | Mega1609 | Mega1608 | Mega809 | Mega808 | +|------------------|----------------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------| +| **Flash** | 48 kB | 48 kB | 32 kB | 32 kB | 16 kB | 16 kB | 8 kB | 8 kB | +| **RAM** | 6 kB | 6 kB | 4 kB | 4 kB | 2 kB | 2 kB | 1 kB | 1 kB | +| **EEPROM** | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | +| **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | +| **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | +| **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | -* Physical reset pin is disabled - SSOP28 package -†† SSOP28 package and reset disabled +* TQFP32/QFN32 package +** SSOP28 package +*** DIP40 package ## Programming +### Using a UPDI programmer Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) or an official Atmel/Microchip UPDI compatible programmer. Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. +### Using a bootloader +Programming can also be done using the [Optiboot bootloader](https://github.com/optiboot/Optiboot). It is available for all megaAVR-0 chips, and can be used with all hardware serial ports including alternative pin positions. Simply select what UART number to use, default/alternative pin position and click "Burn bootloader". The bootloader will flash an LED connected to PA7 (digital pin 7 on most pinouts) twice when a hardware reset occurs. The upload speed is 115200 baud. Note that that the reset pin cannot be used as a GPIO when using a bootloader. It doesn't matter if you have set the reset pin as GPIO in the tools menu or not; the bootloader option will override this setting. ## Supported clock frequencies MegaCoreX lets you choose what clock frequency you want to run your microcontroller at. From e39ec415e31a2907d4b932c456d9d503cb12587f Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 21 Oct 2019 20:22:02 +0200 Subject: [PATCH 099/351] Update minimal setup schematics --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 9b518bd..2c85db5 100644 --- a/README.md +++ b/README.md @@ -212,7 +212,7 @@ Here's some simple schematics that shows a minimal setup. The straight 6-pin hea | 48-pin *ATmega809/1609/3209/4809* | 40-pin *ATmega4809* | 32-pin *ATmega808/1608/3208/4808* | |-------------------------------------------------------|-------------------------------------------------------|-------------------------------------------------------| -|||| +|||| ## Getting your hardware working ### Arduino Uno WiFi Rev2 @@ -222,13 +222,13 @@ Click to enlarge: ### Curiosity Nano -[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. Use the `LED_BUILTIN` macro to control the onboard LED. Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. +[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: ### AVR-IOT WG -[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Use the `LED_BUILTIN` macro to control the onboard LED marked with *WIFI*. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. +[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. Click to enlarge: From 9edbe32572cfac60df0bdc9967d98948708deac0 Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 22 Oct 2019 10:21:40 +0200 Subject: [PATCH 100/351] Add into text and fix some spelling --- README.md | 39 +++++++++++++++++++-------------------- 1 file changed, 19 insertions(+), 20 deletions(-) diff --git a/README.md b/README.md index 2c85db5..29d3336 100644 --- a/README.md +++ b/README.md @@ -1,10 +1,9 @@ # MegaCoreX +An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. Its largest variant, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis. -An Arduino core for the new megaAVR series! +Compared to older AVR families they also have more advanced and accurate internal oscillators which can provide base frequencies of 16 and 20 MHz. These can again be divided down internally to reduce the processor speed and power consumption. This means in most applications an external clock isn't necessary anymore. You can read more about clocks and clock frequencies in the [Supported clock frequencies](#supported-clock-frequencies) section. -**TODO:** -* Readme - - Need some good intro text at the beginning +For programming, these chips use a UPDI programming interface. This is a bi-directional single wire interface and requires a programmer that supports UPDI. If you rather prefer uploading using a USB to serial adapter there is an option to use the Optiboot bootloader. Read more about UPDI and bootloaders in the [Programming](#programming) section below. # Table of contents @@ -51,10 +50,10 @@ An Arduino core for the new megaAVR series! ### Using a UPDI programmer Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) or an official Atmel/Microchip UPDI compatible programmer. -Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. +Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto-detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. ### Using a bootloader -Programming can also be done using the [Optiboot bootloader](https://github.com/optiboot/Optiboot). It is available for all megaAVR-0 chips, and can be used with all hardware serial ports including alternative pin positions. Simply select what UART number to use, default/alternative pin position and click "Burn bootloader". The bootloader will flash an LED connected to PA7 (digital pin 7 on most pinouts) twice when a hardware reset occurs. The upload speed is 115200 baud. Note that that the reset pin cannot be used as a GPIO when using a bootloader. It doesn't matter if you have set the reset pin as GPIO in the tools menu or not; the bootloader option will override this setting. +Programming can also be done using the [Optiboot bootloader](https://github.com/optiboot/Optiboot). It is available for all megaAVR-0 chips and can be used with all hardware serial ports including alternative pin positions. Simply select what UART number to use, default/alternative pin position and click "Burn bootloader". The bootloader will flash an LED connected to PA7 (digital pin 7 on most pinouts) twice when a hardware reset occurs. The upload speed is 115200 baud. Note that that the reset pin cannot be used as a GPIO when using a bootloader. It doesn't matter if you have set the reset pin as GPIO in the tools menu or not; the bootloader option will override this setting. ## Supported clock frequencies MegaCoreX lets you choose what clock frequency you want to run your microcontroller at. @@ -73,12 +72,12 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol | 8 MHz | External clock | | | 1 MHz | External clock | | -Note that unlike other AVRs none of these chips are able to drive an external crystal or resonator. If you need an external oscillator it has to be one with a driven clock output. +Note that unlike other AVRs **none of these chips can drive an external crystal or resonator**. If you need an external oscillator it has to be one with a driven clock output. The microcontroller will freeze if the external clock suddenly drops out. If not present on boot, it will automatically choose the 16 MHz internal oscillator instead. ## BOD option -Brown out detection, or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brown out setting. Below is a table that shows the available BOD options: +Brownout detection or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brownout setting. Below is a table that shows the available BOD options: | BOD threshold | |--------------------------------| @@ -94,14 +93,14 @@ Brown out detection, or BOD for short lets the microcontroller sense the input v ## Reset pin -None of the megaAVR-0 microcontrollers needs the reset line in order to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer in order to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general purpose button for your project. +None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. ## Pinout This core provides several different Arduino pin mappings based on your current hardware -- **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much more clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. +- **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. - **32 pin standard**: This is the pinout for the 32 pin version of the ATmega3208/4808. Again, it will not be compatible with shields or anything like that, but it's clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. -- **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. Will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. +- **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. It will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. Please have a look at the pins_arduino.h files for detailed info.

@@ -123,13 +122,13 @@ PWM output, `analogWrite()`, is available for the following pins: | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where -`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. A best effort within the constraints of the hardware will be made to match the request. +`kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. The best effort within the constraints of the hardware will be made to match the request. Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. ## Configurable Custom Logic (CCL) -The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performence. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from eachother, connected together or generate interrupt for to the CPU. I've made a [light weight, high level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integraion with the CCL hardware. +The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performance. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from each other, connected together or generate an interrupt to the CPU. I've made a [light weight, high-level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integration with the CCL hardware. ## Analog Comparator (AC) @@ -138,7 +137,7 @@ Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/maste ## Alternative pins -The megaAVR-0 microcontrollers support alternative pin assignments for some of its built in peripherals. +The megaAVR-0 microcontrollers support alternative pin assignments for some of its built-in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. They will return `true` if that swap or pin combination is supported. For `Serial` peripherals the method is `pins(tx,rx)`, for `Wire` it's `pins(sda,scl)` and for `SPI` it's `pins(mosi,miso,sck,ss)`. @@ -203,11 +202,11 @@ Available pin combinations for the *Uno WiFi* pinout are: #### Manual Installation Click on the "Download ZIP" button. Extract the ZIP file, and move the extracted folder to the location "**~/Documents/Arduino/hardware**". Create the "hardware" folder if it doesn't exist. -Open Arduino IDE, and a new category in the boards menu called "MightyCoreX" will show up. +Open Arduino IDE and a new category in the boards menu called "MightyCoreX" will show up. ## Minimal setup -Here's some simple schematics that shows a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. +Here are some simple schematics that show a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. Click to enlarge:
| 48-pin *ATmega809/1609/3209/4809* | 40-pin *ATmega4809* | 32-pin *ATmega808/1608/3208/4808* | @@ -216,25 +215,25 @@ Here's some simple schematics that shows a minimal setup. The straight 6-pin hea ## Getting your hardware working ### Arduino Uno WiFi Rev2 -[The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with, because it's officially supported by Arduino. It uses an ATmega4809, and recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer in order to upload code. For more information about this board please see the product page and its schematic. +[The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with because it's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. For more information about this board please see the product page and its schematic. Click to enlarge: ### Curiosity Nano -[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. Recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. +[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: ### AVR-IOT WG -[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often refered to as the debug serial port). This means tou'll have to use `Serial2.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. +[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: ### ATmega4809 Xplained Pro -[The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. Recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often refered to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` in order to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer in order to upload code. For more information about this board please refer to the userguide and its schematic. +[The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: From 7bbd6980bdedd86773ca25c81e3dbe58b95af58d Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 23 Oct 2019 22:30:35 +0200 Subject: [PATCH 101/351] Update pinout diagrams New LED position and analog comparator pins added --- README.md | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 29d3336..12686d2 100644 --- a/README.md +++ b/README.md @@ -106,9 +106,9 @@ This core provides several different Arduino pin mappings based on your current Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: -| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | -|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | +|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +|

|























| ## PWM output @@ -218,22 +218,22 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he [The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with because it's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: - + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: - + ### ATmega4809 Xplained Pro [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: - + From a4e65f44a1224a3dbaca4e9f7a500dbe92d2d8d5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 24 Oct 2019 22:03:11 +0200 Subject: [PATCH 102/351] Remove dummy app from bootloader file May cause issues when sketch + bootloader is mergen into the same hex file --- .../optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex | 2 -- .../optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex | 2 -- 8 files changed, 16 deletions(-) diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex index 8a36e1f..cf32e3b 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000C150E9F7CF91F1CF88ED84BF6093000192 :0A01B000809102108370E1F70895BA :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C6DF0C94000035 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex index 5f09d61..0dac87b 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000E9F7CF91F1CF88ED84BF60930001809192 :0801B00002108370E1F70895CD :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex index a1b4057..a3af427 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000C150E9F7CF91F1CF88ED84BF6093000192 :0A01B000809102108370E1F70895BA :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C6DF0C94000035 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex index c996adf..689e36f 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000E9F7CF91F1CF88ED84BF60930001809192 :0801B00002108370E1F70895CD :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex index f8be480..ed9b4d0 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000C150E9F7CF91F1CF88ED84BF6093000192 :0A01B000809102108370E1F70895BA :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C6DF0C94000035 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex index e24ac40..f829c9b 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000E9F7CF91F1CF88ED84BF60930001809192 :0801B00002108370E1F70895CD :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex index 70bfcaf..ec6e572 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000C150E9F7CF91F1CF88ED84BF6093000192 :0A01B000809102108370E1F70895BA :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C6DF0C94000035 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex index 81553f4..8348a47 100644 --- a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +++ b/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex @@ -27,6 +27,4 @@ :1001A000E9F7CF91F1CF88ED84BF60930001809192 :0801B00002108370E1F70895CD :0201FE000009F6 -:10020000E0E4F0E0808180838091FE019091FF0125 -:1002100050E040E064E090E080E0C5DF0C94000036 :00000001FF From 2241fb461c926b2b5115e64b6496c48012d174a8 Mon Sep 17 00:00:00 2001 From: Hans Date: Fri, 25 Oct 2019 19:39:59 +0200 Subject: [PATCH 103/351] Add info about slow baud rates and fast clocks Closes #27 --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 12686d2..0043b66 100644 --- a/README.md +++ b/README.md @@ -75,6 +75,8 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol Note that unlike other AVRs **none of these chips can drive an external crystal or resonator**. If you need an external oscillator it has to be one with a driven clock output. The microcontroller will freeze if the external clock suddenly drops out. If not present on boot, it will automatically choose the 16 MHz internal oscillator instead. +Another thing to watch out for is the lowest possible baudrates when running at 16 or 20 MHz. At 16 MHz the lowest baud rate is 1200 baud. When running at 20 MHz the lowest is 2400 baud. This is caused by the way the internal baud rate generator works. If you need lower baud rates you'll either have to reduce the main clock speed or use the software serial library instead. + ## BOD option Brownout detection or BOD for short lets the microcontroller sense the input voltage and shut down if the voltage goes below the brownout setting. Below is a table that shows the available BOD options: From a9328ce7e603c8c134dbd35cede09cd37290c00f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 26 Oct 2019 10:13:58 +0200 Subject: [PATCH 104/351] Fix typo --- megaavr/variants/uno-wifi/pins_arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index df2b39c..0fbe8c8 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -304,7 +304,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN1_bm, // 12 PE1 PIN2_bm, // 13 PE2 PIN0_bm, // 14 PD0/AI0 - PIN1_bm, // 15 PD1AI1 + PIN1_bm, // 15 PD1/AI1 PIN2_bm, // 16 PD2/AI2 PIN3_bm, // 17 PD3/AI3 PIN4_bm, // 18 PD4/AI4 From 2a45bb5d0b360121df56570e81f62276a4c06772 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 26 Oct 2019 10:15:41 +0200 Subject: [PATCH 105/351] Add support for Arduino Nano Every --- megaavr/boards.txt | 8 + megaavr/platform.txt | 7 + megaavr/variants/nano-every/pins_arduino.h | 355 +++++++++++++++++++++ megaavr/variants/nano-every/variant.c | 134 ++++++++ 4 files changed, 504 insertions(+) create mode 100644 megaavr/variants/nano-every/pins_arduino.h create mode 100644 megaavr/variants/nano-every/variant.c diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 6b2648c..79a1346 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -35,6 +35,14 @@ menu.bootloader=Bootloader 4809.menu.pinout.uno_wifi.build.variant=uno-wifi 4809.menu.pinout.uno_wifi.build.compat= +4809.menu.pinout.nano_every=Nano Every +4809.menu.pinout.nano_every.build.variant=nano-every +4809.menu.pinout.nano_every.upload.tool=avrdude_nanoevery +4809.menu.pinout.nano_every.upload.use_1200bps_touch=true +4809.menu.pinout.nano_every.upload.protocol=jtag2updi +4809.menu.pinout.nano_every.program.extra_params=-P{serial.port} -e +4809.menu.pinout.nano_every.build.compat= + # Reset pin 4809.menu.resetpin.reset=Reset 4809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 7d964c0..46aaf81 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -104,6 +104,13 @@ tools.avrdude.upload.verify= tools.avrdude.upload.params.noverify=-V tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} -P{serial.port} -b{upload.speed} -D "-Uflash:w:{build.path}/{build.project_name}.hex:i" +# Kind of a hacky way to implement support for the Nano every, where the IDE requires an upload sequence to perform 1200bps touch +tools.avrdude_nanoevery.upload.params.verbose=-v +tools.avrdude_nanoevery.upload.params.quiet=-q -q +tools.avrdude_nanoevery.upload.verify= +tools.avrdude_nanoevery.upload.params.noverify=-V +tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i" "-Ufuse0:w:{bootloader.WDTCFG}:m" "-Ufuse1:w:{bootloader.BODCFG}:m" "-Ufuse2:w:{bootloader.OSCCFG}:m" "-Ufuse4:w:{bootloader.TCD0CFG}:m" "-Ufuse5:w:{bootloader.SYSCFG0}:m" "-Ufuse6:w:{bootloader.SYSCFG1}:m" "-Ufuse7:w:{bootloader.APPEND}:m" "-Ufuse8:w:{bootloader.BOOTEND}:m" "-Ulock:w:{bootloader.LOCKBIT}:m" + tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q # tools.avrdude.program.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h new file mode 100644 index 0000000..c28a416 --- /dev/null +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -0,0 +1,355 @@ +/* + pins_arduino.h - Pin definition functions for Arduino + Part of Arduino - http://www.arduino.cc/ + + Copyright (c) 2007 David A. Mellis + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General + Public License along with this library; if not, write to the + Free Software Foundation, Inc., 59 Temple Place, Suite 330, + Boston, MA 02111-1307 USA +*/ + +#ifndef Pins_Arduino_h +#define Pins_Arduino_h + +#include +#include "timers.h" + +#define NANO_EVERY_PINOUT +#define NONA4809_PINOUT + +#define NUM_DIGITAL_PINS 41 +#define NUM_ANALOG_INPUTS 16 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 // (SDA / SCL) +#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) +#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) +#define ANALOG_INPUT_OFFSET 14 +#define digitalPinToAnalogInput(p) (((p) == A0) ? (3) : ((p) == A1) ? (2) : ((p) == A2) ? (1): ((p) == A3) ? (0): ((p) == A4) ? (12): ((p) == A5) ? (13): ((p) == A6) ? (4): ((p) == A7) ? (5): ((p) == A8) ? (7): ((p) == A9) ? (10) : ((p) == A10) ? (9): ((p) == A11) ? (8): ((p) == A12) ? (11): ((p) == A13) ? (14): ((p) == A14) ? (15) :((p) == A15) ? (29) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) + +#define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation + +#define EXTERNAL_NUM_INTERRUPTS (48) + +#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10) + +#define SPI_MUX (PORTMUX_SPI0_ALT2_gc) +#define SPI_INTERFACES_COUNT 1 +#define PIN_SPI_MISO (12) +#define PIN_SPI_SCK (13) +#define PIN_SPI_MOSI (11) +#define PIN_SPI_SS (8) +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; + +#define PIN_WIRE_SDA (22) +#define PIN_WIRE_SCL (23) +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; +#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) + +// Nano every main USART available on Arduino header pins +// USART1 on mega4809 (alternative pins) +// Mapped to HWSERIAL0 in Serial library +#define HWSERIAL1 (&USART1) +#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) +#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) +#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) +#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) +#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL1_TX (1) +#define PIN_WIRE_HWSERIAL1_RX (0) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (34) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (35) + +// Nano Every debug USART (not available on headers, only via the SAMD11 virtual COM port) +// USART3 on mega4809 (alternative pins) +// Mapped to HWSERIAL0 in Serial library +#define HWSERIAL0 (&USART3) +#define HWSERIAL0_DRE_VECTOR (USART3_DRE_vect) +#define HWSERIAL0_DRE_VECTOR_NUM (USART3_DRE_vect_num) +#define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) +#define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) +#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL0_TX (25) +#define PIN_WIRE_HWSERIAL0_RX (24) +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (9) +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) + +// Nano Every pare USART available on testpoints +// USART0 on mega4809 (alternative pins) +// Mapped to HWSERIAL2 in Serial library +#define HWSERIAL2 (&USART0) +#define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) +#define HWSERIAL2_DRE_VECTOR_NUM (USART0_DRE_vect_num) +#define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) +#define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) +#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL2_TX (24) +#define PIN_WIRE_HWSERIAL2_RX (23) +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (2) +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) + +#define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) + +#define LED_BUILTIN 13 + +#define PIN_A0 (14) // AIN3 +#define PIN_A1 (15) // AIN2 +#define PIN_A2 (16) // AIN1 +#define PIN_A3 (17) // AIN0 +#define PIN_A4 (18) // AIN12 +#define PIN_A5 (19) // AIN13 +#define PIN_A6 (20) // AIN4 +#define PIN_A7 (21) // AIN5 +#define PIN_A8 (39) // AIN7 +#define PIN_A9 (13) // AIN10 +#define PIN_A10 (12) // AIN9 +#define PIN_A11 (11) // AIN8 +#define PIN_A12 (8) // AIN11 +#define PIN_A13 (6) // AIN14 +#define PIN_A14 (3) // AIN15 +#define PIN_A14 (29) // AIN6 + +static const uint8_t A0 = PIN_A0; +static const uint8_t A1 = PIN_A1; +static const uint8_t A2 = PIN_A2; +static const uint8_t A3 = PIN_A3; +static const uint8_t A4 = PIN_A4; +static const uint8_t A5 = PIN_A5; +static const uint8_t A6 = PIN_A6; +static const uint8_t A7 = PIN_A7; +static const uint8_t A8 = PIN_A8; +static const uint8_t A9 = PIN_A9; +static const uint8_t A10 = PIN_A10; +static const uint8_t A11 = PIN_A11; +static const uint8_t A12 = PIN_A12; +static const uint8_t A13 = PIN_A13; +static const uint8_t A14 = PIN_A14; +static const uint8_t A15 = PIN_A15; + +#define PINS_COUNT (41u) + +#ifdef ARDUINO_MAIN + +const uint8_t digital_pin_to_port[] = { + PC, // 0 PC5/USART1_Rx_alt + PC, // 1 PC4/USART1_Tx_alt + PA, // 2 PA0/USART0_Tx + PF, // 3 PF5/USART2_Rx_alt/AIN6 + PC, // 4 PC6 + PB, // 5 PB2 + PF, // 6 PF4/USART2_Tx_alt/AIN14 + PA, // 7 PA1/USART0_Rx + PE, // 8 PE3/AIN11 + PB, // 9 PB0/USART3_Tx + PB, // 10 PB1/USART3_Rx + PE, // 11 PE0/AIN8 + PE, // 12 PE1/AIN9 + PE, // 13 PE2/AIN10 + PD, // 14 PD3/AIN3 + PD, // 15 PD2/AIN2 + PD, // 16 PD1/AIN1 + PD, // 17 PD0/AIN0 + PF, // 18 PF2/AIN12 + PF, // 19 PF3/AIN13 + PD, // 20 PD4/AIN4 + PD, // 21 PD5/AIN5 + PA, // 22 PA2/TWI_SDA + PA, // 23 PA3/TWI_SCL + PB, // 24 PB5/USART3_Rx_alt + PB, // 25 PB4/USART3_Tx_alt + PC, // 26 PC3 + PA, // 27 PA5/USART0_Rx_alt + PA, // 28 PA4/USART0_Tx_alt + PD, // 29 PD6/AIN6 + PA, // 30 PA6 + PA, // 31 PA7 + PB, // 32 PB3 + PC, // 33 PC7 + PC, // 34 PC0/MOSI/USART1_Tx + PC, // 35 PC1/MISO/USART1_Rx + PC, // 36 PC2/SCK + PF, // 37 PF0/USART2_Tx + PF, // 38 PF1/USART2_Rx + PD, // 39 PD7/VREF/AIN7 + PF // 40 PF6/RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_position[] = { + PIN5_bp, // 0 PC5/USART1_Rx_alt + PIN4_bp, // 1 PC4/USART1_Tx_alt + PIN0_bp, // 2 PA0/USART0_Tx + PIN5_bp, // 3 PF5/USART2_Rx_alt/AIN15 + PIN6_bp, // 4 PC6 + PIN2_bp, // 5 PB2 + PIN4_bp, // 6 PF4/USART2_Tx_alt/AIN15 + PIN1_bp, // 7 PA1/USART0_Rx + PIN3_bp, // 8 PE3/AIN11 + PIN0_bp, // 9 PB0/USART3_Tx + PIN1_bp, // 10 PB1/USART3_Rx + PIN0_bp, // 11 PE0/AIN8 + PIN1_bp, // 12 PE1/AIN9 + PIN2_bp, // 13 PE2/AIN10 + PIN3_bp, // 14 PD3/AIN3 + PIN2_bp, // 15 PD2/AIN2 + PIN1_bp, // 16 PD1/AIN1 + PIN0_bp, // 17 PD0/AIN0 + PIN2_bp, // 18 PF2/AIN12 + PIN3_bp, // 19 PF3/AIN13 + PIN4_bp, // 20 PD4/AIN4 + PIN5_bp, // 21 PD5/AIN5 + PIN2_bp, // 22 PA2/TWI_SDA + PIN3_bp, // 23 PA3/TWI_SCL + PIN5_bp, // 24 PB5/USART3_Rx_alt + PIN4_bp, // 25 PB4/USART3_Tx_alt + PIN3_bp, // 26 PC3 + PIN5_bp, // 27 PA5/USART0_Rx_alt + PIN4_bp, // 28 PA4/USART0_Tx_alt + PIN6_bp, // 29 PD6/AIN6 + PIN6_bp, // 30 PA6 + PIN7_bp, // 31 PA7 + PIN3_bp, // 32 PB3 + PIN7_bp, // 33 PC7 + PIN0_bp, // 34 PC0/MOSI/USART1_Tx + PIN1_bp, // 35 PC1/MISO/USART1_Rx + PIN2_bp, // 36 PC2/SCK + PIN0_bp, // 37 PF0/USART2_Tx + PIN1_bp, // 38 PF1/USART2_Rx + PIN7_bp, // 39 PD7/VREF/AIN7 + PIN6_bp, // 40 PF6/RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_mask[] = { + PIN5_bm, // 0 PC5/USART1_Rx_alt + PIN4_bm, // 1 PC4/USART1_Tx_alt + PIN0_bm, // 2 PA0/USART0_Tx + PIN5_bm, // 3 PF5/USART2_Rx_alt/AIN15 + PIN6_bm, // 4 PC6 + PIN2_bm, // 5 PB2 + PIN4_bm, // 6 PF4/USART2_Tx_alt/AIN14 + PIN1_bm, // 7 PA1/USART0_Rx + PIN3_bm, // 8 PE3/AIN11 + PIN0_bm, // 9 PB0/USART3_Tx + PIN1_bm, // 10 PB1/USART3_Rx + PIN0_bm, // 11 PE0/AIN8 + PIN1_bm, // 12 PE1/AIN9 + PIN2_bm, // 13 PE2/AIN19 + PIN3_bm, // 14 PD3/AIN3 + PIN2_bm, // 15 PD2/AIN2 + PIN1_bm, // 16 PD1/AIN1 + PIN0_bm, // 17 PD0/AIN0 + PIN2_bm, // 18 PF2/AIN12 + PIN3_bm, // 19 PF3/AIN13 + PIN4_bm, // 20 PD4/AIN4 + PIN5_bm, // 21 PD5/AIN5 + PIN2_bm, // 22 PA2/TWI_SDA + PIN3_bm, // 23 PA3/TWI_SCL + PIN5_bm, // 24 PB5/USART3_Rx_alt + PIN4_bm, // 25 PB4/USART3_Tx_alt + PIN3_bm, // 26 PC3 + PIN5_bm, // 27 PA5/USART0_Rx_alt + PIN4_bm, // 28 PA4/USART0_Tx_alt + PIN6_bm, // 29 PD6/AIN6 + PIN6_bm, // 30 PA6 + PIN7_bm, // 31 PA7 + PIN3_bm, // 32 PB3 + PIN7_bm, // 33 PC7 + PIN0_bm, // 34 PC0/MOSI/USART1_Tx + PIN1_bm, // 35 PC1/MISO/USART1_Rx + PIN2_bm, // 36 PC2/SCK + PIN0_bm, // 37 PF0/USART2_Tx + PIN1_bm, // 38 PF1/USART2_Rx + PIN7_bm, // 39 PD7/VREF/AIN7 + PIN6_bm, // 40 PF6/RESET +}; + +const uint8_t digital_pin_to_timer[] = { + NOT_ON_TIMER, // 0 PC5/USART1_Rx_alt + NOT_ON_TIMER, // 1 PC4/USART1_Tx_alt + NOT_ON_TIMER, // 2 PA0/USART0_Tx + TIMERB1, // 3 PF5/USART2_Rx_alt/AIN15 + NOT_ON_TIMER, // 4 PC6 + TIMERA0, // 5 PB2 + TIMERB0, // 6 PF4/USART2_Tx_alt/AIN14 + NOT_ON_TIMER, // 7 PA1/USART0_Rx + NOT_ON_TIMER, // 8 PE3/AIN11 + TIMERA0, // 9 PB0/USART3_Tx + TIMERA0, // 10 PB1/USART3_Rx + NOT_ON_TIMER, // 11 PE0/AIN8 + NOT_ON_TIMER, // 12 PE1/AIN9 + NOT_ON_TIMER, // 13 PE2/AIN10 + NOT_ON_TIMER, // 14 PD3/AIN3 + NOT_ON_TIMER, // 15 PD2/AIN2 + NOT_ON_TIMER, // 16 PD1/AIN1 + NOT_ON_TIMER, // 17 PD0/AIN0 + NOT_ON_TIMER, // 18 PF2/AIN12 + NOT_ON_TIMER, // 19 PF3/AIN13 + NOT_ON_TIMER, // 20 PD4/AIN4 + NOT_ON_TIMER, // 21 PD5/AIN5 + NOT_ON_TIMER, // 22 PA2/TWI_SDA + NOT_ON_TIMER, // 23 PA3/TWI_SCL + NOT_ON_TIMER, // 24 PB5/USART3_Rx + NOT_ON_TIMER, // 25 PB4/USART3_Tx + NOT_ON_TIMER, // 26 PC3 + NOT_ON_TIMER, // 27 PA5/USART0_Rx_alt + NOT_ON_TIMER, // 28 PA4/USART0_Tx_alt + NOT_ON_TIMER, // 29 PD6/AIN6 + NOT_ON_TIMER, // 30 PA6 + NOT_ON_TIMER, // 31 PA7 + NOT_ON_TIMER, // 32 PB3 + NOT_ON_TIMER, // 33 PC7 + NOT_ON_TIMER, // 34 PC0/MOSI/USART1_Tx + NOT_ON_TIMER, // 35 PC1/MISO/USART1_Rx + NOT_ON_TIMER, // 36 PC2/SCK + NOT_ON_TIMER, // 37 PF0/USART2_Tx + NOT_ON_TIMER, // 38 PF1/USART2_Rx + NOT_ON_TIMER, // 39 PD7/VREF/AIN7 + NOT_ON_TIMER, // 40 PF6/RESET +}; + +//const uint8_t analog_pin_to_channel[] = { 3, 2, 1, 0, 12, 13, 4, 5 , 7, 10, 9, 8, 11, 14, 15}; + +#endif + + + + +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_USBVIRTUAL Serial + +#endif diff --git a/megaavr/variants/nano-every/variant.c b/megaavr/variants/nano-every/variant.c new file mode 100644 index 0000000..08673b4 --- /dev/null +++ b/megaavr/variants/nano-every/variant.c @@ -0,0 +1,134 @@ +#include + +#include "pins_arduino.h" +#include "api/Common.h" + +#define FORCE_INLINE __attribute__((always_inline)) inline + +void setup_timers() { + + // TYPE A TIMER + + // PORTMUX setting for TCA -> all outputs [0:2] point to PORTB pins [0:2] + PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTB_gc; + + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; + + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; + + // Default duty 50%, will re-assign in analogWrite() + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; + +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 8000000L + // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else + // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif + + // TYPE B TIMERS + + // Setup TCB0 routing + #if defined(TCB0) + PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 + #endif + + // Setup TCB1 routing + #if defined(TCB1) + PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 + #endif + + // Start with TCB0 + TCB_t *timer_B = (TCB_t *)&TCB0; + + // Find end timer + #if defined(TCB3) + TCB_t *timer_B_end = (TCB_t *)&TCB3; + #elif defined(TCB2) + TCB_t *timer_B_end = (TCB_t *)&TCB2; + #elif defined(TCB1) + TCB_t *timer_B_end = (TCB_t *)&TCB1; + #else + TCB_t *timer_B_end = (TCB_t *)&TCB0; + #endif + + // Timer B Setup loop for TCB[0:3] + do + { + // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() + timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); + + // Assign 8-bit period + timer_B->CCMPL = PWM_TIMER_PERIOD; + + // default duty 50%, set when output enabled + timer_B->CCMPH = PWM_TIMER_COMPARE; + + // Use TCA clock (250kHz) and enable + // (sync update commented out, might try to synchronize later + timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) + //|(TCB_SYNCUPD_bm) + |(TCB_ENABLE_bm); + + // Increment pointer to next TCB instance + timer_B++; + + // Stop when pointing to TCB3 + } while (timer_B <= timer_B_end); + + // Stuff for synchronizing PWM timers +// // Restart TCA to sync TCBs +// // should not be needed +// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; +// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; +// +// timer_B = (TCB_t *)&TCB0; +// +// // TCB are sync to TCA, remove setting +// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); +// digitial_pin_timer < (TIMERB3 - TIMERB0); +// digitial_pin_timer++) +// { +// // disable sync with tca +// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); +// +// // Add offset to register +// timer_B++; +// +// } +} + +FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { + (void)pin; + + /* Check if TWI is operating on double bonded pin (Master Enable is high + in both Master and Slave mode for bus error detection, so this can + indicate an active state for Wire) */ + //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; + + /* Special check for SPI_SS double bonded pin -- no action if SPI is active + (Using SPI Enable bit as indicator of SPI activity) */ + //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; + + // May check Serial3 that may conflict with A-timers + + return false; +} + +void initVariant() { +} \ No newline at end of file From 3b740f777ba91b6d62e195badcd2d33e485dcab2 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 26 Oct 2019 10:50:02 +0200 Subject: [PATCH 106/351] Add Arduino Nano Every --- README.md | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 0043b66..d60cc75 100644 --- a/README.md +++ b/README.md @@ -25,6 +25,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [Minimal setup](#minimal-setup) * [Getting your hardware working](#getting-your-hardware-working) - [Arduino Uno WiFi Rev2](#arduino-uno-wifi-rev2) + - [Arduino Nano Every](#arduino-nano-every) - [Curiosity Nano](#curiosity-nano) - [AVR-IOT-WG](#avr-iot-wg) - [4809 Xplained Pro](#atmega4809-xplained-pro) @@ -217,11 +218,17 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he ## Getting your hardware working ### Arduino Uno WiFi Rev2 -[The Arduino Uno WiFi Rev2](https://store.arduino.cc/usa/arduino-uno-wifi-rev2) is the easiest board out of these to get started with because it's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. For more information about this board please see the product page and its schematic. +[The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: +### Arduino Nano Every +[The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. + +Click to enlarge: + + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. From e04feed1ece1544a2cfb24e93dd899d6d8900444 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 26 Oct 2019 12:16:11 +0200 Subject: [PATCH 107/351] Update README.md --- README.md | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index d60cc75..4499770 100644 --- a/README.md +++ b/README.md @@ -96,7 +96,7 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol ## Reset pin -None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. +None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. Note that the reset pin cannot be usd as a GPIO when using a bootloader ## Pinout @@ -105,6 +105,7 @@ This core provides several different Arduino pin mappings based on your current - **32 pin standard**: This is the pinout for the 32 pin version of the ATmega3208/4808. Again, it will not be compatible with shields or anything like that, but it's clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. It will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. +- **Uno WiFi**: This pinout is 100% compatible with the Arduino Nano Every. If you have code that's written for the Nano Every it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. This pinout is only available when ATmega4809 is selected. Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: @@ -196,8 +197,15 @@ Available pin combinations for the *Uno WiFi* pinout are: | Serial | swap(0) **or** pins(27,26) | swap(1) **or** pins(9,10) | | Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) | | Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | -| Wire | swap(0) **or** pins(20,21) | | -| SPI | swap(0) **or** pins(32,33,34,10) | | + +Available pin combinations for the *Nano Every* pinout are: + +| Peripheral | Default | Alternative | +|------------|------------------------------------|------------------------------| +| Serial | swap(0) **or** pins(25,24) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) | +| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | + ## How to install #### Boards Manager Installation @@ -227,7 +235,7 @@ Click to enlarge: [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. From 4b88011e6c0def06786f96dba4ffa8e34dbb8a2a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 26 Oct 2019 12:17:00 +0200 Subject: [PATCH 108/351] Formatting --- megaavr/variants/nano-every/pins_arduino.h | 52 +++++++++++----------- 1 file changed, 26 insertions(+), 26 deletions(-) diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index c28a416..d17815c 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -64,20 +64,6 @@ static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; #define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -// Nano every main USART available on Arduino header pins -// USART1 on mega4809 (alternative pins) -// Mapped to HWSERIAL0 in Serial library -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (1) -#define PIN_WIRE_HWSERIAL1_RX (0) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (34) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (35) - // Nano Every debug USART (not available on headers, only via the SAMD11 virtual COM port) // USART3 on mega4809 (alternative pins) // Mapped to HWSERIAL0 in Serial library @@ -92,6 +78,20 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (9) #define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) +// Nano every main USART available on Arduino header pins +// USART1 on mega4809 (alternative pins) +// Mapped to HWSERIAL1 in Serial library +#define HWSERIAL1 (&USART1) +#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) +#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) +#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) +#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) +#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL1_TX (1) +#define PIN_WIRE_HWSERIAL1_RX (0) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (34) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (35) + // Nano Every pare USART available on testpoints // USART0 on mega4809 (alternative pins) // Mapped to HWSERIAL2 in Serial library @@ -183,9 +183,9 @@ const uint8_t digital_pin_to_port[] = { PA, // 31 PA7 PB, // 32 PB3 PC, // 33 PC7 - PC, // 34 PC0/MOSI/USART1_Tx - PC, // 35 PC1/MISO/USART1_Rx - PC, // 36 PC2/SCK + PC, // 34 PC0/USART1_Tx + PC, // 35 PC1/USART1_Rx + PC, // 36 PC2 PF, // 37 PF0/USART2_Tx PF, // 38 PF1/USART2_Rx PD, // 39 PD7/VREF/AIN7 @@ -228,9 +228,9 @@ const uint8_t digital_pin_to_bit_position[] = { PIN7_bp, // 31 PA7 PIN3_bp, // 32 PB3 PIN7_bp, // 33 PC7 - PIN0_bp, // 34 PC0/MOSI/USART1_Tx - PIN1_bp, // 35 PC1/MISO/USART1_Rx - PIN2_bp, // 36 PC2/SCK + PIN0_bp, // 34 PC0/USART1_Tx + PIN1_bp, // 35 PC1/USART1_Rx + PIN2_bp, // 36 PC2 PIN0_bp, // 37 PF0/USART2_Tx PIN1_bp, // 38 PF1/USART2_Rx PIN7_bp, // 39 PD7/VREF/AIN7 @@ -273,9 +273,9 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN7_bm, // 31 PA7 PIN3_bm, // 32 PB3 PIN7_bm, // 33 PC7 - PIN0_bm, // 34 PC0/MOSI/USART1_Tx - PIN1_bm, // 35 PC1/MISO/USART1_Rx - PIN2_bm, // 36 PC2/SCK + PIN0_bm, // 34 PC0/USART1_Tx + PIN1_bm, // 35 PC1/USART1_Rx + PIN2_bm, // 36 PC2 PIN0_bm, // 37 PF0/USART2_Tx PIN1_bm, // 38 PF1/USART2_Rx PIN7_bm, // 39 PD7/VREF/AIN7 @@ -317,9 +317,9 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 31 PA7 NOT_ON_TIMER, // 32 PB3 NOT_ON_TIMER, // 33 PC7 - NOT_ON_TIMER, // 34 PC0/MOSI/USART1_Tx - NOT_ON_TIMER, // 35 PC1/MISO/USART1_Rx - NOT_ON_TIMER, // 36 PC2/SCK + NOT_ON_TIMER, // 34 PC0/USART1_Tx + NOT_ON_TIMER, // 35 PC1/USART1_Rx + NOT_ON_TIMER, // 36 PC2 NOT_ON_TIMER, // 37 PF0/USART2_Tx NOT_ON_TIMER, // 38 PF1/USART2_Rx NOT_ON_TIMER, // 39 PD7/VREF/AIN7 From a4e6e3c60c60ac353cef3af394a879c9ab48f993 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 26 Oct 2019 12:32:11 +0200 Subject: [PATCH 109/351] Update Nano Every pinout pic Serial pin swap pins were missing --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 4499770..ed449c9 100644 --- a/README.md +++ b/README.md @@ -235,7 +235,7 @@ Click to enlarge: [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. From 739c0453843321fb9425436e43d43e79a6b72b09 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 26 Oct 2019 12:54:40 +0200 Subject: [PATCH 110/351] Add PWM table for Nano Every --- README.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index ed449c9..e6db0f1 100644 --- a/README.md +++ b/README.md @@ -105,7 +105,7 @@ This core provides several different Arduino pin mappings based on your current - **32 pin standard**: This is the pinout for the 32 pin version of the ATmega3208/4808. Again, it will not be compatible with shields or anything like that, but it's clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. It will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. -- **Uno WiFi**: This pinout is 100% compatible with the Arduino Nano Every. If you have code that's written for the Nano Every it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. This pinout is only available when ATmega4809 is selected. +- **Nano Every**: This pinout is 100% compatible with the Arduino Nano Every. If you have code that's written for the Nano Every it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. This pinout is only available when ATmega4809 is selected. Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: @@ -124,6 +124,7 @@ PWM output, `analogWrite()`, is available for the following pins: | *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | +| *Nano Every* | 5 | 3, 5, 6, 9, 10 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where `kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. The best effort within the constraints of the hardware will be made to match the request. From e50b9ede94da1b04b541e7bf403620745361317b Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 27 Oct 2019 18:06:37 +0100 Subject: [PATCH 111/351] Create LICENSE --- LICENSE | 504 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 504 insertions(+) create mode 100644 LICENSE diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..8000a6f --- /dev/null +++ b/LICENSE @@ -0,0 +1,504 @@ + GNU LESSER GENERAL PUBLIC LICENSE + Version 2.1, February 1999 + + Copyright (C) 1991, 1999 Free Software Foundation, Inc. + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + +[This is the first released version of the Lesser GPL. It also counts + as the successor of the GNU Library Public License, version 2, hence + the version number 2.1.] + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +Licenses are intended to guarantee your freedom to share and change +free software--to make sure the software is free for all its users. + + This license, the Lesser General Public License, applies to some +specially designated software packages--typically libraries--of the +Free Software Foundation and other authors who decide to use it. You +can use it too, but we suggest you first think carefully about whether +this license or the ordinary General Public License is the better +strategy to use in any particular case, based on the explanations below. + + When we speak of free software, we are referring to freedom of use, +not price. Our General Public Licenses are designed to make sure that +you have the freedom to distribute copies of free software (and charge +for this service if you wish); that you receive source code or can get +it if you want it; that you can change the software and use pieces of +it in new free programs; and that you are informed that you can do +these things. + + To protect your rights, we need to make restrictions that forbid +distributors to deny you these rights or to ask you to surrender these +rights. These restrictions translate to certain responsibilities for +you if you distribute copies of the library or if you modify it. + + For example, if you distribute copies of the library, whether gratis +or for a fee, you must give the recipients all the rights that we gave +you. You must make sure that they, too, receive or can get the source +code. If you link other code with the library, you must provide +complete object files to the recipients, so that they can relink them +with the library after making changes to the library and recompiling +it. And you must show them these terms so they know their rights. + + We protect your rights with a two-step method: (1) we copyright the +library, and (2) we offer you this license, which gives you legal +permission to copy, distribute and/or modify the library. + + To protect each distributor, we want to make it very clear that +there is no warranty for the free library. Also, if the library is +modified by someone else and passed on, the recipients should know +that what they have is not the original version, so that the original +author's reputation will not be affected by problems that might be +introduced by others. + + Finally, software patents pose a constant threat to the existence of +any free program. We wish to make sure that a company cannot +effectively restrict the users of a free program by obtaining a +restrictive license from a patent holder. Therefore, we insist that +any patent license obtained for a version of the library must be +consistent with the full freedom of use specified in this license. + + Most GNU software, including some libraries, is covered by the +ordinary GNU General Public License. This license, the GNU Lesser +General Public License, applies to certain designated libraries, and +is quite different from the ordinary General Public License. We use +this license for certain libraries in order to permit linking those +libraries into non-free programs. + + When a program is linked with a library, whether statically or using +a shared library, the combination of the two is legally speaking a +combined work, a derivative of the original library. The ordinary +General Public License therefore permits such linking only if the +entire combination fits its criteria of freedom. The Lesser General +Public License permits more lax criteria for linking other code with +the library. + + We call this license the "Lesser" General Public License because it +does Less to protect the user's freedom than the ordinary General +Public License. It also provides other free software developers Less +of an advantage over competing non-free programs. These disadvantages +are the reason we use the ordinary General Public License for many +libraries. However, the Lesser license provides advantages in certain +special circumstances. + + For example, on rare occasions, there may be a special need to +encourage the widest possible use of a certain library, so that it becomes +a de-facto standard. To achieve this, non-free programs must be +allowed to use the library. A more frequent case is that a free +library does the same job as widely used non-free libraries. In this +case, there is little to gain by limiting the free library to free +software only, so we use the Lesser General Public License. + + In other cases, permission to use a particular library in non-free +programs enables a greater number of people to use a large body of +free software. For example, permission to use the GNU C Library in +non-free programs enables many more people to use the whole GNU +operating system, as well as its variant, the GNU/Linux operating +system. + + Although the Lesser General Public License is Less protective of the +users' freedom, it does ensure that the user of a program that is +linked with the Library has the freedom and the wherewithal to run +that program using a modified version of the Library. + + The precise terms and conditions for copying, distribution and +modification follow. Pay close attention to the difference between a +"work based on the library" and a "work that uses the library". The +former contains code derived from the library, whereas the latter must +be combined with the library in order to run. + + GNU LESSER GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License Agreement applies to any software library or other +program which contains a notice placed by the copyright holder or +other authorized party saying it may be distributed under the terms of +this Lesser General Public License (also called "this License"). +Each licensee is addressed as "you". + + A "library" means a collection of software functions and/or data +prepared so as to be conveniently linked with application programs +(which use some of those functions and data) to form executables. + + The "Library", below, refers to any such software library or work +which has been distributed under these terms. A "work based on the +Library" means either the Library or any derivative work under +copyright law: that is to say, a work containing the Library or a +portion of it, either verbatim or with modifications and/or translated +straightforwardly into another language. (Hereinafter, translation is +included without limitation in the term "modification".) + + "Source code" for a work means the preferred form of the work for +making modifications to it. For a library, complete source code means +all the source code for all modules it contains, plus any associated +interface definition files, plus the scripts used to control compilation +and installation of the library. + + Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running a program using the Library is not restricted, and output from +such a program is covered only if its contents constitute a work based +on the Library (independent of the use of the Library in a tool for +writing it). Whether that is true depends on what the Library does +and what the program that uses the Library does. + + 1. You may copy and distribute verbatim copies of the Library's +complete source code as you receive it, in any medium, provided that +you conspicuously and appropriately publish on each copy an +appropriate copyright notice and disclaimer of warranty; keep intact +all the notices that refer to this License and to the absence of any +warranty; and distribute a copy of this License along with the +Library. + + You may charge a fee for the physical act of transferring a copy, +and you may at your option offer warranty protection in exchange for a +fee. + + 2. You may modify your copy or copies of the Library or any portion +of it, thus forming a work based on the Library, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) The modified work must itself be a software library. + + b) You must cause the files modified to carry prominent notices + stating that you changed the files and the date of any change. + + c) You must cause the whole of the work to be licensed at no + charge to all third parties under the terms of this License. + + d) If a facility in the modified Library refers to a function or a + table of data to be supplied by an application program that uses + the facility, other than as an argument passed when the facility + is invoked, then you must make a good faith effort to ensure that, + in the event an application does not supply such function or + table, the facility still operates, and performs whatever part of + its purpose remains meaningful. + + (For example, a function in a library to compute square roots has + a purpose that is entirely well-defined independent of the + application. Therefore, Subsection 2d requires that any + application-supplied function or table used by this function must + be optional: if the application does not supply it, the square + root function must still compute square roots.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Library, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Library, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote +it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Library. + +In addition, mere aggregation of another work not based on the Library +with the Library (or with a work based on the Library) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may opt to apply the terms of the ordinary GNU General Public +License instead of this License to a given copy of the Library. To do +this, you must alter all the notices that refer to this License, so +that they refer to the ordinary GNU General Public License, version 2, +instead of to this License. (If a newer version than version 2 of the +ordinary GNU General Public License has appeared, then you can specify +that version instead if you wish.) Do not make any other change in +these notices. + + Once this change is made in a given copy, it is irreversible for +that copy, so the ordinary GNU General Public License applies to all +subsequent copies and derivative works made from that copy. + + This option is useful when you wish to copy part of the code of +the Library into a program that is not a library. + + 4. You may copy and distribute the Library (or a portion or +derivative of it, under Section 2) in object code or executable form +under the terms of Sections 1 and 2 above provided that you accompany +it with the complete corresponding machine-readable source code, which +must be distributed under the terms of Sections 1 and 2 above on a +medium customarily used for software interchange. + + If distribution of object code is made by offering access to copy +from a designated place, then offering equivalent access to copy the +source code from the same place satisfies the requirement to +distribute the source code, even though third parties are not +compelled to copy the source along with the object code. + + 5. A program that contains no derivative of any portion of the +Library, but is designed to work with the Library by being compiled or +linked with it, is called a "work that uses the Library". Such a +work, in isolation, is not a derivative work of the Library, and +therefore falls outside the scope of this License. + + However, linking a "work that uses the Library" with the Library +creates an executable that is a derivative of the Library (because it +contains portions of the Library), rather than a "work that uses the +library". The executable is therefore covered by this License. +Section 6 states terms for distribution of such executables. + + When a "work that uses the Library" uses material from a header file +that is part of the Library, the object code for the work may be a +derivative work of the Library even though the source code is not. +Whether this is true is especially significant if the work can be +linked without the Library, or if the work is itself a library. The +threshold for this to be true is not precisely defined by law. + + If such an object file uses only numerical parameters, data +structure layouts and accessors, and small macros and small inline +functions (ten lines or less in length), then the use of the object +file is unrestricted, regardless of whether it is legally a derivative +work. (Executables containing this object code plus portions of the +Library will still fall under Section 6.) + + Otherwise, if the work is a derivative of the Library, you may +distribute the object code for the work under the terms of Section 6. +Any executables containing that work also fall under Section 6, +whether or not they are linked directly with the Library itself. + + 6. As an exception to the Sections above, you may also combine or +link a "work that uses the Library" with the Library to produce a +work containing portions of the Library, and distribute that work +under terms of your choice, provided that the terms permit +modification of the work for the customer's own use and reverse +engineering for debugging such modifications. + + You must give prominent notice with each copy of the work that the +Library is used in it and that the Library and its use are covered by +this License. You must supply a copy of this License. If the work +during execution displays copyright notices, you must include the +copyright notice for the Library among them, as well as a reference +directing the user to the copy of this License. Also, you must do one +of these things: + + a) Accompany the work with the complete corresponding + machine-readable source code for the Library including whatever + changes were used in the work (which must be distributed under + Sections 1 and 2 above); and, if the work is an executable linked + with the Library, with the complete machine-readable "work that + uses the Library", as object code and/or source code, so that the + user can modify the Library and then relink to produce a modified + executable containing the modified Library. (It is understood + that the user who changes the contents of definitions files in the + Library will not necessarily be able to recompile the application + to use the modified definitions.) + + b) Use a suitable shared library mechanism for linking with the + Library. A suitable mechanism is one that (1) uses at run time a + copy of the library already present on the user's computer system, + rather than copying library functions into the executable, and (2) + will operate properly with a modified version of the library, if + the user installs one, as long as the modified version is + interface-compatible with the version that the work was made with. + + c) Accompany the work with a written offer, valid for at + least three years, to give the same user the materials + specified in Subsection 6a, above, for a charge no more + than the cost of performing this distribution. + + d) If distribution of the work is made by offering access to copy + from a designated place, offer equivalent access to copy the above + specified materials from the same place. + + e) Verify that the user has already received a copy of these + materials or that you have already sent this user a copy. + + For an executable, the required form of the "work that uses the +Library" must include any data and utility programs needed for +reproducing the executable from it. However, as a special exception, +the materials to be distributed need not include anything that is +normally distributed (in either source or binary form) with the major +components (compiler, kernel, and so on) of the operating system on +which the executable runs, unless that component itself accompanies +the executable. + + It may happen that this requirement contradicts the license +restrictions of other proprietary libraries that do not normally +accompany the operating system. Such a contradiction means you cannot +use both them and the Library together in an executable that you +distribute. + + 7. You may place library facilities that are a work based on the +Library side-by-side in a single library together with other library +facilities not covered by this License, and distribute such a combined +library, provided that the separate distribution of the work based on +the Library and of the other library facilities is otherwise +permitted, and provided that you do these two things: + + a) Accompany the combined library with a copy of the same work + based on the Library, uncombined with any other library + facilities. This must be distributed under the terms of the + Sections above. + + b) Give prominent notice with the combined library of the fact + that part of it is a work based on the Library, and explaining + where to find the accompanying uncombined form of the same work. + + 8. You may not copy, modify, sublicense, link with, or distribute +the Library except as expressly provided under this License. Any +attempt otherwise to copy, modify, sublicense, link with, or +distribute the Library is void, and will automatically terminate your +rights under this License. However, parties who have received copies, +or rights, from you under this License will not have their licenses +terminated so long as such parties remain in full compliance. + + 9. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Library or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Library (or any work based on the +Library), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Library or works based on it. + + 10. Each time you redistribute the Library (or any work based on the +Library), the recipient automatically receives a license from the +original licensor to copy, distribute, link with or modify the Library +subject to these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties with +this License. + + 11. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Library at all. For example, if a patent +license would not permit royalty-free redistribution of the Library by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Library. + +If any portion of this section is held invalid or unenforceable under any +particular circumstance, the balance of the section is intended to apply, +and the section as a whole is intended to apply in other circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 12. If the distribution and/or use of the Library is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Library under this License may add +an explicit geographical distribution limitation excluding those countries, +so that distribution is permitted only in or among countries not thus +excluded. In such case, this License incorporates the limitation as if +written in the body of this License. + + 13. The Free Software Foundation may publish revised and/or new +versions of the Lesser General Public License from time to time. +Such new versions will be similar in spirit to the present version, +but may differ in detail to address new problems or concerns. + +Each version is given a distinguishing version number. If the Library +specifies a version number of this License which applies to it and +"any later version", you have the option of following the terms and +conditions either of that version or of any later version published by +the Free Software Foundation. If the Library does not specify a +license version number, you may choose any version ever published by +the Free Software Foundation. + + 14. If you wish to incorporate parts of the Library into other free +programs whose distribution conditions are incompatible with these, +write to the author to ask for permission. For software which is +copyrighted by the Free Software Foundation, write to the Free +Software Foundation; we sometimes make exceptions for this. Our +decision will be guided by the two goals of preserving the free status +of all derivatives of our free software and of promoting the sharing +and reuse of software generally. + + NO WARRANTY + + 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO +WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. +EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR +OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY +KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE +LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME +THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. + + 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN +WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY +AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU +FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR +CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE +LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING +RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A +FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF +SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH +DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Libraries + + If you develop a new library, and you want it to be of the greatest +possible use to the public, we recommend making it free software that +everyone can redistribute and change. You can do so by permitting +redistribution under these terms (or, alternatively, under the terms of the +ordinary General Public License). + + To apply these terms, attach the following notices to the library. It is +safest to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least the +"copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 + USA + +Also add information on how to contact you by electronic and paper mail. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the library, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the + library `Frob' (a library for tweaking knobs) written by James Random + Hacker. + + , 1 April 1990 + Ty Coon, President of Vice + +That's all there is to it! From 820181de51b6e86012ac764ae2fed002a698f2c3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 27 Oct 2019 18:58:58 +0100 Subject: [PATCH 112/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 46aaf81..7bc2bee 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=0.1.0 +version=1.0.0 # AVR compile variables # --------------------- From e3c337f75efbd78dba1ac7a6765ce4f128f47335 Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 29 Oct 2019 15:06:31 +0100 Subject: [PATCH 113/351] Add section about pin interrupts --- README.md | 31 ++++++++++++++++++++----------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index e6db0f1..6cb7fe0 100644 --- a/README.md +++ b/README.md @@ -15,10 +15,11 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [BOD option](#bod-option) * [Reset pin](#reset-pin) * [Pinout](#pinout) -* [PWM output](#pwm-output) -* [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) -* [Analog Comparator (AC)](#analog-comparator-ac) -* [Alternative pins](#alternative-pins) +* [Hardware features](#hardware-features) + - [PWM output](#pwm-output) + - [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) + - [Analog Comparator (AC)](#analog-comparator-ac) + - [Alternative pins](#alternative-pins) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) @@ -115,7 +116,18 @@ Please have a look at the pins_arduino.h files for detailed info.

|

|























| -## PWM output +## Hardware features +Here's some hardware spesific features that differs from the older AVR families. + +### Interrupt pins +Unlike older AVRs the megaAVR-0 microcontrollers have fully featured interrupts on every pin. +Supported states are *RISING*, *FALLING*, *CHANGE*, *HIGH* and *LOW*. This means there's no need to use the `digitalPinToInterrupt` macro. Simply call attachInterrupt like this: + +```c +attachInterrupt(myPin, myInterruptFunction, RISING); +``` + +### PWM output PWM output, `analogWrite()`, is available for the following pins: | Pinout | Number of PWM pins | Available PWM pins | @@ -131,17 +143,14 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. - -## Configurable Custom Logic (CCL) +### Configurable Custom Logic (CCL) The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performance. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from each other, connected together or generate an interrupt to the CPU. I've made a [light weight, high-level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integration with the CCL hardware. - -## Analog Comparator (AC) +### Analog Comparator (AC) The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. - -## Alternative pins +### Alternative pins The megaAVR-0 microcontrollers support alternative pin assignments for some of its built-in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. They will return `true` if that swap or pin combination is supported. From 869cd554b1cc86664fca35e7af529d0a5f8bf9c7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 10 Nov 2019 22:14:29 +0100 Subject: [PATCH 114/351] Rename bootloader files and add bootloader source files --- megaavr/boards.txt | 185 ++-- megaavr/bootloaders/optiboot/Makefile | 168 ++++ megaavr/bootloaders/optiboot/README.TXT | 99 +++ megaavr/bootloaders/optiboot/boot_opt.h | 101 +++ .../Optiboot_mega0_UART0_ALT_115200_A7.hex} | 0 .../Optiboot_mega0_UART0_DEF_115200_A7.hex} | 0 .../Optiboot_mega0_UART1_ALT_115200_A7.hex} | 0 .../Optiboot_mega0_UART1_DEF_115200_A7.hex} | 0 .../Optiboot_mega0_UART2_ALT_115200_A7.hex} | 0 .../Optiboot_mega0_UART2_DEF_115200_A7.hex} | 0 .../Optiboot_mega0_UART3_ALT_115200_A7.hex} | 0 .../Optiboot_mega0_UART3_DEF_115200_A7.hex} | 0 megaavr/bootloaders/optiboot/makeall | 9 + megaavr/bootloaders/optiboot/omake | 9 + megaavr/bootloaders/optiboot/omake.bat | 2 + megaavr/bootloaders/optiboot/optiboot_x.c | 729 ++++++++++++++++ megaavr/bootloaders/optiboot/parse_options.mk | 138 +++ megaavr/bootloaders/optiboot/pin_defs_x.h | 815 ++++++++++++++++++ megaavr/bootloaders/optiboot/stk500.h | 49 ++ 19 files changed, 2240 insertions(+), 64 deletions(-) create mode 100755 megaavr/bootloaders/optiboot/Makefile create mode 100755 megaavr/bootloaders/optiboot/README.TXT create mode 100755 megaavr/bootloaders/optiboot/boot_opt.h rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART0_ALT_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART0_DEF_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART1_ALT_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART1_DEF_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART2_ALT_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART2_DEF_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART3_ALT_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex} (100%) rename megaavr/bootloaders/optiboot/{optiboot_mega0_UART3_DEF_115200_PA7.hex => bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex} (100%) create mode 100755 megaavr/bootloaders/optiboot/makeall create mode 100755 megaavr/bootloaders/optiboot/omake create mode 100755 megaavr/bootloaders/optiboot/omake.bat create mode 100755 megaavr/bootloaders/optiboot/optiboot_x.c create mode 100755 megaavr/bootloaders/optiboot/parse_options.mk create mode 100755 megaavr/bootloaders/optiboot/pin_defs_x.h create mode 100755 megaavr/bootloaders/optiboot/stk500.h diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 79a1346..59aa327 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -147,78 +147,86 @@ menu.bootloader=Bootloader 4809.menu.bootloader.no_bootloader.upload.maximum_size=49152 4809.menu.bootloader.no_bootloader.upload.extra_params= 4809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -4809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +4809.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 4809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 4809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 4809.menu.bootloader.uart0_default.upload.maximum_size=48640 4809.menu.bootloader.uart0_default.upload.protocol=arduino +4809.menu.bootloader.uart0_default.upload.port=UART0_DEF 4809.menu.bootloader.uart0_default.upload.extra_params= 4809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +4809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 4809.menu.bootloader.uart0_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart0_alternative.upload.protocol=arduino +4809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4809.menu.bootloader.uart0_alternative.upload.extra_params= 4809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +4809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 4809.menu.bootloader.uart1_default.upload.maximum_size=48640 4809.menu.bootloader.uart1_default.upload.protocol=arduino +4809.menu.bootloader.uart1_default.upload.port=UART1_DEF 4809.menu.bootloader.uart1_default.upload.extra_params= 4809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +4809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 4809.menu.bootloader.uart1_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart1_alternative.upload.protocol=arduino +4809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4809.menu.bootloader.uart1_alternative.upload.extra_params= 4809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +4809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 4809.menu.bootloader.uart2_default.upload.maximum_size=48640 4809.menu.bootloader.uart2_default.upload.protocol=arduino +4809.menu.bootloader.uart2_default.upload.port=UART2_DEF 4809.menu.bootloader.uart2_default.upload.extra_params= 4809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +4809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 4809.menu.bootloader.uart2_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart2_alternative.upload.protocol=arduino +4809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4809.menu.bootloader.uart2_alternative.upload.extra_params= 4809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +4809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 4809.menu.bootloader.uart3_default.upload.maximum_size=48640 4809.menu.bootloader.uart3_default.upload.protocol=arduino +4809.menu.bootloader.uart3_default.upload.port=UART3_DEF 4809.menu.bootloader.uart3_default.upload.extra_params= 4809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +4809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 4809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 4809.menu.bootloader.uart3_alternative.upload.maximum_size=48640 4809.menu.bootloader.uart3_alternative.upload.protocol=arduino +4809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 4809.menu.bootloader.uart3_alternative.upload.extra_params= 4809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +4809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -349,64 +357,71 @@ menu.bootloader=Bootloader 4808.menu.bootloader.no_bootloader.upload.maximum_size=49152 4808.menu.bootloader.no_bootloader.upload.extra_params= 4808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -4808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +4808.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 4808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 4808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 4808.menu.bootloader.uart0_default.upload.maximum_size=48640 4808.menu.bootloader.uart0_default.upload.protocol=arduino +4808.menu.bootloader.uart0_default.upload.port=UART0_DEF 4808.menu.bootloader.uart0_default.upload.extra_params= 4808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +4808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 4808.menu.bootloader.uart0_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart0_alternative.upload.protocol=arduino +4808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4808.menu.bootloader.uart0_alternative.upload.extra_params= 4808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +4808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 4808.menu.bootloader.uart1_default.upload.maximum_size=48640 4808.menu.bootloader.uart1_default.upload.protocol=arduino +4808.menu.bootloader.uart1_default.upload.port=UART1_DEF 4808.menu.bootloader.uart1_default.upload.extra_params= 4808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +4808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 4808.menu.bootloader.uart1_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart1_alternative.upload.protocol=arduino +4808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4808.menu.bootloader.uart1_alternative.upload.extra_params= 4808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +4808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 4808.menu.bootloader.uart2_default.upload.maximum_size=48640 4808.menu.bootloader.uart2_default.upload.protocol=arduino +4808.menu.bootloader.uart2_default.upload.port=UART2_DEF 4808.menu.bootloader.uart2_default.upload.extra_params= 4808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +4808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 4808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 4808.menu.bootloader.uart2_alternative.upload.maximum_size=48640 4808.menu.bootloader.uart2_alternative.upload.protocol=arduino +4808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4808.menu.bootloader.uart2_alternative.upload.extra_params= 4808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +4808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 + ##################### #### ATmega3209 #### ##################### @@ -535,78 +550,86 @@ menu.bootloader=Bootloader 3209.menu.bootloader.no_bootloader.upload.maximum_size=32768 3209.menu.bootloader.no_bootloader.upload.extra_params= 3209.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -3209.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +3209.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 3209.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 3209.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 3209.menu.bootloader.uart0_default.upload.maximum_size=32256 3209.menu.bootloader.uart0_default.upload.protocol=arduino +3209.menu.bootloader.uart0_default.upload.port=UART0_DEF 3209.menu.bootloader.uart0_default.upload.extra_params= 3209.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +3209.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 3209.menu.bootloader.uart0_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart0_alternative.upload.protocol=arduino +3209.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3209.menu.bootloader.uart0_alternative.upload.extra_params= 3209.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +3209.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 3209.menu.bootloader.uart1_default.upload.maximum_size=32256 3209.menu.bootloader.uart1_default.upload.protocol=arduino +3209.menu.bootloader.uart1_default.upload.port=UART1_DEF 3209.menu.bootloader.uart1_default.upload.extra_params= 3209.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +3209.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 3209.menu.bootloader.uart1_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart1_alternative.upload.protocol=arduino +3209.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3209.menu.bootloader.uart1_alternative.upload.extra_params= 3209.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +3209.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 3209.menu.bootloader.uart2_default.upload.maximum_size=32256 3209.menu.bootloader.uart2_default.upload.protocol=arduino +3209.menu.bootloader.uart2_default.upload.port=UART2_DEF 3209.menu.bootloader.uart2_default.upload.extra_params= 3209.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +3209.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 3209.menu.bootloader.uart2_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart2_alternative.upload.protocol=arduino +3209.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3209.menu.bootloader.uart2_alternative.upload.extra_params= 3209.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +3209.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 3209.menu.bootloader.uart3_default.upload.maximum_size=32256 3209.menu.bootloader.uart3_default.upload.protocol=arduino +3209.menu.bootloader.uart3_default.upload.port=UART3_DEF 3209.menu.bootloader.uart3_default.upload.extra_params= 3209.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +3209.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 3209.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 3209.menu.bootloader.uart3_alternative.upload.maximum_size=32256 3209.menu.bootloader.uart3_alternative.upload.protocol=arduino +3209.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 3209.menu.bootloader.uart3_alternative.upload.extra_params= 3209.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +3209.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -737,60 +760,66 @@ menu.bootloader=Bootloader 3208.menu.bootloader.no_bootloader.upload.maximum_size=32768 3208.menu.bootloader.no_bootloader.upload.extra_params= 3208.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -3208.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +3208.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 3208.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 3208.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 3208.menu.bootloader.uart0_default.upload.maximum_size=32256 3208.menu.bootloader.uart0_default.upload.protocol=arduino +3208.menu.bootloader.uart0_default.upload.port=UART0_DEF 3208.menu.bootloader.uart0_default.upload.extra_params= 3208.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +3208.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 3208.menu.bootloader.uart0_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart0_alternative.upload.protocol=arduino +3208.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3208.menu.bootloader.uart0_alternative.upload.extra_params= 3208.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +3208.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 3208.menu.bootloader.uart1_default.upload.maximum_size=32256 3208.menu.bootloader.uart1_default.upload.protocol=arduino +3208.menu.bootloader.uart1_default.upload.port=UART1_DEF 3208.menu.bootloader.uart1_default.upload.extra_params= 3208.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +3208.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 3208.menu.bootloader.uart1_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart1_alternative.upload.protocol=arduino +3208.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3208.menu.bootloader.uart1_alternative.upload.extra_params= 3208.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +3208.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 3208.menu.bootloader.uart2_default.upload.maximum_size=32256 3208.menu.bootloader.uart2_default.upload.protocol=arduino +3208.menu.bootloader.uart2_default.upload.port=UART2_DEF 3208.menu.bootloader.uart2_default.upload.extra_params= 3208.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +3208.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 3208.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 3208.menu.bootloader.uart2_alternative.upload.maximum_size=32256 3208.menu.bootloader.uart2_alternative.upload.protocol=arduino +3208.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3208.menu.bootloader.uart2_alternative.upload.extra_params= 3208.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +3208.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -923,78 +952,86 @@ menu.bootloader=Bootloader 1609.menu.bootloader.no_bootloader.upload.maximum_size=16384 1609.menu.bootloader.no_bootloader.upload.extra_params= 1609.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -1609.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +1609.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 1609.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 1609.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 1609.menu.bootloader.uart0_default.upload.maximum_size=15872 1609.menu.bootloader.uart0_default.upload.protocol=arduino +1609.menu.bootloader.uart0_default.upload.port=UART0_DEF 1609.menu.bootloader.uart0_default.upload.extra_params= 1609.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +1609.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 1609.menu.bootloader.uart0_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart0_alternative.upload.protocol=arduino +1609.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1609.menu.bootloader.uart0_alternative.upload.extra_params= 1609.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +1609.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 1609.menu.bootloader.uart1_default.upload.maximum_size=15872 1609.menu.bootloader.uart1_default.upload.protocol=arduino +1609.menu.bootloader.uart1_default.upload.port=UART1_DEF 1609.menu.bootloader.uart1_default.upload.extra_params= 1609.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +1609.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 1609.menu.bootloader.uart1_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart1_alternative.upload.protocol=arduino +1609.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1609.menu.bootloader.uart1_alternative.upload.extra_params= 1609.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +1609.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 1609.menu.bootloader.uart2_default.upload.maximum_size=15872 1609.menu.bootloader.uart2_default.upload.protocol=arduino +1609.menu.bootloader.uart2_default.upload.port=UART2_DEF 1609.menu.bootloader.uart2_default.upload.extra_params= 1609.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +1609.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 1609.menu.bootloader.uart2_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart2_alternative.upload.protocol=arduino +1609.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1609.menu.bootloader.uart2_alternative.upload.extra_params= 1609.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +1609.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 1609.menu.bootloader.uart3_default.upload.maximum_size=15872 1609.menu.bootloader.uart3_default.upload.protocol=arduino +1609.menu.bootloader.uart3_default.upload.port=UART3_DEF 1609.menu.bootloader.uart3_default.upload.extra_params= 1609.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +1609.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 1609.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 1609.menu.bootloader.uart3_alternative.upload.maximum_size=15872 1609.menu.bootloader.uart3_alternative.upload.protocol=arduino +1609.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 1609.menu.bootloader.uart3_alternative.upload.extra_params= 1609.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +1609.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1125,60 +1162,66 @@ menu.bootloader=Bootloader 1608.menu.bootloader.no_bootloader.upload.maximum_size=16384 1608.menu.bootloader.no_bootloader.upload.extra_params= 1608.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -1608.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +1608.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 1608.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 1608.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 1608.menu.bootloader.uart0_default.upload.maximum_size=15872 1608.menu.bootloader.uart0_default.upload.protocol=arduino +1608.menu.bootloader.uart0_default.upload.port=UART0_DEF 1608.menu.bootloader.uart0_default.upload.extra_params= 1608.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +1608.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 1608.menu.bootloader.uart0_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart0_alternative.upload.protocol=arduino +1608.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1608.menu.bootloader.uart0_alternative.upload.extra_params= 1608.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +1608.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 1608.menu.bootloader.uart1_default.upload.maximum_size=15872 1608.menu.bootloader.uart1_default.upload.protocol=arduino +1608.menu.bootloader.uart1_default.upload.port=UART1_DEF 1608.menu.bootloader.uart1_default.upload.extra_params= 1608.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +1608.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 1608.menu.bootloader.uart1_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart1_alternative.upload.protocol=arduino +1608.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1608.menu.bootloader.uart1_alternative.upload.extra_params= 1608.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +1608.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 1608.menu.bootloader.uart2_default.upload.maximum_size=15872 1608.menu.bootloader.uart2_default.upload.protocol=arduino +1608.menu.bootloader.uart2_default.upload.port=UART2_DEF 1608.menu.bootloader.uart2_default.upload.extra_params= 1608.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +1608.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 1608.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 1608.menu.bootloader.uart2_alternative.upload.maximum_size=15872 1608.menu.bootloader.uart2_alternative.upload.protocol=arduino +1608.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1608.menu.bootloader.uart2_alternative.upload.extra_params= 1608.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +1608.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1311,78 +1354,86 @@ menu.bootloader=Bootloader 809.menu.bootloader.no_bootloader.upload.maximum_size=8192 809.menu.bootloader.no_bootloader.upload.extra_params= 809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -809.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +809.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 809.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 809.menu.bootloader.uart0_default.upload.maximum_size=7680 809.menu.bootloader.uart0_default.upload.protocol=arduino +809.menu.bootloader.uart0_default.upload.port=UART0_DEF 809.menu.bootloader.uart0_default.upload.extra_params= 809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 809.menu.bootloader.uart0_alternative.upload.maximum_size=7680 809.menu.bootloader.uart0_alternative.upload.protocol=arduino +809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 809.menu.bootloader.uart0_alternative.upload.extra_params= 809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 809.menu.bootloader.uart1_default.upload.maximum_size=7680 809.menu.bootloader.uart1_default.upload.protocol=arduino +809.menu.bootloader.uart1_default.upload.port=UART1_DEF 809.menu.bootloader.uart1_default.upload.extra_params= 809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 809.menu.bootloader.uart1_alternative.upload.maximum_size=7680 809.menu.bootloader.uart1_alternative.upload.protocol=arduino +809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 809.menu.bootloader.uart1_alternative.upload.extra_params= 809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 809.menu.bootloader.uart2_default.upload.maximum_size=7680 809.menu.bootloader.uart2_default.upload.protocol=arduino +809.menu.bootloader.uart2_default.upload.port=UART2_DEF 809.menu.bootloader.uart2_default.upload.extra_params= 809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 809.menu.bootloader.uart2_alternative.upload.maximum_size=7680 809.menu.bootloader.uart2_alternative.upload.protocol=arduino +809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 809.menu.bootloader.uart2_alternative.upload.extra_params= 809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 809.menu.bootloader.uart3_default.upload.maximum_size=7680 809.menu.bootloader.uart3_default.upload.protocol=arduino +809.menu.bootloader.uart3_default.upload.port=UART3_DEF 809.menu.bootloader.uart3_default.upload.extra_params= 809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart3_default.bootloader.file=/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex +809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 809.menu.bootloader.uart3_alternative.upload.maximum_size=7680 809.menu.bootloader.uart3_alternative.upload.protocol=arduino +809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 809.menu.bootloader.uart3_alternative.upload.extra_params= 809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart3_alternative.bootloader.file=/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex +809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1513,59 +1564,65 @@ menu.bootloader=Bootloader 808.menu.bootloader.no_bootloader.upload.maximum_size=8192 808.menu.bootloader.no_bootloader.upload.extra_params= 808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 -808.menu.bootloader.no_bootloader.bootloader.file=/empty/empty.hex +808.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 808.menu.bootloader.uart0_default=Optiboot (UART0 default pins) 808.menu.bootloader.uart0_default.upload.maximum_size=7680 808.menu.bootloader.uart0_default.upload.protocol=arduino +808.menu.bootloader.uart0_default.upload.port=UART0_DEF 808.menu.bootloader.uart0_default.upload.extra_params= 808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart0_default.bootloader.file=/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex +808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 808.menu.bootloader.uart0_alternative.upload.maximum_size=7680 808.menu.bootloader.uart0_alternative.upload.protocol=arduino +808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 808.menu.bootloader.uart0_alternative.upload.extra_params= 808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart0_alternative.bootloader.file=/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex +808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 808.menu.bootloader.uart1_default.upload.maximum_size=7680 808.menu.bootloader.uart1_default.upload.protocol=arduino +808.menu.bootloader.uart1_default.upload.port=UART1_DEF 808.menu.bootloader.uart1_default.upload.extra_params= 808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart1_default.bootloader.file=/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex +808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 808.menu.bootloader.uart1_alternative.upload.maximum_size=7680 808.menu.bootloader.uart1_alternative.upload.protocol=arduino +808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 808.menu.bootloader.uart1_alternative.upload.extra_params= 808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart1_alternative.bootloader.file=/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex +808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 808.menu.bootloader.uart2_default.upload.maximum_size=7680 808.menu.bootloader.uart2_default.upload.protocol=arduino +808.menu.bootloader.uart2_default.upload.port=UART2_DEF 808.menu.bootloader.uart2_default.upload.extra_params= 808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart2_default.bootloader.file=/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex +808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 808.menu.bootloader.uart2_alternative.upload.maximum_size=7680 808.menu.bootloader.uart2_alternative.upload.protocol=arduino +808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 808.menu.bootloader.uart2_alternative.upload.extra_params= 808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart2_alternative.bootloader.file=/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex +808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 diff --git a/megaavr/bootloaders/optiboot/Makefile b/megaavr/bootloaders/optiboot/Makefile new file mode 100755 index 0000000..35d6ea9 --- /dev/null +++ b/megaavr/bootloaders/optiboot/Makefile @@ -0,0 +1,168 @@ +# Makefile for AVR Mega-0 (4809), Tiny-0, and Tiny-1 version of Optiboot +# Bill Westfield, 2019 +# $Id$ +# +# Edit History +# Sep-2019 refactor from the normal AVR Makefile. +# * Copyright 2013-2019 by Bill Westfield. Part of Optiboot. +# * This software is licensed under version 2 of the Gnu Public Licence. +# * See optiboot.c for details. + +HELPTEXT = "\n" +#---------------------------------------------------------------------- +# +# program name should not be changed... +PROGRAM = optiboot_x +MF:= $(MAKEFILE_LIST) + +# export symbols to recursive makes (for ISP) +export + +LDSECTIONS = -Wl,-section-start=.text=0 \ + -Wl,--section-start=.application=0x200 \ + -Wl,--section-start=.version=0x1fe + +BAUD_RATE=115200 + +# Place your avr-gcc tool root here +GCCROOT =/Applications/Arduino.app/Contents/Java/hardware/tools/avr/bin/ + +# +# End of build environment code. + + +CC = $(GCCROOT)avr-gcc +RCC = $(abspath $(CC)) +#$(info wildcard ("$(wildcard $(CC))","")) +ifndef PRODUCTION +$(info Using Compiler at: ${RCC}) +endif + + + + +OPTIMIZE = -Os -fno-split-wide-types -mrelax + +# Override is only needed by avr-lib build system. + +override CFLAGS = -g -Wall $(OPTIMIZE) +override LDFLAGS = $(LDSECTIONS) -Wl,--relax -nostartfiles -nostdlib + +OBJCOPY = $(GCCROOT)avr-objcopy +OBJDUMP = $(GCCROOT)avr-objdump +SIZE = $(GCCROOT)avr-size + +include parse_options.mk + +.PRECIOUS: optiboot_%.elf + +ifndef PRODUCTION +LISTING= $(OBJDUMP) -S +else +LISTING= @true +endif + +ifeq ($(UARTTX), A0) +UART=0 +UARTMUX=DEF +endif +ifeq ($(UARTTX), B0) +UART=3 +UARTMUX=DEF +endif +ifeq ($(UARTTX), C0) +UART=1 +UARTMUX=DEF +endif +ifeq ($(UARTTX), F0) +UART=2 +UARTMUX=DEF +endif +ifeq ($(UARTTX), A4) +UART=0 +UARTMUX=ALT +endif +ifeq ($(UARTTX), B4) +UART=3 +UARTMUX=ALT +endif +ifeq ($(UARTTX), C4) +UART=1 +UARTMUX=ALT +endif +ifeq ($(UARTTX), F4) +UART=2 +UARTMUX=ALT +endif + + +#--------------------------------------------------------------------------- +# "Chip-level Platform" targets. +# A "Chip-level Platform" compiles for a particular chip, but probably does +# not have "standard" values for things like clock speed, LED pin, etc. +# Makes for chip-level platforms should usually explicitly define their +# options like: "make atmega4809 UARTTX=A4 LED=D0" +#--------------------------------------------------------------------------- +# +# Mega0, tiny0, tiny1 don't really have any chip-specific requirements. +# +# Note about fuses: +# The fuses are defined in the source code. There are 9! +# Be sure to use a programmer that will program the fuses from the object file. +# +#--------------------------------------------------------------------------- +# + + + +optiboot_%.hex: optiboot_%.elf + $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O ihex $< $@ + +%.hex: %.elf + $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O ihex $< $@ + +%.elf: optiboot_x.c FORCE + $(CC) $(CFLAGS) $(CPU_OPTIONS) $(LED_OPTIONS) $(UART_OPTIONS) $(COMMON_OPTIONS) $(LDFLAGS) $(PACK_OPT) -mmcu=$(TARGET) -o $@ $< + $(SIZE) $@ + + +#--------------------------------------------------------------------------- +# "Board-level Platform" targets. +# A "Board-level Platform" implies a manufactured platform with a particular +# AVR_FREQ, LED, and so on. Parameters are not particularly changable from +# the "make" command line. +# Most of the board-level platform builds should envoke make recursively +# appropriate specific options +#--------------------------------------------------------------------------- + + +mega0: TARGET=atmega4809 +mega0: bootloaders/mega0/$(BAUD_RATE)/Optiboot_mega0_UART$(UART)_$(UARTMUX)_$(BAUD_RATE)_$(LED).hex + + +#--------------------------------------------------------------------------- +# +# Generic build instructions +# + +FORCE: + +#windows "rm" is dumb and objects to wildcards that don't exist +clean: + @touch __temp_.o __temp_.elf __temp_.lst __temp_.map + @touch __temp_.sym __temp_.lss __temp_.eep __temp_.srec + @touch __temp_.bin __temp_.hex __temp_.tmp.sh + rm -rf *.o *.elf *.lst *.map *.sym *.lss *.eep *.srec *.bin *.hex *.tmp.sh + +clean_asm: + rm -rf *.lst + +%.lst: %.elf FORCE + $(OBJDUMP) -h -S $< > $@ + +%.srec: %.elf FORCE + $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O srec $< $@ + +%.bin: %.elf FORCE + $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O binary $< $@ + diff --git a/megaavr/bootloaders/optiboot/README.TXT b/megaavr/bootloaders/optiboot/README.TXT new file mode 100755 index 0000000..b4db4c9 --- /dev/null +++ b/megaavr/bootloaders/optiboot/README.TXT @@ -0,0 +1,99 @@ +This directory contains the Optiboot small bootloader for AVR +microcontrollers, somewhat modified specifically for the Arduino +environment. + +Optiboot is more fully described here: http://github.com/Optiboot/optiboot +and is the work of Peter Knight (aka Cathedrow), building on work of Jason P +Kyle, Spiff, and Ladyada. More recent maintenance and modifications are by +Bill Westfield (aka WestfW) + +Arduino-specific issues are tracked as part of the Arduino project +at http://github.com/arduino/Arduino + + +Most of the information in this file is superceeded by the wiki content at +https://github.com/Optiboot/optiboot/wiki + +It's till here "just in case." + +------------------------------------------------------------ + +Building optiboot for Arduino. + +Production builds of optiboot for Arduino are done on a Mac in "unix mode" +using CrossPack-AVR-20100115. CrossPack tracks WINAVR (for windows), which +is just a package of avr-gcc and related utilities, so similar builds should +work on Windows or Linux systems. + +One of the Arduino-specific changes is modifications to the makefile to +allow building optiboot using only the tools installed as part of the +Arduino environment, or the Arduino source development tree. All three +build procedures should yield identical binaries (.hex files) (although +this may change if compiler versions drift apart between CrossPack and +the Arduino IDE.) + + +Building Optiboot in the Arduino IDE Install. + +Work in the .../hardware/arduino/bootloaders/optiboot/ and use the +"omake " command, which just generates a command that uses +the arduino-included "make" utility with a command like: + make OS=windows ENV=arduino +or make OS=macosx ENV=arduino +On windows, this assumes you're using the windows command shell. If +you're using a cygwin or mingw shell, or have one of those in your +path, the build will probably break due to slash vs backslash issues. +On a Mac, if you have the developer tools installed, you can use the +Apple-supplied version of make. +The makefile uses relative paths ("../../../tools/" and such) to find +the programs it needs, so you need to work in the existing optiboot +directory (or something created at the same "level") for it to work. + + +Building Optiboot in the Arduino Source Development Install. + +In this case, there is no special shell script, and you're assumed to +have "make" installed somewhere in your path. +Build the Arduino source ("ant build") to unpack the tools into the +expected directory. +Work in Arduino/hardware/arduino/bootloaders/optiboot and use + make OS=windows ENV=arduinodev +or make OS=macosx ENV=arduinodev + + +Programming Chips Using the _isp Targets + +The CPU targets have corresponding ISP targets that will actuall +program the bootloader into a chip. "atmega328_isp" for the atmega328, +for example. These will set the fuses and lock bits as appropriate as +well as uploading the bootloader code. + +ISP Targets in Version 5.0 and later: + +The isp targets are now built using a separate "Makefile.isp" makefile, +which should make modification easier and more obvious. This also fixes +the atmega8_isp target problem mentioned below. The default +configuration assumes an ArduinoISP setup, but you will probably need to +update at least the serial port, since those are different for each +Arduino board and/or system/ + + +ISP Targets in Version 4.6 and earlier: + +The older makefiles default to using a USB programmer, but you can use a +serial programmer like ArduinoISP by changing the appropriate variables +when you invoke make: + + make ISPTOOL=stk500v1 ISPPORT=/dev/tty.usbserial-A20e1eAN \ + ISPSPEED=-b19200 atmega328_isp + +The "atmega8_isp" target does not currently work, because the mega8 +doesn't have the "extended" fuse that the generic ISP target wants to +pass on to avrdude. You'll need to run avrdude manually. + + +Standard Targets + +I've reduced the pre-built and source-version-controlled targets +(.hex and .lst files included in the git repository) to just the +three basic 16MHz targets: atmega8, atmega16, atmega328. diff --git a/megaavr/bootloaders/optiboot/boot_opt.h b/megaavr/bootloaders/optiboot/boot_opt.h new file mode 100755 index 0000000..d0285a6 --- /dev/null +++ b/megaavr/bootloaders/optiboot/boot_opt.h @@ -0,0 +1,101 @@ +// Get all the "standard" definitions from the official boot.h +#include + + +/* + * Implement some optimized versions that will use OUT instead + * of STS to write SPMCSR. + * (However, omit the *_extended_short, since by the time you + * need _extended_, the extra byte shouldn't be relevant any more) + * + * The C preprocessor can not determin at compile time whether SPMCSR is + * "out of range" of the OUT instruction, but we CAN do that in the + * assembler. We can even make it pretty with a macro. + * With this modification, the _short functions should work on cpus + * (like ATmega128) where STS is required. + */ + +asm(".macro __wr_spmcsr p, v \n\t" + ".if \\p > 0x57 \n\t" + "sts \\p, \\v \n\t" + ".else \n\t" + "out \\p-0x20, \\v \n\t" + ".endif \n\t" + ".endm \n"); + + +#if defined(__SPM_REG) + +#define __boot_page_fill_short(address, data) \ +(__extension__({ \ + __asm__ __volatile__ \ + ( \ + "movw r0, %3\n\t" \ + "__wr_spmcsr %0, %1\n\t" \ + "spm\n\t" \ + "clr r1\n\t" \ + : \ + : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ + "r" ((uint8_t)__BOOT_PAGE_FILL), \ + "z" ((uint16_t)address), \ + "r" ((uint16_t)data) \ + : "r0" \ + ); \ +})) + +#define __boot_page_erase_short(address) \ +(__extension__({ \ + __asm__ __volatile__ \ + ( \ + "__wr_spmcsr %0, %1\n\t" \ + "spm\n\t" \ + : \ + : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ + "r" ((uint8_t)__BOOT_PAGE_ERASE), \ + "z" ((uint16_t)address) \ + ); \ +})) + +#define __boot_page_write_short(address) \ +(__extension__({ \ + __asm__ __volatile__ \ + ( \ + "__wr_spmcsr %0, %1\n\t" \ + "spm\n\t" \ + : \ + : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ + "r" ((uint8_t)__BOOT_PAGE_WRITE), \ + "z" ((uint16_t)address) \ + ); \ +})) + +#define __boot_rww_enable_short() \ +(__extension__({ \ + __asm__ __volatile__ \ + ( \ + "__wr_spmcsr %0, %1\n\t" \ + "spm\n\t" \ + : \ + : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ + "r" ((uint8_t)__BOOT_RWW_ENABLE) \ + ); \ +})) + +#endif // __SPM_REG + +#ifndef __boot_page_erase_short + +/* + * if __SPM_REG didn't get defined by now, but we didn't exit it means + * we have some sort of new-fangled chip that post-dates the version + * of boot.h that we know about. In this case, it's possible that the + * standard boot.h still has workable functions, so we'll alias those. + */ + +#define __boot_page_fill_short(address, data) boot_page_fill(address, data) +#define __boot_page_erase_short(address) boot_page_erase(address) +#define __boot_page_write_short(address) boot_page_write(address) +#define __boot_rww_enable_short() boot_rww_enable() + +#endif + diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART0_ALT_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART0_DEF_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART1_ALT_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART1_DEF_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART2_ALT_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART2_DEF_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART3_ALT_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex similarity index 100% rename from megaavr/bootloaders/optiboot/optiboot_mega0_UART3_DEF_115200_PA7.hex rename to megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex diff --git a/megaavr/bootloaders/optiboot/makeall b/megaavr/bootloaders/optiboot/makeall new file mode 100755 index 0000000..f2d7625 --- /dev/null +++ b/megaavr/bootloaders/optiboot/makeall @@ -0,0 +1,9 @@ +# Build for 115200 baud +make mega0 UARTTX=A0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=A4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=B0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=B4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=C0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=C4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=F0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=F4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 diff --git a/megaavr/bootloaders/optiboot/omake b/megaavr/bootloaders/optiboot/omake new file mode 100755 index 0000000..59d23d9 --- /dev/null +++ b/megaavr/bootloaders/optiboot/omake @@ -0,0 +1,9 @@ +#%/bin/bash +if [ -d ../../../tools ]; then + mypath=../../../tools/avr/bin +else + mypath=../../../../tools/avr/bin +fi + +echo $mypath/make OS=macosx ENV=arduino $* +$mypath/make OS=macosx ENV=arduino $* diff --git a/megaavr/bootloaders/optiboot/omake.bat b/megaavr/bootloaders/optiboot/omake.bat new file mode 100755 index 0000000..83538ca --- /dev/null +++ b/megaavr/bootloaders/optiboot/omake.bat @@ -0,0 +1,2 @@ +call .\install-avr-tools.bat +make %* diff --git a/megaavr/bootloaders/optiboot/optiboot_x.c b/megaavr/bootloaders/optiboot/optiboot_x.c new file mode 100755 index 0000000..e916fc9 --- /dev/null +++ b/megaavr/bootloaders/optiboot/optiboot_x.c @@ -0,0 +1,729 @@ +/**********************************************************/ +/* Optiboot bootloader for Arduino */ +/* */ +/* http://optiboot.googlecode.com */ +/* */ +/* Arduino-maintained version : See README.TXT */ +/* http://code.google.com/p/arduino/ */ +/* It is the intent that changes not relevant to the */ +/* Arduino production envionment get moved from the */ +/* optiboot project to the arduino project in "lumps." */ +/* */ +/* Heavily optimised bootloader that is faster and */ +/* smaller than the Arduino standard bootloader */ +/* */ +/* Enhancements: */ +/* Fits in 512 bytes, saving 1.5K of code space */ +/* Higher baud rate speeds up programming */ +/* Written almost entirely in C */ +/* Customisable timeout with accurate timeconstant */ +/* */ +/* What you lose: */ +/* Implements a skeleton STK500 protocol which is */ +/* missing several features including EEPROM */ +/* programming and non-page-aligned writes */ +/* High baud rate breaks compatibility with standard */ +/* Arduino flash settings */ +/* */ +/* Copyright 2013-2019 by Bill Westfield. */ +/* Copyright 2010 by Peter Knight. */ +/* */ +/* 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 2 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, write */ +/* to the Free Software Foundation, Inc., */ +/* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +/* */ +/* Licence can be viewed at */ +/* http://www.fsf.org/licenses/gpl.txt */ +/* */ +/**********************************************************/ + + +/**********************************************************/ +/* */ +/* Optional defines: */ +/* */ +/**********************************************************/ +/* */ +/* BIGBOOT: */ +/* Build a 1k bootloader, not 512 bytes. This turns on */ +/* extra functionality. */ +/* */ +/* BAUD_RATE: */ +/* Set bootloader baud rate. */ +/* */ +/* LED_START_FLASHES: */ +/* Number of LED flashes on bootup. */ +/* */ +/* LED_DATA_FLASH: */ +/* Flash LED when transferring data. For boards without */ +/* TX or RX LEDs, or for people who like blinky lights. */ +/* */ +/* TIMEOUT_MS: */ +/* Bootloader timeout period, in milliseconds. */ +/* 500,1000,2000,4000,8000 supported. */ +/* */ +/* UART: */ +/* UART number (0..n) for devices with more than */ +/* one hardware uart (644P, 1284P, etc) */ +/* */ +/**********************************************************/ + +/**********************************************************/ +/* Version Numbers! */ +/* */ +/* Arduino Optiboot now includes this Version number in */ +/* the source and object code. */ +/* */ +/* Version 3 was released as zip from the optiboot */ +/* repository and was distributed with Arduino 0022. */ +/* Version 4 starts with the arduino repository commit */ +/* that brought the arduino repository up-to-date with */ +/* the optiboot source tree changes since v3. */ +/* : */ +/* Version 9 splits off the Mega0/Xtiny support. */ +/* This is very different from normal AVR because of */ +/* changed peripherals and unified address space. */ +/* */ +/* It would be good if versions implemented outside the */ +/* official repository used an out-of-seqeunce version */ +/* number (like 104.6 if based on based on 4.5) to */ +/* prevent collisions. The CUSTOM_VERSION=n option */ +/* adds n to the high version to facilitate this. */ +/* */ +/**********************************************************/ + +/**********************************************************/ +/* Edit History: */ +/* */ +/* Aug 2019 */ +/* 9.0 Refactored for Mega0/Xtiny from optiboot.c */ +/* : */ +/* 4.1 WestfW: put version number in binary. */ +/**********************************************************/ + +#define OPTIBOOT_MAJVER 9 +#define OPTIBOOT_MINVER 0 + +/* + * OPTIBOOT_CUSTOMVER should be defined (by the makefile) for custom edits + * of optiboot. That way you don't wind up with very different code that + * matches the version number of a "released" optiboot. + */ + +#if !defined(OPTIBOOT_CUSTOMVER) +# define OPTIBOOT_CUSTOMVER 0 +#endif + +unsigned const int __attribute__((section(".version"))) __attribute__((used)) +optiboot_version = 256*(OPTIBOOT_MAJVER + OPTIBOOT_CUSTOMVER) + OPTIBOOT_MINVER; + + +#include +#include + +#if (!defined(__AVR_XMEGA__)) || (__AVR_ARCH__ != 103) +#error CPU not supported by this version of Optiboot. +#include // include a non-existent file to stop compilation +#endif + +/* + * Fuses. + * This is an example of what they'd be like, but some should not + * necessarilly be under control of the bootloader. You'll need a + * a programmer that processes the .fuses section to actually get + * these programmed into the chip. + * The fuses actually REQUIRED by Optiboot are: + * BOOTEND=2, SYSCFG0=(CRC off, RSTPIN as appropriate) + * On some chips, the "reset" pin can be either RESET or GPIO. + * Other also have the UPDI option. If RESET is not enabled we won't be + * able to auto-reset. But if the UPDI pin is set to cause RESET, we + * won't be able to reprogram the chip without HV UPDI (which is uncommon.) + * The settings show will set chips (ie m4809) with RESET/GPIO to use RESET, + * and chips with RESET/GPIO/UPDI to leave it in UPDI mode - the bootloader + * can still be started by a power-on RESET. + */ +FUSES = { + .WDTCFG = 0, /* Watchdog Configuration */ + .BODCFG = FUSE_BODCFG_DEFAULT, /* BOD Configuration */ + .OSCCFG = FREQSEL_20MHZ_gc, /* 20MHz */ +#ifdef FUSE_TCD0CFG_DEFAULT + .TCD0CFG = FUSE_TCD0CFG_DEFAULT, /* TCD0 Configuration */ +#endif +#ifdef RSTPIN + .SYSCFG0 = CRCSRC_NOCRC_gc | RSTPINCFG_RST_gc, /* RESET is enabled */ +#else +# ifdef FUSE_RSTPINCFG_gm // group mask will be defined for triple-func pins + .SYSCFG0 = CRCSRC_NOCRC_gc | RSTPINCFG_UPDI_gc, /* RESET is not yet */ +# else + .SYSCFG0 = CRCSRC_NOCRC_gc, /* RESET is not yet */ +# endif +#endif + .SYSCFG1 = 0x06, /* startup 32ms */ + .APPEND = 0, /* Application Code Section End */ + .BOOTEND = 2 /* Boot Section End */ +}; + + +/* + * optiboot uses several "address" variables that are sometimes byte pointers, + * sometimes word pointers. sometimes 16bit quantities, and sometimes built + * up from 8bit input characters. avr-gcc is not great at optimizing the + * assembly of larger words from bytes, but we can use the usual union to + * do this manually. Expanding it a little, we can also get rid of casts. + */ +typedef union { + uint8_t *bptr; + uint16_t *wptr; + uint16_t word; + uint8_t bytes[2]; +} addr16_t; + + +/* + * pin_defs.h + * This contains most of the rather ugly defines that implement our + * ability to use UART=n and LED=D3, and some avr family bit name differences. + */ +#include "pin_defs_x.h" + +/* + * stk500.h contains the constant definitions for the stk500v1 comm protocol + */ +#include "stk500.h" + +#ifndef LED_START_FLASHES +# define LED_START_FLASHES 0 +#endif + +/* + * The mega-0, tiny-0, and tiny-1 chips all reset to running on the + * internal oscillator, with a prescaler of 6. The internal oscillator + * is either 20MHz or 16MHz, depending on a fuse setting - we can read + * the fuse to figure our which. + * The BRG divisor is also fractional, permitting (afaik) any reasonable + * bit rate between about 1000bps and 1Mbps. + * This makes the BRG generation a bit different than for prior processors. + */ +/* set the UART baud rate defaults */ +#ifndef BAUD_RATE +# define BAUD_RATE 115200L // Highest rate Avrdude win32 will support +#endif +#ifdef F_CPU +# warning F_CPU is ignored for this chip (run from internal osc.) +#endif +#ifdef SINGLESPEED +# warning SINGLESPEED ignored for this chip. +#endif +#ifdef UART +# warning UART is ignored for this chip (use UARTTX=PortPin instead) +#endif + +#define BAUD_SETTING_16 (((16000000/6)*64) / (16L*BAUD_RATE)) +#define BAUD_ACTUAL_16 ((64L*(16000000/6)) / (16L*BAUD_SETTING)) +#define BAUD_SETTING_20 (((20000000/6)*64) / (16L*BAUD_RATE)) +#define BAUD_ACTUAL_20 ((64L*(20000000/6)) / (16L*BAUD_SETTING)) + +#if BAUD_SETTING_16 < 64 // divisor must be > 1. Low bits are fraction. +# error Unachievable baud rate (too fast) BAUD_RATE +#endif + +#if BAUD_SETTING > 65635 +# error Unachievable baud rate (too slow) BAUD_RATE +#endif // baud rate slow check + +/* + * Watchdog timeout translations from human readable to config vals + */ +#ifndef WDTTIME +# define WDTPERIOD WDT_PERIOD_1KCLK_gc // 1 second +#elif WDTTIME == 1 +# define WDTPERIOD WDT_PERIOD_1KCLK_gc // 1 second +#elif WDTTIME == 2 +# define WDTPERIOD WDT_PERIOD_2KCLK_gc // 2 seconds +#elif WDTTIME == 4 +# define WDTPERIOD WDT_PERIOD_4KCLK_gc // 4 seconds +#elif WDTTIME == 8 +# define WDTPERIOD WDT_PERIOD_8KCLK_gc // 8 seconds +#else +#endif + +/* + * We can never load flash with more than 1 page at a time, so we can save + * some code space on parts with smaller pagesize by using a smaller int. + */ +#if MAPPED_PROGMEM_PAGE_SIZE > 255 +typedef uint16_t pagelen_t; +# define GETLENGTH(len) len = getch()<<8; len |= getch() +#else +typedef uint8_t pagelen_t; +# define GETLENGTH(len) (void) getch() /* skip high byte */; len = getch() +#endif + + +/* Function Prototypes + * The main() function is in init9, which removes the interrupt vector table + * we don't need. It is also 'OS_main', which means the compiler does not + * generate any entry or exit code itself (but unlike 'naked', it doesn't + * supress some compile-time options we want.) + */ + +void pre_main(void) __attribute__ ((naked)) __attribute__ ((section (".init8"))); +int main(void) __attribute__ ((OS_main)) __attribute__ ((section (".init9"))) __attribute__((used)); + +void __attribute__((noinline)) __attribute__((leaf)) putch(char); +uint8_t __attribute__((noinline)) __attribute__((leaf)) getch(void) ; +void __attribute__((noinline)) verifySpace(); +void __attribute__((noinline)) watchdogConfig(uint8_t x); + +static void getNch(uint8_t); + +#if LED_START_FLASHES > 0 +static inline void flash_led(uint8_t); +#endif + +#define watchdogReset() __asm__ __volatile__ ("wdr\n") + +/* + * RAMSTART should be self-explanatory. It's bigger on parts with a + * lot of peripheral registers. + * Note that RAMSTART (for optiboot) need not be exactly at the start of RAM. + */ +#if !defined(RAMSTART) // newer versions of gcc avr-libc define RAMSTART +#error RAMSTART not defined. +#endif + +/* everything that needs to run VERY early */ +void pre_main (void) { + // Allow convenient way of calling do_spm function - jump table, + // so entry to this function will always be here, indepedent + // of compilation, features, etc + __asm__ __volatile__ ( + " rjmp 1f\n" +#ifndef APP_NOSPM + " rjmp do_nvmctrl\n" +#else + " ret\n" // if do_spm isn't include, return without doing anything +#endif + "1:\n" + ); +} + +/* main program starts here */ +int main (void) { + uint8_t ch; + + /* + * Making these local and in registers prevents the need for initializing + * them, and also saves space because code no longer stores to memory. + * (initializing address keeps the compiler happy, but isn't really + * necessary, and uses 4 bytes of flash.) + */ + register addr16_t address; + register pagelen_t length; + + // This is the first code to run. + // + // Optiboot C code makes the following assumptions: + // No interrupts will execute + // SP points to RAMEND + + __asm__ __volatile__ ("clr __zero_reg__"); // known-zero required by avr-libc +#define RESET_EXTERNAL (RSTCTRL_EXTRF_bm|RSTCTRL_UPDIRF_bm|RSTCTRL_SWRF_bm) +#ifndef FANCY_RESET_LOGIC + ch = RSTCTRL.RSTFR; // get reset cause + RSTCTRL.RSTFR = ch; // and reset them all! + if (ch & RSTCTRL_WDRF_bm) { + // Start the app. + __asm__ __volatile__ ("mov r2, %0\n" :: "r" (ch)); + watchdogConfig(WDT_PERIOD_OFF_gc); + __asm__ __volatile__ ( + "jmp app\n" + ); + } +#else + /* + * Protect as much Reset Cause as possible for application + * and still skip bootloader if not necessary + */ + ch = RSTCTRL.RSTFR; + if (ch != 0) { + /* + * We want to run the bootloader when an external reset has occurred. + * On these mega0/XTiny chips, there are three types of ext reset: + * reset pin (may not exist), UPDI reset, and SW-request reset. + * One of these reset causes, together with watchdog reset, should + * mean that Optiboot timed out, and it's time to run the app. + * Other reset causes (notably poweron) should run the app directly. + * If a user app wants to utilize and detect watchdog resets, it + * must make sure that the other reset causes are cleared. + */ + if (ch & RSTCTRL_WDRF_bm) { + if (ch & RESET_EXTERNAL) { + /* + * Clear WDRF because it was most probably set by wdr in + * bootloader. It's also needed to avoid loop by broken + * application which could prevent entering bootloader. + */ + RSTCTRL.RSTFR = RSTCTRL_WDRF_bm; + } + } + if (!(ch & RESET_EXTERNAL)) { + /* + * save the reset flags in the designated register. + * This can be saved in a main program by putting code in + * .init0 (which executes before normal c init code) to save R2 + * to a global variable. + */ + __asm__ __volatile__ ("mov r2, %0\n" :: "r" (ch)); + + // switch off watchdog + watchdogConfig(WDT_PERIOD_OFF_gc); + __asm__ __volatile__ ( + "jmp 512\n" + ); + } + } +#endif // Fancy reset cause stuff + + watchdogReset(); +// _PROTECTED_WRITE(CLKCTRL.MCLKCTRLB, 0); // full speed clock + + MYUART_TXPORT.DIR |= MYUART_TXPIN; // set TX pin to output + MYUART_TXPORT.OUT |= MYUART_TXPIN; // and "1" as per datasheet +#if defined (MYUART_PMUX_VAL) + MYPMUX_REG = MYUART_PMUX_VAL; // alternate pinout to use +#endif + if ((FUSE_OSCCFG & FUSE_FREQSEL_gm) == FREQSEL_16MHZ_gc) { + MYUART.BAUD = BAUD_SETTING_16; + } else { + MYUART.BAUD = BAUD_SETTING_20; + } + MYUART.DBGCTRL = 1; // run during debug + MYUART.CTRLC = (USART_CHSIZE_gm & USART_CHSIZE_8BIT_gc); // Async, Parity Disabled, 1 StopBit + MYUART.CTRLA = 0; // Interrupts: all off + MYUART.CTRLB = USART_RXEN_bm | USART_TXEN_bm; + + // Set up watchdog to trigger after a bit + // (nominally:, 1s for autoreset, longer for manual) + watchdogConfig(WDTPERIOD); + +#if (LED_START_FLASHES > 0) || defined(LED_DATA_FLASH) || defined(LED_START_ON) + /* Set LED pin as output */ + LED_PORT.DIR |= LED; +#endif + +#if LED_START_FLASHES > 0 + /* Flash onboard LED to signal entering of bootloader */ +# ifdef LED_INVERT + flash_led(LED_START_FLASHES * 2+1); +# else + flash_led(LED_START_FLASHES * 2); +# endif +#else +#if defined(LED_START_ON) +# ifndef LED_INVERT + /* Turn on LED to indicate starting bootloader (less code!) */ + LED_PORT.OUT |= LED; +# endif +#endif +#endif + + /* Forever loop: exits by causing WDT reset */ + for (;;) { + /* get character from UART */ + ch = getch(); + + if(ch == STK_GET_PARAMETER) { + unsigned char which = getch(); + verifySpace(); + /* + * Send optiboot version as "SW version" + * Note that the references to memory are optimized away. + */ + if (which == STK_SW_MINOR) { + putch(optiboot_version & 0xFF); + } else if (which == STK_SW_MAJOR) { + putch(optiboot_version >> 8); + } else { + /* + * GET PARAMETER returns a generic 0x03 reply for + * other parameters - enough to keep Avrdude happy + */ + putch(0x03); + } + } + else if(ch == STK_SET_DEVICE) { + // SET DEVICE is ignored + getNch(20); + } + else if(ch == STK_SET_DEVICE_EXT) { + // SET DEVICE EXT is ignored + getNch(5); + } + else if(ch == STK_LOAD_ADDRESS) { + // LOAD ADDRESS + address.bytes[0] = getch(); + address.bytes[1] = getch(); + // ToDo: will there be mega-0 chips with >128k of RAM? +/* UPDI chips apparently have byte-addressable FLASH ? + address.word *= 2; // Convert from word address to byte address +*/ + verifySpace(); + } + else if(ch == STK_UNIVERSAL) { +#ifndef RAMPZ + // UNIVERSAL command is ignored + getNch(4); + putch(0x00); +#endif + } + /* Write memory, length is big endian and is in bytes */ + else if(ch == STK_PROG_PAGE) { + // PROGRAM PAGE - any kind of page! + uint8_t desttype; + + GETLENGTH(length); + desttype = getch(); + + if (desttype == 'F') { + address.word += MAPPED_PROGMEM_START; + } else { + address.word += MAPPED_EEPROM_START; + } + // TODO: user row? + + do { + *(address.bptr++) = getch(); + } while (--length); + + // Read command terminator, start reply + verifySpace(); + /* + * Actually Write the buffer to flash (and wait for it to finish.) + */ + _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_PAGEERASEWRITE_gc); + while (NVMCTRL.STATUS & (NVMCTRL_FBUSY_bm|NVMCTRL_EEBUSY_bm)) + ; // wait for flash and EEPROM not busy, just in case. + } + /* Read memory block mode, length is big endian. */ + else if(ch == STK_READ_PAGE) { + uint8_t desttype; + GETLENGTH(length); + + desttype = getch(); + + verifySpace(); + if (desttype == 'F') { + address.word += MAPPED_PROGMEM_START; + } else { + address.word += MAPPED_EEPROM_START; + } + // TODO: user row? + + do { + putch(*(address.bptr++)); + } while (--length); + } + + /* Get device signature bytes */ + else if(ch == STK_READ_SIGN) { + // READ SIGN - return what Avrdude wants to hear + verifySpace(); + putch(SIGROW_DEVICEID0); + putch(SIGROW_DEVICEID1); + putch(SIGROW_DEVICEID2); + } + else if (ch == STK_LEAVE_PROGMODE) { /* 'Q' */ + // Adaboot no-wait mod + watchdogConfig(WDT_PERIOD_8CLK_gc); + verifySpace(); + } + else { + // This covers the response to commands like STK_ENTER_PROGMODE + verifySpace(); + } + putch(STK_OK); + } +} + +void putch (char ch) { + while (0 == (MYUART.STATUS & USART_DREIF_bm)) + ; + MYUART.TXDATAL = ch; +} + +uint8_t getch (void) { + uint8_t ch, flags; + while (!(MYUART.STATUS & USART_RXCIF_bm)) + ; + flags = MYUART.RXDATAH; + ch = MYUART.RXDATAL; + if ((flags & USART_FERR_bm) == 0) + watchdogReset(); +#ifdef LED_DATA_FLASH + LED_PORT.IN |= LED; +#endif + + return ch; +} + +void getNch (uint8_t count) { + do getch(); while (--count); + verifySpace(); +} + +void verifySpace () { + if (getch() != CRC_EOP) { + watchdogConfig(WDT_PERIOD_8CLK_gc); // shorten WD timeout + while (1) // and busy-loop so that WD causes + ; // a reset and app start. + } + putch(STK_INSYNC); +} + +#if LED_START_FLASHES > 0 +void flash_led (uint8_t count) { + uint16_t delay; // at 20MHz/6, a 16bit delay counter is enough + while (count--) { + LED_PORT.IN |= LED; + // delay assuming 20Mhz OSC. It's only to "look about right", anyway. + for (delay = ((20E6/6)/150); delay; delay--) { + watchdogReset(); + if (MYUART.STATUS & USART_RXCIF_bm) + return; + } + } + watchdogReset(); // for breakpointing +} +#endif + + +/* + * Change the watchdog configuration. + * Could be a new timeout, could be off... + */ +void watchdogConfig (uint8_t x) { + while(WDT.STATUS & WDT_SYNCBUSY_bm) + ; // Busy wait for sycnhronization is required! + _PROTECTED_WRITE(WDT.CTRLA, x); +} + + +#ifndef APP_NOSPM + +/* + * Separate function for doing spm stuff + * It's needed for application to do SPM, as SPM instruction works only + * from bootloader. + * + * How it works: + * - do SPM + * - wait for SPM to complete + * - if chip have RWW/NRWW sections it does additionaly: + * - if command is WRITE or ERASE, AND data=0 then reenable RWW section + * + * In short: + * If you play erase-fill-write, just set data to 0 in ERASE and WRITE + * If you are brave, you have your code just below bootloader in NRWW section + * you could do fill-erase-write sequence with data!=0 in ERASE and + * data=0 in WRITE + */ +static void do_nvmctrl(uint16_t address, uint8_t command, uint16_t data) __attribute__ ((used)); +static void do_nvmctrl (uint16_t address, uint8_t command, uint16_t data) { + _PROTECTED_WRITE(WDT.CTRLA, command); + while (NVMCTRL.STATUS & (NVMCTRL_FBUSY_bm|NVMCTRL_EEBUSY_bm)) + ; // wait for flash and EEPROM not busy, just in case. +} +#endif + + + +#ifdef BIGBOOT +/* + * Optiboot is designed to fit in 512 bytes, with a minimum feature set. + * Some chips have a minimum bootloader size of 1024 bytes, and sometimes + * it is desirable to add extra features even though 512bytes is exceedded. + * In that case, the BIGBOOT can be used. + * Our extra features so far don't come close to filling 1k, so we can + * add extra "frivolous" data to the image. In particular, we can add + * information about how Optiboot was built (which options were selected, + * what version, all in human-readable form (and extractable from the + * binary with avr-strings.) + * + * This can always be removed or trimmed if more actual program space + * is needed in the future. Currently the data occupies about 160 bytes, + */ +#define xstr(s) str(s) +#define str(s) #s +#define OPTFLASHSECT __attribute__((section(".fini8"))) +#define OPT2FLASH(o) OPTFLASHSECT const char f##o[] = #o "=" xstr(o) + + +#ifdef LED_START_FLASHES +OPT2FLASH(LED_START_FLASHES); +#endif +#ifdef LED_DATA_FLASH +OPT2FLASH(LED_DATA_FLASH); +#endif +#ifdef LED_START_ON +OPT2FLASH(LED_START_ON); +#endif +#ifdef LED_NAME +OPTFLASHSECT const char f_LED[] = "LED=" LED_NAME; +#endif + +#ifdef SUPPORT_EEPROM +OPT2FLASH(SUPPORT_EEPROM); +#endif + +#ifdef BAUD_RATE +OPT2FLASH(BAUD_RATE); +#endif +#ifdef UARTTX +OPTFLASHSECT const char f_uart[] = "UARTTX=" UART_NAME; +#endif + +OPTFLASHSECT const char f_date[] = "Built:" __DATE__ ":" __TIME__; +#ifdef BIGBOOT +OPT2FLASH(BIGBOOT); +#endif +OPTFLASHSECT const char f_device[] = "Device=" xstr(__AVR_DEVICE_NAME__); +#ifdef OPTIBOOT_CUSTOMVER +# if OPTIBOOT_CUSTOMVER != 0 +OPT2FLASH(OPTIBOOT_CUSTOMVER); +# endif +#endif +OPTFLASHSECT const char f_version[] = "Version=" xstr(OPTIBOOT_MAJVER) "." xstr(OPTIBOOT_MINVER); + +#endif + +// Dummy application that will loop back into the bootloader if not overwritten +// This gives the bootloader somewhere to jump, and by referencing otherwise +// unused variables/functions in the bootloader, it prevents them from being +// omitted by the linker, with fewer mysterious link options. +void __attribute__((section( ".application"))) + __attribute__((naked)) app(); +void app() +{ + uint8_t ch; + + ch = RSTCTRL.RSTFR; + RSTCTRL.RSTFR = ch; // reset causes + *(volatile uint16_t *)(&optiboot_version); // reference the version + do_nvmctrl(0, NVMCTRL_CMD_PAGEBUFCLR_gc, 0); // reference this function! + __asm__ __volatile__ ("jmp 0"); // similar to running off end of memory +// _PROTECTED_WRITE(RSTCTRL.SWRR, 1); // cause new reset +} diff --git a/megaavr/bootloaders/optiboot/parse_options.mk b/megaavr/bootloaders/optiboot/parse_options.mk new file mode 100755 index 0000000..7da4ff2 --- /dev/null +++ b/megaavr/bootloaders/optiboot/parse_options.mk @@ -0,0 +1,138 @@ +# Make command-line Options for Optiboot, Optiboot-Mega0 +# Permit commands like "make atmega4809 LED_START_FLASHES=10" to pass the +# appropriate parameters ("-DLED_START_FLASHES=10") to gcc +# + +ifdef PRODUCTION +ifneq ($(PRODUCTION),0) +VERSION_CMD = -DPRODUCTION=1 +endif +dummy = FORCE +endif + + +# Build Options + +ifdef CUSTOM_VERSION +ifneq ($(CUSTOM_VERSION), 0) +VERSION_CMD = -DOPTIBOOT_CUSTOMVER=$(CUSTOM_VERSION) +else +VERSION_CMD = -DPRODUCTION=1 +endif +dummy = FORCE +endif + +# BIGBOOT: Include extra features, up to 1K. +ifdef BIGBOOT +ifneq ($(BIGBOOT), 0) +BIGBOOT_CMD = -DBIGBOOT=1 +dummy = FORCE +endif +endif + +ifdef SUPPORT_EEPROM +ifneq ($(SUPPORT_EEPROM), 0) +SUPPORT_EEPROM_CMD = -DSUPPORT_EEPROM +dummy = FORCE +endif +endif + +ifdef NO_APP_SPM +ifneq ($(NO_APP_SPM),0) +APPSPM_CMD = -DAPP_NOSPM=1 +endif +endif + + +# LED options + +ifdef LED +LED_CMD = -DLED=$(LED) +dummy = FORCE +endif + +ifdef LED_START_FLASHES +LED_START_FLASHES_CMD = -DLED_START_FLASHES=$(LED_START_FLASHES) +dummy = FORCE +else +LED_START_FLASHES_CMD = -DLED_START_FLASHES=3 +endif + +ifdef LED_DATA_FLASH +ifneq ($(LED_DATA_FLASH), 0) +LED_DATA_FLASH_CMD = -DLED_DATA_FLASH=1 +dummy = FORCE +endif +endif + +ifdef LED_START_ON +ifneq ($(LED_START_ON), 0) +LED_START_ON_CMD = -DLED_START_ON=1 +endif +dummy = FORCE +endif + +ifdef LED_INVERT +ifneq ($(LED_INVERT), 0) +LEDINV_CMD = -DLED_INVERT=1 +endif +dummy = FORCE +endif + + +# UART options + +ifdef BAUD_RATE +BAUD_RATE_CMD = -DBAUD_RATE=$(BAUD_RATE) +dummy = FORCE +else +BAUD_RATE_CMD = -DBAUD_RATE=115200 +endif + +ifdef SOFT_UART +ifneq ($(SOFT_UART), 0) +SOFT_UART_CMD = -DSOFT_UART=1 +dummy = FORCE +endif +endif + +ifdef SINGLESPEED +ifneq ($(SINGLESPEED), 0) +SS_CMD = -DSINGLESPEED=1 +endif +endif + + +#CPU Options + +ifdef TIMEOUT +TIMEOUT_CMD = -DWDTTIME=$(TIMEOUT) +dummy = FORCE +endif + +ifdef RESETPIN +RESETPIN_CMD = -DRSTPIN=$(RESETPIN) +dummy = FORCE +endif + +ifdef AVR_FREQ +FCPU_CMD = -DF_CPU=$(AVR_FREQ) +dummy = FORCE +endif + + + +LED_OPTIONS = $(LED_START_FLASHES_CMD) $(LED_DATA_FLASH_CMD) $(LED_CMD) $(LED_START_ON_CMD) $(LEDINV_CMD) +CPU_OPTIONS = $(RESETPIN_CMD) $(TIMEOUT_CMD) $(FCPU_CMD) +COMMON_OPTIONS = $(BIGBOOT_CMD) $(APPSPM_CMD) $(VERSION_CMD) +COMMON_OPTIONS += $(SUPPORT_EEPROM_CMD) + +#UART is handled separately and only passed for devices with more than one. +ifdef UART +UART_CMD = -DUART=$(UART) +endif +ifdef UARTTX +UART_CMD = -DUARTTX=$(UARTTX) +endif + +UART_OPTIONS = $(UART_CMD) $(BAUD_RATE_CMD) $(SOFT_UART_CMD) $(SS_CMD) diff --git a/megaavr/bootloaders/optiboot/pin_defs_x.h b/megaavr/bootloaders/optiboot/pin_defs_x.h new file mode 100755 index 0000000..a51c0f0 --- /dev/null +++ b/megaavr/bootloaders/optiboot/pin_defs_x.h @@ -0,0 +1,815 @@ +/* + * pin_defs.h + * optiboot helper defining the default pin assignments (LED, SOFT_UART) + * for the various chips that are supported. This also has some ugly macros + * for selecting among various UARTs and LED possibilities using command-line + * defines like "UART=2 LED=B5" + * + * Copyright 2013-2015 by Bill Westfield. + * Copyright 2010 by Peter Knight. + * This software is licensed under version 2 of the Gnu Public Licence. + * See optiboot.c for details. + */ + + +/* + * ------------------------------------------------------------------------ + * A bunch of macros to enable the LED to be specifed as "B5" for bit 5 + * of port B, and similar. + * We define symbols for all the legal combination of port/bit on a chip, + * and do pre-processor tests to see if there's a match. This ends up + * being very verbose, but it is pretty easy to generate semi-automatically. + * (We wouldn't need this if the preprocessor could do string compares.) + */ + +// Symbols for each PortA bit. +#define A0 0x100 +#define A1 0x101 +#define A2 0x102 +#define A3 0x103 +#define A4 0x104 +#define A5 0x105 +#define A6 0x106 +#define A7 0x107 +// If there is no PORTA on this chip, don't allow these to be used +// (and indicate the error by redefining LED) +#if !defined(PORTA) +#if LED >= A0 && LED <= A7 +#undef LED +#define LED -1 +#endif +#endif + +#define B0 0x200 +#define B1 0x201 +#define B2 0x202 +#define B3 0x203 +#define B4 0x204 +#define B5 0x205 +#define B6 0x206 +#define B7 0x207 +#if !defined(PORTB) +#if LED >= B0 && LED <= B7 +#undef LED +#define LED -1 +#endif +#endif + +#define C0 0x300 +#define C1 0x301 +#define C2 0x302 +#define C3 0x303 +#define C4 0x304 +#define C5 0x305 +#define C6 0x306 +#define C7 0x307 +#if !(defined(PORTC)) +#if LED >= C0 && LED <= C7 +#undef LED +#define LED -1 +#endif +#endif + +#define D0 0x400 +#define D1 0x401 +#define D2 0x402 +#define D3 0x403 +#define D4 0x404 +#define D5 0x405 +#define D6 0x406 +#define D7 0x407 +#if !(defined(PORTD)) +#if LED >= D0 && LED <= D7 +#undef LED +#define LED -1 +#endif +#endif + +#define E0 0x500 +#define E1 0x501 +#define E2 0x502 +#define E3 0x503 +#define E4 0x504 +#define E5 0x505 +#define E6 0x506 +#define E7 0x507 +#if !(defined(PORTE)) +#if LED >= E0 && LED <= E7 +#undef LED +#define LED -1 +#endif +#endif + +#define F0 0x600 +#define F1 0x601 +#define F2 0x602 +#define F3 0x603 +#define F4 0x604 +#define F5 0x605 +#define F6 0x606 +#define F7 0x607 +#if !(defined(PORTF)) +#if LED >= F0 && LED <= F7 +#undef LED +#define LED -1 +#endif +#endif + +#define G0 0x700 +#define G1 0x701 +#define G2 0x702 +#define G3 0x703 +#define G4 0x704 +#define G5 0x705 +#define G6 0x706 +#define G7 0x707 +#if !defined(PORTG) +#if LED >= G0 && LED <= G7 +#undef LED +#define LED -1 +#endif +#endif + +#define H0 0x800 +#define H1 0x801 +#define H2 0x802 +#define H3 0x803 +#define H4 0x804 +#define H5 0x805 +#define H6 0x806 +#define H7 0x807 +#if !(defined(PORTH)) +#if LED >= H0 && LED <= H7 +#undef LED +#define LED -1 +#endif +#endif + +#define J0 0xA00 +#define J1 0xA01 +#define J2 0xA02 +#define J3 0xA03 +#define J4 0xA04 +#define J5 0xA05 +#define J6 0xA06 +#define J7 0xA07 +#if !(defined(PORTJ)) +#if LED >= J0 && LED <= J7 +#undef LED +#define LED -1 +#endif +#endif + +#define K0 0xB00 +#define K1 0xB01 +#define K2 0xB02 +#define K3 0xB03 +#define K4 0xB04 +#define K5 0xB05 +#define K6 0xB06 +#define K7 0xB07 +#if !(defined(PORTK)) +#if LED >= K0 && LED <= K7 +#undef LED +#define LED -1 +#endif +#endif + +#define L0 0xC00 +#define L1 0xC01 +#define L2 0xC02 +#define L3 0xC03 +#define L4 0xC04 +#define L5 0xC05 +#define L6 0xC06 +#define L7 0xC07 +#if !(defined(PORTL)) +#if LED >= L0 && LED <= L7 +#undef LED +#define LED -1 +#endif +#endif + + +/* + * A statement like "#if LED == B0" will evaluation (in the preprocessor) + * to #if C0 == B0, and then to #if 0x301 == 0x201 + */ +#if LED == B0 +#define LED_NAME "B0" +#undef LED +#define LED_PORT VPORTB +#define LED (1< Date: Tue, 12 Nov 2019 13:53:59 +0100 Subject: [PATCH 115/351] Fix period of PWM timers so that the value 0 is to LOW, the value 255 is HIGH, and any value inbetween is a corresponding PWM pulse. The prevous behaviour was that the range was 0 to 256, which is not in accordance to the Arduino standard. --- megaavr/cores/coreX-corefiles/timers.h | 2 +- megaavr/cores/coreX-corefiles/wiring_analog.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/timers.h b/megaavr/cores/coreX-corefiles/timers.h index 5030896..d380563 100644 --- a/megaavr/cores/coreX-corefiles/timers.h +++ b/megaavr/cores/coreX-corefiles/timers.h @@ -5,7 +5,7 @@ #define TIME_TRACKING_TIMER_DIVIDER 1 // Timer F_CPU Clock divider (can be 1 or 2) #define TIME_TRACKING_TIMER_COUNT (F_CPU/(1000*TIME_TRACKING_TIMER_DIVIDER)) // Should correspond to exactly 1 ms, i.e. millis() -#define PWM_TIMER_PERIOD 0xFF // For frequency +#define PWM_TIMER_PERIOD 0xFE // For frequency #define PWM_TIMER_COMPARE 0x80 // For duty cycle #endif diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index d9a0cf3..3993df8 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -130,11 +130,11 @@ void analogWrite(uint8_t pin, int val) // call for the analog output pins. pinMode(pin, OUTPUT); - if(val < 1){ /* if zero or negative drive digital low */ + if(val <= 0){ /* if zero or negative drive digital low */ digitalWrite(pin, LOW); - } else if(val > 255){ /* if max or greater drive digital high */ + } else if(val >= 255){ /* if max or greater drive digital high */ digitalWrite(pin, HIGH); From 330445d1cfaaadeeecdf1af47a3daf403bef5a01 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 14 Nov 2019 23:11:06 +0100 Subject: [PATCH 116/351] Move flush() from Stream.h to Print.h Done according to the official Arduino API repo --- megaavr/cores/coreX-corefiles/api/Print.h | 2 ++ megaavr/cores/coreX-corefiles/api/Stream.h | 1 - 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/Print.h b/megaavr/cores/coreX-corefiles/api/Print.h index 9001cfb..e8a64d4 100644 --- a/megaavr/cores/coreX-corefiles/api/Print.h +++ b/megaavr/cores/coreX-corefiles/api/Print.h @@ -80,5 +80,7 @@ class Print int16_t printf(const char *format, ...); int16_t printf(const __FlashStringHelper *format, ...); + + virtual void flush() { /* Empty implementation for backward compatibility */ } }; diff --git a/megaavr/cores/coreX-corefiles/api/Stream.h b/megaavr/cores/coreX-corefiles/api/Stream.h index 7dbe2fd..ef59370 100644 --- a/megaavr/cores/coreX-corefiles/api/Stream.h +++ b/megaavr/cores/coreX-corefiles/api/Stream.h @@ -58,7 +58,6 @@ class Stream : public Print virtual int available() = 0; virtual int read() = 0; virtual int peek() = 0; - virtual void flush() = 0; Stream() {_timeout=1000;} From 937dee4657dd0b303d63c50a80eb63e8f96a79b3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 14 Nov 2019 23:12:27 +0100 Subject: [PATCH 117/351] Add availableForWrite() --- megaavr/cores/coreX-corefiles/api/Print.h | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/api/Print.h b/megaavr/cores/coreX-corefiles/api/Print.h index e8a64d4..72b1467 100644 --- a/megaavr/cores/coreX-corefiles/api/Print.h +++ b/megaavr/cores/coreX-corefiles/api/Print.h @@ -53,6 +53,10 @@ class Print return write((const uint8_t *)buffer, size); } + // default to zero, meaning "a single write may block" + // should be overriden by subclasses with buffering + virtual int availableForWrite() { return 0; } + size_t print(const __FlashStringHelper *); size_t print(const String &); size_t print(const char[]); @@ -77,10 +81,10 @@ class Print size_t println(double, int = 2); size_t println(const Printable&); size_t println(void); - + int16_t printf(const char *format, ...); int16_t printf(const __FlashStringHelper *format, ...); - + virtual void flush() { /* Empty implementation for backward compatibility */ } }; From a6dfa226d17550ee40df1fcd9e07c86073307f2f Mon Sep 17 00:00:00 2001 From: Hans Date: Thu, 14 Nov 2019 23:52:05 +0100 Subject: [PATCH 118/351] Add info about printf --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index 6cb7fe0..c205033 100644 --- a/README.md +++ b/README.md @@ -14,6 +14,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [Supported clock frequencies](#supported-clock-frequencies) * [BOD option](#bod-option) * [Reset pin](#reset-pin) +* [Printf support](#printf-support) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -100,6 +101,12 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. Note that the reset pin cannot be usd as a GPIO when using a bootloader +## Printf support +Unlike the official Arduino core, MegaCoreX has printf support out of the box. If you're not familiar with printf you should probably [read this first](https://www.tutorialspoint.com/c_standard_library/c_function_printf.htm). It's added to the Print class and will work with all libraries that inherit Print. Printf is a standard C function that lets you format text much easier than using Arduino's built-in print and println. Note that this implementation of printf will NOT print floats or doubles. This is a limitation of the avr-libc printf implementation on AVR microcontrollers, and nothing I can easily fix. + +If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other libraries that inherit the Print class (and thus supports printf) are SoftwareSerial and the LiquidCrystal LCD library. + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. From 8bcf269c4d412c3fab46e381c66e92819d85b089 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bart=C5=82omiej=20Zimo=C5=84?= Date: Wed, 20 Nov 2019 18:42:07 +0100 Subject: [PATCH 119/351] update avrdude path related to #55 --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 7bc2bee..c69f606 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -92,7 +92,7 @@ recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} { # ------------------------------ tools.avrdude.path={runtime.tools.avrdude.path} -tools.avrdude.cmd.path={path}/bin/avrdude +tools.avrdude.cmd.path={runtime.tools.avrdude.path}/bin/avrdude tools.avrdude.config.path={runtime.platform.path}/avrdude.conf tools.avrdude.network_cmd={runtime.tools.arduinoOTA.path}/bin/arduinoOTA From 391a41cd37c718f0a61760b0d10a8ca6257cb879 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 25 Nov 2019 16:47:17 +0100 Subject: [PATCH 120/351] Fix incorrect bootloader file name Fix #57 --- megaavr/boards.txt | 112 ++++++++++++++++++++++----------------------- 1 file changed, 56 insertions(+), 56 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 59aa327..f0172b0 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -156,7 +156,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_default.upload.port=UART0_DEF 4809.menu.bootloader.uart0_default.upload.extra_params= 4809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -166,7 +166,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4809.menu.bootloader.uart0_alternative.upload.extra_params= 4809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -176,7 +176,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_default.upload.port=UART1_DEF 4809.menu.bootloader.uart1_default.upload.extra_params= 4809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -186,7 +186,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4809.menu.bootloader.uart1_alternative.upload.extra_params= 4809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -196,7 +196,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_default.upload.port=UART2_DEF 4809.menu.bootloader.uart2_default.upload.extra_params= 4809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -206,7 +206,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4809.menu.bootloader.uart2_alternative.upload.extra_params= 4809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -216,7 +216,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_default.upload.port=UART3_DEF 4809.menu.bootloader.uart3_default.upload.extra_params= 4809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -226,7 +226,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 4809.menu.bootloader.uart3_alternative.upload.extra_params= 4809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -4809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -366,7 +366,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_default.upload.port=UART0_DEF 4808.menu.bootloader.uart0_default.upload.extra_params= 4808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -376,7 +376,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4808.menu.bootloader.uart0_alternative.upload.extra_params= 4808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -386,7 +386,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_default.upload.port=UART1_DEF 4808.menu.bootloader.uart1_default.upload.extra_params= 4808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -396,7 +396,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4808.menu.bootloader.uart1_alternative.upload.extra_params= 4808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -406,7 +406,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_default.upload.port=UART2_DEF 4808.menu.bootloader.uart2_default.upload.extra_params= 4808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -416,7 +416,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4808.menu.bootloader.uart2_alternative.upload.extra_params= 4808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -4808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +4808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -559,7 +559,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_default.upload.port=UART0_DEF 3209.menu.bootloader.uart0_default.upload.extra_params= 3209.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -569,7 +569,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3209.menu.bootloader.uart0_alternative.upload.extra_params= 3209.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -579,7 +579,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_default.upload.port=UART1_DEF 3209.menu.bootloader.uart1_default.upload.extra_params= 3209.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -589,7 +589,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3209.menu.bootloader.uart1_alternative.upload.extra_params= 3209.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -599,7 +599,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_default.upload.port=UART2_DEF 3209.menu.bootloader.uart2_default.upload.extra_params= 3209.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -609,7 +609,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3209.menu.bootloader.uart2_alternative.upload.extra_params= 3209.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -619,7 +619,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_default.upload.port=UART3_DEF 3209.menu.bootloader.uart3_default.upload.extra_params= 3209.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -629,7 +629,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 3209.menu.bootloader.uart3_alternative.upload.extra_params= 3209.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -3209.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3209.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -769,7 +769,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_default.upload.port=UART0_DEF 3208.menu.bootloader.uart0_default.upload.extra_params= 3208.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -779,7 +779,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3208.menu.bootloader.uart0_alternative.upload.extra_params= 3208.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -789,7 +789,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_default.upload.port=UART1_DEF 3208.menu.bootloader.uart1_default.upload.extra_params= 3208.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -799,7 +799,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3208.menu.bootloader.uart1_alternative.upload.extra_params= 3208.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -809,7 +809,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_default.upload.port=UART2_DEF 3208.menu.bootloader.uart2_default.upload.extra_params= 3208.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -819,7 +819,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3208.menu.bootloader.uart2_alternative.upload.extra_params= 3208.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -3208.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +3208.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -961,7 +961,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_default.upload.port=UART0_DEF 1609.menu.bootloader.uart0_default.upload.extra_params= 1609.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -971,7 +971,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1609.menu.bootloader.uart0_alternative.upload.extra_params= 1609.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -981,7 +981,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_default.upload.port=UART1_DEF 1609.menu.bootloader.uart1_default.upload.extra_params= 1609.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -991,7 +991,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1609.menu.bootloader.uart1_alternative.upload.extra_params= 1609.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1001,7 +1001,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_default.upload.port=UART2_DEF 1609.menu.bootloader.uart2_default.upload.extra_params= 1609.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1011,7 +1011,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1609.menu.bootloader.uart2_alternative.upload.extra_params= 1609.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1021,7 +1021,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_default.upload.port=UART3_DEF 1609.menu.bootloader.uart3_default.upload.extra_params= 1609.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -1031,7 +1031,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 1609.menu.bootloader.uart3_alternative.upload.extra_params= 1609.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -1609.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1609.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1171,7 +1171,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_default.upload.port=UART0_DEF 1608.menu.bootloader.uart0_default.upload.extra_params= 1608.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1181,7 +1181,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1608.menu.bootloader.uart0_alternative.upload.extra_params= 1608.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1191,7 +1191,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_default.upload.port=UART1_DEF 1608.menu.bootloader.uart1_default.upload.extra_params= 1608.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1201,7 +1201,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1608.menu.bootloader.uart1_alternative.upload.extra_params= 1608.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1211,7 +1211,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_default.upload.port=UART2_DEF 1608.menu.bootloader.uart2_default.upload.extra_params= 1608.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1221,7 +1221,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1608.menu.bootloader.uart2_alternative.upload.extra_params= 1608.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -1608.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +1608.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1363,7 +1363,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_default.upload.port=UART0_DEF 809.menu.bootloader.uart0_default.upload.extra_params= 809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1373,7 +1373,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 809.menu.bootloader.uart0_alternative.upload.extra_params= 809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1383,7 +1383,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_default.upload.port=UART1_DEF 809.menu.bootloader.uart1_default.upload.extra_params= 809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1393,7 +1393,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 809.menu.bootloader.uart1_alternative.upload.extra_params= 809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1403,7 +1403,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_default.upload.port=UART2_DEF 809.menu.bootloader.uart2_default.upload.extra_params= 809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1413,7 +1413,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 809.menu.bootloader.uart2_alternative.upload.extra_params= 809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1423,7 +1423,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_default.upload.port=UART3_DEF 809.menu.bootloader.uart3_default.upload.extra_params= 809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 -809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -1433,7 +1433,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 809.menu.bootloader.uart3_alternative.upload.extra_params= 809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 -809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1573,7 +1573,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_default.upload.port=UART0_DEF 808.menu.bootloader.uart0_default.upload.extra_params= 808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1583,7 +1583,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 808.menu.bootloader.uart0_alternative.upload.extra_params= 808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1593,7 +1593,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_default.upload.port=UART1_DEF 808.menu.bootloader.uart1_default.upload.extra_params= 808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1603,7 +1603,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 808.menu.bootloader.uart1_alternative.upload.extra_params= 808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1613,7 +1613,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_default.upload.port=UART2_DEF 808.menu.bootloader.uart2_default.upload.extra_params= 808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 -808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1623,6 +1623,6 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 808.menu.bootloader.uart2_alternative.upload.extra_params= 808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 -808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/optiboot_mega0_{upload.port}_{upload.speed}_A7.hex +808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 From fc1bea759b46474bc5d2108d8249b9f41ef3a68b Mon Sep 17 00:00:00 2001 From: Hans Date: Fri, 6 Dec 2019 09:41:17 +0100 Subject: [PATCH 121/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index c69f606..97c18fa 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.0 +version=1.0.1 # AVR compile variables # --------------------- From 3b4c7be15188d627de518af92f0abf0b972d9a5c Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 5 Jan 2020 00:55:46 +0100 Subject: [PATCH 122/351] Add boards manager installation --- README.md | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index c205033..9d595e5 100644 --- a/README.md +++ b/README.md @@ -226,7 +226,18 @@ Available pin combinations for the *Nano Every* pinout are: ## How to install #### Boards Manager Installation -*Not yet implemented* +* Open Arduino IDE. +* Open the **File > Preferences** menu item. +* Enter the following URL in **Additional Boards Manager URLs**: + ``` + https://mcudude.github.io/MegaCoreX/package_MCUdude_MegaCoreX_index.json + ``` +* Separate the URLs using a comma ( **,** ) if you have more than one URL +* Open the **Tools > Board > Boards Manager...** menu item. +* Wait for the platform indexes to finish downloading. +* Scroll down until you see the **MegaCoreX** entry and click on it. +* Click **Install**. +* After installation is complete close the **Boards Manager** window. #### Manual Installation Click on the "Download ZIP" button. Extract the ZIP file, and move the extracted folder to the location "**~/Documents/Arduino/hardware**". Create the "hardware" folder if it doesn't exist. From 41accb448e413234c146f37176611189b860f2e5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 1 Feb 2020 23:24:14 +0100 Subject: [PATCH 123/351] Fix SPI SS pin issue Closes #60 --- megaavr/libraries/SPI/src/SPI.cpp | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index 61601e3..e71b6fb 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -100,14 +100,12 @@ void SPIClass::begin() // MISO is set to input by the controller if(_uc_mux == SPI_MUX) { - pinMode(PIN_SPI_SS, INPUT); pinMode(PIN_SPI_MOSI, OUTPUT); pinMode(PIN_SPI_SCK, OUTPUT); } #if defined(SPI_MUX_PINSWAP_1) else if(_uc_mux == SPI_MUX_PINSWAP_1) { - pinMode(PIN_SPI_SS_PINSWAP_1, INPUT); pinMode(PIN_SPI_MOSI_PINSWAP_1, OUTPUT); pinMode(PIN_SPI_SCK_PINSWAP_1, OUTPUT); } @@ -115,12 +113,12 @@ void SPIClass::begin() #if defined(SPI_MUX_PINSWAP_2) else if(_uc_mux == SPI_MUX_PINSWAP_2) { - pinMode(PIN_SPI_SS_PINSWAP_2, INPUT); pinMode(PIN_SPI_MOSI_PINSWAP_2, OUTPUT); pinMode(PIN_SPI_SCK_PINSWAP_2, OUTPUT); } #endif + // We don't need HW SS since salve/master mode is selected via registers SPI0.CTRLB |= (SPI_SSD_bm); SPI0.CTRLA |= (SPI_ENABLE_bm | SPI_MASTER_bm); From b20fc2746238b6d1f284a72c50db8bf84b17730a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 28 Feb 2020 15:04:16 +0100 Subject: [PATCH 124/351] Fix typo --- megaavr/variants/nano-every/pins_arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index d17815c..7011a83 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -125,7 +125,7 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_A12 (8) // AIN11 #define PIN_A13 (6) // AIN14 #define PIN_A14 (3) // AIN15 -#define PIN_A14 (29) // AIN6 +#define PIN_A15 (29) // AIN6 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; From 4a43a058669bb6a7e6a1d15c69f4117926247bdd Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 5 Apr 2020 10:34:05 +0200 Subject: [PATCH 125/351] remove isDoubleBondedActive Wasn't used anyways --- megaavr/cores/coreX-corefiles/Arduino.h | 1 - megaavr/cores/coreX-corefiles/wiring_analog.c | 13 +++++-------- megaavr/cores/coreX-corefiles/wiring_digital.c | 18 ++++++++++-------- megaavr/variants/28pin-standard/variant.c | 17 ----------------- megaavr/variants/32pin-standard/variant.c | 17 ----------------- megaavr/variants/48pin-standard/variant.c | 17 ----------------- megaavr/variants/nano-every/variant.c | 17 ----------------- megaavr/variants/uno-wifi/variant.c | 17 ----------------- 8 files changed, 15 insertions(+), 102 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index b7e3955..3b07515 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -116,7 +116,6 @@ extern const uint8_t digital_pin_to_timer[]; #define TIMERB3 5 void setup_timers(); -bool isDoubleBondedActive(uint8_t pin); #define digitalPinToPort(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_port[pin] : NOT_A_PIN ) #define digitalPinToBitPosition(pin) ( (pin < NUM_TOTAL_PINS) ? digital_pin_to_bit_position[pin] : NOT_A_PIN ) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 3993df8..3703819 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -69,12 +69,8 @@ void analogReference(uint8_t mode) int analogRead(uint8_t pin) { pin = digitalPinToAnalogInput(pin); - if(pin > NUM_ANALOG_INPUTS) return NOT_A_PIN; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - if(isDoubleBondedActive(pin)) return 0; + if(pin > NUM_ANALOG_INPUTS) + return NOT_A_PIN; uint8_t low, high; @@ -121,7 +117,8 @@ void analogWrite(uint8_t pin, int val) { uint8_t bit_pos = digitalPinToBitPosition(pin); - if(bit_pos == NOT_A_PIN || isDoubleBondedActive(pin)) return; + if(bit_pos == NOT_A_PIN) + return; // We need to make sure the PWM output is enabled for those pins // that support it, as we turn it off when digitally reading or @@ -204,7 +201,7 @@ void analogWrite(uint8_t pin, int val) // best effort will be made to find something that matches. // void analogWriteFrequency(uint8_t kHz) { - static const byte index2setting[] = { + static const byte index2setting[] = { #if F_CPU > 1000000L #if F_CPU > 2000000L #if F_CPU > 4000000L diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index 0c25d73..f8b1cbd 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -26,18 +26,17 @@ #include "wiring_private.h" #include "pins_arduino.h" -__attribute__((weak)) bool isDoubleBondedActive(uint8_t pin __attribute__((unused))) { - return false; -}; void pinMode(uint8_t pin, PinMode mode) { uint8_t bit_mask = digitalPinToBitMask(pin); - if ((bit_mask == NOT_A_PIN) || (mode > INPUT_PULLUP) || isDoubleBondedActive(pin)) return; + if ((bit_mask == NOT_A_PIN) || (mode > INPUT_PULLUP)) + return; PORT_t* port = digitalPinToPortStruct(pin); - if(port == NULL) return; + if(port == NULL) + return; if(mode == OUTPUT){ @@ -95,7 +94,8 @@ static void turnOffPWM(uint8_t pin) /* Get pin's timer */ uint8_t timer = digitalPinToTimer(pin); - if(timer == NOT_ON_TIMER) return; + if(timer == NOT_ON_TIMER) + return; uint8_t bit_pos; TCB_t *timerB; @@ -134,7 +134,8 @@ void digitalWrite(uint8_t pin, PinStatus val) { /* Get bit mask for pin */ uint8_t bit_mask = digitalPinToBitMask(pin); - if(bit_mask == NOT_A_PIN || isDoubleBondedActive(pin)) return; + if(bit_mask == NOT_A_PIN) + return; /* Turn off PWM if applicable */ @@ -197,7 +198,8 @@ PinStatus digitalRead(uint8_t pin) { /* Get bit mask and check valid pin */ uint8_t bit_mask = digitalPinToBitMask(pin); - if(bit_mask == NOT_A_PIN || isDoubleBondedActive(pin)) return LOW; + if(bit_mask == NOT_A_PIN) + return LOW; // If the pin that support PWM output, we need to turn it off // before getting a digital reading. diff --git a/megaavr/variants/28pin-standard/variant.c b/megaavr/variants/28pin-standard/variant.c index 175cf87..c88add1 100644 --- a/megaavr/variants/28pin-standard/variant.c +++ b/megaavr/variants/28pin-standard/variant.c @@ -113,23 +113,6 @@ void setup_timers() { // } } -FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { - (void)pin; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; - - /* Special check for SPI_SS double bonded pin -- no action if SPI is active - (Using SPI Enable bit as indicator of SPI activity) */ - //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; - - // May check Serial1 that may conflict with A-timers (swapped or not) - - return false; -} - void initVariant() { // Not used } diff --git a/megaavr/variants/32pin-standard/variant.c b/megaavr/variants/32pin-standard/variant.c index 175cf87..c88add1 100644 --- a/megaavr/variants/32pin-standard/variant.c +++ b/megaavr/variants/32pin-standard/variant.c @@ -113,23 +113,6 @@ void setup_timers() { // } } -FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { - (void)pin; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; - - /* Special check for SPI_SS double bonded pin -- no action if SPI is active - (Using SPI Enable bit as indicator of SPI activity) */ - //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; - - // May check Serial1 that may conflict with A-timers (swapped or not) - - return false; -} - void initVariant() { // Not used } diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c index c3c577e..0c19ed9 100644 --- a/megaavr/variants/48pin-standard/variant.c +++ b/megaavr/variants/48pin-standard/variant.c @@ -117,23 +117,6 @@ void setup_timers() { // } } -FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { - (void)pin; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; - - /* Special check for SPI_SS double bonded pin -- no action if SPI is active - (Using SPI Enable bit as indicator of SPI activity) */ - //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; - - // May check Serial1 that may conflict with A-timers (swapped or not) - - return false; -} - void initVariant() { // Not used } diff --git a/megaavr/variants/nano-every/variant.c b/megaavr/variants/nano-every/variant.c index 08673b4..57b8e6b 100644 --- a/megaavr/variants/nano-every/variant.c +++ b/megaavr/variants/nano-every/variant.c @@ -113,22 +113,5 @@ void setup_timers() { // } } -FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { - (void)pin; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; - - /* Special check for SPI_SS double bonded pin -- no action if SPI is active - (Using SPI Enable bit as indicator of SPI activity) */ - //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; - - // May check Serial3 that may conflict with A-timers - - return false; -} - void initVariant() { } \ No newline at end of file diff --git a/megaavr/variants/uno-wifi/variant.c b/megaavr/variants/uno-wifi/variant.c index e738e81..ce45a3e 100644 --- a/megaavr/variants/uno-wifi/variant.c +++ b/megaavr/variants/uno-wifi/variant.c @@ -113,23 +113,6 @@ void setup_timers() { // } } -FORCE_INLINE bool isDoubleBondedActive(uint8_t pin) { - (void)pin; - - /* Check if TWI is operating on double bonded pin (Master Enable is high - in both Master and Slave mode for bus error detection, so this can - indicate an active state for Wire) */ - //if(((pin == PIN_A4) || (pin == PIN_A5)) && (TWI0.MCTRLA & TWI_ENABLE_bm)) return true; - - /* Special check for SPI_SS double bonded pin -- no action if SPI is active - (Using SPI Enable bit as indicator of SPI activity) */ - //if((pin == 10) && (SPI0.CTRLA & SPI_ENABLE_bm)) return true; - - // May check Serial3 that may conflict with A-timers - - return false; -} - void initVariant() { // NINA - SPI boot pinMode(NINA_GPIO0, OUTPUT); From 20b8dc17990641a773714f87c91ec45141196a6a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 5 Apr 2020 14:56:11 +0200 Subject: [PATCH 126/351] Reformat timer setup code and remove variant.c files Now we have a general timer setup function located in Wiring.c where timer pin routing is defined in pins_arduino.h. Much neater --- megaavr/cores/coreX-corefiles/main.cpp | 5 - megaavr/cores/coreX-corefiles/wiring.c | 114 ++++++++++++++- .../variants/28pin-standard/pins_arduino.h | 13 +- megaavr/variants/28pin-standard/variant.c | 118 ---------------- .../variants/32pin-standard/pins_arduino.h | 10 +- megaavr/variants/32pin-standard/variant.c | 118 ---------------- .../variants/48pin-standard/pins_arduino.h | 11 +- megaavr/variants/48pin-standard/variant.c | 122 ---------------- megaavr/variants/nano-every/pins_arduino.h | 35 +++-- megaavr/variants/nano-every/variant.c | 117 ---------------- megaavr/variants/uno-wifi/pins_arduino.h | 40 +++++- megaavr/variants/uno-wifi/variant.c | 132 ------------------ 12 files changed, 199 insertions(+), 636 deletions(-) delete mode 100644 megaavr/variants/28pin-standard/variant.c delete mode 100644 megaavr/variants/32pin-standard/variant.c delete mode 100644 megaavr/variants/48pin-standard/variant.c delete mode 100644 megaavr/variants/nano-every/variant.c delete mode 100644 megaavr/variants/uno-wifi/variant.c diff --git a/megaavr/cores/coreX-corefiles/main.cpp b/megaavr/cores/coreX-corefiles/main.cpp index 17aa21d..ef9f8f4 100644 --- a/megaavr/cores/coreX-corefiles/main.cpp +++ b/megaavr/cores/coreX-corefiles/main.cpp @@ -22,11 +22,6 @@ // Declared weak in Arduino.h to allow user redefinitions. int atexit(void (* /*func*/ )()) { return 0; } -// Weak empty variant initialization function. -// May be redefined by variant files. -void initVariant() __attribute__((weak)); -void initVariant() { } - void setupUSB() __attribute__((weak)); void setupUSB() { } diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 930cc16..946d24c 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -378,4 +378,116 @@ void init() sei(); } -void setup_timers(void) __attribute__((weak)); +void setup_timers() { + + // TYPE A TIMER + + // PORTMUX setting for TCA (defined in pins_arduino.h) + PORTMUX.TCAROUTEA = TCA0_PINS; + + // Enable split mode before anything else + TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; + + // Period setting, two 8 bit registers + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; + + // Default duty 50%, will re-assign in analogWrite() + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; + +#if F_CPU <= 1000000L + // Use DIV4 prescaler (giving 250kHz clock on 1MHz), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 2000000L + // Use DIV8 prescaler (giving 250kHz clock on 2MHz), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); +#elif F_CPU <= 8000000L + // Use DIV16 prescaler (giving 250kHz clocke on 4MHz, 500kHz clock on 8MHz), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); +#else + // Use DIV64 prescaler (giving 250kHz clock on 16MHz), enable TCA timer + TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); +#endif + + // TYPE B TIMERS + + // Set up routing (defined in pins_arduino.h) + PORTMUX.TCBROUTEA = 0 + #if defined(TCB0) + | TCB0_PINS + #endif + #if defined(TCB1) + | TCB1_PINS + #endif + #if defined(TCB2) + | TCB2_PINS + #endif + #if defined(TCB3) + | TCB3_PINS + #endif + ; + + // Start with TCB0 + TCB_t *timer_B = (TCB_t *)&TCB0; + + // Find end timer + #if defined(TCB3) + TCB_t *timer_B_end = (TCB_t *)&TCB3; + #elif defined(TCB2) + TCB_t *timer_B_end = (TCB_t *)&TCB2; + #elif defined(TCB1) + TCB_t *timer_B_end = (TCB_t *)&TCB1; + #else + TCB_t *timer_B_end = (TCB_t *)&TCB0; + #endif + + // Timer B Setup loop for TCB[0:end] + do + { + // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() + timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); + + // Assign 8-bit period + timer_B->CCMPL = PWM_TIMER_PERIOD; + + // default duty 50%, set when output enabled + timer_B->CCMPH = PWM_TIMER_COMPARE; + + // Use TCA clock (250kHz) and enable + // (sync update commented out, might try to synchronize later + timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) + //|(TCB_SYNCUPD_bm) + |(TCB_ENABLE_bm); + + // Increment pointer to next TCB instance + timer_B++; + + // Stop when pointing to TCB3 + } while (timer_B <= timer_B_end); + + // Stuff for synchronizing PWM timers +// // Restart TCA to sync TCBs +// // should not be needed +// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; +// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; +// +// timer_B = (TCB_t *)&TCB0; +// +// // TCB are sync to TCA, remove setting +// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); +// digitial_pin_timer < (TIMERB3 - TIMERB0); +// digitial_pin_timer++) +// { +// // disable sync with tca +// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); +// +// // Add offset to register +// timer_B++; +// +// } +} diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index c7e7df3..14b9cde 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -41,6 +41,13 @@ #define digitalPinHasPWM(p) ((p) >= 8 && (p) <= 11) +// Timer pin mapping +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + // SPI 0 // No pinswap by default // Pinswap 2 not available @@ -61,7 +68,7 @@ static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; static const uint8_t SCK = PIN_SPI_SCK; -// TWO 0 +// TWI 0 // No pinswap enabled by default #define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) #define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) @@ -239,7 +246,9 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER // 22 PF6 RESET }; - #endif +void initVariant() __attribute__((weak)); +void initVariant() { } + #endif diff --git a/megaavr/variants/28pin-standard/variant.c b/megaavr/variants/28pin-standard/variant.c deleted file mode 100644 index c88add1..0000000 --- a/megaavr/variants/28pin-standard/variant.c +++ /dev/null @@ -1,118 +0,0 @@ -#include - -#include "pins_arduino.h" -#include "api/Common.h" - -#define FORCE_INLINE __attribute__((always_inline)) inline - -void setup_timers() { - - // TYPE A TIMER - - // PORTMUX setting for TCA -> outputs [2:3] point to PORTC pins [2:3] - PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - - // Enable split mode before anything else - TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - - // Period setting, two 8 bit registers - TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; - - // Default duty 50%, will re-assign in analogWrite() - TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; - -#if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 8000000L - // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); -#else - // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); -#endif - - // TYPE B TIMERS - - // Setup TCB0 routing - #if defined(TCB0) - PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 - #endif - - // Setup TCB1 routing - #if defined(TCB1) - PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 - #endif - - // Start with TCB0 - TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif - - // Timer B Setup loop for TCB[0:end] - do - { - // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() - timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); - - // Assign 8-bit period - timer_B->CCMPL = PWM_TIMER_PERIOD; - - // default duty 50%, set when output enabled - timer_B->CCMPH = PWM_TIMER_COMPARE; - - // Use TCA clock (250kHz) and enable - // (sync update commented out, might try to synchronize later - timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); - - // Increment pointer to next TCB instance - timer_B++; - - // Stop when pointing to TCB3 - } while (timer_B <= timer_B_end); - - // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } -} - -void initVariant() { -// Not used -} diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 817ecad..e5c706b 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -41,6 +41,13 @@ #define digitalPinHasPWM(p) (((p) >= 8 && (p) <= 11) || (p) == 24 || (p) == 25) +// Timer pin mapping +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + // SPI 0 // No pinswap enabled by default // Pinswap 2 not available @@ -270,7 +277,8 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER // 26 PF6 RESET }; - #endif +void initVariant() {} + #endif diff --git a/megaavr/variants/32pin-standard/variant.c b/megaavr/variants/32pin-standard/variant.c deleted file mode 100644 index c88add1..0000000 --- a/megaavr/variants/32pin-standard/variant.c +++ /dev/null @@ -1,118 +0,0 @@ -#include - -#include "pins_arduino.h" -#include "api/Common.h" - -#define FORCE_INLINE __attribute__((always_inline)) inline - -void setup_timers() { - - // TYPE A TIMER - - // PORTMUX setting for TCA -> outputs [2:3] point to PORTC pins [2:3] - PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - - // Enable split mode before anything else - TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - - // Period setting, two 8 bit registers - TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; - - // Default duty 50%, will re-assign in analogWrite() - TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; - -#if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 8000000L - // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); -#else - // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); -#endif - - // TYPE B TIMERS - - // Setup TCB0 routing - #if defined(TCB0) - PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 - #endif - - // Setup TCB1 routing - #if defined(TCB1) - PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 - #endif - - // Start with TCB0 - TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif - - // Timer B Setup loop for TCB[0:end] - do - { - // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() - timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); - - // Assign 8-bit period - timer_B->CCMPL = PWM_TIMER_PERIOD; - - // default duty 50%, set when output enabled - timer_B->CCMPH = PWM_TIMER_COMPARE; - - // Use TCA clock (250kHz) and enable - // (sync update commented out, might try to synchronize later - timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); - - // Increment pointer to next TCB instance - timer_B++; - - // Stop when pointing to TCB3 - } while (timer_B <= timer_B_end); - - // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } -} - -void initVariant() { -// Not used -} diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index b428112..e9c7776 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -54,6 +54,13 @@ #define digitalPinHasPWM(p) ((p) == 12 || ((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) #endif +// Timer pin swaps +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + // SPI 0 // No pinswap enabled by default // Pinswap 2 not available @@ -374,7 +381,9 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER // 40 PF6 RESET }; - #endif +void initVariant() __attribute__((weak)); +void initVariant() { } + #endif diff --git a/megaavr/variants/48pin-standard/variant.c b/megaavr/variants/48pin-standard/variant.c deleted file mode 100644 index 0c19ed9..0000000 --- a/megaavr/variants/48pin-standard/variant.c +++ /dev/null @@ -1,122 +0,0 @@ -#include - -#include "pins_arduino.h" -#include "api/Common.h" - -#define FORCE_INLINE __attribute__((always_inline)) inline - -void setup_timers() { - - // TYPE A TIMER - - // PORTMUX setting for TCA -> outputs [2:5] point to PORTC pins [2:5] - PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTC_gc; - - // Enable split mode before anything else - TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - - // Period setting, two 8 bit registers - TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; - - // Default duty 50%, will re-assign in analogWrite() - TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; - -#if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock on 1MHz), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock on 2MHz), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 8000000L - // Use DIV16 prescaler (giving 250kHz clocke on 4MHz, 500kHz clock on 8MHz), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); -#else - // Use DIV64 prescaler (giving 250kHz clock on 16MHz), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); -#endif - - // TYPE B TIMERS - - // Set up routing - PORTMUX.TCBROUTEA = 0 - #if defined(TCB0) - | PORTMUX_TCB0_bm // Route signal to PF4 instead of PA2 - #endif - #if defined(TCB1) - | PORTMUX_TCB1_bm // Route signal to PF5 instead of PA3 - #endif - #if defined(TCB2) - | PORTMUX_TCB2_bm // Route signal to PB4 instead of PC0 - #endif - // For TCB3 routing, default PB5 is used, alternative is PC1 - ; - - // Start with TCB0 - TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif - - // Timer B Setup loop for TCB[0:end] - do - { - // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() - timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); - - // Assign 8-bit period - timer_B->CCMPL = PWM_TIMER_PERIOD; - - // default duty 50%, set when output enabled - timer_B->CCMPH = PWM_TIMER_COMPARE; - - // Use TCA clock (250kHz) and enable - // (sync update commented out, might try to synchronize later - timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); - - // Increment pointer to next TCB instance - timer_B++; - - // Stop when pointing to TCB3 - } while (timer_B <= timer_B_end); - - // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } -} - -void initVariant() { -// Not used -} diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index 7011a83..1c797a5 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -45,24 +45,35 @@ #define EXTERNAL_NUM_INTERRUPTS (48) -#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10) +#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) -#define SPI_MUX (PORTMUX_SPI0_ALT2_gc) +// Timer pin mapping +#define TCA0_PINS PORTMUX_TCA0_PORTB_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS 0x00 +#define TCB3_PINS 0x00 + +// SPI 0 +// Pinswap enabled by default and no alternative available #define SPI_INTERFACES_COUNT 1 -#define PIN_SPI_MISO (12) -#define PIN_SPI_SCK (13) -#define PIN_SPI_MOSI (11) -#define PIN_SPI_SS (8) +#define SPI_MUX (PORTMUX_SPI0_ALT2_gc) +#define PIN_SPI_MISO (12) +#define PIN_SPI_SCK (13) +#define PIN_SPI_MOSI (11) +#define PIN_SPI_SS (8) static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; static const uint8_t SCK = PIN_SPI_SCK; -#define PIN_WIRE_SDA (22) -#define PIN_WIRE_SCL (23) +// TWI 0 +// No pinswap enabled by default, and no alternative available +#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) +#define PIN_WIRE_SDA (22) +#define PIN_WIRE_SCL (23) static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) // Nano Every debug USART (not available on headers, only via the SAMD11 virtual COM port) // USART3 on mega4809 (alternative pins) @@ -330,9 +341,6 @@ const uint8_t digital_pin_to_timer[] = { #endif - - - // These serial port names are intended to allow libraries and architecture-neutral // sketches to automatically default to the correct port name for a particular type // of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, @@ -352,4 +360,7 @@ const uint8_t digital_pin_to_timer[] = { #define SERIAL_PORT_HARDWARE Serial1 #define SERIAL_PORT_USBVIRTUAL Serial +void initVariant() __attribute__((weak)); +void initVariant() { } + #endif diff --git a/megaavr/variants/nano-every/variant.c b/megaavr/variants/nano-every/variant.c deleted file mode 100644 index 57b8e6b..0000000 --- a/megaavr/variants/nano-every/variant.c +++ /dev/null @@ -1,117 +0,0 @@ -#include - -#include "pins_arduino.h" -#include "api/Common.h" - -#define FORCE_INLINE __attribute__((always_inline)) inline - -void setup_timers() { - - // TYPE A TIMER - - // PORTMUX setting for TCA -> all outputs [0:2] point to PORTB pins [0:2] - PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTB_gc; - - // Enable split mode before anything else - TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - - // Period setting, two 8 bit registers - TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; - - // Default duty 50%, will re-assign in analogWrite() - TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; - -#if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 8000000L - // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); -#else - // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); -#endif - - // TYPE B TIMERS - - // Setup TCB0 routing - #if defined(TCB0) - PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 - #endif - - // Setup TCB1 routing - #if defined(TCB1) - PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 - #endif - - // Start with TCB0 - TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif - - // Timer B Setup loop for TCB[0:3] - do - { - // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() - timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); - - // Assign 8-bit period - timer_B->CCMPL = PWM_TIMER_PERIOD; - - // default duty 50%, set when output enabled - timer_B->CCMPH = PWM_TIMER_COMPARE; - - // Use TCA clock (250kHz) and enable - // (sync update commented out, might try to synchronize later - timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); - - // Increment pointer to next TCB instance - timer_B++; - - // Stop when pointing to TCB3 - } while (timer_B <= timer_B_end); - - // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } -} - -void initVariant() { -} \ No newline at end of file diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 0fbe8c8..6b0f876 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -45,20 +45,31 @@ #define EXTERNAL_NUM_INTERRUPTS (47) -#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10) +#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) +// Timer pin mapping +#define TCA0_PINS PORTMUX_TCA0_PORTB_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + +// SPI 0 +// Pinswap enabled by default and no alternative available +#define SPI_INTERFACES_COUNT 1 #define SPI_MUX (PORTMUX_SPI0_ALT1_gc) #define PIN_SPI_MISO (33) #define PIN_SPI_SCK (34) #define PIN_SPI_MOSI (32) #define PIN_SPI_SS (10) - static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; static const uint8_t SCK = PIN_SPI_SCK; -// No pinswap available +// TWI 0 +// No pinswap enabled by default, and no alternative available +#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) #define PIN_WIRE_SDA (20) #define PIN_WIRE_SCL (21) static const uint8_t SDA = PIN_WIRE_SDA; @@ -107,10 +118,6 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) #define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) //PORTMUX_TWI0_ALT1_gc - -#define MUX_SPI (SPI_MUX) -#define SPI_INTERFACES_COUNT 1 #define LED_BUILTIN 25 @@ -404,4 +411,23 @@ const uint8_t digital_pin_to_timer[] = { #define SERIAL_PORT_HARDWARE_OPEN Serial2 #define SerialNina Serial2 +void initVariant() __attribute__((weak)); +void initVariant() { + // NINA - SPI boot + pinMode(NINA_GPIO0, OUTPUT); + digitalWrite(NINA_GPIO0, HIGH); + + // disable the NINA + pinMode(NINA_RESETN, OUTPUT); + digitalWrite(NINA_RESETN, HIGH); + + // NINA SS HIGH by default + pinMode(SPIWIFI_SS, OUTPUT); + digitalWrite(SPIWIFI_SS, HIGH); + + // IMU SS HIGH by default + pinMode(SPIIMU_SS, OUTPUT); + digitalWrite(SPIIMU_SS, HIGH); +} + #endif diff --git a/megaavr/variants/uno-wifi/variant.c b/megaavr/variants/uno-wifi/variant.c deleted file mode 100644 index ce45a3e..0000000 --- a/megaavr/variants/uno-wifi/variant.c +++ /dev/null @@ -1,132 +0,0 @@ -#include - -#include "pins_arduino.h" -#include "api/Common.h" - -#define FORCE_INLINE __attribute__((always_inline)) inline - -void setup_timers() { - - // TYPE A TIMER - - // PORTMUX setting for TCA -> all outputs [0:2] point to PORTB pins [0:2] - PORTMUX.TCAROUTEA = PORTMUX_TCA0_PORTB_gc; - - // Enable split mode before anything else - TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; - - // Period setting, two 8 bit registers - TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; - - // Default duty 50%, will re-assign in analogWrite() - TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; - -#if F_CPU <= 1000000L - // Use DIV4 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV4_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 2000000L - // Use DIV8 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV8_gc) | (TCA_SPLIT_ENABLE_bm); -#elif F_CPU <= 8000000L - // Use DIV16 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV16_gc) | (TCA_SPLIT_ENABLE_bm); -#else - // Use DIV64 prescaler (giving 250kHz clock), enable TCA timer - TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); -#endif - - // TYPE B TIMERS - - // Setup TCB0 routing - #if defined(TCB0) - PORTMUX.TCBROUTEA |= PORTMUX_TCB0_bm; // Route signal to PF4 - #endif - - // Setup TCB1 routing - #if defined(TCB1) - PORTMUX.TCBROUTEA |= PORTMUX_TCB1_bm; // Route signal to PF5 - #endif - - // Start with TCB0 - TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif - - // Timer B Setup loop for TCB[0:3] - do - { - // 8 bit PWM mode, but do not enable output yet, will do in analogWrite() - timer_B->CTRLB = (TCB_CNTMODE_PWM8_gc); - - // Assign 8-bit period - timer_B->CCMPL = PWM_TIMER_PERIOD; - - // default duty 50%, set when output enabled - timer_B->CCMPH = PWM_TIMER_COMPARE; - - // Use TCA clock (250kHz) and enable - // (sync update commented out, might try to synchronize later - timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); - - // Increment pointer to next TCB instance - timer_B++; - - // Stop when pointing to TCB3 - } while (timer_B <= timer_B_end); - - // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } -} - -void initVariant() { - // NINA - SPI boot - pinMode(NINA_GPIO0, OUTPUT); - digitalWrite(NINA_GPIO0, HIGH); - - // disable the NINA - pinMode(NINA_RESETN, OUTPUT); - digitalWrite(NINA_RESETN, HIGH); - - // NINA SS HIGH by default - pinMode(SPIWIFI_SS, OUTPUT); - digitalWrite(SPIWIFI_SS, HIGH); - - // IMU SS HIGH by default - pinMode(SPIIMU_SS, OUTPUT); - digitalWrite(SPIIMU_SS, HIGH); -} From 26381f972433acaf2c54c65d463b0ddc277566de Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 5 Apr 2020 15:14:34 +0200 Subject: [PATCH 127/351] Remove F_CPU_CORRECTED Not used anyways --- megaavr/cores/coreX-corefiles/Tone.cpp | 4 ++-- megaavr/cores/coreX-corefiles/wiring.c | 6 ++---- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Tone.cpp b/megaavr/cores/coreX-corefiles/Tone.cpp index 42353cf..87f5da1 100644 --- a/megaavr/cores/coreX-corefiles/Tone.cpp +++ b/megaavr/cores/coreX-corefiles/Tone.cpp @@ -107,13 +107,13 @@ void tone(uint8_t pin, unsigned int frequency, unsigned long duration) } // Calculate compare value, assuming F_CPU/2 used as clock - compare_val = F_CPU_CORRECTED / frequency / 4 - 1; + compare_val = F_CPU / frequency / 4 - 1; // If compare larger than 16bits, need to prescale (will be DIV64) uint8_t prescaler = 0; if (compare_val > 0xFFFF){ // recalculate with new prescaler prescaler = timerPrescaler(); - compare_val = F_CPU_CORRECTED / frequency / 2 / prescaler - 1; + compare_val = F_CPU / frequency / 2 / prescaler - 1; if (compare_val > 0xFFFF) compare_val = 0xFFFF; // request lower frequency than supported } diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 946d24c..3ae5a7d 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -29,8 +29,6 @@ #include "wiring_private.h" -uint32_t F_CPU_CORRECTED = F_CPU; - volatile uint32_t timer_millis = 0; inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk){ @@ -38,7 +36,7 @@ inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk){ } inline uint16_t clockCyclesPerMicrosecond(){ - return clockCyclesPerMicrosecondComp(F_CPU_CORRECTED); + return clockCyclesPerMicrosecondComp(F_CPU); } inline unsigned long clockCyclesToMicroseconds(unsigned long cycles){ @@ -350,7 +348,7 @@ void init() /********************* TCB for system time tracking **************************/ - // BUG: we can compensate for F_CPU_CORRECTED by fine tuning value of TIME_TRACKING_TIMER_COUNT + // BUG: we can compensate for F_CPU by fine tuning value of TIME_TRACKING_TIMER_COUNT /* Select vanilla 16 bit periodic interrupt mode */ _timer->CTRLB = TCB_CNTMODE_INT_gc; From 0e032fc4d5bb7bf67bc62b938e6e273715f31625 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 6 Apr 2020 19:28:11 +0200 Subject: [PATCH 128/351] Improve EEPROM library Now lets you write to user row (one aditional EEPROM page with other peroperties). More or less stolen from megaTinyCore --- megaavr/libraries/EEPROM/README.md | 32 ++++++++---- megaavr/libraries/EEPROM/library.properties | 8 +-- megaavr/libraries/EEPROM/src/EEPROM.h | 55 ++++++++++++--------- 3 files changed, 58 insertions(+), 37 deletions(-) diff --git a/megaavr/libraries/EEPROM/README.md b/megaavr/libraries/EEPROM/README.md index a624136..3e16839 100644 --- a/megaavr/libraries/EEPROM/README.md +++ b/megaavr/libraries/EEPROM/README.md @@ -1,13 +1,27 @@ -## **EEPROM Library V2.0** for Arduino +## **EEPROM Library V2.1** -**Written by:** _Christopher Andrews_. +**Written by:** _Christopher Andrews_. + +**Modified by:** _Spence Konde_ for better megaAVR support. ### **What is the EEPROM library.** -Th EEPROM library provides an easy to use interface to interact with the internal non-volatile storage found in AVR based Arduino boards. This library will work on many AVR devices like ATtiny and ATmega chips. +The EEPROM library provides an easy to use interface to interact with the internal non-volatile storage found on megaAVR ATtiny and ATmega devices. It was adapted for these devices by Spence Konde for distribution as part of [megaTinyCore](https://github.com/SpenceKonde/megaTinyCore). The interface is fully compatible with the standard Arduino EEPROM.h library. EEPROM memory will retain it's stored data when the device is powered off. If the EESAVE bit in the SYSCFG0 fuse is set, it will retain it's values even if a UPDI programmer is used to issue a Chip Erase command, unless the part has been "locked" via the LOCKBIT fuse, in which case the EEPROM is always cleared. + +### **Additional features when used with the megaavr devices** + +Like all AVR microcontrollers, the megaAVR devices have the usual complement of EEPROM memory available (See the datasheet or megaTinyCore part-specific documentation for more details). In addition to the standard EEPROM, the megaavr devices also have an additional "page" of memory available in what Atmel/Microchip refers to as the "user row". When using this version of EEPROM.h (Included in megaTinyCore 1.1.9 and later), the same methods described below work in the same way to read and write the user row. The library will treat any address greater than 0xFF (255) as pointing to the user row, as no currently available megaavr devices provide more than 256b of EEPROM memory. + +The user row can be used like normal EEPROM. Unlike normal EEPROM, when the chip is locked (via the LOCKBIT fuse), it can be *written to* (but not read from) via UPDI. It is still erased when a Chip Erase instruction is used. + +### **Library limitations** + +As with most Arduino libraries, this library sacrifices performance and functionality in favor of ease of use. This is particularly true of the megaAVR parts - unlike "classic" AVR devices, these provide a readiliy accessible facility for programming flash and EEPROM memory a whole page at a time (see the datasheet for additional information) - this library writes all memory one byte at a time. Providing a high performance library that made use of that would require that the library br aware of the page boundaries; after consideration, it was decided that the flash and performance overhead of such a system would not nr justified in the resource-constrained environment of a TinyAVR device as this version of the library is intended for. For applications where space is at a particular premium, megaTinyCore provides a minimal eeprom libtary called TinyEEPROM ( https://github.com/SpenceKonde/megaTinyCore/extras/TinyEEPROM.md .) + +No facility for wear leveling is provided, other than the `update()` and `put()` methods checking that the contents have not changed before writing. Under typical usage scenarios, further wear leveling methods are unnecessary - these devices are rated for 100,000 erase-write cycles, and according to the datasheet, the hardware only erases and writes bytes which have been written to the page buffer - it deos not perform a read-modify-write cycle on the whole page when any byte within the page is written or erased. If you do determine thas wear leveling is required for your application, many libraries that do this are available from various authors. Be aware that there is a bug in eeprom_is_ready() macro provided by the included with most versions of avr-libc, which impacts many third party EEPROM-rel;ated libraries. The symptom of this issue is an error referring to NVM_STATUS; to fix it, search the library code for eeprom_is_ready(). Replace `eeprom_is_ready()` with `!(NVMCTRL.STATUS & NVMCTRL_EEBUSY_bm)` and the library should work, assuming they do not make use of direct register writes that would require hand-porting to other families of AVR. ### **How to use it** -The EEPROM library is included in your IDE download. To add its functionality to your sketch you'll need to reference the library header file. You do this by adding an include directive to the top of your sketch. +The EEPROM library is provided as part of all board packages for hardware with this sort of memory - this particular version is supplied with megaTinyCore. It will be used whenver you are compiling for ```Arduino #include @@ -66,7 +80,7 @@ This function returns a reference to the `object` passed in. It does not need to #### **Subscript operator: `EEPROM[address]`** [[_example_]](examples/eeprom_crc/eeprom_crc.ino) -This operator allows using the identifier `EEPROM` like an array. +This operator allows using the identifier `EEPROM` like an array. EEPROM cells can be read _and_ **_written_** directly using this method. This operator returns a reference to the EEPROM cell. @@ -113,7 +127,7 @@ unsigned char val = ref; //Read referenced cell. #### **`EEPtr` class** This object is a bidirectional pointer to EEPROM cells represented by `EERef` objects. -Just like a normal pointer type, this type can be dereferenced and repositioned using +Just like a normal pointer type, this type can be dereferenced and repositioned using increment/decrement operators. ```C++ @@ -128,12 +142,12 @@ ptr++; //Move to next EEPROM cell. #### **`EEPROM.begin()`** -This function returns an `EEPtr` pointing to the first cell in the EEPROM. +This function returns an `EEPtr` pointing to the first cell in the EEPROM. This is useful for STL objects, custom iteration and C++11 style ranged for loops. #### **`EEPROM.end()`** -This function returns an `EEPtr` pointing at the location after the last EEPROM cell. +This function returns an `EEPtr` pointing at the location after the last EEPROM cell. Used with `begin()` to provide custom iteration. -**Note:** The `EEPtr` returned is invalid as it is out of range. Infact the hardware causes wrapping of the address (overflow) and `EEPROM.end()` actually references the first EEPROM cell. +**Note:** The `EEPtr` returned is invalid as it is out of range. Infact the hardware causes wrapping of the address (overflow) and `EEPROM.end()` actually references the first EEPROM cell. \ No newline at end of file diff --git a/megaavr/libraries/EEPROM/library.properties b/megaavr/libraries/EEPROM/library.properties index 2bd5552..4c639be 100644 --- a/megaavr/libraries/EEPROM/library.properties +++ b/megaavr/libraries/EEPROM/library.properties @@ -1,9 +1,9 @@ name=EEPROM -version=2.0 +version=2.1 author=Arduino, Christopher Andrews -maintainer=Arduino -sentence=Enables reading and writing to the permanent board storage. -paragraph=This library allows to read and write data in a memory type, the EEPROM, that keeps its content also when the board is powered off. The amount of EEPROM available depends on the microcontroller type. +maintainer=MCUdude +sentence=Enables reading and writing to EEPROM and USERROW on megaAVR parts. +paragraph=This library allows a sketch to read and write data in a memory type, the EEPROM, that keeps its content also when the board is powered off. This version of the library also supports reading and writing the USERROW page on megaAVR parts. category=Data Storage url=http://www.arduino.cc/en/Reference/EEPROM architectures=megaavr diff --git a/megaavr/libraries/EEPROM/src/EEPROM.h b/megaavr/libraries/EEPROM/src/EEPROM.h index a600835..906bfaa 100644 --- a/megaavr/libraries/EEPROM/src/EEPROM.h +++ b/megaavr/libraries/EEPROM/src/EEPROM.h @@ -2,49 +2,58 @@ EEPROM.h - EEPROM library Original Copyright (c) 2006 David A. Mellis. All right reserved. New version by Christopher Andrews 2015. - This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. - This library 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 Lesser General Public License for more details. - You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + Expanded by Spence Konde for megaTinyCore, with several new additions + First, owing to recently discovered */ #ifndef EEPROM_h #define EEPROM_h #include -#include #include /*** EERef class. - This object references an EEPROM cell. Its purpose is to mimic a typical byte of RAM, however its storage is the EEPROM. This class has an overhead of two bytes, similar to storing a pointer to an EEPROM cell. ***/ +#define nvm_read_byte(idx) *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) + +void nvm_write_byte(uint16_t idx, uint8_t dat) { + *(uint8_t*)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) = dat; + uint8_t oldSREG = SREG; + cli(); + _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_PAGEERASEWRITE_gc); + SREG = oldSREG; + while (NVMCTRL.STATUS & NVMCTRL_EEBUSY_bm); +} + + struct EERef{ EERef( const int index ) : index( index ) {} - + //Access/read members. - uint8_t operator*() const { return eeprom_read_byte( (uint8_t*) index ); } + uint8_t operator*() const { return nvm_read_byte( index ); } operator uint8_t() const { return **this; } - + //Assignment/write members. EERef &operator=( const EERef &ref ) { return *this = *ref; } - EERef &operator=( uint8_t in ) { return eeprom_write_byte( (uint8_t*) index, in ), *this; } + EERef &operator=( uint8_t in ) { return nvm_write_byte( index, in ), *this; } EERef &operator +=( uint8_t in ) { return *this = **this + in; } EERef &operator -=( uint8_t in ) { return *this = **this - in; } EERef &operator *=( uint8_t in ) { return *this = **this * in; } @@ -55,32 +64,31 @@ struct EERef{ EERef &operator |=( uint8_t in ) { return *this = **this | in; } EERef &operator <<=( uint8_t in ) { return *this = **this << in; } EERef &operator >>=( uint8_t in ) { return *this = **this >> in; } - + EERef &update( uint8_t in ) { return in != *this ? *this = in : *this; } - + /** Prefix increment/decrement **/ EERef& operator++() { return *this += 1; } EERef& operator--() { return *this -= 1; } - + /** Postfix increment/decrement **/ - uint8_t operator++ (int){ + uint8_t operator++ (int){ uint8_t ret = **this; return ++(*this), ret; } - uint8_t operator-- (int){ + uint8_t operator-- (int){ uint8_t ret = **this; return --(*this), ret; } - + int index; //Index of current EEPROM cell. }; /*** EEPtr class. - This object is a bidirectional pointer to EEPROM cells represented by EERef objects. - Just like a normal pointer type, this can be dereferenced and repositioned using + Just like a normal pointer type, this can be dereferenced and repositioned using increment/decrement operators. ***/ @@ -88,14 +96,14 @@ struct EEPtr{ EEPtr( const int index ) : index( index ) {} - + operator int() const { return index; } EEPtr &operator=( int in ) { return index = in, *this; } - + //Iterator functionality. bool operator!=( const EEPtr &ptr ) { return index != ptr.index; } EERef operator*() { return index; } - + /** Prefix & Postfix increment/decrement **/ EEPtr& operator++() { return ++index, *this; } EEPtr& operator--() { return --index, *this; } @@ -107,7 +115,6 @@ struct EEPtr{ /*** EEPROMClass class. - This object represents the entire EEPROM space. It wraps the functionality of EEPtr and EERef into a basic interface. This class is also 100% backwards compatible with earlier Arduino core releases. @@ -120,12 +127,12 @@ struct EEPROMClass{ uint8_t read( int idx ) { return EERef( idx ); } void write( int idx, uint8_t val ) { (EERef( idx )) = val; } void update( int idx, uint8_t val ) { EERef( idx ).update( val ); } - + //STL and C++11 iteration capability. EEPtr begin() { return 0x00; } EEPtr end() { return length(); } //Standards requires this to be the item after the last valid entry. The returned pointer is invalid. uint16_t length() { return EEPROM_SIZE; } - + //Functionality to 'get' and 'put' objects to and from EEPROM. template< typename T > T &get( int idx, T &t ){ EEPtr e = idx; @@ -133,7 +140,7 @@ struct EEPROMClass{ for( int count = sizeof(T) ; count ; --count, ++e ) *ptr++ = *e; return t; } - + template< typename T > const T &put( int idx, const T &t ){ EEPtr e = idx; const uint8_t *ptr = (const uint8_t*) &t; From 6daa67583aa5200a9e6bc5a442d0f10534f503a1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Apr 2020 08:42:20 +0200 Subject: [PATCH 129/351] Use F_CPU instead of F_CPU_CORRECTED --- megaavr/libraries/Wire/src/utility/twi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 0bdfd87..e566e9c 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -208,7 +208,7 @@ void TWI_MasterSetBaud(uint32_t frequency){ t_rise = 1000; } - uint32_t baud = ((F_CPU_CORRECTED/frequency) - (((F_CPU_CORRECTED*t_rise)/1000)/1000)/1000 - 10)/2; + uint32_t baud = ((F_CPU/frequency) - (((F_CPU*t_rise)/1000)/1000)/1000 - 10)/2; TWI0.MBAUD = (uint8_t)baud; } From fb93094d6e149b625d3b0c98f9544a959b1cd87b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Apr 2020 10:08:11 +0200 Subject: [PATCH 130/351] Implement 'classic' pinMode/digitalRead/digitalWrite Ensures better compatibility across other cores/architectures --- megaavr/cores/coreX-corefiles/WInterrupts.c | 2 +- megaavr/cores/coreX-corefiles/api/Common.h | 65 +++++++++---------- .../cores/coreX-corefiles/wiring_digital.c | 6 +- megaavr/cores/coreX-corefiles/wiring_shift.c | 4 +- .../libraries/Comparator/src/Comparator.cpp | 2 +- megaavr/libraries/Comparator/src/Comparator.h | 2 +- megaavr/libraries/Logic/src/Logic.cpp | 2 +- megaavr/libraries/Logic/src/Logic.h | 2 +- megaavr/libraries/SPI/src/SPI.cpp | 4 +- megaavr/libraries/SPI/src/SPI.h | 11 ++-- 10 files changed, 47 insertions(+), 53 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/WInterrupts.c b/megaavr/cores/coreX-corefiles/WInterrupts.c index 64cd9ae..1a6f8e4 100644 --- a/megaavr/cores/coreX-corefiles/WInterrupts.c +++ b/megaavr/cores/coreX-corefiles/WInterrupts.c @@ -34,7 +34,7 @@ static volatile voidFuncPtr intFunc[EXTERNAL_NUM_INTERRUPTS]; -void attachInterrupt(uint8_t pin, void (*userFunc)(void), PinStatus mode) { +void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) { /* Get bit position and check pin validity */ uint8_t bit_pos = digitalPinToBitPosition(pin); diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index db6feba..79e1dd0 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -6,35 +6,30 @@ extern "C"{ void yield(void); -typedef enum { - LOW = 0, - HIGH = 1, - CHANGE = 2, - FALLING = 3, - RISING = 4, -} PinStatus; - -typedef enum { - INPUT = 0x0, - OUTPUT = 0x1, - INPUT_PULLUP = 0x2, - INPUT_PULLDOWN = 0x3, -} PinMode; - -typedef enum { - LSBFIRST = 0, - MSBFIRST = 1, -} BitOrder; - -#define PI 3.1415926535897932384626433832795 -#define HALF_PI 1.5707963267948966192313216916398 -#define TWO_PI 6.283185307179586476925286766559 -#define DEG_TO_RAD 0.017453292519943295769236907684886 -#define RAD_TO_DEG 57.295779513082320876798154814105 -#define EULER 2.718281828459045235360287471352 - -#define SERIAL 0x0 -#define DISPLAY 0x1 +#define LOW 0 +#define HIGH 1 + +#define FALLING 2 +#define RISING 3 +#define CHANGE 4 + +#define INPUT 0 +#define OUTPUT 1 +#define INPUT_PULLUP 2 +//#define INPUT_PULLDOWN 3 + +#define LSBFIRST 0 +#define MSBFIRST 1 + +#define PI 3.1415926535897932384626433832795 +#define HALF_PI 1.5707963267948966192313216916398 +#define TWO_PI 6.283185307179586476925286766559 +#define DEG_TO_RAD 0.017453292519943295769236907684886 +#define RAD_TO_DEG 57.295779513082320876798154814105 +#define EULER 2.718281828459045235360287471352 + +#define SERIAL 0 +#define DISPLAY 1 #ifndef min #define min(a,b) \ @@ -100,9 +95,9 @@ typedef uint32_t pin_size_t; typedef uint8_t pin_size_t; #endif -void pinMode(pin_size_t pinNumber, PinMode pinMode); -void digitalWrite(pin_size_t pinNumber, PinStatus status); -PinStatus digitalRead(pin_size_t pinNumber); +void pinMode(pin_size_t pinNumber, uint8_t pinMode); +void digitalWrite(pin_size_t pinNumber, uint8_t status); +int digitalRead(pin_size_t pinNumber); int analogRead(pin_size_t pinNumber); void analogReference(uint8_t mode); void analogWrite(pin_size_t pinNumber, int value); @@ -115,10 +110,10 @@ void delayMicroseconds(unsigned int us); unsigned long pulseIn(pin_size_t pin, uint8_t state, unsigned long timeout); unsigned long pulseInLong(pin_size_t pin, uint8_t state, unsigned long timeout); -void shiftOut(pin_size_t dataPin, pin_size_t clockPin, BitOrder bitOrder, uint8_t val); -pin_size_t shiftIn(pin_size_t dataPin, pin_size_t clockPin, BitOrder bitOrder); +void shiftOut(pin_size_t dataPin, pin_size_t clockPin, uint8_t bitOrder, uint8_t val); +pin_size_t shiftIn(pin_size_t dataPin, pin_size_t clockPin, uint8_t bitOrder); -void attachInterrupt(pin_size_t interruptNumber, voidFuncPtr callback, PinStatus mode); +void attachInterrupt(pin_size_t interruptNumber, voidFuncPtr callback, uint8_t mode); void detachInterrupt(pin_size_t interruptNumber); void setup(void); diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index f8b1cbd..49bece4 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -27,7 +27,7 @@ #include "pins_arduino.h" -void pinMode(uint8_t pin, PinMode mode) +void pinMode(uint8_t pin, uint8_t mode) { uint8_t bit_mask = digitalPinToBitMask(pin); @@ -130,7 +130,7 @@ static void turnOffPWM(uint8_t pin) } } -void digitalWrite(uint8_t pin, PinStatus val) +void digitalWrite(uint8_t pin, uint8_t val) { /* Get bit mask for pin */ uint8_t bit_mask = digitalPinToBitMask(pin); @@ -194,7 +194,7 @@ void digitalWrite(uint8_t pin, PinStatus val) } -PinStatus digitalRead(uint8_t pin) +int digitalRead(uint8_t pin) { /* Get bit mask and check valid pin */ uint8_t bit_mask = digitalPinToBitMask(pin); diff --git a/megaavr/cores/coreX-corefiles/wiring_shift.c b/megaavr/cores/coreX-corefiles/wiring_shift.c index 0848df9..441fcd3 100644 --- a/megaavr/cores/coreX-corefiles/wiring_shift.c +++ b/megaavr/cores/coreX-corefiles/wiring_shift.c @@ -22,7 +22,7 @@ #include -uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, BitOrder bitOrder) { +uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder) { uint8_t value = 0; uint8_t i; @@ -37,7 +37,7 @@ uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, BitOrder bitOrder) { return value; } -void shiftOut(uint8_t dataPin, uint8_t clockPin, BitOrder bitOrder, uint8_t val) +void shiftOut(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder, uint8_t val) { uint8_t i; diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index 2d88189..032f061 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -86,7 +86,7 @@ void AnalogComparator::stop() start(false); } -void AnalogComparator::attachInterrupt(void (*userFunc)(void), PinStatus mode) +void AnalogComparator::attachInterrupt(void (*userFunc)(void), uint8_t mode) { AC_INTMODE_t intmode; switch (mode) diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 663866c..17821bd 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -67,7 +67,7 @@ class AnalogComparator void init(); void start(bool state = true); void stop(); - void attachInterrupt(voidFuncPtr callback, PinStatus mode); + void attachInterrupt(voidFuncPtr callback, uint8_t mode); void detachInterrupt(); out::output_t output = out::disable; diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 7201662..7036022 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -252,7 +252,7 @@ void Logic::init() #if defined(CCL_CCL_vect) -void Logic::attachInterrupt(void (*userFunc)(void), PinStatus mode) +void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) { CCL_INTMODE0_t intmode; switch (mode) diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 212b80e..68d671c 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -74,7 +74,7 @@ class Logic Logic(const uint8_t block_number); void init(); #if defined(CCL_CCL_vect) - void attachInterrupt(voidFuncPtr callback, PinStatus mode); + void attachInterrupt(voidFuncPtr callback, uint8_t mode); void detachInterrupt(); #endif diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index e71b6fb..9216045 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -272,9 +272,9 @@ void SPIClass::endTransaction(void) } } -void SPIClass::setBitOrder(BitOrder order) +void SPIClass::setBitOrder(uint8_t bitOrder) { - if (order == LSBFIRST) + if (bitOrder == LSBFIRST) SPI0.CTRLA |= (SPI_DORD_bm); else SPI0.CTRLA &= ~(SPI_DORD_bm); diff --git a/megaavr/libraries/SPI/src/SPI.h b/megaavr/libraries/SPI/src/SPI.h index 7947930..8a478e8 100644 --- a/megaavr/libraries/SPI/src/SPI.h +++ b/megaavr/libraries/SPI/src/SPI.h @@ -52,7 +52,7 @@ class SPISettings { public: - SPISettings(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { + SPISettings(uint32_t clock, uint8_t bitOrder, uint8_t dataMode) { if (__builtin_constant_p(clock)) { init_AlwaysInline(clock, bitOrder, dataMode); } else { @@ -64,11 +64,11 @@ class SPISettings { SPISettings() { init_AlwaysInline(4000000, MSBFIRST, SPI_MODE0); } private: - void init_MightInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { + void init_MightInline(uint32_t clock, uint8_t bitOrder, uint8_t dataMode) { init_AlwaysInline(clock, bitOrder, dataMode); } - void init_AlwaysInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) __attribute__((__always_inline__)) { + void init_AlwaysInline(uint32_t clock, uint8_t bitOrder, uint8_t dataMode) __attribute__((__always_inline__)) { // Clock settings are defined as follows. Note that this shows SPI2X // inverted, so the bits form increasing numbers. Also note that // fosc/64 appears twice. If FOSC is 16 Mhz @@ -93,12 +93,11 @@ class SPISettings { // away. When clock is not known, use a loop instead, which generates // shorter code. - /* This is no longer the case since, F_CPU_CORRECTED is variable */ /* set at run time. */ uint32_t clockSetting = 0; - clockSetting = F_CPU_CORRECTED / 2; + clockSetting = F_CPU / 2; clockDiv = 0; while ((clockDiv < 6) && (clock < clockSetting)) { clockSetting /= 2; @@ -162,7 +161,7 @@ class SPIClass { void begin(); void end(); - void setBitOrder(BitOrder order); + void setBitOrder(uint8_t bitOrder); void setDataMode(uint8_t uc_mode); void setClockDivider(uint8_t uc_div); From fceccb50c3dadeffb8878853a59219aa862750e3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Apr 2020 22:07:19 +0200 Subject: [PATCH 131/351] ADC improvements --- megaavr/cores/coreX-corefiles/Arduino.h | 33 ++++---- megaavr/cores/coreX-corefiles/wiring_analog.c | 79 ++++++------------- 2 files changed, 41 insertions(+), 71 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 3b07515..3280925 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -45,27 +45,30 @@ extern "C"{ /* Values shifted to avoid clashing with ADC REFSEL defines Will shift back in analog_reference function */ -#define INTERNAL0V55 (VREF_ADC0REFSEL_0V55_gc >> VREF_ADC0REFSEL_gp) -#define INTERNAL1V1 (VREF_ADC0REFSEL_1V1_gc >> VREF_ADC0REFSEL_gp) -#define INTERNAL2V5 (VREF_ADC0REFSEL_2V5_gc >> VREF_ADC0REFSEL_gp) -#define INTERNAL4V3 (VREF_ADC0REFSEL_4V34_gc >> VREF_ADC0REFSEL_gp) -#define INTERNAL1V5 (VREF_ADC0REFSEL_1V5_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL0V55 (VREF_ADC0REFSEL_0V55_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL1V1 (VREF_ADC0REFSEL_1V1_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL2V5 (VREF_ADC0REFSEL_2V5_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL4V3 (VREF_ADC0REFSEL_4V34_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL4V34 INTERNAL4V3 +#define INTERNAL1V5 (VREF_ADC0REFSEL_1V5_gc >> VREF_ADC0REFSEL_gp) -#define DEFAULT INTERNAL0V55 -#define INTERNAL ADC_REFSEL_INTREF_gc -#define VDD ADC_REFSEL_VDDREF_gc -#define EXTERNAL ADC_REFSEL_VREFA_gc +#define DEFAULT ADC_REFSEL_VDDREF_gc +#define INTERNAL ADC_REFSEL_INTREF_gc +#define VDD ADC_REFSEL_VDDREF_gc +#define EXTERNAL ADC_REFSEL_VREFA_gc -#define VCC_5V0 2 -#define VCC_3V3 1 -#define VCC_1V8 0 +#define ADC_TEMPERATURE ADC_MUXPOS_TEMPSENSE_gc -#define interrupts() sei() -#define noInterrupts() cli() +#define VCC_5V0 2 +#define VCC_3V3 1 +#define VCC_1V8 0 + +#define interrupts() sei() +#define noInterrupts() cli() // avr-libc defines _NOP() since 1.6.2 #ifndef _NOP -#define _NOP() do { __asm__ volatile ("nop"); } while (0) + #define _NOP() do { __asm__ volatile ("nop"); } while (0) #endif /* Allows performing a correction on the CPU value using the signature row diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 3703819..ccd9c4c 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -26,43 +26,28 @@ #include "pins_arduino.h" #include "Arduino.h" -uint8_t analog_reference = DEFAULT; - void analogReference(uint8_t mode) { - /* Clear relevant settings */ - ADC0.CTRLC &= ~(ADC_REFSEL_gm); - VREF.CTRLA &= ~(VREF_ADC0REFSEL_gm); - - /* If reference NOT using internal reference from VREF */ - if((mode == EXTERNAL) || (mode == VDD)) { - - /* Set reference in ADC peripheral */ - ADC0.CTRLC |= mode; - - /* If reference using internal reference from VREF */ - } else if ( - (mode == INTERNAL0V55) - || (mode == INTERNAL1V1) - || (mode == INTERNAL2V5) - || (mode == INTERNAL4V3) - || (mode == INTERNAL1V5)) { - - /* Set ADC reference to INTERNAL */ - ADC0.CTRLC |= INTERNAL; - - /* Configure VREF ADC0 reference */ - VREF.CTRLA |= (mode << VREF_ADC0REFSEL_gp); - - /* Non-standard values / default */ - } else { - - /* Non valid value will set default */ - /* Set ADC reference to INTERNAL */ - ADC0.CTRLC |= INTERNAL; - - /* Configure VREF ADC0 reference */ - VREF.CTRLA |= (INTERNAL0V55 << VREF_ADC0REFSEL_gp); + switch (mode) + { + case EXTERNAL: + case VDD: + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | mode | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... + // VREF.CTRLA does not need to be reconfigured, as the voltage references only supply their specified voltage when requested to do so by the ADC. + break; + case INTERNAL0V55: + VREF.CTRLA = VREF.CTRLA & ~(VREF_ADC0REFSEL_gm); // These bits are all 0 for 0.55v reference, so no need to do the mode << VREF_ADC0REFSEL_gp here; + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm | ADC_SAMPCAP_bm)) | INTERNAL; // Per datasheet, recommended SAMPCAP=0 at ref < 1v + break; + case INTERNAL1V1: + case INTERNAL2V5: + case INTERNAL4V34: + case INTERNAL1V5: + VREF.CTRLA = (VREF.CTRLA & ~(VREF_ADC0REFSEL_gm)) | (mode << VREF_ADC0REFSEL_gp); + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | INTERNAL | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v + break; + default: + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | VDD | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... } } @@ -72,12 +57,6 @@ int analogRead(uint8_t pin) if(pin > NUM_ANALOG_INPUTS) return NOT_A_PIN; - uint8_t low, high; - -#if defined(analogPinToChannel) - /* If analog pin number != adc0 channel */ -#endif - #if defined(ADC0) /* Reference should be already set up */ /* Select channel */ @@ -89,24 +68,12 @@ int analogRead(uint8_t pin) /* Wait for result ready */ while(!(ADC0.INTFLAGS & ADC_RESRDY_bm)); - /* Save state */ - uint8_t status = SREG; - cli(); - - /* Read result */ - low = ADC0.RESL; - high = ADC0.RESH; - - /* Restore state */ - SREG = status; + /* Combine two bytes */ + return ADC0.RES; #else /* No ADC, return 0 */ - low = 0; - high = 0; + return 0; #endif - - /* Combine two bytes */ - return (high << 8) | low; } // Right now, PWM output only works on the pins with From 4d2cd8aaccd168fb33d9784e58ac1ac5736a521d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Apr 2020 22:09:35 +0200 Subject: [PATCH 132/351] Formatting --- megaavr/cores/coreX-corefiles/Arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 3280925..9c138d4 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -47,10 +47,10 @@ extern "C"{ */ #define INTERNAL0V55 (VREF_ADC0REFSEL_0V55_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL1V1 (VREF_ADC0REFSEL_1V1_gc >> VREF_ADC0REFSEL_gp) +#define INTERNAL1V5 (VREF_ADC0REFSEL_1V5_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL2V5 (VREF_ADC0REFSEL_2V5_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL4V3 (VREF_ADC0REFSEL_4V34_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL4V34 INTERNAL4V3 -#define INTERNAL1V5 (VREF_ADC0REFSEL_1V5_gc >> VREF_ADC0REFSEL_gp) #define DEFAULT ADC_REFSEL_VDDREF_gc #define INTERNAL ADC_REFSEL_INTREF_gc From e4528a0db77063e377f0d1f101d2e5f48a40429a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Apr 2020 14:59:05 +0200 Subject: [PATCH 133/351] add digitalReadFast and digitalWriteFast Closes #58 --- README.md | 6 +++ megaavr/cores/coreX-corefiles/api/Common.h | 8 +++- .../cores/coreX-corefiles/wiring_digital.c | 42 +++++++++++++++++-- 3 files changed, 51 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 9d595e5..b9fc202 100644 --- a/README.md +++ b/README.md @@ -15,6 +15,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [BOD option](#bod-option) * [Reset pin](#reset-pin) * [Printf support](#printf-support) +* [Fast IO](#fast-io) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -107,6 +108,11 @@ Unlike the official Arduino core, MegaCoreX has printf support out of the box. I If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other libraries that inherit the Print class (and thus supports printf) are SoftwareSerial and the LiquidCrystal LCD library. +## Fast IO +For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compiles down to a single instruction. +Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that in order to gain any speed improvements, the pin number has to be a constant. + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 79e1dd0..e5e7ee2 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -97,7 +97,13 @@ typedef uint8_t pin_size_t; void pinMode(pin_size_t pinNumber, uint8_t pinMode); void digitalWrite(pin_size_t pinNumber, uint8_t status); -int digitalRead(pin_size_t pinNumber); +void _dwfast(pin_size_t pinNumber, uint8_t status); +#define digitalWriteFast(pin, val) \ + (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _dwfast(pin, val) : digitalWrite(pin, val)) +uint8_t digitalRead(pin_size_t pinNumber); +uint8_t _drfast(pin_size_t pinNumber); +#define digitalReadFast(pin) \ + (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _drfast(pin) : digitalRead(pin)) int analogRead(pin_size_t pinNumber); void analogReference(uint8_t mode); void analogWrite(pin_size_t pinNumber, int value); diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index 49bece4..e66e28d 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -191,10 +191,29 @@ void digitalWrite(uint8_t pin, uint8_t val) /* Restore system status */ SREG = status; } +} + +inline __attribute__((always_inline)) void _dwfast(uint8_t pin, uint8_t val) +{ + // Mega-0, Tiny-1 style IOPORTs + // Assumes VPORTs exist starting at 0 for each PORT structure + uint8_t mask = 1 << digital_pin_to_bit_position[pin]; + uint8_t port = digital_pin_to_port[pin]; + VPORT_t *vport; + + // Write pin value from VPORTx.OUT register + vport = (VPORT_t *)(port * 4); + + if (val == HIGH) + vport->OUT |= mask; + else if (val == LOW) + vport->OUT &= ~mask; + else // CHANGE + vport->IN = mask; } -int digitalRead(uint8_t pin) +uint8_t digitalRead(uint8_t pin) { /* Get bit mask and check valid pin */ uint8_t bit_mask = digitalPinToBitMask(pin); @@ -209,10 +228,25 @@ int digitalRead(uint8_t pin) PORT_t *port = digitalPinToPortStruct(pin); /* Read pin value from PORTx.IN register */ - if(port->IN & bit_mask){ + if(port->IN & bit_mask) return HIGH; - } else { + else return LOW; - } + return LOW; } + +inline __attribute__((always_inline)) uint8_t _drfast(uint8_t pin) +{ + // Mega-0, Tiny-1 style IOPORTs + // Assumes VPORTs exist starting at 0 for each PORT structure + uint8_t mask = 1 << digital_pin_to_bit_position[pin]; + uint8_t port = digital_pin_to_port[pin]; + VPORT_t *vport; + + // Old style port logic is a small integer 0 for PORTA, 1 for PORTB etc. + vport = (VPORT_t *)(port * 4); + + // Read pin value from VPORTx.IN register + return !!(vport->IN & mask); +} From 078584796635c0d3c0196486185da00588bc1892 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Apr 2020 16:04:50 +0200 Subject: [PATCH 134/351] Add PIN macros --- README.md | 13 ++++++ .../variants/28pin-standard/pins_arduino.h | 26 ++++++++++- .../variants/32pin-standard/pins_arduino.h | 30 ++++++++++++- .../variants/48pin-standard/pins_arduino.h | 42 ++++++++++++++++++ megaavr/variants/nano-every/pins_arduino.h | 42 ++++++++++++++++++ megaavr/variants/uno-wifi/pins_arduino.h | 43 +++++++++++++++++++ 6 files changed, 194 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index b9fc202..3ae59a9 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [Reset pin](#reset-pin) * [Printf support](#printf-support) * [Fast IO](#fast-io) +* [Pin macros](#pin-macros) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -113,6 +114,18 @@ For timing critical applications the standard `digitalRead()` and `digitalWrite( Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that in order to gain any speed improvements, the pin number has to be a constant. +## Pin macros +Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that maps "Arduino pins" to the port and port number: + +```c++ +// Use PIN_PA0 macro to refer to pin PA0 (Arduino pin 0) +digitalWrite(PIN_PA0, HIGH); + +// Results in the exact same compiled code +digitalWrite(0, HIGH); + + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 14b9cde..49b7a8d 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -195,7 +195,7 @@ const uint8_t digital_pin_to_bit_position[] = { /* Use this for accessing PINnCTRL register */ const uint8_t digital_pin_to_bit_mask[] = { - PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN + PIN0_bm, // 0 PA0/USART0_Tx/CLKIN PIN1_bm, // 1 PA1/USART0_Rx PIN2_bm, // 2 PA2/SDA PIN3_bm, // 3 PA3/SCL @@ -220,6 +220,30 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 22 PF6 RESET }; +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF6 22 + const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index e5c706b..f9d29ef 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -218,7 +218,7 @@ const uint8_t digital_pin_to_bit_position[] = { /* Use this for accessing PINnCTRL register */ const uint8_t digital_pin_to_bit_mask[] = { - PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN + PIN0_bm, // 0 PA0/USART0_Tx/CLKIN PIN1_bm, // 1 PA1/USART0_Rx PIN2_bm, // 2 PA2/SDA PIN3_bm, // 3 PA3/SCL @@ -247,6 +247,34 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 26 PF6 RESET }; +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF2 22 +#define PIN_PF3 23 +#define PIN_PF4 24 +#define PIN_PF5 25 +#define PIN_PF6 26 + const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index e9c7776..f7fb1e8 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -321,6 +321,48 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PB0 8 +#define PIN_PB1 9 +#define PIN_PB2 10 +#define PIN_PB3 11 +#define PIN_PB4 12 +#define PIN_PB5 13 +#define PIN_PC0 14 +#define PIN_PC1 15 +#define PIN_PC2 16 +#define PIN_PC3 17 +#define PIN_PC4 18 +#define PIN_PC5 19 +#define PIN_PC6 20 +#define PIN_PC7 21 +#define PIN_PD0 22 +#define PIN_PD1 23 +#define PIN_PD2 24 +#define PIN_PD3 25 +#define PIN_PD4 26 +#define PIN_PD5 27 +#define PIN_PD6 28 +#define PIN_PD7 29 +#define PIN_PE0 30 +#define PIN_PE1 31 +#define PIN_PE2 32 +#define PIN_PE3 33 +#define PIN_PF0 34 +#define PIN_PF1 35 +#define PIN_PF2 36 +#define PIN_PF3 37 +#define PIN_PF4 38 +#define PIN_PF5 39 +#define PIN_PF6 40 + const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index 1c797a5..d05539d 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -293,6 +293,48 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm, // 40 PF6/RESET }; +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD3 14 +#define PIN_PD2 15 +#define PIN_PD1 16 +#define PIN_PD0 17 +#define PIN_PF2 18 +#define PIN_PF3 19 +#define PIN_PD4 20 +#define PIN_PD5 21 +#define PIN_PA2 22 +#define PIN_PA3 23 +#define PIN_PB5 24 +#define PIN_PB4 25 +#define PIN_PC3 26 +#define PIN_PA5 27 +#define PIN_PA4 28 +#define PIN_PD6 29 +#define PIN_PA6 30 +#define PIN_PA7 31 +#define PIN_PB3 32 +#define PIN_PC7 33 +#define PIN_PC0 34 +#define PIN_PC1 35 +#define PIN_PC2 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PC5/USART1_Rx_alt NOT_ON_TIMER, // 1 PC4/USART1_Tx_alt diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 6b0f876..49d59d6 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -339,6 +339,49 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; + +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD0 14 +#define PIN_PD1 15 +#define PIN_PD2 16 +#define PIN_PD3 17 +#define PIN_PD4 18 +#define PIN_PD5 19 +#define PIN_PA2 20 +#define PIN_PA3 21 +#define PIN_PC3 22 +#define PIN_PA5 23 +#define PIN_PA4 24 +#define PIN_PD6 25 +#define PIN_PB5 26 +#define PIN_PB4 27 +#define PIN_PA6 28 +#define PIN_PA7 29 +#define PIN_PB3 30 +#define PIN_PC7 31 +#define PIN_PC0 32 +#define PIN_PC1 33 +#define PIN_PC2 34 +#define PIN_PF2 35 +#define PIN_PF3 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PC5/USART1_Rx NOT_ON_TIMER, // 1 PC4/USART1_Tx From dff211f54f6cb87755f16671955dab03e7174e35 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Apr 2020 16:10:51 +0200 Subject: [PATCH 135/351] Fix formatting --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 3ae59a9..7d4acbd 100644 --- a/README.md +++ b/README.md @@ -123,7 +123,7 @@ digitalWrite(PIN_PA0, HIGH); // Results in the exact same compiled code digitalWrite(0, HIGH); - +``` ## Pinout From 504d14ef2f6a6affef74e65f64d0b83345c4f449 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Apr 2020 22:31:03 +0200 Subject: [PATCH 136/351] Improve pin swap handling Now done similar to the Wire library --- megaavr/libraries/SPI/src/SPI.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index 9216045..4355ae4 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -70,20 +70,21 @@ bool SPIClass::swap(uint8_t state) { if(state == 0) { + _uc_mux = SPI_MUX; pins(PIN_SPI_MOSI, PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_SS); return true; } #if defined(SPI_MUX_PINSWAP_1) else if(state == 1) { - pins(PIN_SPI_MOSI_PINSWAP_1, PIN_SPI_MISO_PINSWAP_1, PIN_SPI_SCK_PINSWAP_1, PIN_SPI_SS_PINSWAP_1); + _uc_mux = SPI_MUX_PINSWAP_1; return true; } #endif #if defined(SPI_MUX_PINSWAP_2) else if(state == 2) { - pins(PIN_SPI_MOSI_PINSWAP_2, PIN_SPI_MISO_PINSWAP_2, PIN_SPI_SCK_PINSWAP_2, PIN_SPI_SS_PINSWAP_2); + _uc_mux = SPI_MUX_PINSWAP_2; return true; } #endif From e54b7f3486ce5030e9b357803dbaf04d742de557 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 13 Apr 2020 09:41:44 +0200 Subject: [PATCH 137/351] Code formatting Semi automatically formatted using VS Code with the following Clang setting { BasedOnStyle: Google, IndentWidth: 2, UseTab: Never, BreakBeforeBraces: Allman, ColumnLimit: 0, SpacesBeforeTrailingComments: 1} --- megaavr/cores/coreX-corefiles/Arduino.h | 12 +- megaavr/cores/coreX-corefiles/CDC.cpp | 373 +++--- megaavr/cores/coreX-corefiles/CDC.h | 132 +- megaavr/cores/coreX-corefiles/MSC.h | 12 +- megaavr/cores/coreX-corefiles/Tone.cpp | 251 ++-- megaavr/cores/coreX-corefiles/UART.cpp | 348 +++--- megaavr/cores/coreX-corefiles/UART0.cpp | 5 +- megaavr/cores/coreX-corefiles/UART1.cpp | 5 +- megaavr/cores/coreX-corefiles/UART2.cpp | 5 +- megaavr/cores/coreX-corefiles/UART3.cpp | 5 +- megaavr/cores/coreX-corefiles/UART_private.h | 9 +- megaavr/cores/coreX-corefiles/UNO_compat.h | 465 +++---- megaavr/cores/coreX-corefiles/USBCore.cpp | 1063 +++++++++-------- megaavr/cores/coreX-corefiles/USBCore.h | 451 +++---- megaavr/cores/coreX-corefiles/WInterrupts.c | 59 +- megaavr/cores/coreX-corefiles/WMath.cpp | 14 +- .../cores/coreX-corefiles/api/ArduinoAPI.h | 12 +- megaavr/cores/coreX-corefiles/api/Client.h | 22 +- megaavr/cores/coreX-corefiles/api/Common.cpp | 2 +- .../cores/coreX-corefiles/api/HardwareI2C.h | 34 +- .../coreX-corefiles/api/HardwareSerial.h | 136 +-- .../cores/coreX-corefiles/api/IPAddress.cpp | 116 +- megaavr/cores/coreX-corefiles/api/IPAddress.h | 93 +- .../coreX-corefiles/api/PluggableUSB.cpp | 124 +- .../cores/coreX-corefiles/api/PluggableUSB.h | 41 +- megaavr/cores/coreX-corefiles/api/Print.cpp | 70 +- megaavr/cores/coreX-corefiles/api/Print.h | 1 - megaavr/cores/coreX-corefiles/api/Printable.h | 1 - .../cores/coreX-corefiles/api/RingBuffer.cpp | 101 +- .../cores/coreX-corefiles/api/RingBuffer.h | 45 +- megaavr/cores/coreX-corefiles/api/Server.h | 8 +- megaavr/cores/coreX-corefiles/api/Stream.cpp | 144 ++- megaavr/cores/coreX-corefiles/api/Stream.h | 75 +- megaavr/cores/coreX-corefiles/api/String.cpp | 815 +++++++------ megaavr/cores/coreX-corefiles/api/String.h | 398 +++--- megaavr/cores/coreX-corefiles/api/USBAPI.h | 21 +- megaavr/cores/coreX-corefiles/api/Udp.h | 44 +- megaavr/cores/coreX-corefiles/api/Udp.h.orig | 6 +- .../cores/coreX-corefiles/api/WCharacter.h | 72 +- megaavr/cores/coreX-corefiles/api/itoa.h | 12 +- megaavr/cores/coreX-corefiles/hooks.c | 2 +- megaavr/cores/coreX-corefiles/main.cpp | 24 +- megaavr/cores/coreX-corefiles/new.cpp | 13 +- megaavr/cores/coreX-corefiles/new.h | 5 +- megaavr/cores/coreX-corefiles/timers.h | 8 +- megaavr/cores/coreX-corefiles/wiring.c | 574 ++++----- megaavr/cores/coreX-corefiles/wiring_analog.c | 263 ++-- .../cores/coreX-corefiles/wiring_digital.c | 352 +++--- .../cores/coreX-corefiles/wiring_private.h | 11 +- megaavr/cores/coreX-corefiles/wiring_pulse.c | 83 +- megaavr/cores/coreX-corefiles/wiring_shift.c | 55 +- megaavr/libraries/EEPROM/src/EEPROM.h | 195 +-- megaavr/libraries/HID/src/HID.cpp | 231 ++-- megaavr/libraries/HID/src/HID.h | 59 +- megaavr/libraries/Wire/src/Wire.cpp | 308 ++--- megaavr/libraries/Wire/src/utility/twi.c | 1006 ++++++++-------- megaavr/libraries/Wire/src/utility/twi.h | 102 +- 57 files changed, 4656 insertions(+), 4237 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 9c138d4..664aab8 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -43,7 +43,7 @@ extern "C"{ // internal from VREF /* Values shifted to avoid clashing with ADC REFSEL defines - Will shift back in analog_reference function + Will shift back in analog_reference function */ #define INTERNAL0V55 (VREF_ADC0REFSEL_0V55_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL1V1 (VREF_ADC0REFSEL_1V1_gc >> VREF_ADC0REFSEL_gp) @@ -68,17 +68,17 @@ extern "C"{ // avr-libc defines _NOP() since 1.6.2 #ifndef _NOP - #define _NOP() do { __asm__ volatile ("nop"); } while (0) + #define _NOP() do { __asm__ volatile ("nop"); } while (0) #endif /* Allows performing a correction on the CPU value using the signature row - values indicating oscillator error provided from the device manufacturer */ + values indicating oscillator error provided from the device manufacturer */ #define PERFORM_SIGROW_CORRECTION_F_CPU 0 /* Variable containing corrected F_CPU value, after checks for safe operating - frequency vs supply voltage, oscillator fuse setting and MCLK divider. - Also includes the correction from signature row values if above #define - PERFORM_SIGROW_CORRECTION_F_CPU = 1 */ + frequency vs supply voltage, oscillator fuse setting and MCLK divider. + Also includes the correction from signature row values if above #define + PERFORM_SIGROW_CORRECTION_F_CPU = 1 */ extern uint32_t F_CPU_CORRECTED; uint16_t clockCyclesPerMicrosecondComp(uint32_t clk); diff --git a/megaavr/cores/coreX-corefiles/CDC.cpp b/megaavr/cores/coreX-corefiles/CDC.cpp index 9c2b947..7c5cc04 100644 --- a/megaavr/cores/coreX-corefiles/CDC.cpp +++ b/megaavr/cores/coreX-corefiles/CDC.cpp @@ -28,11 +28,11 @@ typedef struct { - uint32_t dwDTERate; - uint8_t bCharFormat; - uint8_t bParityType; - uint8_t bDataBits; - uint8_t lineState; + uint32_t dwDTERate; + uint8_t bCharFormat; + uint8_t bParityType; + uint8_t bDataBits; + uint8_t lineState; } LineInfo; static volatile LineInfo _usbLineInfo = { 57600, 0x00, 0x00, 0x00, 0x00 }; @@ -45,137 +45,140 @@ static uint8_t wdtcsr_save; extern const CDCDescriptor _cdcInterface PROGMEM; const CDCDescriptor _cdcInterface = { - D_IAD(0,2,CDC_COMMUNICATION_INTERFACE_CLASS,CDC_ABSTRACT_CONTROL_MODEL,1), - - // CDC communication interface - D_INTERFACE(CDC_ACM_INTERFACE,1,CDC_COMMUNICATION_INTERFACE_CLASS,CDC_ABSTRACT_CONTROL_MODEL,0), - D_CDCCS(CDC_HEADER,0x10,0x01), // Header (1.10 bcd) - D_CDCCS(CDC_CALL_MANAGEMENT,1,1), // Device handles call management (not) - D_CDCCS4(CDC_ABSTRACT_CONTROL_MANAGEMENT,6), // SET_LINE_CODING, GET_LINE_CODING, SET_CONTROL_LINE_STATE supported - D_CDCCS(CDC_UNION,CDC_ACM_INTERFACE,CDC_DATA_INTERFACE), // Communication interface is master, data interface is slave 0 - D_ENDPOINT(USB_ENDPOINT_IN (CDC_ENDPOINT_ACM),USB_ENDPOINT_TYPE_INTERRUPT,0x10,0x40), - - // CDC data interface - D_INTERFACE(CDC_DATA_INTERFACE,2,CDC_DATA_INTERFACE_CLASS,0,0), - D_ENDPOINT(USB_ENDPOINT_OUT(CDC_ENDPOINT_OUT),USB_ENDPOINT_TYPE_BULK,USB_EP_SIZE,0), - D_ENDPOINT(USB_ENDPOINT_IN (CDC_ENDPOINT_IN ),USB_ENDPOINT_TYPE_BULK,USB_EP_SIZE,0) + D_IAD(0,2,CDC_COMMUNICATION_INTERFACE_CLASS,CDC_ABSTRACT_CONTROL_MODEL,1), + + // CDC communication interface + D_INTERFACE(CDC_ACM_INTERFACE,1,CDC_COMMUNICATION_INTERFACE_CLASS,CDC_ABSTRACT_CONTROL_MODEL,0), + D_CDCCS(CDC_HEADER,0x10,0x01), // Header (1.10 bcd) + D_CDCCS(CDC_CALL_MANAGEMENT,1,1), // Device handles call management (not) + D_CDCCS4(CDC_ABSTRACT_CONTROL_MANAGEMENT,6), // SET_LINE_CODING, GET_LINE_CODING, SET_CONTROL_LINE_STATE supported + D_CDCCS(CDC_UNION,CDC_ACM_INTERFACE,CDC_DATA_INTERFACE), // Communication interface is master, data interface is slave 0 + D_ENDPOINT(USB_ENDPOINT_IN (CDC_ENDPOINT_ACM),USB_ENDPOINT_TYPE_INTERRUPT,0x10,0x40), + + // CDC data interface + D_INTERFACE(CDC_DATA_INTERFACE,2,CDC_DATA_INTERFACE_CLASS,0,0), + D_ENDPOINT(USB_ENDPOINT_OUT(CDC_ENDPOINT_OUT),USB_ENDPOINT_TYPE_BULK,USB_EP_SIZE,0), + D_ENDPOINT(USB_ENDPOINT_IN (CDC_ENDPOINT_IN ),USB_ENDPOINT_TYPE_BULK,USB_EP_SIZE,0) }; bool isLUFAbootloader() { - return pgm_read_word(FLASHEND - 1) == NEW_LUFA_SIGNATURE; + return pgm_read_word(FLASHEND - 1) == NEW_LUFA_SIGNATURE; } int CDC_GetInterface(uint8_t* interfaceNum) { - interfaceNum[0] += 2; // uses 2 - return USB_SendControl(TRANSFER_PGM,&_cdcInterface,sizeof(_cdcInterface)); + interfaceNum[0] += 2; // Uses 2 + return USB_SendControl(TRANSFER_PGM,&_cdcInterface,sizeof(_cdcInterface)); } -bool CDC_Setup(USBSetup& setup) +bool CDC_Setup(USBSetup &setup) { - uint8_t r = setup.bRequest; - uint8_t requestType = setup.bmRequestType; - - if (REQUEST_DEVICETOHOST_CLASS_INTERFACE == requestType) - { - if (CDC_GET_LINE_CODING == r) - { - USB_SendControl(0,(void*)&_usbLineInfo,7); - return true; - } - } - - if (REQUEST_HOSTTODEVICE_CLASS_INTERFACE == requestType) - { - if (CDC_SEND_BREAK == r) - { - breakValue = ((uint16_t)setup.wValueH << 8) | setup.wValueL; - } - - if (CDC_SET_LINE_CODING == r) - { - USB_RecvControl((void*)&_usbLineInfo,7); - } - - if (CDC_SET_CONTROL_LINE_STATE == r) - { - _usbLineInfo.lineState = setup.wValueL; - - // auto-reset into the bootloader is triggered when the port, already - // open at 1200 bps, is closed. this is the signal to start the watchdog - // with a relatively long period so it can finish housekeeping tasks - // like servicing endpoints before the sketch ends - - uint16_t magic_key_pos = MAGIC_KEY_POS; + uint8_t r = setup.bRequest; + uint8_t requestType = setup.bmRequestType; + + if (REQUEST_DEVICETOHOST_CLASS_INTERFACE == requestType) + { + if (CDC_GET_LINE_CODING == r) + { + USB_SendControl(0, (void *)&_usbLineInfo, 7); + return true; + } + } + + if (REQUEST_HOSTTODEVICE_CLASS_INTERFACE == requestType) + { + if (CDC_SEND_BREAK == r) + { + breakValue = ((uint16_t)setup.wValueH << 8) | setup.wValueL; + } + + if (CDC_SET_LINE_CODING == r) + { + USB_RecvControl((void *)&_usbLineInfo, 7); + } + + if (CDC_SET_CONTROL_LINE_STATE == r) + { + _usbLineInfo.lineState = setup.wValueL; + + // auto-reset into the bootloader is triggered when the port, already + // open at 1200 bps, is closed. this is the signal to start the watchdog + // with a relatively long period so it can finish housekeeping tasks + // like servicing endpoints before the sketch ends + + uint16_t magic_key_pos = MAGIC_KEY_POS; // If we don't use the new RAMEND directly, check manually if we have a newer bootloader. // This is used to keep compatible with the old leonardo bootloaders. // You are still able to set the magic key position manually to RAMEND-1 to save a few bytes for this check. -#if MAGIC_KEY_POS != (RAMEND-1) - // For future boards save the key in the inproblematic RAMEND - // Which is reserved for the main() return value (which will never return) - if (isLUFAbootloader()) { - // horray, we got a new bootloader! - magic_key_pos = (RAMEND-1); - } +#if MAGIC_KEY_POS != (RAMEND - 1) + // For future boards save the key in the inproblematic RAMEND + // Which is reserved for the main() return value (which will never return) + if (isLUFAbootloader()) + { + // horray, we got a new bootloader! + magic_key_pos = (RAMEND - 1); + } #endif - // We check DTR state to determine if host port is open (bit 0 of lineState). - if (1200 == _usbLineInfo.dwDTERate && (_usbLineInfo.lineState & 0x01) == 0) - { -#if MAGIC_KEY_POS != (RAMEND-1) - // Backup ram value if its not a newer bootloader and it hasn't already been saved. - // This should avoid memory corruption at least a bit, not fully - if (magic_key_pos != (RAMEND-1) && *(uint16_t *)magic_key_pos != MAGIC_KEY) { - *(uint16_t *)(RAMEND-1) = *(uint16_t *)magic_key_pos; - } + // We check DTR state to determine if host port is open (bit 0 of lineState). + if (1200 == _usbLineInfo.dwDTERate && (_usbLineInfo.lineState & 0x01) == 0) + { +#if MAGIC_KEY_POS != (RAMEND - 1) + // Backup ram value if its not a newer bootloader and it hasn't already been saved. + // This should avoid memory corruption at least a bit, not fully + if (magic_key_pos != (RAMEND - 1) && *(uint16_t *)magic_key_pos != MAGIC_KEY) + { + *(uint16_t *)(RAMEND - 1) = *(uint16_t *)magic_key_pos; + } #endif - // Store boot key - *(uint16_t *)magic_key_pos = MAGIC_KEY; - // Save the watchdog state in case the reset is aborted. - wdtcsr_save = WDTCSR; - wdt_enable(WDTO_120MS); - } - else if (*(uint16_t *)magic_key_pos == MAGIC_KEY) - { - // Most OSs do some intermediate steps when configuring ports and DTR can - // twiggle more than once before stabilizing. - // To avoid spurious resets we set the watchdog to 120ms and eventually - // cancel if DTR goes back high. - // Cancellation is only done if an auto-reset was started, which is - // indicated by the magic key having been set. - - wdt_reset(); - // Restore the watchdog state in case the sketch was using it. - WDTCSR |= (1<= 0) { - return 1 + USB_Available(CDC_RX); - } - return USB_Available(CDC_RX); + if (peek_buffer >= 0) + return 1 + USB_Available(CDC_RX); + return USB_Available(CDC_RX); } int Serial_::peek(void) { - if (peek_buffer < 0) - peek_buffer = USB_Recv(CDC_RX); - return peek_buffer; + if (peek_buffer < 0) + peek_buffer = USB_Recv(CDC_RX); + return peek_buffer; } int Serial_::read(void) { - if (peek_buffer >= 0) { - int c = peek_buffer; - peek_buffer = -1; - return c; - } - return USB_Recv(CDC_RX); + if (peek_buffer >= 0) + { + int c = peek_buffer; + peek_buffer = -1; + return c; + } + return USB_Recv(CDC_RX); } int Serial_::availableForWrite(void) { - return USB_SendSpace(CDC_TX); + return USB_SendSpace(CDC_TX); } void Serial_::flush(void) { - USB_Flush(CDC_TX); + USB_Flush(CDC_TX); } size_t Serial_::write(uint8_t c) { - return write(&c, 1); + return write(&c, 1); } size_t Serial_::write(const uint8_t *buffer, size_t size) { - /* only try to send bytes if the high-level CDC connection itself - is open (not just the pipe) - the OS should set lineState when the port - is opened and clear lineState when the port is closed. - bytes sent before the user opens the connection or after - the connection is closed are lost - just like with a UART. */ - - // TODO - ZE - check behavior on different OSes and test what happens if an - // open connection isn't broken cleanly (cable is yanked out, host dies - // or locks up, or host virtual serial port hangs) - if (_usbLineInfo.lineState > 0) { - int r = USB_Send(CDC_TX,buffer,size); - if (r > 0) { - return r; - } else { - setWriteError(); - return 0; - } - } - setWriteError(); - return 0; + /* only try to send bytes if the high-level CDC connection itself + is open (not just the pipe) - the OS should set lineState when the port + is opened and clear lineState when the port is closed. + bytes sent before the user opens the connection or after + the connection is closed are lost - just like with a UART. */ + + // TODO - ZE - check behavior on different OSes and test what happens if an + // open connection isn't broken cleanly (cable is yanked out, host dies + // or locks up, or host virtual serial port hangs) + if (_usbLineInfo.lineState > 0) + { + int r = USB_Send(CDC_TX, buffer, size); + if (r > 0) + { + return r; + } + else + { + setWriteError(); + return 0; + } + } + setWriteError(); + return 0; } // This operator is a convenient way for a sketch to check whether the // port has actually been configured and opened by the host (as opposed -// to just being connected to the host). It can be used, for example, in +// to just being connected to the host). It can be used, for example, in // setup() before printing to ensure that an application on the host is // actually ready to receive and display the data. // We add a short delay before returning to fix a bug observed by Federico // where the port is configured (lineState != 0) but not quite opened. -Serial_::operator bool() { - bool result = false; - if (_usbLineInfo.lineState > 0) - result = true; - delay(10); - return result; +Serial_::operator bool() +{ + bool result = false; + if (_usbLineInfo.lineState > 0) + result = true; + delay(10); + return result; } -unsigned long Serial_::baud() { - // Disable interrupts while reading a multi-byte value - uint32_t baudrate; - ATOMIC_BLOCK(ATOMIC_RESTORESTATE) { - baudrate = _usbLineInfo.dwDTERate; - } - return baudrate; +unsigned long Serial_::baud() +{ + // Disable interrupts while reading a multi-byte value + uint32_t baudrate; + ATOMIC_BLOCK(ATOMIC_RESTORESTATE) + { + baudrate = _usbLineInfo.dwDTERate; + } + return baudrate; } -uint8_t Serial_::stopbits() { - return _usbLineInfo.bCharFormat; +uint8_t Serial_::stopbits() +{ + return _usbLineInfo.bCharFormat; } -uint8_t Serial_::paritytype() { - return _usbLineInfo.bParityType; +uint8_t Serial_::paritytype() +{ + return _usbLineInfo.bParityType; } -uint8_t Serial_::numbits() { - return _usbLineInfo.bDataBits; +uint8_t Serial_::numbits() +{ + return _usbLineInfo.bDataBits; } -bool Serial_::dtr() { - return _usbLineInfo.lineState & 0x1; +bool Serial_::dtr() +{ + return _usbLineInfo.lineState & 0x1; } -bool Serial_::rts() { - return _usbLineInfo.lineState & 0x2; +bool Serial_::rts() +{ + return _usbLineInfo.lineState & 0x2; } -int32_t Serial_::readBreak() { - int32_t ret; - // Disable IRQs while reading and clearing breakValue to make - // sure we don't overwrite a value just set by the ISR. - ATOMIC_BLOCK(ATOMIC_RESTORESTATE) { - ret = breakValue; - breakValue = -1; - } - return ret; +int32_t Serial_::readBreak() +{ + int32_t ret; + // Disable IRQs while reading and clearing breakValue to make + // sure we don't overwrite a value just set by the ISR. + ATOMIC_BLOCK(ATOMIC_RESTORESTATE) + { + ret = breakValue; + breakValue = -1; + } + return ret; } Serial_ Serial; diff --git a/megaavr/cores/coreX-corefiles/CDC.h b/megaavr/cores/coreX-corefiles/CDC.h index 43b382e..4df6459 100644 --- a/megaavr/cores/coreX-corefiles/CDC.h +++ b/megaavr/cores/coreX-corefiles/CDC.h @@ -4,11 +4,11 @@ #include "api/Stream.h" #include "api/USBAPI.h" -#if defined (USBCON) +#if defined(USBCON) //================================================================================ //================================================================================ -// Serial over CDC (Serial1 is the physical port) +// Serial over CDC (Serial1 is the physical port) #define RINGBUFFER_FORCE_SMALL_SIZE #include "api/RingBuffer.h" @@ -26,65 +26,67 @@ class Serial_ : public Stream { -private: - int peek_buffer; -public: - Serial_() { peek_buffer = -1; }; - void begin(unsigned long); - void begin(unsigned long, uint8_t); - void end(void); - - virtual int available(void); - virtual int peek(void); - virtual int read(void); - virtual int availableForWrite(void); - virtual void flush(void); - virtual size_t write(uint8_t); - virtual size_t write(const uint8_t*, size_t); - using Print::write; // pull in write(str) and write(buf, size) from Print - operator bool(); - - //RingBuffer _rx_buffer(SERIAL_BUFFER_SIZE); - - // This method allows processing "SEND_BREAK" requests sent by - // the USB host. Those requests indicate that the host wants to - // send a BREAK signal and are accompanied by a single uint16_t - // value, specifying the duration of the break. The value 0 - // means to end any current break, while the value 0xffff means - // to start an indefinite break. - // readBreak() will return the value of the most recent break - // request, but will return it at most once, returning -1 when - // readBreak() is called again (until another break request is - // received, which is again returned once). - // This also mean that if two break requests are received - // without readBreak() being called in between, the value of the - // first request is lost. - // Note that the value returned is a long, so it can return - // 0-0xffff as well as -1. - int32_t readBreak(); - - // These return the settings specified by the USB host for the - // serial port. These aren't really used, but are offered here - // in case a sketch wants to act on these settings. - uint32_t baud(); - uint8_t stopbits(); - uint8_t paritytype(); - uint8_t numbits(); - bool dtr(); - bool rts(); - enum { - ONE_STOP_BIT = 0, - ONE_AND_HALF_STOP_BIT = 1, - TWO_STOP_BITS = 2, - }; - enum { - NO_PARITY = 0, - ODD_PARITY = 1, - EVEN_PARITY = 2, - MARK_PARITY = 3, - SPACE_PARITY = 4, - }; - + private: + int peek_buffer; + + public: + Serial_() { peek_buffer = -1; }; + void begin(unsigned long); + void begin(unsigned long, uint8_t); + void end(void); + + virtual int available(void); + virtual int peek(void); + virtual int read(void); + virtual int availableForWrite(void); + virtual void flush(void); + virtual size_t write(uint8_t); + virtual size_t write(const uint8_t*, size_t); + using Print::write; // pull in write(str) and write(buf, size) from Print + operator bool(); + + //RingBuffer _rx_buffer(SERIAL_BUFFER_SIZE); + + // This method allows processing "SEND_BREAK" requests sent by + // the USB host. Those requests indicate that the host wants to + // send a BREAK signal and are accompanied by a single uint16_t + // value, specifying the duration of the break. The value 0 + // means to end any current break, while the value 0xffff means + // to start an indefinite break. + // readBreak() will return the value of the most recent break + // request, but will return it at most once, returning -1 when + // readBreak() is called again (until another break request is + // received, which is again returned once). + // This also mean that if two break requests are received + // without readBreak() being called in between, the value of the + // first request is lost. + // Note that the value returned is a long, so it can return + // 0-0xffff as well as -1. + int32_t readBreak(); + + // These return the settings specified by the USB host for the + // serial port. These aren't really used, but are offered here + // in case a sketch wants to act on these settings. + uint32_t baud(); + uint8_t stopbits(); + uint8_t paritytype(); + uint8_t numbits(); + bool dtr(); + bool rts(); + enum + { + ONE_STOP_BIT = 0, + ONE_AND_HALF_STOP_BIT = 1, + TWO_STOP_BITS = 2, + }; + enum + { + NO_PARITY = 0, + ODD_PARITY = 1, + EVEN_PARITY = 2, + MARK_PARITY = 3, + SPACE_PARITY = 4, + }; }; extern Serial_ Serial; @@ -92,11 +94,11 @@ extern Serial_ Serial; //================================================================================ //================================================================================ -// CSC 'Driver' +// CSC 'Driver' -int CDC_GetInterface(uint8_t* interfaceNum); -int CDC_GetDescriptor(int i); -bool CDC_Setup(USBSetup& setup); +int CDC_GetInterface(uint8_t* interfaceNum); +int CDC_GetDescriptor(int i); +bool CDC_Setup(USBSetup& setup); #endif diff --git a/megaavr/cores/coreX-corefiles/MSC.h b/megaavr/cores/coreX-corefiles/MSC.h index 96028e1..3705587 100644 --- a/megaavr/cores/coreX-corefiles/MSC.h +++ b/megaavr/cores/coreX-corefiles/MSC.h @@ -1,4 +1,4 @@ -#if defined (USBCON) +#if defined(USBCON) #ifndef __MSC_H__ #define __MSC_H__ @@ -7,12 +7,12 @@ //================================================================================ //================================================================================ -// MSC 'Driver' +// MSC 'Driver' -int MSC_GetInterface(uint8_t* interfaceNum); -int MSC_GetDescriptor(int i); -bool MSC_Setup(USBSetup& setup); -bool MSC_Data(uint8_t rx,uint8_t tx); +int MSC_GetInterface(uint8_t* interfaceNum); +int MSC_GetDescriptor(int i); +bool MSC_Setup(USBSetup& setup); +bool MSC_Data(uint8_t rx, uint8_t tx); #endif diff --git a/megaavr/cores/coreX-corefiles/Tone.cpp b/megaavr/cores/coreX-corefiles/Tone.cpp index 87f5da1..791154f 100644 --- a/megaavr/cores/coreX-corefiles/Tone.cpp +++ b/megaavr/cores/coreX-corefiles/Tone.cpp @@ -36,29 +36,30 @@ #include #include + #include "Arduino.h" #include "pins_arduino.h" /* For more than one tone, change AVAILABLE_TONE_PINS and uncomment the correct number of timers */ -#define AVAILABLE_TONE_PINS 1 +#define AVAILABLE_TONE_PINS 1 -#define USE_TIMERB1 // interferes with TCB1 PWM +#define USE_TIMERB1 // interferes with TCB1 PWM /* #define USE_TIMERB2 // interferes with TCB2 PWM, and timer in many configurations #define USE_TIMERB0 // interferes with TCB0 PWM */ #if !defined(USE_TIMERB0) && !defined(USE_TIMERB1) && !defined(USE_TIMERB2) && !defined(USE_TIMERB3) - # error "No timers allowed for tone()" - /* Please uncomment a timer above and rebuild */ +#error "No timers allowed for tone()" +/* Please uncomment a timer above and rebuild */ #endif // Can't use timer assigned for application time tracking (usually TIMERB2 or TIMERB3) // Using TIMERA0 NOT RECOMMENDED -- all other timers use its clock! -static volatile TCB_t* _timer = +static volatile TCB_t *_timer = #if defined(USE_TIMERB0) -&TCB0; + &TCB0; #endif #if defined(USE_TIMERB1) &TCB1; @@ -88,108 +89,119 @@ static byte timerPrescaler(); // frequency (in hertz) and duration (in milliseconds). void tone(uint8_t pin, unsigned int frequency, unsigned long duration) { - long toggle_count = 0; - uint32_t compare_val = 0; - - if (_pin != pin) { - pinMode(pin, OUTPUT); - _pin = pin; - } - - // Get pin related stuff - PORT_t *port = digitalPinToPortStruct(_pin); - uint8_t *port_outtgl = (uint8_t *)&(port->OUTTGL); - uint8_t bit_mask = digitalPinToBitMask(_pin); - - if (frequency == 0) { - bit_mask = 0; - frequency = 1; - } - - // Calculate compare value, assuming F_CPU/2 used as clock - compare_val = F_CPU / frequency / 4 - 1; - // If compare larger than 16bits, need to prescale (will be DIV64) - uint8_t prescaler = 0; - if (compare_val > 0xFFFF){ - // recalculate with new prescaler - prescaler = timerPrescaler(); - compare_val = F_CPU / frequency / 2 / prescaler - 1; - if (compare_val > 0xFFFF) compare_val = 0xFFFF; // request lower frequency than supported - } - - // Calculate the toggle count - if (duration > 0){ // Duration defined - toggle_count = 2 * frequency * duration / 1000; - } else { // Duration not defined -- tone until noTone() call - toggle_count = -1; - } - - // Timer settings -- will be type B - uint8_t status = SREG; - cli(); - - // Disable for now, set clk according to whether 'prescaler' is zero - // (Prescaled clock will come from TCA -- - // by default it should have a prescaler of 64 (250kHz clock) - // but this may have changed with analogWriteFrequency() - // TCA default initialization is in wiring.c -- init() ) - if(prescaler != 0){ - _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; - } else { - _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; - } - - // Timer to Periodic interrupt mode - // This write will also disable any active PWM outputs - _timer->CTRLB = TCB_CNTMODE_INT_gc; - - // Write compare register - _timer->CCMP = compare_val; - - // Enable interrupt - _timer->INTCTRL = TCB_CAPTEI_bm; - - timer_outtgl_reg = port_outtgl; - timer_bit_mask = bit_mask; - timer_toggle_count = toggle_count; - - // Enable timer - _timer->CTRLA |= TCB_ENABLE_bm; - - SREG = status; + long toggle_count = 0; + uint32_t compare_val = 0; + + if (_pin != pin) + { + pinMode(pin, OUTPUT); + _pin = pin; + } + + // Get pin related stuff + PORT_t *port = digitalPinToPortStruct(_pin); + uint8_t *port_outtgl = (uint8_t *)&(port->OUTTGL); + uint8_t bit_mask = digitalPinToBitMask(_pin); + + if (frequency == 0) + { + bit_mask = 0; + frequency = 1; + } + + // Calculate compare value, assuming F_CPU/2 used as clock + compare_val = F_CPU / frequency / 4 - 1; + // If compare larger than 16bits, need to prescale (will be DIV64) + uint8_t prescaler = 0; + if (compare_val > 0xFFFF) + { + // recalculate with new prescaler + prescaler = timerPrescaler(); + compare_val = F_CPU / frequency / 2 / prescaler - 1; + if (compare_val > 0xFFFF) compare_val = 0xFFFF; // request lower frequency than supported + } + + // Calculate the toggle count + if (duration > 0) + { // Duration defined + toggle_count = 2 * frequency * duration / 1000; + } + else + { // Duration not defined -- tone until noTone() call + toggle_count = -1; + } + + // Timer settings -- will be type B + uint8_t status = SREG; + cli(); + + // Disable for now, set clk according to whether 'prescaler' is zero + // (Prescaled clock will come from TCA -- + // by default it should have a prescaler of 64 (250kHz clock) + // but this may have changed with analogWriteFrequency() + // TCA default initialization is in wiring.c -- init() ) + if (prescaler != 0) + { + _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; + } + else + { + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; + } + + // Timer to Periodic interrupt mode + // This write will also disable any active PWM outputs + _timer->CTRLB = TCB_CNTMODE_INT_gc; + + // Write compare register + _timer->CCMP = compare_val; + + // Enable interrupt + _timer->INTCTRL = TCB_CAPTEI_bm; + + timer_outtgl_reg = port_outtgl; + timer_bit_mask = bit_mask; + timer_toggle_count = toggle_count; + + // Enable timer + _timer->CTRLA |= TCB_ENABLE_bm; + + SREG = status; } // pin which currently is being used for a tone void noTone(uint8_t pin) { - if (pin == _pin) { - timer_toggle_count = 0; - //disableTimer(); - // Keep pin low after disabling of timer - digitalWrite(_pin, LOW); - _pin = NOT_A_PIN; - } + if (pin == _pin) + { + timer_toggle_count = 0; + //disableTimer(); + // Keep pin low after disabling of timer + digitalWrite(_pin, LOW); + _pin = NOT_A_PIN; + } } // helper function for noTone() // find which timer prescaler is currently used static byte timerPrescaler() { - byte clksel = (TCA0.SPLIT.CTRLA & TCA_SPLIT_CLKSEL_gm) >> TCA_SPLIT_CLKSEL_gp; - - // the next five lines may have been a #if, - // but alas the C preprocessor does not understand enums - // they should produce no real code, though - if ((TCA_SPLIT_CLKSEL_DIV1_gc>>TCA_SPLIT_CLKSEL_gp) == 0 - && (TCA_SPLIT_CLKSEL_DIV2_gc>>TCA_SPLIT_CLKSEL_gp) == 1 - && (TCA_SPLIT_CLKSEL_DIV4_gc>>TCA_SPLIT_CLKSEL_gp) == 2 - && (TCA_SPLIT_CLKSEL_DIV8_gc>>TCA_SPLIT_CLKSEL_gp) == 3 - && (TCA_SPLIT_CLKSEL_DIV16_gc>>TCA_SPLIT_CLKSEL_gp) == 4 - && clksel <= (TCA_SPLIT_CLKSEL_DIV16_gc>>TCA_SPLIT_CLKSEL_gp)) { - // non-standard TCA clock selection is used - return 1 << clksel; - } - return 64; + byte clksel = (TCA0.SPLIT.CTRLA & TCA_SPLIT_CLKSEL_gm) >> TCA_SPLIT_CLKSEL_gp; + + // the next five lines may have been a #if, + // but alas the C preprocessor does not understand enums + // they should produce no real code, though + if ((TCA_SPLIT_CLKSEL_DIV1_gc >> TCA_SPLIT_CLKSEL_gp) == 0 + && (TCA_SPLIT_CLKSEL_DIV2_gc >> TCA_SPLIT_CLKSEL_gp) == 1 + && (TCA_SPLIT_CLKSEL_DIV4_gc >> TCA_SPLIT_CLKSEL_gp) == 2 + && (TCA_SPLIT_CLKSEL_DIV8_gc >> TCA_SPLIT_CLKSEL_gp) == 3 + && (TCA_SPLIT_CLKSEL_DIV16_gc >> TCA_SPLIT_CLKSEL_gp) == 4 + && clksel <= (TCA_SPLIT_CLKSEL_DIV16_gc >> TCA_SPLIT_CLKSEL_gp)) + { + // non-standard TCA clock selection is used + return 1 << clksel; + } + return 64; } // helper function for noTone() @@ -197,11 +209,11 @@ static byte timerPrescaler() configuration it had to output PWM for analogWrite() */ static void disableTimer() { - // Reinit back to producing PWM -- timer will be type B - // Disable interrupt - _timer->INTCTRL = 0; - // Disable timer - _timer->CTRLA = 0; + // Reinit back to producing PWM -- timer will be type B + // Disable interrupt + _timer->INTCTRL = 0; + // Disable timer + _timer->CTRLA = 0; #if 0 // RESTORE PWM FUNCTIONALITY: @@ -217,7 +229,6 @@ static void disableTimer() #endif } - #if defined USE_TIMERB0 ISR(TCB0_INT_vect) #elif defined USE_TIMERB1 @@ -226,23 +237,25 @@ ISR(TCB1_INT_vect) ISR(TCB2_INT_vect) #endif { - if (timer_toggle_count != 0){ - - // toggle the pin - *timer_outtgl_reg = timer_bit_mask; - - // If duration was defined, decrement - if (timer_toggle_count > 0){ - timer_toggle_count--; - } - - // If no duration (toggle count negative), go on until noTone() call + if (timer_toggle_count != 0) + { + // toggle the pin + *timer_outtgl_reg = timer_bit_mask; + + // If duration was defined, decrement + if (timer_toggle_count > 0) + { + timer_toggle_count--; + } - } else if (timer_toggle_count == 0) { // If toggle count = 0, stop + // If no duration (toggle count negative), go on until noTone() call + } + else if (timer_toggle_count == 0) + { // If toggle count = 0, stop - disableTimer(); - } + disableTimer(); + } - /* Clear flag */ - _timer->INTFLAGS = TCB_CAPT_bm; + /* Clear flag */ + _timer->INTFLAGS = TCB_CAPT_bm; } diff --git a/megaavr/cores/coreX-corefiles/UART.cpp b/megaavr/cores/coreX-corefiles/UART.cpp index 23002d4..1ce409d 100644 --- a/megaavr/cores/coreX-corefiles/UART.cpp +++ b/megaavr/cores/coreX-corefiles/UART.cpp @@ -63,16 +63,16 @@ bool Serial3_available() __attribute__((weak)); void serialEventRun(void) { #if defined(HAVE_HWSERIAL0) - if (Serial0_available && serialEvent && Serial0_available()) serialEvent(); + if (Serial0_available && serialEvent && Serial0_available()) serialEvent(); #endif #if defined(HAVE_HWSERIAL1) - if (Serial1_available && serialEvent1 && Serial1_available()) serialEvent1(); + if (Serial1_available && serialEvent1 && Serial1_available()) serialEvent1(); #endif #if defined(HAVE_HWSERIAL2) - if (Serial2_available && serialEvent2 && Serial2_available()) serialEvent2(); + if (Serial2_available && serialEvent2 && Serial2_available()) serialEvent2(); #endif #if defined(HAVE_HWSERIAL3) - if (Serial3_available && serialEvent3 && Serial3_available()) serialEvent3(); + if (Serial3_available && serialEvent3 && Serial3_available()) serialEvent3(); #endif } @@ -87,65 +87,71 @@ void serialEventRun(void) void UartClass::_tx_data_empty_irq(void) { - // Check if tx buffer already empty. - if (_tx_buffer_head == _tx_buffer_tail) { - // Buffer empty, so disable "data register empty" interrupt - (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); - return; - } + // Check if tx buffer already empty. + if (_tx_buffer_head == _tx_buffer_tail) + { + // Buffer empty, so disable "data register empty" interrupt + (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); + return; + } - // There must be more data in the output - // buffer. Send the next byte - unsigned char c = _tx_buffer[_tx_buffer_tail]; - _tx_buffer_tail = (_tx_buffer_tail + 1) % SERIAL_TX_BUFFER_SIZE; + // There must be more data in the output + // buffer. Send the next byte + unsigned char c = _tx_buffer[_tx_buffer_tail]; + _tx_buffer_tail = (_tx_buffer_tail + 1) % SERIAL_TX_BUFFER_SIZE; - // clear the TXCIF flag -- "can be cleared by writing a one to its bit - // location". This makes sure flush() won't return until the bytes - // actually got written - (*_hwserial_module).STATUS = USART_TXCIF_bm; + // clear the TXCIF flag -- "can be cleared by writing a one to its bit + // location". This makes sure flush() won't return until the bytes + // actually got written + (*_hwserial_module).STATUS = USART_TXCIF_bm; - (*_hwserial_module).TXDATAL = c; - - if (_tx_buffer_head == _tx_buffer_tail) { - // Buffer empty, so disable "data register empty" interrupt - (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); + (*_hwserial_module).TXDATAL = c; - //Take the DRE interrupt back no normal priority level if it has been elevated - if(_hwserial_dre_interrupt_elevated) { - CPUINT.LVL1VEC = _prev_lvl1_interrupt_vect; - _hwserial_dre_interrupt_elevated = 0; - } + if (_tx_buffer_head == _tx_buffer_tail) + { + // Buffer empty, so disable "data register empty" interrupt + (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); + + //Take the DRE interrupt back no normal priority level if it has been elevated + if (_hwserial_dre_interrupt_elevated) + { + CPUINT.LVL1VEC = _prev_lvl1_interrupt_vect; + _hwserial_dre_interrupt_elevated = 0; } + } } // To invoke data empty "interrupt" via a call, use this method void UartClass::_poll_tx_data_empty(void) { - if ( (!(SREG & CPU_I_bm)) || (!((*_hwserial_module).CTRLA & USART_DREIE_bm)) ) { + if ((!(SREG & CPU_I_bm)) || (!((*_hwserial_module).CTRLA & USART_DREIE_bm))) + { // Interrupts are disabled either globally or for data register empty, // so we'll have to poll the "data register empty" flag ourselves. // If it is set, pretend an interrupt has happened and call the handler // to free up space for us. // Invoke interrupt handler only if conditions data register is empty - if ((*_hwserial_module).STATUS & USART_DREIF_bm) { + if ((*_hwserial_module).STATUS & USART_DREIF_bm) + { _tx_data_empty_irq(); } } // In case interrupts are enabled, the interrupt routine will be invoked by itself } - // Public Methods ////////////////////////////////////////////////////////////// // Invoke this function before 'begin' to define the pins used bool UartClass::pins(uint8_t tx, uint8_t rx) { - for (_pin_set = 0; _pin_set < SERIAL_PIN_SETS; ++_pin_set) { - if (tx == _hw_set[_pin_set].tx_pin && rx == _hw_set[_pin_set].rx_pin) { + for (_pin_set = 0; _pin_set < SERIAL_PIN_SETS; ++_pin_set) + { + if (tx == _hw_set[_pin_set].tx_pin && rx == _hw_set[_pin_set].rx_pin) + { // We are good, this set of pins is supported - return true; - } + return true; + } } _pin_set = 0; // Default to standard return false; @@ -153,17 +159,17 @@ bool UartClass::pins(uint8_t tx, uint8_t rx) bool UartClass::swap(uint8_t state) { - if(state == 1) // Use alternative pin position + if (state == 1) // Use alternative pin position { _pin_set = state; return true; } - else if(state == 0) // Use default pin position + else if (state == 0) // Use default pin position { _pin_set = 0; return true; } - else // Invalid swap value. Use default position + else // Invalid swap value. Use default position { _pin_set = 0; return false; @@ -172,196 +178,208 @@ bool UartClass::swap(uint8_t state) void UartClass::begin(unsigned long baud, uint16_t config) { - // Make sure no transmissions are ongoing and USART is disabled in case begin() is called by accident - // without first calling end() - if(_written) { - this->end(); - } + // Make sure no transmissions are ongoing and USART is disabled in case begin() is called by accident + // without first calling end() + if (_written) + { + this->end(); + } - struct UartPinSet *set = &_hw_set[_pin_set]; + struct UartPinSet *set = &_hw_set[_pin_set]; - int32_t baud_setting = 0; + int32_t baud_setting = 0; - //Make sure global interrupts are disabled during initialization - uint8_t oldSREG = SREG; - cli(); + //Make sure global interrupts are disabled during initialization + uint8_t oldSREG = SREG; + cli(); - baud_setting = (((8 * F_CPU) / baud) + 1) / 2; - // Disable CLK2X - (*_hwserial_module).CTRLB &= (~USART_RXMODE_CLK2X_gc); - (*_hwserial_module).CTRLB |= USART_RXMODE_NORMAL_gc; + baud_setting = (((8 * F_CPU) / baud) + 1) / 2; + // Disable CLK2X + (*_hwserial_module).CTRLB &= (~USART_RXMODE_CLK2X_gc); + (*_hwserial_module).CTRLB |= USART_RXMODE_NORMAL_gc; - _written = false; + _written = false; - int8_t sigrow_val = 0; + int8_t sigrow_val = 0; // Use error compensation if internal oscillator is used #if !defined(USE_EXTERNAL_OSCILLATOR) - #if F_CPU == 20000000L - sigrow_val = SIGROW.OSC20ERR5V; - #else - sigrow_val = SIGROW.OSC16ERR5V; - #endif +#if F_CPU == 20000000L + sigrow_val = SIGROW.OSC20ERR5V; +#else + sigrow_val = SIGROW.OSC16ERR5V; +#endif #endif - baud_setting += (baud_setting * sigrow_val) / 1024; - - // assign the baud_setting, a.k.a. BAUD (USART Baud Rate Register) - (*_hwserial_module).BAUD = (uint16_t)baud_setting; + baud_setting += (baud_setting * sigrow_val) / 1024; - // Set USART mode of operation - (*_hwserial_module).CTRLC = config; + // assign the baud_setting, a.k.a. BAUD (USART Baud Rate Register) + (*_hwserial_module).BAUD = (uint16_t)baud_setting; - // Enable transmitter and receiver - (*_hwserial_module).CTRLB |= (USART_RXEN_bm | USART_TXEN_bm); + // Set USART mode of operation + (*_hwserial_module).CTRLC = config; - (*_hwserial_module).CTRLA |= USART_RXCIE_bm; + // Enable transmitter and receiver + (*_hwserial_module).CTRLB |= (USART_RXEN_bm | USART_TXEN_bm); + (*_hwserial_module).CTRLA |= USART_RXCIE_bm; - // Let PORTMUX point to alternative UART pins as requested - PORTMUX.USARTROUTEA = set->mux | (PORTMUX.USARTROUTEA & ~_hw_set[1].mux); + // Let PORTMUX point to alternative UART pins as requested + PORTMUX.USARTROUTEA = set->mux | (PORTMUX.USARTROUTEA & ~_hw_set[1].mux); - // Set pin state for swapped UART pins - pinMode(set->rx_pin, INPUT_PULLUP); - digitalWrite(set->tx_pin, HIGH); - pinMode(set->tx_pin, OUTPUT); + // Set pin state for swapped UART pins + pinMode(set->rx_pin, INPUT_PULLUP); + digitalWrite(set->tx_pin, HIGH); + pinMode(set->tx_pin, OUTPUT); - // Restore SREG content - SREG = oldSREG; + // Restore SREG content + SREG = oldSREG; } void UartClass::end() { - // wait for transmission of outgoing data - flush(); + // wait for transmission of outgoing data + flush(); - // Disable receiver and transmitter as well as the RX complete and - // data register empty interrupts. - (*_hwserial_module).CTRLB &= ~(USART_RXEN_bm | USART_TXEN_bm); - (*_hwserial_module).CTRLA &= ~(USART_RXCIE_bm | USART_DREIE_bm); + // Disable receiver and transmitter as well as the RX complete and + // data register empty interrupts. + (*_hwserial_module).CTRLB &= ~(USART_RXEN_bm | USART_TXEN_bm); + (*_hwserial_module).CTRLA &= ~(USART_RXCIE_bm | USART_DREIE_bm); - // clear any received data - _rx_buffer_head = _rx_buffer_tail; + // clear any received data + _rx_buffer_head = _rx_buffer_tail; - // Note: Does not change output pins - _written = false; + // Note: Does not change output pins + _written = false; } int UartClass::available(void) { - return ((unsigned int)(SERIAL_RX_BUFFER_SIZE + _rx_buffer_head - _rx_buffer_tail)) % SERIAL_RX_BUFFER_SIZE; + return ((unsigned int)(SERIAL_RX_BUFFER_SIZE + _rx_buffer_head - _rx_buffer_tail)) % SERIAL_RX_BUFFER_SIZE; } int UartClass::peek(void) { - if (_rx_buffer_head == _rx_buffer_tail) { - return -1; - } else { - return _rx_buffer[_rx_buffer_tail]; - } + if (_rx_buffer_head == _rx_buffer_tail) + { + return -1; + } + else + { + return _rx_buffer[_rx_buffer_tail]; + } } int UartClass::read(void) { - // if the head isn't ahead of the tail, we don't have any characters - if (_rx_buffer_head == _rx_buffer_tail) { - return -1; - } else { - unsigned char c = _rx_buffer[_rx_buffer_tail]; - _rx_buffer_tail = (rx_buffer_index_t)(_rx_buffer_tail + 1) % SERIAL_RX_BUFFER_SIZE; - return c; - } + // if the head isn't ahead of the tail, we don't have any characters + if (_rx_buffer_head == _rx_buffer_tail) + { + return -1; + } + else + { + unsigned char c = _rx_buffer[_rx_buffer_tail]; + _rx_buffer_tail = (rx_buffer_index_t)(_rx_buffer_tail + 1) % SERIAL_RX_BUFFER_SIZE; + return c; + } } int UartClass::availableForWrite(void) { - tx_buffer_index_t head; - tx_buffer_index_t tail; + tx_buffer_index_t head; + tx_buffer_index_t tail; - TX_BUFFER_ATOMIC { - head = _tx_buffer_head; - tail = _tx_buffer_tail; - } - if (head >= tail) return SERIAL_TX_BUFFER_SIZE - 1 - head + tail; - return tail - head - 1; + TX_BUFFER_ATOMIC + { + head = _tx_buffer_head; + tail = _tx_buffer_tail; + } + if (head >= tail) return SERIAL_TX_BUFFER_SIZE - 1 - head + tail; + return tail - head - 1; } void UartClass::flush() { - // If we have never written a byte, no need to flush. This special - // case is needed since there is no way to force the TXCIF (transmit - // complete) bit to 1 during initialization - if (!_written) { - return; - } - - //Check if we are inside an ISR already (e.g. connected to a different peripheral then UART), in which case the UART ISRs will not be called. - //Temporarily elevate the DRE interrupt to allow it to run. - if(CPUINT.STATUS & CPUINT_LVL0EX_bm) { - //Elevate the priority level of the Data Register Empty Interrupt vector - //and copy whatever vector number that might be in the register already. - _prev_lvl1_interrupt_vect = CPUINT.LVL1VEC; - CPUINT.LVL1VEC = _hwserial_dre_interrupt_vect_num; + // If we have never written a byte, no need to flush. This special + // case is needed since there is no way to force the TXCIF (transmit + // complete) bit to 1 during initialization + if (!_written) + { + return; + } - _hwserial_dre_interrupt_elevated = 1; - } + //Check if we are inside an ISR already (e.g. connected to a different peripheral then UART), in which case the UART ISRs will not be called. + //Temporarily elevate the DRE interrupt to allow it to run. + if (CPUINT.STATUS & CPUINT_LVL0EX_bm) + { + //Elevate the priority level of the Data Register Empty Interrupt vector + //and copy whatever vector number that might be in the register already. + _prev_lvl1_interrupt_vect = CPUINT.LVL1VEC; + CPUINT.LVL1VEC = _hwserial_dre_interrupt_vect_num; - // Spin until the data-register-empty-interrupt is disabled and TX complete interrupt flag is raised - while ( ((*_hwserial_module).CTRLA & USART_DREIE_bm) || (!((*_hwserial_module).STATUS & USART_TXCIF_bm)) ) { + _hwserial_dre_interrupt_elevated = 1; + } - // If interrupts are globally disabled or the and DR empty interrupt is disabled, - // poll the "data register empty" interrupt flag to prevent deadlock - _poll_tx_data_empty(); - } - // If we get here, nothing is queued anymore (DREIE is disabled) and - // the hardware finished transmission (TXCIF is set). + // Spin until the data-register-empty-interrupt is disabled and TX complete interrupt flag is raised + while (((*_hwserial_module).CTRLA & USART_DREIE_bm) || (!((*_hwserial_module).STATUS & USART_TXCIF_bm))) + { + // If interrupts are globally disabled or the and DR empty interrupt is disabled, + // poll the "data register empty" interrupt flag to prevent deadlock + _poll_tx_data_empty(); + } + // If we get here, nothing is queued anymore (DREIE is disabled) and + // the hardware finished transmission (TXCIF is set). } size_t UartClass::write(uint8_t c) { - _written = true; + _written = true; - // If the buffer and the data register is empty, just write the byte - // to the data register and be done. This shortcut helps - // significantly improve the effective data rate at high (> - // 500kbit/s) bit rates, where interrupt overhead becomes a slowdown. - if ( (_tx_buffer_head == _tx_buffer_tail) && ((*_hwserial_module).STATUS & USART_DREIF_bm) ) { - (*_hwserial_module).TXDATAL = c; - (*_hwserial_module).STATUS = USART_TXCIF_bm; + // If the buffer and the data register is empty, just write the byte + // to the data register and be done. This shortcut helps + // significantly improve the effective data rate at high (> + // 500kbit/s) bit rates, where interrupt overhead becomes a slowdown. + if ((_tx_buffer_head == _tx_buffer_tail) && ((*_hwserial_module).STATUS & USART_DREIF_bm)) + { + (*_hwserial_module).TXDATAL = c; + (*_hwserial_module).STATUS = USART_TXCIF_bm; - // Make sure data register empty interrupt is disabled to avoid - // that the interrupt handler is called in this situation - (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); + // Make sure data register empty interrupt is disabled to avoid + // that the interrupt handler is called in this situation + (*_hwserial_module).CTRLA &= (~USART_DREIE_bm); - return 1; - } + return 1; + } - //Check if we are inside an ISR already (could be from by a source other than UART), - // in which case the UART ISRs will be blocked. - if(CPUINT.STATUS & CPUINT_LVL0EX_bm) { - //Elevate the priority level of the Data Register Empty Interrupt vector - //and copy whatever vector number that might be in the register already. - _prev_lvl1_interrupt_vect = CPUINT.LVL1VEC; - CPUINT.LVL1VEC = _hwserial_dre_interrupt_vect_num; + //Check if we are inside an ISR already (could be from by a source other than UART), + // in which case the UART ISRs will be blocked. + if (CPUINT.STATUS & CPUINT_LVL0EX_bm) + { + //Elevate the priority level of the Data Register Empty Interrupt vector + //and copy whatever vector number that might be in the register already. + _prev_lvl1_interrupt_vect = CPUINT.LVL1VEC; + CPUINT.LVL1VEC = _hwserial_dre_interrupt_vect_num; - _hwserial_dre_interrupt_elevated = 1; - } + _hwserial_dre_interrupt_elevated = 1; + } - tx_buffer_index_t i = (_tx_buffer_head + 1) % SERIAL_TX_BUFFER_SIZE; + tx_buffer_index_t i = (_tx_buffer_head + 1) % SERIAL_TX_BUFFER_SIZE; - //If the output buffer is full, there's nothing for it other than to - //wait for the interrupt handler to empty it a bit (or emulate interrupts) - while (i == _tx_buffer_tail) { - _poll_tx_data_empty(); - } + //If the output buffer is full, there's nothing for it other than to + //wait for the interrupt handler to empty it a bit (or emulate interrupts) + while (i == _tx_buffer_tail) + { + _poll_tx_data_empty(); + } - _tx_buffer[_tx_buffer_head] = c; - _tx_buffer_head = i; + _tx_buffer[_tx_buffer_head] = c; + _tx_buffer_head = i; - // Enable data "register empty interrupt" - (*_hwserial_module).CTRLA |= USART_DREIE_bm; + // Enable data "register empty interrupt" + (*_hwserial_module).CTRLA |= USART_DREIE_bm; - return 1; + return 1; } #endif // whole file diff --git a/megaavr/cores/coreX-corefiles/UART0.cpp b/megaavr/cores/coreX-corefiles/UART0.cpp index 50b2264..72e93c6 100644 --- a/megaavr/cores/coreX-corefiles/UART0.cpp +++ b/megaavr/cores/coreX-corefiles/UART0.cpp @@ -55,12 +55,13 @@ ISR(HWSERIAL0_DRE_VECTOR) #endif #if defined(HWSERIAL0) - UartClass Serial(HWSERIAL0, PIN_WIRE_HWSERIAL0_RX, PIN_WIRE_HWSERIAL0_TX, PIN_WIRE_HWSERIAL0_RX_PINSWAP_1, PIN_WIRE_HWSERIAL0_TX_PINSWAP_1, HWSERIAL0_DRE_VECTOR_NUM, HWSERIAL0_MUX, HWSERIAL0_MUX_PINSWAP_1); +UartClass Serial(HWSERIAL0, PIN_WIRE_HWSERIAL0_RX, PIN_WIRE_HWSERIAL0_TX, PIN_WIRE_HWSERIAL0_RX_PINSWAP_1, PIN_WIRE_HWSERIAL0_TX_PINSWAP_1, HWSERIAL0_DRE_VECTOR_NUM, HWSERIAL0_MUX, HWSERIAL0_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent // pulling in this file if it's not otherwise used. -bool Serial0_available() { +bool Serial0_available() +{ return Serial.available(); } diff --git a/megaavr/cores/coreX-corefiles/UART1.cpp b/megaavr/cores/coreX-corefiles/UART1.cpp index c15332e..68610e3 100644 --- a/megaavr/cores/coreX-corefiles/UART1.cpp +++ b/megaavr/cores/coreX-corefiles/UART1.cpp @@ -55,12 +55,13 @@ ISR(HWSERIAL1_DRE_VECTOR) #endif #if defined(HWSERIAL1) - UartClass Serial1(HWSERIAL1, PIN_WIRE_HWSERIAL1_RX, PIN_WIRE_HWSERIAL1_TX, PIN_WIRE_HWSERIAL1_RX_PINSWAP_1, PIN_WIRE_HWSERIAL1_TX_PINSWAP_1, HWSERIAL1_DRE_VECTOR_NUM, HWSERIAL1_MUX, HWSERIAL1_MUX_PINSWAP_1); +UartClass Serial1(HWSERIAL1, PIN_WIRE_HWSERIAL1_RX, PIN_WIRE_HWSERIAL1_TX, PIN_WIRE_HWSERIAL1_RX_PINSWAP_1, PIN_WIRE_HWSERIAL1_TX_PINSWAP_1, HWSERIAL1_DRE_VECTOR_NUM, HWSERIAL1_MUX, HWSERIAL1_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent // pulling in this file if it's not otherwise used. -bool Serial1_available() { +bool Serial1_available() +{ return Serial1.available(); } diff --git a/megaavr/cores/coreX-corefiles/UART2.cpp b/megaavr/cores/coreX-corefiles/UART2.cpp index 4fc9940..6a1c86c 100644 --- a/megaavr/cores/coreX-corefiles/UART2.cpp +++ b/megaavr/cores/coreX-corefiles/UART2.cpp @@ -55,12 +55,13 @@ ISR(HWSERIAL2_DRE_VECTOR) #endif #if defined(HWSERIAL2) - UartClass Serial2(HWSERIAL2, PIN_WIRE_HWSERIAL2_RX, PIN_WIRE_HWSERIAL2_TX, PIN_WIRE_HWSERIAL2_RX_PINSWAP_1, PIN_WIRE_HWSERIAL2_TX_PINSWAP_1, HWSERIAL2_DRE_VECTOR_NUM, HWSERIAL2_MUX, HWSERIAL2_MUX_PINSWAP_1); +UartClass Serial2(HWSERIAL2, PIN_WIRE_HWSERIAL2_RX, PIN_WIRE_HWSERIAL2_TX, PIN_WIRE_HWSERIAL2_RX_PINSWAP_1, PIN_WIRE_HWSERIAL2_TX_PINSWAP_1, HWSERIAL2_DRE_VECTOR_NUM, HWSERIAL2_MUX, HWSERIAL2_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent // pulling in this file if it's not otherwise used. -bool Serial2_available() { +bool Serial2_available() +{ return Serial2.available(); } diff --git a/megaavr/cores/coreX-corefiles/UART3.cpp b/megaavr/cores/coreX-corefiles/UART3.cpp index d6d60b8..45f0c78 100644 --- a/megaavr/cores/coreX-corefiles/UART3.cpp +++ b/megaavr/cores/coreX-corefiles/UART3.cpp @@ -55,12 +55,13 @@ ISR(HWSERIAL3_DRE_VECTOR) #endif #if defined(HWSERIAL3) - UartClass Serial3(HWSERIAL3, PIN_WIRE_HWSERIAL3_RX, PIN_WIRE_HWSERIAL3_TX, PIN_WIRE_HWSERIAL3_RX_PINSWAP_1, PIN_WIRE_HWSERIAL3_TX_PINSWAP_1, HWSERIAL3_DRE_VECTOR_NUM, HWSERIAL3_MUX, HWSERIAL3_MUX_PINSWAP_1); +UartClass Serial3(HWSERIAL3, PIN_WIRE_HWSERIAL3_RX, PIN_WIRE_HWSERIAL3_TX, PIN_WIRE_HWSERIAL3_RX_PINSWAP_1, PIN_WIRE_HWSERIAL3_TX_PINSWAP_1, HWSERIAL3_DRE_VECTOR_NUM, HWSERIAL3_MUX, HWSERIAL3_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent // pulling in this file if it's not otherwise used. -bool Serial3_available() { +bool Serial3_available() +{ return Serial3.available(); } diff --git a/megaavr/cores/coreX-corefiles/UART_private.h b/megaavr/cores/coreX-corefiles/UART_private.h index 5e8e1f1..72845eb 100644 --- a/megaavr/cores/coreX-corefiles/UART_private.h +++ b/megaavr/cores/coreX-corefiles/UART_private.h @@ -40,7 +40,7 @@ UartClass::UartClass( volatile uint8_t uart_mux_swap) : _hwserial_module(hwserial_module), _hw_set { { hwserial_rx_pin, hwserial_tx_pin, uart_mux }, - { hwserial_rx_pin_swap, hwserial_tx_pin_swap, uart_mux_swap } }, + { hwserial_rx_pin_swap, hwserial_tx_pin_swap, uart_mux_swap } }, _pin_set(0), _written(false), _rx_buffer_head(0), _rx_buffer_tail(0), @@ -66,11 +66,14 @@ void UartClass::_rx_complete_irq(void) // just before the tail (meaning that the head would advance to the // current location of the tail), we're about to overflow the buffer // and so we don't write the character or advance the head. - if (i != _rx_buffer_tail) { + if (i != _rx_buffer_tail) + { _rx_buffer[_rx_buffer_head] = c; _rx_buffer_head = i; } - } else { + } + else + { // Parity error, read byte but discard it (*_hwserial_module).RXDATAL; } diff --git a/megaavr/cores/coreX-corefiles/UNO_compat.h b/megaavr/cores/coreX-corefiles/UNO_compat.h index 1aad58d..42f43c4 100644 --- a/megaavr/cores/coreX-corefiles/UNO_compat.h +++ b/megaavr/cores/coreX-corefiles/UNO_compat.h @@ -40,241 +40,296 @@ A5 PC5 PD5 */ -#define PORTA_ARDUINO (*(PORT_t *) 0x0400) /* I/O Ports */ -#define PORTB_ARDUINO (*(PORT_t *) 0x0420) /* I/O Ports */ -#define PORTC_ARDUINO (*(PORT_t *) 0x0440) /* I/O Ports */ -#define PORTD_ARDUINO (*(PORT_t *) 0x0460) /* I/O Ports */ -#define PORTE_ARDUINO (*(PORT_t *) 0x0480) /* I/O Ports */ -#define PORTF_ARDUINO (*(PORT_t *) 0x04A0) /* I/O Ports */ +#define PORTA_ARDUINO (*(PORT_t*)0x0400) /* I/O Ports */ +#define PORTB_ARDUINO (*(PORT_t*)0x0420) /* I/O Ports */ +#define PORTC_ARDUINO (*(PORT_t*)0x0440) /* I/O Ports */ +#define PORTD_ARDUINO (*(PORT_t*)0x0460) /* I/O Ports */ +#define PORTE_ARDUINO (*(PORT_t*)0x0480) /* I/O Ports */ +#define PORTF_ARDUINO (*(PORT_t*)0x04A0) /* I/O Ports */ #undef PORTB #undef PORTC #undef PORTD -#define SET_PORT_REGISTER(inPosition, port, position) if ((1 << inPosition) & (uint8_t)value) { port.OUTSET = (1 << position);} -#define CLEAR_PORT_REGISTER(inPosition, port, position) if ((uint8_t)~(1 << inPosition) == (uint8_t)value) { port.OUTCLR = (1 << position);} -#define SET_OR_CLEAR_PORT_REGISTER(inPosition, port, position) if ((uint8_t)~(1 << inPosition) & (uint8_t)value) { port.OUTSET = (1 << position); } else {port.OUTCLR = (1 << position); } - -#define SET_DIR_REGISTER(inPosition, port, position) if ((1 << inPosition) & (uint8_t)value) { port.DIRSET = (1 << position);} -#define CLEAR_DIR_REGISTER(inPosition, port, position) if ((uint8_t)~(1 << inPosition) == (uint8_t)value) { port.DIRCLR = (1 << position);} -#define SET_OR_CLEAR_DIR_REGISTER(inPosition, port, position) if ((uint8_t)~(1 << inPosition) & (uint8_t)value) { port.DIRSET = (1 << position); } else {port.DIRCLR = (1 << position); } +#define SET_PORT_REGISTER(inPosition, port, position) \ + if ((1 << inPosition) & (uint8_t)value) \ + { \ + port.OUTSET = (1 << position); \ + } +#define CLEAR_PORT_REGISTER(inPosition, port, position) \ + if ((uint8_t) ~(1 << inPosition) == (uint8_t)value) \ + { \ + port.OUTCLR = (1 << position); \ + } +#define SET_OR_CLEAR_PORT_REGISTER(inPosition, port, position) \ + if ((uint8_t) ~(1 << inPosition) & (uint8_t)value) \ + { \ + port.OUTSET = (1 << position); \ + } \ + else \ + { \ + port.OUTCLR = (1 << position); \ + } +#define SET_DIR_REGISTER(inPosition, port, position) \ + if ((1 << inPosition) & (uint8_t)value) \ + { \ + port.DIRSET = (1 << position); \ + } +#define CLEAR_DIR_REGISTER(inPosition, port, position) \ + if ((uint8_t) ~(1 << inPosition) == (uint8_t)value) \ + { \ + port.DIRCLR = (1 << position); \ + } +#define SET_OR_CLEAR_DIR_REGISTER(inPosition, port, position) \ + if ((uint8_t) ~(1 << inPosition) & (uint8_t)value) \ + { \ + port.DIRSET = (1 << position); \ + } \ + else \ + { \ + port.DIRCLR = (1 << position); \ + } /** DDR Classes**/ -class DDRBClass { - public: - DDRBClass() {} - DDRBClass& operator=(uint8_t value) { - SET_OR_CLEAR_DIR_REGISTER(0, PORTE_ARDUINO, 3); - SET_OR_CLEAR_DIR_REGISTER(1, PORTB_ARDUINO, 0); - SET_OR_CLEAR_DIR_REGISTER(2, PORTB_ARDUINO, 1); - SET_OR_CLEAR_DIR_REGISTER(3, PORTE_ARDUINO, 0); - SET_OR_CLEAR_DIR_REGISTER(4, PORTE_ARDUINO, 1); - SET_OR_CLEAR_DIR_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } +class DDRBClass +{ + public: + DDRBClass() {} + DDRBClass& operator=(uint8_t value) + { + SET_OR_CLEAR_DIR_REGISTER(0, PORTE_ARDUINO, 3); + SET_OR_CLEAR_DIR_REGISTER(1, PORTB_ARDUINO, 0); + SET_OR_CLEAR_DIR_REGISTER(2, PORTB_ARDUINO, 1); + SET_OR_CLEAR_DIR_REGISTER(3, PORTE_ARDUINO, 0); + SET_OR_CLEAR_DIR_REGISTER(4, PORTE_ARDUINO, 1); + SET_OR_CLEAR_DIR_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } - DDRBClass& operator&=(uint8_t value) { - CLEAR_DIR_REGISTER(0, PORTE_ARDUINO, 3); - CLEAR_DIR_REGISTER(1, PORTB_ARDUINO, 0); - CLEAR_DIR_REGISTER(2, PORTB_ARDUINO, 1); - CLEAR_DIR_REGISTER(3, PORTE_ARDUINO, 0); - CLEAR_DIR_REGISTER(4, PORTE_ARDUINO, 1); - CLEAR_DIR_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } + DDRBClass& operator&=(uint8_t value) + { + CLEAR_DIR_REGISTER(0, PORTE_ARDUINO, 3); + CLEAR_DIR_REGISTER(1, PORTB_ARDUINO, 0); + CLEAR_DIR_REGISTER(2, PORTB_ARDUINO, 1); + CLEAR_DIR_REGISTER(3, PORTE_ARDUINO, 0); + CLEAR_DIR_REGISTER(4, PORTE_ARDUINO, 1); + CLEAR_DIR_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } - DDRBClass& operator|=(uint8_t value) { - SET_DIR_REGISTER(0, PORTE_ARDUINO, 3); - SET_DIR_REGISTER(1, PORTB_ARDUINO, 0); - SET_DIR_REGISTER(2, PORTB_ARDUINO, 1); - SET_DIR_REGISTER(3, PORTE_ARDUINO, 0); - SET_DIR_REGISTER(4, PORTE_ARDUINO, 1); - SET_DIR_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } + DDRBClass& operator|=(uint8_t value) + { + SET_DIR_REGISTER(0, PORTE_ARDUINO, 3); + SET_DIR_REGISTER(1, PORTB_ARDUINO, 0); + SET_DIR_REGISTER(2, PORTB_ARDUINO, 1); + SET_DIR_REGISTER(3, PORTE_ARDUINO, 0); + SET_DIR_REGISTER(4, PORTE_ARDUINO, 1); + SET_DIR_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } }; -class DDRCClass { - public: - DDRCClass() {} - DDRCClass& operator=(uint8_t value) { - SET_OR_CLEAR_DIR_REGISTER(0, PORTD_ARDUINO, 0); - SET_OR_CLEAR_DIR_REGISTER(1, PORTD_ARDUINO, 1); - SET_OR_CLEAR_DIR_REGISTER(2, PORTD_ARDUINO, 2); - SET_OR_CLEAR_DIR_REGISTER(3, PORTD_ARDUINO, 3); - SET_OR_CLEAR_DIR_REGISTER(4, PORTD_ARDUINO, 4); - SET_OR_CLEAR_DIR_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } +class DDRCClass +{ + public: + DDRCClass() {} + DDRCClass& operator=(uint8_t value) + { + SET_OR_CLEAR_DIR_REGISTER(0, PORTD_ARDUINO, 0); + SET_OR_CLEAR_DIR_REGISTER(1, PORTD_ARDUINO, 1); + SET_OR_CLEAR_DIR_REGISTER(2, PORTD_ARDUINO, 2); + SET_OR_CLEAR_DIR_REGISTER(3, PORTD_ARDUINO, 3); + SET_OR_CLEAR_DIR_REGISTER(4, PORTD_ARDUINO, 4); + SET_OR_CLEAR_DIR_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } - DDRCClass& operator&=(uint8_t value) { - CLEAR_DIR_REGISTER(0, PORTD_ARDUINO, 0); - CLEAR_DIR_REGISTER(1, PORTD_ARDUINO, 1); - CLEAR_DIR_REGISTER(2, PORTD_ARDUINO, 2); - CLEAR_DIR_REGISTER(3, PORTD_ARDUINO, 3); - CLEAR_DIR_REGISTER(4, PORTD_ARDUINO, 4); - CLEAR_DIR_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } + DDRCClass& operator&=(uint8_t value) + { + CLEAR_DIR_REGISTER(0, PORTD_ARDUINO, 0); + CLEAR_DIR_REGISTER(1, PORTD_ARDUINO, 1); + CLEAR_DIR_REGISTER(2, PORTD_ARDUINO, 2); + CLEAR_DIR_REGISTER(3, PORTD_ARDUINO, 3); + CLEAR_DIR_REGISTER(4, PORTD_ARDUINO, 4); + CLEAR_DIR_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } - DDRCClass& operator|=(uint8_t value) { - SET_DIR_REGISTER(0, PORTD_ARDUINO, 0); - SET_DIR_REGISTER(1, PORTD_ARDUINO, 1); - SET_DIR_REGISTER(2, PORTD_ARDUINO, 2); - SET_DIR_REGISTER(3, PORTD_ARDUINO, 3); - SET_DIR_REGISTER(4, PORTD_ARDUINO, 4); - SET_DIR_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } + DDRCClass& operator|=(uint8_t value) + { + SET_DIR_REGISTER(0, PORTD_ARDUINO, 0); + SET_DIR_REGISTER(1, PORTD_ARDUINO, 1); + SET_DIR_REGISTER(2, PORTD_ARDUINO, 2); + SET_DIR_REGISTER(3, PORTD_ARDUINO, 3); + SET_DIR_REGISTER(4, PORTD_ARDUINO, 4); + SET_DIR_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } }; -class DDRDClass { - public: - DDRDClass() {} - DDRDClass& operator=(uint8_t value) { - SET_OR_CLEAR_DIR_REGISTER(0, PORTC_ARDUINO, 5); - SET_OR_CLEAR_DIR_REGISTER(1, PORTC_ARDUINO, 4); - SET_OR_CLEAR_DIR_REGISTER(2, PORTA_ARDUINO, 0); - SET_OR_CLEAR_DIR_REGISTER(3, PORTF_ARDUINO, 5); - SET_OR_CLEAR_DIR_REGISTER(4, PORTC_ARDUINO, 6); - SET_OR_CLEAR_DIR_REGISTER(5, PORTB_ARDUINO, 2); - SET_OR_CLEAR_DIR_REGISTER(6, PORTF_ARDUINO, 4); - SET_OR_CLEAR_DIR_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } +class DDRDClass +{ + public: + DDRDClass() {} + DDRDClass& operator=(uint8_t value) + { + SET_OR_CLEAR_DIR_REGISTER(0, PORTC_ARDUINO, 5); + SET_OR_CLEAR_DIR_REGISTER(1, PORTC_ARDUINO, 4); + SET_OR_CLEAR_DIR_REGISTER(2, PORTA_ARDUINO, 0); + SET_OR_CLEAR_DIR_REGISTER(3, PORTF_ARDUINO, 5); + SET_OR_CLEAR_DIR_REGISTER(4, PORTC_ARDUINO, 6); + SET_OR_CLEAR_DIR_REGISTER(5, PORTB_ARDUINO, 2); + SET_OR_CLEAR_DIR_REGISTER(6, PORTF_ARDUINO, 4); + SET_OR_CLEAR_DIR_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } - DDRDClass& operator&=(uint8_t value) { - CLEAR_DIR_REGISTER(0, PORTC_ARDUINO, 5); - CLEAR_DIR_REGISTER(1, PORTC_ARDUINO, 4); - CLEAR_DIR_REGISTER(2, PORTA_ARDUINO, 0); - CLEAR_DIR_REGISTER(3, PORTF_ARDUINO, 5); - CLEAR_DIR_REGISTER(4, PORTC_ARDUINO, 6); - CLEAR_DIR_REGISTER(5, PORTB_ARDUINO, 2); - CLEAR_DIR_REGISTER(6, PORTF_ARDUINO, 4); - CLEAR_DIR_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } + DDRDClass& operator&=(uint8_t value) + { + CLEAR_DIR_REGISTER(0, PORTC_ARDUINO, 5); + CLEAR_DIR_REGISTER(1, PORTC_ARDUINO, 4); + CLEAR_DIR_REGISTER(2, PORTA_ARDUINO, 0); + CLEAR_DIR_REGISTER(3, PORTF_ARDUINO, 5); + CLEAR_DIR_REGISTER(4, PORTC_ARDUINO, 6); + CLEAR_DIR_REGISTER(5, PORTB_ARDUINO, 2); + CLEAR_DIR_REGISTER(6, PORTF_ARDUINO, 4); + CLEAR_DIR_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } - DDRDClass& operator|=(uint8_t value) { - SET_DIR_REGISTER(0, PORTC_ARDUINO, 5); - SET_DIR_REGISTER(1, PORTC_ARDUINO, 4); - SET_DIR_REGISTER(2, PORTA_ARDUINO, 0); - SET_DIR_REGISTER(3, PORTF_ARDUINO, 5); - SET_DIR_REGISTER(4, PORTC_ARDUINO, 6); - SET_DIR_REGISTER(5, PORTB_ARDUINO, 2); - SET_DIR_REGISTER(6, PORTF_ARDUINO, 4); - SET_DIR_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } + DDRDClass& operator|=(uint8_t value) + { + SET_DIR_REGISTER(0, PORTC_ARDUINO, 5); + SET_DIR_REGISTER(1, PORTC_ARDUINO, 4); + SET_DIR_REGISTER(2, PORTA_ARDUINO, 0); + SET_DIR_REGISTER(3, PORTF_ARDUINO, 5); + SET_DIR_REGISTER(4, PORTC_ARDUINO, 6); + SET_DIR_REGISTER(5, PORTB_ARDUINO, 2); + SET_DIR_REGISTER(6, PORTF_ARDUINO, 4); + SET_DIR_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } }; /** PORT Classes**/ -class PORTBClass { - public: - PORTBClass() {} - PORTBClass& operator=(uint8_t value) { - SET_OR_CLEAR_PORT_REGISTER(0, PORTE_ARDUINO, 3); - SET_OR_CLEAR_PORT_REGISTER(1, PORTB_ARDUINO, 0); - SET_OR_CLEAR_PORT_REGISTER(2, PORTB_ARDUINO, 1); - SET_OR_CLEAR_PORT_REGISTER(3, PORTE_ARDUINO, 0); - SET_OR_CLEAR_PORT_REGISTER(4, PORTE_ARDUINO, 1); - SET_OR_CLEAR_PORT_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } +class PORTBClass +{ + public: + PORTBClass() {} + PORTBClass& operator=(uint8_t value) + { + SET_OR_CLEAR_PORT_REGISTER(0, PORTE_ARDUINO, 3); + SET_OR_CLEAR_PORT_REGISTER(1, PORTB_ARDUINO, 0); + SET_OR_CLEAR_PORT_REGISTER(2, PORTB_ARDUINO, 1); + SET_OR_CLEAR_PORT_REGISTER(3, PORTE_ARDUINO, 0); + SET_OR_CLEAR_PORT_REGISTER(4, PORTE_ARDUINO, 1); + SET_OR_CLEAR_PORT_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } - PORTBClass& operator&=(uint8_t value) { - CLEAR_PORT_REGISTER(0, PORTE_ARDUINO, 3); - CLEAR_PORT_REGISTER(1, PORTB_ARDUINO, 0); - CLEAR_PORT_REGISTER(2, PORTB_ARDUINO, 1); - CLEAR_PORT_REGISTER(3, PORTE_ARDUINO, 0); - CLEAR_PORT_REGISTER(4, PORTE_ARDUINO, 1); - CLEAR_PORT_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } + PORTBClass& operator&=(uint8_t value) + { + CLEAR_PORT_REGISTER(0, PORTE_ARDUINO, 3); + CLEAR_PORT_REGISTER(1, PORTB_ARDUINO, 0); + CLEAR_PORT_REGISTER(2, PORTB_ARDUINO, 1); + CLEAR_PORT_REGISTER(3, PORTE_ARDUINO, 0); + CLEAR_PORT_REGISTER(4, PORTE_ARDUINO, 1); + CLEAR_PORT_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } - PORTBClass& operator|=(uint8_t value) { - SET_PORT_REGISTER(0, PORTE_ARDUINO, 3); - SET_PORT_REGISTER(1, PORTB_ARDUINO, 0); - SET_PORT_REGISTER(2, PORTB_ARDUINO, 1); - SET_PORT_REGISTER(3, PORTE_ARDUINO, 0); - SET_PORT_REGISTER(4, PORTE_ARDUINO, 1); - SET_PORT_REGISTER(5, PORTE_ARDUINO, 2); - return *this; - } + PORTBClass& operator|=(uint8_t value) + { + SET_PORT_REGISTER(0, PORTE_ARDUINO, 3); + SET_PORT_REGISTER(1, PORTB_ARDUINO, 0); + SET_PORT_REGISTER(2, PORTB_ARDUINO, 1); + SET_PORT_REGISTER(3, PORTE_ARDUINO, 0); + SET_PORT_REGISTER(4, PORTE_ARDUINO, 1); + SET_PORT_REGISTER(5, PORTE_ARDUINO, 2); + return *this; + } }; -class PORTCClass { - public: - PORTCClass() {} - PORTCClass& operator=(uint8_t value) { - SET_OR_CLEAR_PORT_REGISTER(0, PORTD_ARDUINO, 0); - SET_OR_CLEAR_PORT_REGISTER(1, PORTD_ARDUINO, 1); - SET_OR_CLEAR_PORT_REGISTER(2, PORTD_ARDUINO, 2); - SET_OR_CLEAR_PORT_REGISTER(3, PORTD_ARDUINO, 3); - SET_OR_CLEAR_PORT_REGISTER(4, PORTD_ARDUINO, 4); - SET_OR_CLEAR_PORT_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } +class PORTCClass +{ + public: + PORTCClass() {} + PORTCClass& operator=(uint8_t value) + { + SET_OR_CLEAR_PORT_REGISTER(0, PORTD_ARDUINO, 0); + SET_OR_CLEAR_PORT_REGISTER(1, PORTD_ARDUINO, 1); + SET_OR_CLEAR_PORT_REGISTER(2, PORTD_ARDUINO, 2); + SET_OR_CLEAR_PORT_REGISTER(3, PORTD_ARDUINO, 3); + SET_OR_CLEAR_PORT_REGISTER(4, PORTD_ARDUINO, 4); + SET_OR_CLEAR_PORT_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } - PORTCClass& operator&=(uint8_t value) { - CLEAR_PORT_REGISTER(0, PORTD_ARDUINO, 0); - CLEAR_PORT_REGISTER(1, PORTD_ARDUINO, 1); - CLEAR_PORT_REGISTER(2, PORTD_ARDUINO, 2); - CLEAR_PORT_REGISTER(3, PORTD_ARDUINO, 3); - CLEAR_PORT_REGISTER(4, PORTD_ARDUINO, 4); - CLEAR_PORT_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } + PORTCClass& operator&=(uint8_t value) + { + CLEAR_PORT_REGISTER(0, PORTD_ARDUINO, 0); + CLEAR_PORT_REGISTER(1, PORTD_ARDUINO, 1); + CLEAR_PORT_REGISTER(2, PORTD_ARDUINO, 2); + CLEAR_PORT_REGISTER(3, PORTD_ARDUINO, 3); + CLEAR_PORT_REGISTER(4, PORTD_ARDUINO, 4); + CLEAR_PORT_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } - PORTCClass& operator|=(uint8_t value) { - SET_PORT_REGISTER(0, PORTD_ARDUINO, 0); - SET_PORT_REGISTER(1, PORTD_ARDUINO, 1); - SET_PORT_REGISTER(2, PORTD_ARDUINO, 2); - SET_PORT_REGISTER(3, PORTD_ARDUINO, 3); - SET_PORT_REGISTER(4, PORTD_ARDUINO, 4); - SET_PORT_REGISTER(5, PORTD_ARDUINO, 5); - return *this; - } + PORTCClass& operator|=(uint8_t value) + { + SET_PORT_REGISTER(0, PORTD_ARDUINO, 0); + SET_PORT_REGISTER(1, PORTD_ARDUINO, 1); + SET_PORT_REGISTER(2, PORTD_ARDUINO, 2); + SET_PORT_REGISTER(3, PORTD_ARDUINO, 3); + SET_PORT_REGISTER(4, PORTD_ARDUINO, 4); + SET_PORT_REGISTER(5, PORTD_ARDUINO, 5); + return *this; + } }; -class PORTDClass { - public: - PORTDClass() {} - PORTDClass& operator=(uint8_t value) { - SET_OR_CLEAR_PORT_REGISTER(0, PORTC_ARDUINO, 5); - SET_OR_CLEAR_PORT_REGISTER(1, PORTC_ARDUINO, 4); - SET_OR_CLEAR_PORT_REGISTER(2, PORTA_ARDUINO, 0); - SET_OR_CLEAR_PORT_REGISTER(3, PORTF_ARDUINO, 5); - SET_OR_CLEAR_PORT_REGISTER(4, PORTC_ARDUINO, 6); - SET_OR_CLEAR_PORT_REGISTER(5, PORTB_ARDUINO, 2); - SET_OR_CLEAR_PORT_REGISTER(6, PORTF_ARDUINO, 4); - SET_OR_CLEAR_PORT_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } +class PORTDClass +{ + public: + PORTDClass() {} + PORTDClass& operator=(uint8_t value) + { + SET_OR_CLEAR_PORT_REGISTER(0, PORTC_ARDUINO, 5); + SET_OR_CLEAR_PORT_REGISTER(1, PORTC_ARDUINO, 4); + SET_OR_CLEAR_PORT_REGISTER(2, PORTA_ARDUINO, 0); + SET_OR_CLEAR_PORT_REGISTER(3, PORTF_ARDUINO, 5); + SET_OR_CLEAR_PORT_REGISTER(4, PORTC_ARDUINO, 6); + SET_OR_CLEAR_PORT_REGISTER(5, PORTB_ARDUINO, 2); + SET_OR_CLEAR_PORT_REGISTER(6, PORTF_ARDUINO, 4); + SET_OR_CLEAR_PORT_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } - PORTDClass& operator&=(uint8_t value) { - CLEAR_PORT_REGISTER(0, PORTC_ARDUINO, 5); - CLEAR_PORT_REGISTER(1, PORTC_ARDUINO, 4); - CLEAR_PORT_REGISTER(2, PORTA_ARDUINO, 0); - CLEAR_PORT_REGISTER(3, PORTF_ARDUINO, 5); - CLEAR_PORT_REGISTER(4, PORTC_ARDUINO, 6); - CLEAR_PORT_REGISTER(5, PORTB_ARDUINO, 2); - CLEAR_PORT_REGISTER(6, PORTF_ARDUINO, 4); - CLEAR_PORT_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } + PORTDClass& operator&=(uint8_t value) + { + CLEAR_PORT_REGISTER(0, PORTC_ARDUINO, 5); + CLEAR_PORT_REGISTER(1, PORTC_ARDUINO, 4); + CLEAR_PORT_REGISTER(2, PORTA_ARDUINO, 0); + CLEAR_PORT_REGISTER(3, PORTF_ARDUINO, 5); + CLEAR_PORT_REGISTER(4, PORTC_ARDUINO, 6); + CLEAR_PORT_REGISTER(5, PORTB_ARDUINO, 2); + CLEAR_PORT_REGISTER(6, PORTF_ARDUINO, 4); + CLEAR_PORT_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } - PORTDClass& operator|=(uint8_t value) { - SET_PORT_REGISTER(0, PORTC_ARDUINO, 5); - SET_PORT_REGISTER(1, PORTC_ARDUINO, 4); - SET_PORT_REGISTER(2, PORTA_ARDUINO, 0); - SET_PORT_REGISTER(3, PORTF_ARDUINO, 5); - SET_PORT_REGISTER(4, PORTC_ARDUINO, 6); - SET_PORT_REGISTER(5, PORTB_ARDUINO, 2); - SET_PORT_REGISTER(6, PORTF_ARDUINO, 4); - SET_PORT_REGISTER(7, PORTA_ARDUINO, 1); - return *this; - } + PORTDClass& operator|=(uint8_t value) + { + SET_PORT_REGISTER(0, PORTC_ARDUINO, 5); + SET_PORT_REGISTER(1, PORTC_ARDUINO, 4); + SET_PORT_REGISTER(2, PORTA_ARDUINO, 0); + SET_PORT_REGISTER(3, PORTF_ARDUINO, 5); + SET_PORT_REGISTER(4, PORTC_ARDUINO, 6); + SET_PORT_REGISTER(5, PORTB_ARDUINO, 2); + SET_PORT_REGISTER(6, PORTF_ARDUINO, 4); + SET_PORT_REGISTER(7, PORTA_ARDUINO, 1); + return *this; + } }; extern PORTBClass PORTB; diff --git a/megaavr/cores/coreX-corefiles/USBCore.cpp b/megaavr/cores/coreX-corefiles/USBCore.cpp index e6ee84a..a20ce0a 100644 --- a/megaavr/cores/coreX-corefiles/USBCore.cpp +++ b/megaavr/cores/coreX-corefiles/USBCore.cpp @@ -17,12 +17,14 @@ ** SOFTWARE. */ +#include "USBCore.h" + +#include + #include "Arduino.h" -#include "api/USBAPI.h" #include "api/PluggableUSB.h" -#include "USBCore.h" +#include "api/USBAPI.h" #include "pins_arduino.h" -#include #if defined(USBCON) @@ -40,152 +42,151 @@ extern const uint8_t STRING_MANUFACTURER[] PROGMEM; extern const DeviceDescriptor USB_DeviceDescriptorIAD PROGMEM; const uint16_t STRING_LANGUAGE[2] = { - (3<<8) | (2+2), - 0x0409 // English + (3 << 8) | (2 + 2), + 0x0409 // English }; #ifndef USB_PRODUCT // If no product is provided, use USB IO Board -#define USB_PRODUCT "USB IO Board" +#define USB_PRODUCT "USB IO Board" #endif const uint8_t STRING_PRODUCT[] PROGMEM = USB_PRODUCT; #if USB_VID == 0x2341 -# if defined(USB_MANUFACTURER) -# undef USB_MANUFACTURER -# endif -# define USB_MANUFACTURER "Arduino LLC" +#if defined(USB_MANUFACTURER) +#undef USB_MANUFACTURER +#endif +#define USB_MANUFACTURER "Arduino LLC" #elif USB_VID == 0x1b4f -# if defined(USB_MANUFACTURER) -# undef USB_MANUFACTURER -# endif -# define USB_MANUFACTURER "SparkFun" +#if defined(USB_MANUFACTURER) +#undef USB_MANUFACTURER +#endif +#define USB_MANUFACTURER "SparkFun" #elif !defined(USB_MANUFACTURER) // Fall through to unknown if no manufacturer name was provided in a macro -# define USB_MANUFACTURER "Unknown" +#define USB_MANUFACTURER "Unknown" #endif const uint8_t STRING_MANUFACTURER[] PROGMEM = USB_MANUFACTURER; - #define DEVICE_CLASS 0x02 -// DEVICE DESCRIPTOR +// DEVICE DESCRIPTOR const DeviceDescriptor USB_DeviceDescriptorIAD = - D_DEVICE(0xEF,0x02,0x01,64,USB_VID,USB_PID,0x100,IMANUFACTURER,IPRODUCT,ISERIAL,1); + D_DEVICE(0xEF, 0x02, 0x01, 64, USB_VID, USB_PID, 0x100, IMANUFACTURER, IPRODUCT, ISERIAL, 1); //================================================================== //================================================================== volatile uint8_t _usbConfiguration = 0; volatile uint8_t _usbCurrentStatus = 0; // meaning of bits see usb_20.pdf, Figure 9-4. Information Returned by a GetStatus() Request to a Device -volatile uint8_t _usbSuspendState = 0; // copy of UDINT to check SUSPI and WAKEUPI bits +volatile uint8_t _usbSuspendState = 0; // copy of UDINT to check SUSPI and WAKEUPI bits static inline void WaitIN(void) { - while (!(UEINTX & (1< len) { - n = len; - } - - { - LockEP lock(ep); - // Frame may have been released by the SOF interrupt handler - if (!ReadWriteAllowed()) - continue; - - len -= n; - if (ep & TRANSFER_ZERO) - { - while (n--) - Send8(0); - } - else if (ep & TRANSFER_PGM) - { - while (n--) - Send8(pgm_read_byte(data++)); - } - else - { - while (n--) - Send8(*data++); - } - - if (sendZlp) { - ReleaseTX(); - sendZlp = false; - } else if (!ReadWriteAllowed()) { // ...release if buffer is full... - ReleaseTX(); - if (len == 0) sendZlp = true; - } else if ((len == 0) && (ep & TRANSFER_RELEASE)) { // ...or if forced with TRANSFER_RELEASE - // XXX: TRANSFER_RELEASE is never used can be removed? - ReleaseTX(); - } - } - } - TXLED1; // light the TX LED - TxLEDPulse = TX_RX_LED_PULSE_MS; - return r; + if (!_usbConfiguration) + return -1; + + if (_usbSuspendState & (1 << SUSPI)) + { + //send a remote wakeup + UDCON |= (1 << RMWKUP); + } + + int r = len; + const uint8_t* data = (const uint8_t*)d; + uint8_t timeout = 250; // 250ms timeout on send? TODO + bool sendZlp = false; + + while (len || sendZlp) + { + uint8_t n = USB_SendSpace(ep); + if (n == 0) + { + if (!(--timeout)) + return -1; + delay(1); + continue; + } + + if (n > len) + { + n = len; + } + + { + LockEP lock(ep); + // Frame may have been released by the SOF interrupt handler + if (!ReadWriteAllowed()) + continue; + + len -= n; + if (ep & TRANSFER_ZERO) + { + while (n--) + Send8(0); + } + else if (ep & TRANSFER_PGM) + { + while (n--) + Send8(pgm_read_byte(data++)); + } + else + { + while (n--) + Send8(*data++); + } + + if (sendZlp) + { + ReleaseTX(); + sendZlp = false; + } + else if (!ReadWriteAllowed()) + { // ...release if buffer is full... + ReleaseTX(); + if (len == 0) sendZlp = true; + } + else if ((len == 0) && (ep & TRANSFER_RELEASE)) + { // ...or if forced with TRANSFER_RELEASE + // XXX: TRANSFER_RELEASE is never used can be removed? + ReleaseTX(); + } + } + } + TXLED1; // light the TX LED + TxLEDPulse = TX_RX_LED_PULSE_MS; + return r; } uint16_t _initEndpoints[USB_ENDPOINTS] = -{ - 0, // Control Endpoint - - EP_TYPE_INTERRUPT_IN, // CDC_ENDPOINT_ACM - EP_TYPE_BULK_OUT, // CDC_ENDPOINT_OUT - EP_TYPE_BULK_IN, // CDC_ENDPOINT_IN + { + 0, // Control Endpoint + + EP_TYPE_INTERRUPT_IN, // CDC_ENDPOINT_ACM + EP_TYPE_BULK_OUT, // CDC_ENDPOINT_OUT + EP_TYPE_BULK_IN, // CDC_ENDPOINT_IN - // Following endpoints are automatically initialized to 0 + // Following endpoints are automatically initialized to 0 }; -#define EP_SINGLE_64 0x32 // EP0 -#define EP_DOUBLE_64 0x36 // Other endpoints +#define EP_SINGLE_64 0x32 // EP0 +#define EP_DOUBLE_64 0x36 // Other endpoints #define EP_SINGLE_16 0x12 -void* epBuffer(unsigned int lastEp) { - return &(_initEndpoints[lastEp]); +void* epBuffer(unsigned int lastEp) +{ + return &(_initEndpoints[lastEp]); } -static -void InitEP(uint8_t index, uint8_t type, uint8_t size) +static void InitEP(uint8_t index, uint8_t type, uint8_t size) { - UENUM = index; - UECONX = (1< 64){ - recvLength = 64; - } - - // Write data to fit to the end (not the beginning) of the array - WaitOUT(); - Recv((uint8_t*)d + len - length, recvLength); - ClearOUT(); - length -= recvLength; - } - return len; + auto length = len; + while (length) + { + // Dont receive more than the USB Control EP has to offer + // Use fixed 64 because control EP always have 64 bytes even on 16u2. + auto recvLength = length; + if (recvLength > 64) + { + recvLength = 64; + } + + // Write data to fit to the end (not the beginning) of the array + WaitOUT(); + Recv((uint8_t*)d + len - length, recvLength); + ClearOUT(); + length -= recvLength; + } + return len; } static uint8_t SendInterfaces() { - uint8_t interfaces = 0; + uint8_t interfaces = 0; - CDC_GetInterface(&interfaces); + CDC_GetInterface(&interfaces); #ifdef PLUGGABLE_USB_ENABLED - PluggableUSB().getInterface(&interfaces); + PluggableUSB().getInterface(&interfaces); #endif - return interfaces; + return interfaces; } -// Construct a dynamic configuration descriptor -// This really needs dynamic endpoint allocation etc -// TODO -static -bool SendConfiguration(int maxlen) +// Construct a dynamic configuration descriptor +// This really needs dynamic endpoint allocation etc +// TODO +static bool SendConfiguration(int maxlen) { - // Count and measure interfaces - InitControl(0); - uint8_t interfaces = SendInterfaces(); - ConfigDescriptor config = D_CONFIG(_cmark + sizeof(ConfigDescriptor),interfaces); + // Count and measure interfaces + InitControl(0); + uint8_t interfaces = SendInterfaces(); + ConfigDescriptor config = D_CONFIG(_cmark + sizeof(ConfigDescriptor), interfaces); - // Now send them - InitControl(maxlen); - USB_SendControl(0,&config,sizeof(ConfigDescriptor)); - SendInterfaces(); - return true; + // Now send them + InitControl(maxlen); + USB_SendControl(0, &config, sizeof(ConfigDescriptor)); + SendInterfaces(); + return true; } -static -bool SendDescriptor(USBSetup& setup) +static bool SendDescriptor(USBSetup& setup) { - int ret; - uint8_t t = setup.wValueH; - if (USB_CONFIGURATION_DESCRIPTOR_TYPE == t) - return SendConfiguration(setup.wLength); + int ret; + uint8_t t = setup.wValueH; + if (USB_CONFIGURATION_DESCRIPTOR_TYPE == t) + return SendConfiguration(setup.wLength); - InitControl(setup.wLength); + InitControl(setup.wLength); #ifdef PLUGGABLE_USB_ENABLED - ret = PluggableUSB().getDescriptor(setup); - if (ret != 0) { - return (ret > 0 ? true : false); - } + ret = PluggableUSB().getDescriptor(setup); + if (ret != 0) + { + return (ret > 0 ? true : false); + } #endif - const uint8_t* desc_addr = 0; - if (USB_DEVICE_DESCRIPTOR_TYPE == t) - { - desc_addr = (const uint8_t*)&USB_DeviceDescriptorIAD; - } - else if (USB_STRING_DESCRIPTOR_TYPE == t) - { - if (setup.wValueL == 0) { - desc_addr = (const uint8_t*)&STRING_LANGUAGE; - } - else if (setup.wValueL == IPRODUCT) { - return USB_SendStringDescriptor(STRING_PRODUCT, strlen(USB_PRODUCT), TRANSFER_PGM); - } - else if (setup.wValueL == IMANUFACTURER) { - return USB_SendStringDescriptor(STRING_MANUFACTURER, strlen(USB_MANUFACTURER), TRANSFER_PGM); - } - else if (setup.wValueL == ISERIAL) { + const uint8_t* desc_addr = 0; + if (USB_DEVICE_DESCRIPTOR_TYPE == t) + { + desc_addr = (const uint8_t*)&USB_DeviceDescriptorIAD; + } + else if (USB_STRING_DESCRIPTOR_TYPE == t) + { + if (setup.wValueL == 0) + { + desc_addr = (const uint8_t*)&STRING_LANGUAGE; + } + else if (setup.wValueL == IPRODUCT) + { + return USB_SendStringDescriptor(STRING_PRODUCT, strlen(USB_PRODUCT), TRANSFER_PGM); + } + else if (setup.wValueL == IMANUFACTURER) + { + return USB_SendStringDescriptor(STRING_MANUFACTURER, strlen(USB_MANUFACTURER), TRANSFER_PGM); + } + else if (setup.wValueL == ISERIAL) + { #ifdef PLUGGABLE_USB_ENABLED - char name[ISERIAL_MAX_LEN]; - PluggableUSB().getShortName(name); - return USB_SendStringDescriptor((uint8_t*)name, strlen(name), 0); + char name[ISERIAL_MAX_LEN]; + PluggableUSB().getShortName(name); + return USB_SendStringDescriptor((uint8_t*)name, strlen(name), 0); #endif - } - else - return false; - } + } + else + return false; + } - if (desc_addr == 0) - return false; - uint8_t desc_length = pgm_read_byte(desc_addr); + if (desc_addr == 0) + return false; + uint8_t desc_length = pgm_read_byte(desc_addr); - USB_SendControl(TRANSFER_PGM,desc_addr,desc_length); - return true; + USB_SendControl(TRANSFER_PGM, desc_addr, desc_length); + return true; } -// Endpoint 0 interrupt +// Endpoint 0 interrupt ISR(USB_COM_vect) { - SetEP(0); - if (!ReceivedSetupInt()) - return; - - USBSetup setup; - Recv((uint8_t*)&setup,8); - ClearSetupInt(); - - uint8_t requestType = setup.bmRequestType; - if (requestType & REQUEST_DEVICETOHOST) - WaitIN(); - else - ClearIN(); - - bool ok = true; - if (REQUEST_STANDARD == (requestType & REQUEST_TYPE)) - { - // Standard Requests - uint8_t r = setup.bRequest; - uint16_t wValue = setup.wValueL | (setup.wValueH << 8); - if (GET_STATUS == r) - { - if (requestType == (REQUEST_DEVICETOHOST | REQUEST_STANDARD | REQUEST_DEVICE)) - { - Send8(_usbCurrentStatus); - Send8(0); - } - else - { - // TODO: handle the HALT state of an endpoint here - // see "Figure 9-6. Information Returned by a GetStatus() Request to an Endpoint" in usb_20.pdf for more information - Send8(0); - Send8(0); - } - } - else if (CLEAR_FEATURE == r) - { - if((requestType == (REQUEST_HOSTTODEVICE | REQUEST_STANDARD | REQUEST_DEVICE)) - && (wValue == DEVICE_REMOTE_WAKEUP)) - { - _usbCurrentStatus &= ~FEATURE_REMOTE_WAKEUP_ENABLED; - } - } - else if (SET_FEATURE == r) - { - if((requestType == (REQUEST_HOSTTODEVICE | REQUEST_STANDARD | REQUEST_DEVICE)) - && (wValue == DEVICE_REMOTE_WAKEUP)) - { - _usbCurrentStatus |= FEATURE_REMOTE_WAKEUP_ENABLED; - } - } - else if (SET_ADDRESS == r) - { - WaitIN(); - UDADDR = setup.wValueL | (1< #include #include +#include class USBDevice_ { -public: - USBDevice_(); - bool configured(); - - void attach(); - void detach(); // Serial port goes down too... - void poll(); - bool wakeupHost(); // returns false, when wakeup cannot be processed + public: + USBDevice_(); + bool configured(); + + void attach(); + void detach(); // Serial port goes down too... + void poll(); + bool wakeupHost(); // returns false, when wakeup cannot be processed }; extern USBDevice_ USBDevice; -// Standard requests -#define GET_STATUS 0 -#define CLEAR_FEATURE 1 -#define SET_FEATURE 3 -#define SET_ADDRESS 5 -#define GET_DESCRIPTOR 6 -#define SET_DESCRIPTOR 7 -#define GET_CONFIGURATION 8 -#define SET_CONFIGURATION 9 -#define GET_INTERFACE 10 -#define SET_INTERFACE 11 +// Standard requests +#define GET_STATUS 0 +#define CLEAR_FEATURE 1 +#define SET_FEATURE 3 +#define SET_ADDRESS 5 +#define GET_DESCRIPTOR 6 +#define SET_DESCRIPTOR 7 +#define GET_CONFIGURATION 8 +#define SET_CONFIGURATION 9 +#define GET_INTERFACE 10 +#define SET_INTERFACE 11 // bmRequestType -#define REQUEST_HOSTTODEVICE 0x00 -#define REQUEST_DEVICETOHOST 0x80 -#define REQUEST_DIRECTION 0x80 - -#define REQUEST_STANDARD 0x00 -#define REQUEST_CLASS 0x20 -#define REQUEST_VENDOR 0x40 -#define REQUEST_TYPE 0x60 - -#define REQUEST_DEVICE 0x00 -#define REQUEST_INTERFACE 0x01 -#define REQUEST_ENDPOINT 0x02 -#define REQUEST_OTHER 0x03 -#define REQUEST_RECIPIENT 0x03 - -#define REQUEST_DEVICETOHOST_CLASS_INTERFACE (REQUEST_DEVICETOHOST | REQUEST_CLASS | REQUEST_INTERFACE) -#define REQUEST_HOSTTODEVICE_CLASS_INTERFACE (REQUEST_HOSTTODEVICE | REQUEST_CLASS | REQUEST_INTERFACE) +#define REQUEST_HOSTTODEVICE 0x00 +#define REQUEST_DEVICETOHOST 0x80 +#define REQUEST_DIRECTION 0x80 + +#define REQUEST_STANDARD 0x00 +#define REQUEST_CLASS 0x20 +#define REQUEST_VENDOR 0x40 +#define REQUEST_TYPE 0x60 + +#define REQUEST_DEVICE 0x00 +#define REQUEST_INTERFACE 0x01 +#define REQUEST_ENDPOINT 0x02 +#define REQUEST_OTHER 0x03 +#define REQUEST_RECIPIENT 0x03 + +#define REQUEST_DEVICETOHOST_CLASS_INTERFACE (REQUEST_DEVICETOHOST | REQUEST_CLASS | REQUEST_INTERFACE) +#define REQUEST_HOSTTODEVICE_CLASS_INTERFACE (REQUEST_HOSTTODEVICE | REQUEST_CLASS | REQUEST_INTERFACE) #define REQUEST_DEVICETOHOST_STANDARD_INTERFACE (REQUEST_DEVICETOHOST | REQUEST_STANDARD | REQUEST_INTERFACE) -// Class requests +// Class requests -#define CDC_SET_LINE_CODING 0x20 -#define CDC_GET_LINE_CODING 0x21 -#define CDC_SET_CONTROL_LINE_STATE 0x22 -#define CDC_SEND_BREAK 0x23 +#define CDC_SET_LINE_CODING 0x20 +#define CDC_GET_LINE_CODING 0x21 +#define CDC_SET_CONTROL_LINE_STATE 0x22 +#define CDC_SEND_BREAK 0x23 -#define MSC_RESET 0xFF -#define MSC_GET_MAX_LUN 0xFE +#define MSC_RESET 0xFF +#define MSC_GET_MAX_LUN 0xFE -// Descriptors +// Descriptors #define USB_DEVICE_DESC_SIZE 18 #define USB_CONFIGUARTION_DESC_SIZE 9 #define USB_INTERFACE_DESC_SIZE 9 #define USB_ENDPOINT_DESC_SIZE 7 -#define USB_DEVICE_DESCRIPTOR_TYPE 1 -#define USB_CONFIGURATION_DESCRIPTOR_TYPE 2 -#define USB_STRING_DESCRIPTOR_TYPE 3 -#define USB_INTERFACE_DESCRIPTOR_TYPE 4 -#define USB_ENDPOINT_DESCRIPTOR_TYPE 5 +#define USB_DEVICE_DESCRIPTOR_TYPE 1 +#define USB_CONFIGURATION_DESCRIPTOR_TYPE 2 +#define USB_STRING_DESCRIPTOR_TYPE 3 +#define USB_INTERFACE_DESCRIPTOR_TYPE 4 +#define USB_ENDPOINT_DESCRIPTOR_TYPE 5 // usb_20.pdf Table 9.6 Standard Feature Selectors -#define DEVICE_REMOTE_WAKEUP 1 -#define ENDPOINT_HALT 2 -#define TEST_MODE 3 +#define DEVICE_REMOTE_WAKEUP 1 +#define ENDPOINT_HALT 2 +#define TEST_MODE 3 // usb_20.pdf Figure 9-4. Information Returned by a GetStatus() Request to a Device -#define FEATURE_SELFPOWERED_ENABLED (1 << 0) -#define FEATURE_REMOTE_WAKEUP_ENABLED (1 << 1) +#define FEATURE_SELFPOWERED_ENABLED (1 << 0) +#define FEATURE_REMOTE_WAKEUP_ENABLED (1 << 1) -#define USB_DEVICE_CLASS_COMMUNICATIONS 0x02 -#define USB_DEVICE_CLASS_HUMAN_INTERFACE 0x03 -#define USB_DEVICE_CLASS_STORAGE 0x08 -#define USB_DEVICE_CLASS_VENDOR_SPECIFIC 0xFF +#define USB_DEVICE_CLASS_COMMUNICATIONS 0x02 +#define USB_DEVICE_CLASS_HUMAN_INTERFACE 0x03 +#define USB_DEVICE_CLASS_STORAGE 0x08 +#define USB_DEVICE_CLASS_VENDOR_SPECIFIC 0xFF -#define USB_CONFIG_POWERED_MASK 0x40 -#define USB_CONFIG_BUS_POWERED 0x80 -#define USB_CONFIG_SELF_POWERED 0xC0 -#define USB_CONFIG_REMOTE_WAKEUP 0x20 +#define USB_CONFIG_POWERED_MASK 0x40 +#define USB_CONFIG_BUS_POWERED 0x80 +#define USB_CONFIG_SELF_POWERED 0xC0 +#define USB_CONFIG_REMOTE_WAKEUP 0x20 // bMaxPower in Configuration Descriptor -#define USB_CONFIG_POWER_MA(mA) ((mA)/2) +#define USB_CONFIG_POWER_MA(mA) ((mA) / 2) // bEndpointAddress in Endpoint Descriptor -#define USB_ENDPOINT_DIRECTION_MASK 0x80 -#define USB_ENDPOINT_OUT(addr) (lowByte((addr) | 0x00)) -#define USB_ENDPOINT_IN(addr) (lowByte((addr) | 0x80)) +#define USB_ENDPOINT_DIRECTION_MASK 0x80 +#define USB_ENDPOINT_OUT(addr) (lowByte((addr) | 0x00)) +#define USB_ENDPOINT_IN(addr) (lowByte((addr) | 0x80)) -#define USB_ENDPOINT_TYPE_MASK 0x03 -#define USB_ENDPOINT_TYPE_CONTROL 0x00 -#define USB_ENDPOINT_TYPE_ISOCHRONOUS 0x01 -#define USB_ENDPOINT_TYPE_BULK 0x02 -#define USB_ENDPOINT_TYPE_INTERRUPT 0x03 +#define USB_ENDPOINT_TYPE_MASK 0x03 +#define USB_ENDPOINT_TYPE_CONTROL 0x00 +#define USB_ENDPOINT_TYPE_ISOCHRONOUS 0x01 +#define USB_ENDPOINT_TYPE_BULK 0x02 +#define USB_ENDPOINT_TYPE_INTERRUPT 0x03 -#define TOBYTES(x) ((x) & 0xFF),(((x) >> 8) & 0xFF) +#define TOBYTES(x) ((x)&0xFF), (((x) >> 8) & 0xFF) -#define CDC_V1_10 0x0110 -#define CDC_COMMUNICATION_INTERFACE_CLASS 0x02 +#define CDC_V1_10 0x0110 +#define CDC_COMMUNICATION_INTERFACE_CLASS 0x02 -#define CDC_CALL_MANAGEMENT 0x01 -#define CDC_ABSTRACT_CONTROL_MODEL 0x02 -#define CDC_HEADER 0x00 -#define CDC_ABSTRACT_CONTROL_MANAGEMENT 0x02 -#define CDC_UNION 0x06 -#define CDC_CS_INTERFACE 0x24 -#define CDC_CS_ENDPOINT 0x25 -#define CDC_DATA_INTERFACE_CLASS 0x0A +#define CDC_CALL_MANAGEMENT 0x01 +#define CDC_ABSTRACT_CONTROL_MODEL 0x02 +#define CDC_HEADER 0x00 +#define CDC_ABSTRACT_CONTROL_MANAGEMENT 0x02 +#define CDC_UNION 0x06 +#define CDC_CS_INTERFACE 0x24 +#define CDC_CS_ENDPOINT 0x25 +#define CDC_DATA_INTERFACE_CLASS 0x0A -#define MSC_SUBCLASS_SCSI 0x06 -#define MSC_PROTOCOL_BULK_ONLY 0x50 +#define MSC_SUBCLASS_SCSI 0x06 +#define MSC_PROTOCOL_BULK_ONLY 0x50 #ifndef USB_VERSION #define USB_VERSION 0x200 #endif -#define TRANSFER_PGM 0x80 -#define TRANSFER_RELEASE 0x40 -#define TRANSFER_ZERO 0x20 - -// Device -typedef struct { - uint8_t len; // 18 - uint8_t dtype; // 1 USB_DEVICE_DESCRIPTOR_TYPE - uint16_t usbVersion; // 0x200 or 0x210 - uint8_t deviceClass; - uint8_t deviceSubClass; - uint8_t deviceProtocol; - uint8_t packetSize0; // Packet 0 - uint16_t idVendor; - uint16_t idProduct; - uint16_t deviceVersion; // 0x100 - uint8_t iManufacturer; - uint8_t iProduct; - uint8_t iSerialNumber; - uint8_t bNumConfigurations; +#define TRANSFER_PGM 0x80 +#define TRANSFER_RELEASE 0x40 +#define TRANSFER_ZERO 0x20 + +// Device +typedef struct +{ + uint8_t len; // 18 + uint8_t dtype; // 1 USB_DEVICE_DESCRIPTOR_TYPE + uint16_t usbVersion; // 0x200 or 0x210 + uint8_t deviceClass; + uint8_t deviceSubClass; + uint8_t deviceProtocol; + uint8_t packetSize0; // Packet 0 + uint16_t idVendor; + uint16_t idProduct; + uint16_t deviceVersion; // 0x100 + uint8_t iManufacturer; + uint8_t iProduct; + uint8_t iSerialNumber; + uint8_t bNumConfigurations; } DeviceDescriptor; -// Config -typedef struct { - uint8_t len; // 9 - uint8_t dtype; // 2 - uint16_t clen; // total length - uint8_t numInterfaces; - uint8_t config; - uint8_t iconfig; - uint8_t attributes; - uint8_t maxPower; +// Config +typedef struct +{ + uint8_t len; // 9 + uint8_t dtype; // 2 + uint16_t clen; // total length + uint8_t numInterfaces; + uint8_t config; + uint8_t iconfig; + uint8_t attributes; + uint8_t maxPower; } ConfigDescriptor; -// String +// String -// Interface +// Interface typedef struct { - uint8_t len; // 9 - uint8_t dtype; // 4 - uint8_t number; - uint8_t alternate; - uint8_t numEndpoints; - uint8_t interfaceClass; - uint8_t interfaceSubClass; - uint8_t protocol; - uint8_t iInterface; + uint8_t len; // 9 + uint8_t dtype; // 4 + uint8_t number; + uint8_t alternate; + uint8_t numEndpoints; + uint8_t interfaceClass; + uint8_t interfaceSubClass; + uint8_t protocol; + uint8_t iInterface; } InterfaceDescriptor; -// Endpoint +// Endpoint typedef struct { - uint8_t len; // 7 - uint8_t dtype; // 5 - uint8_t addr; - uint8_t attr; - uint16_t packetSize; - uint8_t interval; + uint8_t len; // 7 + uint8_t dtype; // 5 + uint8_t addr; + uint8_t attr; + uint16_t packetSize; + uint8_t interval; } EndpointDescriptor; // Interface Association Descriptor // Used to bind 2 interfaces together in CDC compostite device typedef struct { - uint8_t len; // 8 - uint8_t dtype; // 11 - uint8_t firstInterface; - uint8_t interfaceCount; - uint8_t functionClass; - uint8_t funtionSubClass; - uint8_t functionProtocol; - uint8_t iInterface; + uint8_t len; // 8 + uint8_t dtype; // 11 + uint8_t firstInterface; + uint8_t interfaceCount; + uint8_t functionClass; + uint8_t funtionSubClass; + uint8_t functionProtocol; + uint8_t iInterface; } IADDescriptor; -// CDC CS interface descriptor +// CDC CS interface descriptor typedef struct { - uint8_t len; // 5 - uint8_t dtype; // 0x24 - uint8_t subtype; - uint8_t d0; - uint8_t d1; + uint8_t len; // 5 + uint8_t dtype; // 0x24 + uint8_t subtype; + uint8_t d0; + uint8_t d1; } CDCCSInterfaceDescriptor; typedef struct { - uint8_t len; // 4 - uint8_t dtype; // 0x24 - uint8_t subtype; - uint8_t d0; + uint8_t len; // 4 + uint8_t dtype; // 0x24 + uint8_t subtype; + uint8_t d0; } CDCCSInterfaceDescriptor4; -typedef struct +typedef struct { - uint8_t len; - uint8_t dtype; // 0x24 - uint8_t subtype; // 1 - uint8_t bmCapabilities; - uint8_t bDataInterface; + uint8_t len; + uint8_t dtype; // 0x24 + uint8_t subtype; // 1 + uint8_t bmCapabilities; + uint8_t bDataInterface; } CMFunctionalDescriptor; - -typedef struct + +typedef struct { - uint8_t len; - uint8_t dtype; // 0x24 - uint8_t subtype; // 1 - uint8_t bmCapabilities; + uint8_t len; + uint8_t dtype; // 0x24 + uint8_t subtype; // 1 + uint8_t bmCapabilities; } ACMFunctionalDescriptor; -typedef struct +typedef struct { - // IAD - IADDescriptor iad; // Only needed on compound device - - // Control - InterfaceDescriptor cif; // - CDCCSInterfaceDescriptor header; - CMFunctionalDescriptor callManagement; // Call Management - ACMFunctionalDescriptor controlManagement; // ACM - CDCCSInterfaceDescriptor functionalDescriptor; // CDC_UNION - EndpointDescriptor cifin; - - // Data - InterfaceDescriptor dif; - EndpointDescriptor in; - EndpointDescriptor out; + // IAD + IADDescriptor iad; // Only needed on compound device + + // Control + InterfaceDescriptor cif; // + CDCCSInterfaceDescriptor header; + CMFunctionalDescriptor callManagement; // Call Management + ACMFunctionalDescriptor controlManagement; // ACM + CDCCSInterfaceDescriptor functionalDescriptor; // CDC_UNION + EndpointDescriptor cifin; + + // Data + InterfaceDescriptor dif; + EndpointDescriptor in; + EndpointDescriptor out; } CDCDescriptor; -typedef struct +typedef struct { - InterfaceDescriptor msc; - EndpointDescriptor in; - EndpointDescriptor out; + InterfaceDescriptor msc; + EndpointDescriptor in; + EndpointDescriptor out; } MSCDescriptor; +#define D_DEVICE(_class, _subClass, _proto, _packetSize0, _vid, _pid, _version, _im, _ip, _is, _configs) \ + { \ + 18, 1, USB_VERSION, _class, _subClass, _proto, _packetSize0, _vid, _pid, _version, _im, _ip, _is, _configs \ + } -#define D_DEVICE(_class,_subClass,_proto,_packetSize0,_vid,_pid,_version,_im,_ip,_is,_configs) \ - { 18, 1, USB_VERSION, _class,_subClass,_proto,_packetSize0,_vid,_pid,_version,_im,_ip,_is,_configs } - -#define D_CONFIG(_totalLength,_interfaces) \ - { 9, 2, _totalLength,_interfaces, 1, 0, USB_CONFIG_BUS_POWERED | USB_CONFIG_REMOTE_WAKEUP, USB_CONFIG_POWER_MA(500) } +#define D_CONFIG(_totalLength, _interfaces) \ + { \ + 9, 2, _totalLength, _interfaces, 1, 0, USB_CONFIG_BUS_POWERED | USB_CONFIG_REMOTE_WAKEUP, USB_CONFIG_POWER_MA(500) \ + } -#define D_INTERFACE(_n,_numEndpoints,_class,_subClass,_protocol) \ - { 9, 4, _n, 0, _numEndpoints, _class,_subClass, _protocol, 0 } +#define D_INTERFACE(_n, _numEndpoints, _class, _subClass, _protocol) \ + { \ + 9, 4, _n, 0, _numEndpoints, _class, _subClass, _protocol, 0 \ + } -#define D_ENDPOINT(_addr,_attr,_packetSize, _interval) \ - { 7, 5, _addr,_attr,_packetSize, _interval } +#define D_ENDPOINT(_addr, _attr, _packetSize, _interval) \ + { \ + 7, 5, _addr, _attr, _packetSize, _interval \ + } #define D_IAD(_firstInterface, _count, _class, _subClass, _protocol) \ - { 8, 11, _firstInterface, _count, _class, _subClass, _protocol, 0 } - -#define D_CDCCS(_subtype,_d0,_d1) { 5, 0x24, _subtype, _d0, _d1 } -#define D_CDCCS4(_subtype,_d0) { 4, 0x24, _subtype, _d0 } + { \ + 8, 11, _firstInterface, _count, _class, _subClass, _protocol, 0 \ + } + +#define D_CDCCS(_subtype, _d0, _d1) \ + { \ + 5, 0x24, _subtype, _d0, _d1 \ + } +#define D_CDCCS4(_subtype, _d0) \ + { \ + 4, 0x24, _subtype, _d0 \ + } // Bootloader related fields // Old Caterina bootloader places the MAGIC key into unsafe RAM locations (it can be rewritten @@ -327,13 +344,13 @@ typedef struct #define USB_ENDPOINTS 5 // AtMegaxxU2 #endif -#define EP_TYPE_CONTROL (0x00) -#define EP_TYPE_BULK_IN ((1< -#include #include +#include #include +#include #include #include "wiring_private.h" static volatile voidFuncPtr intFunc[EXTERNAL_NUM_INTERRUPTS]; -void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) { - +void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) +{ /* Get bit position and check pin validity */ uint8_t bit_pos = digitalPinToBitPosition(pin); - if(bit_pos == NOT_A_PIN) return; + if (bit_pos == NOT_A_PIN) return; /* Get interrupt number from pin */ uint8_t interruptNum = (digitalPinToPort(pin) * 8) + bit_pos; /* Check interrupt number and apply function pointer to correct array index */ - if(interruptNum < EXTERNAL_NUM_INTERRUPTS) { + if (interruptNum < EXTERNAL_NUM_INTERRUPTS) + { intFunc[interruptNum] = userFunc; // Configure the interrupt mode (trigger on low input, any change, rising @@ -52,7 +51,8 @@ void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) { // to the configuration bits in the hardware register, so we simply apply // the setting in the pin control register - switch (mode) { + switch (mode) + { case CHANGE: mode = PORT_ISC_BOTHEDGES_gc; break; @@ -74,7 +74,7 @@ void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) { /* Get pointer to correct pin control register */ PORT_t *port = digitalPinToPortStruct(pin); - volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); + volatile uint8_t *pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); /* Clear any previous setting */ *pin_ctrl_reg &= ~(PORT_ISC_gm); @@ -84,20 +84,22 @@ void attachInterrupt(uint8_t pin, void (*userFunc)(void), uint8_t mode) { } } -void detachInterrupt(uint8_t pin) { +void detachInterrupt(uint8_t pin) +{ /* Get bit position and check pin validity */ uint8_t bit_pos = digitalPinToBitPosition(pin); - if(bit_pos == NOT_A_PIN) return; + if (bit_pos == NOT_A_PIN) return; /* Get interrupt number from pin */ uint8_t interruptNum = (digitalPinToPort(pin) * 8) + bit_pos; - if(interruptNum < EXTERNAL_NUM_INTERRUPTS) { + if (interruptNum < EXTERNAL_NUM_INTERRUPTS) + { // Disable the interrupt. /* Get pointer to correct pin control register */ PORT_t *port = digitalPinToPortStruct(pin); - volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); + volatile uint8_t *pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); /* Clear ISC setting */ *pin_ctrl_reg &= ~(PORT_ISC_gm); @@ -106,8 +108,8 @@ void detachInterrupt(uint8_t pin) { } } -static void port_interrupt_handler(uint8_t port) { - +static void port_interrupt_handler(uint8_t port) +{ PORT_t *portStruct = portToPortStruct(port); /* Copy flags */ uint8_t int_flags = portStruct->INTFLAGS; @@ -115,23 +117,23 @@ static void port_interrupt_handler(uint8_t port) { uint8_t bit_pos = PIN0_bp, bit_mask = PIN0_bm; /* Iterate through flags */ - while(bit_pos <= PIN7_bp){ - + while (bit_pos <= PIN7_bp) + { /* Check if flag raised */ - if(int_flags & bit_mask){ - - /* Get interrupt */ - uint8_t interrupt_num = port*8 + bit_pos; + if (int_flags & bit_mask) + { + /* Get interrupt */ + uint8_t interrupt_num = port * 8 + bit_pos; /* Check if function defined */ - if(intFunc[interrupt_num] != 0){ - + if (intFunc[interrupt_num] != 0) + { /* Call function */ intFunc[interrupt_num](); } } bit_pos++; - bit_mask = (bit_mask << 1); + bit_mask = (bit_mask << 1); } /* Clear flags that have been handled */ @@ -139,9 +141,10 @@ static void port_interrupt_handler(uint8_t port) { } #define IMPLEMENT_ISR(vect, port) \ -ISR(vect) { \ - port_interrupt_handler(port);\ -} \ + ISR(vect) \ + { \ + port_interrupt_handler(port); \ + } IMPLEMENT_ISR(PORTA_PORT_vect, PA) IMPLEMENT_ISR(PORTB_PORT_vect, PB) diff --git a/megaavr/cores/coreX-corefiles/WMath.cpp b/megaavr/cores/coreX-corefiles/WMath.cpp index f4ce2b7..9a5af7d 100644 --- a/megaavr/cores/coreX-corefiles/WMath.cpp +++ b/megaavr/cores/coreX-corefiles/WMath.cpp @@ -1,5 +1,3 @@ -/* -*- mode: jde; c-basic-offset: 2; indent-tabs-mode: nil -*- */ - /* Part of the Wiring project - http://wiring.org.co Copyright (c) 2004-06 Hernando Barragan @@ -21,20 +19,23 @@ Boston, MA 02111-1307 USA */ -extern "C" { +extern "C" +{ #include "stdlib.h" } void randomSeed(unsigned long seed) { - if (seed != 0) { + if (seed != 0) + { srandom(seed); } } long random(long howbig) { - if (howbig == 0) { + if (howbig == 0) + { return 0; } return random() % howbig; @@ -42,7 +43,8 @@ long random(long howbig) long random(long howsmall, long howbig) { - if (howsmall >= howbig) { + if (howsmall >= howbig) + { return howsmall; } long diff = howbig - howsmall; diff --git a/megaavr/cores/coreX-corefiles/api/ArduinoAPI.h b/megaavr/cores/coreX-corefiles/api/ArduinoAPI.h index b737af9..1535fe9 100644 --- a/megaavr/cores/coreX-corefiles/api/ArduinoAPI.h +++ b/megaavr/cores/coreX-corefiles/api/ArduinoAPI.h @@ -30,23 +30,23 @@ #include "HardwareI2C.h" #include "HardwareSerial.h" #include "IPAddress.h" +#include "PluggableUSB.h" #include "Print.h" #include "Printable.h" -#include "PluggableUSB.h" #include "Server.h" -#include "String.h" #include "Stream.h" -#include "Udp.h" +#include "String.h" #include "USBAPI.h" +#include "Udp.h" #include "WCharacter.h" #endif /* Standard C library includes */ -#include -#include +#include #include +#include +#include #include -#include // Misc Arduino core functions #include "Common.h" diff --git a/megaavr/cores/coreX-corefiles/api/Client.h b/megaavr/cores/coreX-corefiles/api/Client.h index c8ebc9f..25cbd95 100644 --- a/megaavr/cores/coreX-corefiles/api/Client.h +++ b/megaavr/cores/coreX-corefiles/api/Client.h @@ -19,16 +19,16 @@ #pragma once -#include "Stream.h" #include "IPAddress.h" +#include "Stream.h" -class Client : public Stream { - -public: - virtual int connect(IPAddress ip, uint16_t port) =0; - virtual int connect(const char *host, uint16_t port) =0; - virtual size_t write(uint8_t) =0; - virtual size_t write(const uint8_t *buf, size_t size) =0; +class Client : public Stream +{ + public: + virtual int connect(IPAddress ip, uint16_t port) = 0; + virtual int connect(const char *host, uint16_t port) = 0; + virtual size_t write(uint8_t) = 0; + virtual size_t write(const uint8_t *buf, size_t size) = 0; virtual int available() = 0; virtual int read() = 0; virtual int read(uint8_t *buf, size_t size) = 0; @@ -37,7 +37,7 @@ class Client : public Stream { virtual void stop() = 0; virtual uint8_t connected() = 0; virtual operator bool() = 0; -protected: - uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); }; -}; + protected: + uint8_t *rawIPAddress(IPAddress &addr) { return addr.raw_address(); }; +}; diff --git a/megaavr/cores/coreX-corefiles/api/Common.cpp b/megaavr/cores/coreX-corefiles/api/Common.cpp index d1f822c..bd7a5e2 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.cpp +++ b/megaavr/cores/coreX-corefiles/api/Common.cpp @@ -7,4 +7,4 @@ long map(long x, long in_min, long in_max, long out_min, long out_max) } uint16_t makeWord(uint16_t w) { return w; } -uint16_t makeWord(uint8_t h, uint8_t l) { return (h << 8) | l; } \ No newline at end of file +uint16_t makeWord(uint8_t h, uint8_t l) { return (h << 8) | l; } diff --git a/megaavr/cores/coreX-corefiles/api/HardwareI2C.h b/megaavr/cores/coreX-corefiles/api/HardwareI2C.h index 25bf40e..5e37368 100644 --- a/megaavr/cores/coreX-corefiles/api/HardwareI2C.h +++ b/megaavr/cores/coreX-corefiles/api/HardwareI2C.h @@ -19,25 +19,25 @@ #pragma once #include + #include "Stream.h" class HardwareI2C : public Stream { - public: - virtual void begin() = 0; - virtual void begin(uint8_t address) = 0; - virtual void end() = 0; - - virtual void setClock(uint32_t freq) = 0; - - virtual void beginTransmission(uint8_t address) = 0; - virtual uint8_t endTransmission(bool stopBit) = 0; - virtual uint8_t endTransmission(void) = 0; - - virtual uint8_t requestFrom(uint8_t address, size_t len, bool stopBit) = 0; - virtual uint8_t requestFrom(uint8_t address, size_t len) = 0; - - virtual void onReceive(void(*)(int)) = 0; - virtual void onRequest(void(*)(void)) = 0; -}; + public: + virtual void begin() = 0; + virtual void begin(uint8_t address) = 0; + virtual void end() = 0; + + virtual void setClock(uint32_t freq) = 0; + virtual void beginTransmission(uint8_t address) = 0; + virtual uint8_t endTransmission(bool stopBit) = 0; + virtual uint8_t endTransmission(void) = 0; + + virtual uint8_t requestFrom(uint8_t address, size_t len, bool stopBit) = 0; + virtual uint8_t requestFrom(uint8_t address, size_t len) = 0; + + virtual void onReceive(void (*)(int)) = 0; + virtual void onRequest(void (*)(void)) = 0; +}; diff --git a/megaavr/cores/coreX-corefiles/api/HardwareSerial.h b/megaavr/cores/coreX-corefiles/api/HardwareSerial.h index 734be67..94207ea 100644 --- a/megaavr/cores/coreX-corefiles/api/HardwareSerial.h +++ b/megaavr/cores/coreX-corefiles/api/HardwareSerial.h @@ -19,86 +19,86 @@ #pragma once #include + #include "Stream.h" // XXX: Those constants should be defined as const int / enums? // XXX: shall we use namespaces too? -#define SERIAL_PARITY_EVEN (0x1ul) -#define SERIAL_PARITY_ODD (0x2ul) -#define SERIAL_PARITY_NONE (0x3ul) -#define SERIAL_PARITY_MARK (0x4ul) -#define SERIAL_PARITY_SPACE (0x5ul) -#define SERIAL_PARITY_MASK (0xFul) +#define SERIAL_PARITY_EVEN (0x1ul) +#define SERIAL_PARITY_ODD (0x2ul) +#define SERIAL_PARITY_NONE (0x3ul) +#define SERIAL_PARITY_MARK (0x4ul) +#define SERIAL_PARITY_SPACE (0x5ul) +#define SERIAL_PARITY_MASK (0xFul) -#define SERIAL_STOP_BIT_1 (0x10ul) -#define SERIAL_STOP_BIT_1_5 (0x20ul) -#define SERIAL_STOP_BIT_2 (0x30ul) +#define SERIAL_STOP_BIT_1 (0x10ul) +#define SERIAL_STOP_BIT_1_5 (0x20ul) +#define SERIAL_STOP_BIT_2 (0x30ul) #define SERIAL_STOP_BIT_MASK (0xF0ul) -#define SERIAL_DATA_5 (0x100ul) -#define SERIAL_DATA_6 (0x200ul) -#define SERIAL_DATA_7 (0x300ul) -#define SERIAL_DATA_8 (0x400ul) -#define SERIAL_DATA_MASK (0xF00ul) +#define SERIAL_DATA_5 (0x100ul) +#define SERIAL_DATA_6 (0x200ul) +#define SERIAL_DATA_7 (0x300ul) +#define SERIAL_DATA_8 (0x400ul) +#define SERIAL_DATA_MASK (0xF00ul) -#define SERIAL_5N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_5) -#define SERIAL_6N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_6) -#define SERIAL_7N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_7) -#define SERIAL_8N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_8) -#define SERIAL_5N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_5) -#define SERIAL_6N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_6) -#define SERIAL_7N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_7) -#define SERIAL_8N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_8) -#define SERIAL_5E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_5) -#define SERIAL_6E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_6) -#define SERIAL_7E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_7) -#define SERIAL_8E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_8) -#define SERIAL_5E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_5) -#define SERIAL_6E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_6) -#define SERIAL_7E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_7) -#define SERIAL_8E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_8) -#define SERIAL_5O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_5) -#define SERIAL_6O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_6) -#define SERIAL_7O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_7) -#define SERIAL_8O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_8) -#define SERIAL_5O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_5) -#define SERIAL_6O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_6) -#define SERIAL_7O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_7) -#define SERIAL_8O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_8) -#define SERIAL_5M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_5) -#define SERIAL_6M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_6) -#define SERIAL_7M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_7) -#define SERIAL_8M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_8) -#define SERIAL_5M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_5) -#define SERIAL_6M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_6) -#define SERIAL_7M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_7) -#define SERIAL_8M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_8) -#define SERIAL_5S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_5) -#define SERIAL_6S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_6) -#define SERIAL_7S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_7) -#define SERIAL_8S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_8) -#define SERIAL_5S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_5) -#define SERIAL_6S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_6) -#define SERIAL_7S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_7) -#define SERIAL_8S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_8) +#define SERIAL_5N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_5) +#define SERIAL_6N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_6) +#define SERIAL_7N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_7) +#define SERIAL_8N1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_NONE | SERIAL_DATA_8) +#define SERIAL_5N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_5) +#define SERIAL_6N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_6) +#define SERIAL_7N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_7) +#define SERIAL_8N2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_NONE | SERIAL_DATA_8) +#define SERIAL_5E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_5) +#define SERIAL_6E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_6) +#define SERIAL_7E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_7) +#define SERIAL_8E1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_EVEN | SERIAL_DATA_8) +#define SERIAL_5E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_5) +#define SERIAL_6E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_6) +#define SERIAL_7E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_7) +#define SERIAL_8E2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_EVEN | SERIAL_DATA_8) +#define SERIAL_5O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_5) +#define SERIAL_6O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_6) +#define SERIAL_7O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_7) +#define SERIAL_8O1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_ODD | SERIAL_DATA_8) +#define SERIAL_5O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_5) +#define SERIAL_6O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_6) +#define SERIAL_7O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_7) +#define SERIAL_8O2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_ODD | SERIAL_DATA_8) +#define SERIAL_5M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_5) +#define SERIAL_6M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_6) +#define SERIAL_7M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_7) +#define SERIAL_8M1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_MARK | SERIAL_DATA_8) +#define SERIAL_5M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_5) +#define SERIAL_6M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_6) +#define SERIAL_7M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_7) +#define SERIAL_8M2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_MARK | SERIAL_DATA_8) +#define SERIAL_5S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_5) +#define SERIAL_6S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_6) +#define SERIAL_7S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_7) +#define SERIAL_8S1 (SERIAL_STOP_BIT_1 | SERIAL_PARITY_SPACE | SERIAL_DATA_8) +#define SERIAL_5S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_5) +#define SERIAL_6S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_6) +#define SERIAL_7S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_7) +#define SERIAL_8S2 (SERIAL_STOP_BIT_2 | SERIAL_PARITY_SPACE | SERIAL_DATA_8) class HardwareSerial : public Stream { - public: - virtual bool pins(uint8_t tx, uint8_t rx) = 0; - virtual bool swap(uint8_t state) = 0; - virtual void begin(unsigned long) = 0; - virtual void begin(unsigned long baudrate, uint16_t config) = 0; - virtual void end() = 0; - virtual int available(void) = 0; - virtual int peek(void) = 0; - virtual int read(void) = 0; - virtual void flush(void) = 0; - virtual size_t write(uint8_t) = 0; - using Print::write; // pull in write(str) and write(buf, size) from Print - virtual operator bool() = 0; + public: + virtual bool pins(uint8_t tx, uint8_t rx) = 0; + virtual bool swap(uint8_t state) = 0; + virtual void begin(unsigned long) = 0; + virtual void begin(unsigned long baudrate, uint16_t config) = 0; + virtual void end() = 0; + virtual int available(void) = 0; + virtual int peek(void) = 0; + virtual int read(void) = 0; + virtual void flush(void) = 0; + virtual size_t write(uint8_t) = 0; + using Print::write; // pull in write(str) and write(buf, size) from Print + virtual operator bool() = 0; }; // XXX: Are we keeping the serialEvent API? extern void serialEventRun(void) __attribute__((weak)); - diff --git a/megaavr/cores/coreX-corefiles/api/IPAddress.cpp b/megaavr/cores/coreX-corefiles/api/IPAddress.cpp index 62244d6..8f70061 100644 --- a/megaavr/cores/coreX-corefiles/api/IPAddress.cpp +++ b/megaavr/cores/coreX-corefiles/api/IPAddress.cpp @@ -18,100 +18,104 @@ */ #include "IPAddress.h" + #include "Print.h" IPAddress::IPAddress() { - _address.dword = 0; + _address.dword = 0; } IPAddress::IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet) { - _address.bytes[0] = first_octet; - _address.bytes[1] = second_octet; - _address.bytes[2] = third_octet; - _address.bytes[3] = fourth_octet; + _address.bytes[0] = first_octet; + _address.bytes[1] = second_octet; + _address.bytes[2] = third_octet; + _address.bytes[3] = fourth_octet; } IPAddress::IPAddress(uint32_t address) { - _address.dword = address; + _address.dword = address; } -IPAddress::IPAddress(const uint8_t *address) +IPAddress::IPAddress(const uint8_t* address) { - memcpy(_address.bytes, address, sizeof(_address.bytes)); + memcpy(_address.bytes, address, sizeof(_address.bytes)); } -bool IPAddress::fromString(const char *address) +bool IPAddress::fromString(const char* address) { - // TODO: add support for "a", "a.b", "a.b.c" formats + // TODO: add support for "a", "a.b", "a.b.c" formats - uint16_t acc = 0; // Accumulator - uint8_t dots = 0; + uint16_t acc = 0; // Accumulator + uint8_t dots = 0; - while (*address) + while (*address) + { + char c = *address++; + if (c >= '0' && c <= '9') { - char c = *address++; - if (c >= '0' && c <= '9') - { - acc = acc * 10 + (c - '0'); - if (acc > 255) { - // Value out of [0..255] range - return false; - } - } - else if (c == '.') - { - if (dots == 3) { - // Too much dots (there must be 3 dots) - return false; - } - _address.bytes[dots++] = acc; - acc = 0; - } - else - { - // Invalid char - return false; - } + acc = acc * 10 + (c - '0'); + if (acc > 255) + { + // Value out of [0..255] range + return false; + } } - - if (dots != 3) { - // Too few dots (there must be 3 dots) + else if (c == '.') + { + if (dots == 3) + { + // Too much dots (there must be 3 dots) return false; + } + _address.bytes[dots++] = acc; + acc = 0; } - _address.bytes[3] = acc; - return true; + else + { + // Invalid char + return false; + } + } + + if (dots != 3) + { + // Too few dots (there must be 3 dots) + return false; + } + _address.bytes[3] = acc; + return true; } -IPAddress& IPAddress::operator=(const uint8_t *address) +IPAddress& IPAddress::operator=(const uint8_t* address) { - memcpy(_address.bytes, address, sizeof(_address.bytes)); - return *this; + memcpy(_address.bytes, address, sizeof(_address.bytes)); + return *this; } IPAddress& IPAddress::operator=(uint32_t address) { - _address.dword = address; - return *this; + _address.dword = address; + return *this; } bool IPAddress::operator==(const uint8_t* addr) const { - return memcmp(addr, _address.bytes, sizeof(_address.bytes)) == 0; + return memcmp(addr, _address.bytes, sizeof(_address.bytes)) == 0; } size_t IPAddress::printTo(Print& p) const { - size_t n = 0; - for (int i =0; i < 3; i++) - { - n += p.print(_address.bytes[i], DEC); - n += p.print('.'); - } - n += p.print(_address.bytes[3], DEC); - return n; + size_t n = 0; + for (int i = 0; i < 3; i++) + { + n += p.print(_address.bytes[i], DEC); + n += p.print('.'); + } + n += p.print(_address.bytes[3], DEC); + return n; } -const IPAddress INADDR_NONE(0,0,0,0); +const IPAddress INADDR_NONE(0, 0, 0, 0); diff --git a/megaavr/cores/coreX-corefiles/api/IPAddress.h b/megaavr/cores/coreX-corefiles/api/IPAddress.h index af33cf8..e95c8fb 100644 --- a/megaavr/cores/coreX-corefiles/api/IPAddress.h +++ b/megaavr/cores/coreX-corefiles/api/IPAddress.h @@ -20,57 +20,58 @@ #pragma once #include + #include "Printable.h" #include "String.h" // A class to make it easier to handle and pass around IP addresses -class IPAddress : public Printable { -private: - union { - uint8_t bytes[4]; // IPv4 address - uint32_t dword; - } _address; - - // Access the raw byte array containing the address. Because this returns a pointer - // to the internal structure rather than a copy of the address this function should only - // be used when you know that the usage of the returned uint8_t* will be transient and not - // stored. - uint8_t* raw_address() { return _address.bytes; }; - -public: - // Constructors - IPAddress(); - IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet); - IPAddress(uint32_t address); - IPAddress(const uint8_t *address); - - bool fromString(const char *address); - bool fromString(const String &address) { return fromString(address.c_str()); } - - // Overloaded cast operator to allow IPAddress objects to be used where a pointer - // to a four-byte uint8_t array is expected - operator uint32_t() const { return _address.dword; }; - bool operator==(const IPAddress& addr) const { return _address.dword == addr._address.dword; }; - bool operator==(const uint8_t* addr) const; - - // Overloaded index operator to allow getting and setting individual octets of the address - uint8_t operator[](int index) const { return _address.bytes[index]; }; - uint8_t& operator[](int index) { return _address.bytes[index]; }; - - // Overloaded copy operators to allow initialisation of IPAddress objects from other types - IPAddress& operator=(const uint8_t *address); - IPAddress& operator=(uint32_t address); - - virtual size_t printTo(Print& p) const; - - friend class EthernetClass; - friend class UDP; - friend class Client; - friend class Server; - friend class DhcpClass; - friend class DNSClient; +class IPAddress : public Printable +{ + private: + union { + uint8_t bytes[4]; // IPv4 address + uint32_t dword; + } _address; + + // Access the raw byte array containing the address. Because this returns a pointer + // to the internal structure rather than a copy of the address this function should only + // be used when you know that the usage of the returned uint8_t* will be transient and not + // stored. + uint8_t* raw_address() { return _address.bytes; }; + + public: + // Constructors + IPAddress(); + IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet); + IPAddress(uint32_t address); + IPAddress(const uint8_t* address); + + bool fromString(const char* address); + bool fromString(const String& address) { return fromString(address.c_str()); } + + // Overloaded cast operator to allow IPAddress objects to be used where a pointer + // to a four-byte uint8_t array is expected + operator uint32_t() const { return _address.dword; }; + bool operator==(const IPAddress& addr) const { return _address.dword == addr._address.dword; }; + bool operator==(const uint8_t* addr) const; + + // Overloaded index operator to allow getting and setting individual octets of the address + uint8_t operator[](int index) const { return _address.bytes[index]; }; + uint8_t& operator[](int index) { return _address.bytes[index]; }; + + // Overloaded copy operators to allow initialisation of IPAddress objects from other types + IPAddress& operator=(const uint8_t* address); + IPAddress& operator=(uint32_t address); + + virtual size_t printTo(Print& p) const; + + friend class EthernetClass; + friend class UDP; + friend class Client; + friend class Server; + friend class DhcpClass; + friend class DNSClient; }; extern const IPAddress INADDR_NONE; - diff --git a/megaavr/cores/coreX-corefiles/api/PluggableUSB.cpp b/megaavr/cores/coreX-corefiles/api/PluggableUSB.cpp index f0c45f0..0ef7364 100644 --- a/megaavr/cores/coreX-corefiles/api/PluggableUSB.cpp +++ b/megaavr/cores/coreX-corefiles/api/PluggableUSB.cpp @@ -17,83 +17,95 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ -#include "USBAPI.h" #include "PluggableUSB.h" +#include "USBAPI.h" + int PluggableUSB_::getInterface(uint8_t* interfaceCount) { - int sent = 0; - PluggableUSBModule* node; - for (node = rootNode; node; node = node->next) { - int res = node->getInterface(interfaceCount); - if (res < 0) - return -1; - sent += res; - } - return sent; + int sent = 0; + PluggableUSBModule* node; + for (node = rootNode; node; node = node->next) + { + int res = node->getInterface(interfaceCount); + if (res < 0) + return -1; + sent += res; + } + return sent; } int PluggableUSB_::getDescriptor(USBSetup& setup) { - PluggableUSBModule* node; - for (node = rootNode; node; node = node->next) { - int ret = node->getDescriptor(setup); - // ret!=0 -> request has been processed - if (ret) - return ret; - } - return 0; + PluggableUSBModule* node; + for (node = rootNode; node; node = node->next) + { + int ret = node->getDescriptor(setup); + // ret!=0 -> request has been processed + if (ret) + return ret; + } + return 0; } -void PluggableUSB_::getShortName(char *iSerialNum) +void PluggableUSB_::getShortName(char* iSerialNum) { - PluggableUSBModule* node; - for (node = rootNode; node; node = node->next) { - iSerialNum += node->getShortName(iSerialNum); - } - *iSerialNum = 0; + PluggableUSBModule* node; + for (node = rootNode; node; node = node->next) + { + iSerialNum += node->getShortName(iSerialNum); + } + *iSerialNum = 0; } bool PluggableUSB_::setup(USBSetup& setup) { - PluggableUSBModule* node; - for (node = rootNode; node; node = node->next) { - if (node->setup(setup)) { - return true; - } - } - return false; + PluggableUSBModule* node; + for (node = rootNode; node; node = node->next) + { + if (node->setup(setup)) + { + return true; + } + } + return false; } -bool PluggableUSB_::plug(PluggableUSBModule *node) +bool PluggableUSB_::plug(PluggableUSBModule* node) { - if ((lastEp + node->numEndpoints) > totalEP) { - return false; - } + if ((lastEp + node->numEndpoints) > totalEP) + { + return false; + } - if (!rootNode) { - rootNode = node; - } else { - PluggableUSBModule *current = rootNode; - while (current->next) { - current = current->next; - } - current->next = node; - } + if (!rootNode) + { + rootNode = node; + } + else + { + PluggableUSBModule* current = rootNode; + while (current->next) + { + current = current->next; + } + current->next = node; + } - node->pluggedInterface = lastIf; - node->pluggedEndpoint = lastEp; - lastIf += node->numInterfaces; - for (uint8_t i = 0; i < node->numEndpoints; i++) { - *(unsigned int*)(epBuffer(lastEp)) = node->endpointType[i]; - lastEp++; - } - return true; - // restart USB layer??? + node->pluggedInterface = lastIf; + node->pluggedEndpoint = lastEp; + lastIf += node->numInterfaces; + for (uint8_t i = 0; i < node->numEndpoints; i++) + { + *(unsigned int*)(epBuffer(lastEp)) = node->endpointType[i]; + lastEp++; + } + return true; + // restart USB layer??? } PluggableUSB_& PluggableUSB() { - static PluggableUSB_ obj; - return obj; -} \ No newline at end of file + static PluggableUSB_ obj; + return obj; +} diff --git a/megaavr/cores/coreX-corefiles/api/PluggableUSB.h b/megaavr/cores/coreX-corefiles/api/PluggableUSB.h index 09b5fed..1d8b760 100644 --- a/megaavr/cores/coreX-corefiles/api/PluggableUSB.h +++ b/megaavr/cores/coreX-corefiles/api/PluggableUSB.h @@ -20,47 +20,54 @@ #ifndef PUSB_h #define PUSB_h -#include "USBAPI.h" -#include #include +#include + +#include "USBAPI.h" // core need to define void* epBuffer(unsigned int n); // -> returns a poointer to the Nth element of the EP buffer structure -class PluggableUSBModule { -public: - PluggableUSBModule(uint8_t numEps, uint8_t numIfs, unsigned int *epType) : - numEndpoints(numEps), numInterfaces(numIfs), endpointType(epType) - { } +class PluggableUSBModule +{ + public: + PluggableUSBModule(uint8_t numEps, uint8_t numIfs, unsigned int* epType) : numEndpoints(numEps), numInterfaces(numIfs), endpointType(epType) + { + } -protected: + protected: virtual bool setup(USBSetup& setup) = 0; virtual int getInterface(uint8_t* interfaceCount) = 0; virtual int getDescriptor(USBSetup& setup) = 0; - virtual uint8_t getShortName(char *name) { name[0] = 'A'+pluggedInterface; return 1; } + virtual uint8_t getShortName(char* name) + { + name[0] = 'A' + pluggedInterface; + return 1; + } uint8_t pluggedInterface; uint8_t pluggedEndpoint; const uint8_t numEndpoints; const uint8_t numInterfaces; - const unsigned int *endpointType; + const unsigned int* endpointType; - PluggableUSBModule *next = NULL; + PluggableUSBModule* next = NULL; friend class PluggableUSB_; }; -class PluggableUSB_ { -public: +class PluggableUSB_ +{ + public: PluggableUSB_(); - bool plug(PluggableUSBModule *node); + bool plug(PluggableUSBModule* node); int getInterface(uint8_t* interfaceCount); int getDescriptor(USBSetup& setup); bool setup(USBSetup& setup); - void getShortName(char *iSerialNum); + void getShortName(char* iSerialNum); -private: + private: uint8_t lastIf; uint8_t lastEp; PluggableUSBModule* rootNode; @@ -72,4 +79,4 @@ class PluggableUSB_ { // https://isocpp.org/wiki/faq/ctors#static-init-order-on-first-use PluggableUSB_& PluggableUSB(); -#endif \ No newline at end of file +#endif diff --git a/megaavr/cores/coreX-corefiles/api/Print.cpp b/megaavr/cores/coreX-corefiles/api/Print.cpp index f23b5f2..feec47c 100644 --- a/megaavr/cores/coreX-corefiles/api/Print.cpp +++ b/megaavr/cores/coreX-corefiles/api/Print.cpp @@ -16,10 +16,10 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ -#include +#include #include +#include #include -#include #include "Print.h" @@ -29,9 +29,12 @@ size_t Print::write(const uint8_t *buffer, size_t size) { size_t n = 0; - while (size--) { - if (write(*buffer++)) n++; - else break; + while (size--) + { + if (write(*buffer++)) + n++; + else + break; } return n; } @@ -41,11 +44,14 @@ size_t Print::print(const __FlashStringHelper *ifsh) #if defined(__AVR__) PGM_P p = reinterpret_cast(ifsh); size_t n = 0; - while (1) { + while (1) + { unsigned char c = pgm_read_byte(p++); if (c == 0) break; - if (write(c)) n++; - else break; + if (write(c)) + n++; + else + break; } return n; #else @@ -70,39 +76,47 @@ size_t Print::print(char c) size_t Print::print(unsigned char b, int base) { - return print((unsigned long) b, base); + return print((unsigned long)b, base); } size_t Print::print(int n, int base) { - return print((long) n, base); + return print((long)n, base); } size_t Print::print(unsigned int n, int base) { - return print((unsigned long) n, base); + return print((unsigned long)n, base); } size_t Print::print(long n, int base) { - if (base == 0) { + if (base == 0) + { return write(n); - } else if (base == 10) { - if (n < 0) { + } + else if (base == 10) + { + if (n < 0) + { int t = print('-'); n = -n; return printNumber(n, 10) + t; } return printNumber(n, 10); - } else { + } + else + { return printNumber(n, base); } } size_t Print::print(unsigned long n, int base) { - if (base == 0) return write(n); - else return printNumber(n, base); + if (base == 0) + return write(n); + else + return printNumber(n, base); } size_t Print::print(double n, int digits) @@ -117,7 +131,7 @@ size_t Print::println(const __FlashStringHelper *ifsh) return n; } -size_t Print::print(const Printable& x) +size_t Print::print(const Printable &x) { return x.printTo(*this); } @@ -190,7 +204,7 @@ size_t Print::println(double num, int digits) return n; } -size_t Print::println(const Printable& x) +size_t Print::println(const Printable &x) { size_t n = print(x); n += println(); @@ -238,12 +252,13 @@ size_t Print::printNumber(unsigned long n, uint8_t base) // prevent crash if called with base == 1 if (base < 2) base = 10; - do { + do + { char c = n % base; n /= base; *--str = c < 10 ? c + '0' : c + 'A' - 10; - } while(n); + } while (n); return write(str); } @@ -254,19 +269,19 @@ size_t Print::printFloat(double number, uint8_t digits) if (isnan(number)) return print("nan"); if (isinf(number)) return print("inf"); - if (number > 4294967040.0) return print ("ovf"); // constant determined empirically - if (number <-4294967040.0) return print ("ovf"); // constant determined empirically + if (number > 4294967040.0) return print("ovf"); // constant determined empirically + if (number < -4294967040.0) return print("ovf"); // constant determined empirically // Handle negative numbers if (number < 0.0) { - n += print('-'); - number = -number; + n += print('-'); + number = -number; } // Round correctly so that print(1.999, 2) prints as "2.00" double rounding = 0.5; - for (uint8_t i=0; i 0) { + if (digits > 0) + { n += print("."); } diff --git a/megaavr/cores/coreX-corefiles/api/Print.h b/megaavr/cores/coreX-corefiles/api/Print.h index 72b1467..b771739 100644 --- a/megaavr/cores/coreX-corefiles/api/Print.h +++ b/megaavr/cores/coreX-corefiles/api/Print.h @@ -87,4 +87,3 @@ class Print virtual void flush() { /* Empty implementation for backward compatibility */ } }; - diff --git a/megaavr/cores/coreX-corefiles/api/Printable.h b/megaavr/cores/coreX-corefiles/api/Printable.h index de45907..63f93d4 100644 --- a/megaavr/cores/coreX-corefiles/api/Printable.h +++ b/megaavr/cores/coreX-corefiles/api/Printable.h @@ -33,4 +33,3 @@ class Printable public: virtual size_t printTo(Print& p) const = 0; }; - diff --git a/megaavr/cores/coreX-corefiles/api/RingBuffer.cpp b/megaavr/cores/coreX-corefiles/api/RingBuffer.cpp index 90cfcbd..ed16b2c 100644 --- a/megaavr/cores/coreX-corefiles/api/RingBuffer.cpp +++ b/megaavr/cores/coreX-corefiles/api/RingBuffer.cpp @@ -17,66 +17,73 @@ */ #include "RingBuffer.h" -#include + #include #include +#include RingBuffer::RingBuffer(rb_index_type size) : size(size) { - _aucBuffer = (uint8_t*)malloc(size); - memset( _aucBuffer, 0, size ) ; - clear(); + _aucBuffer = (uint8_t*)malloc(size); + memset(_aucBuffer, 0, size); + clear(); } -void RingBuffer::store_char( uint8_t c ) +void RingBuffer::store_char(uint8_t c) { - rb_index_type i = nextIndex(_iHead); - - // if we should be storing the received character into the location - // just before the tail (meaning that the head would advance to the - // current location of the tail), we're about to overflow the buffer - // and so we don't write the character or advance the head. - if ( i != _iTail ) + rb_index_type i = nextIndex(_iHead); + + // if we should be storing the received character into the location + // just before the tail (meaning that the head would advance to the + // current location of the tail), we're about to overflow the buffer + // and so we don't write the character or advance the head. + if (i != _iTail) + { + if (_iHead < size) { - if (_iHead < size) { - _aucBuffer[_iHead] = c ; - } else { - additionalBuffer[_iHead - size] = c; - } - _iHead = i ; + _aucBuffer[_iHead] = c; } + else + { + additionalBuffer[_iHead - size] = c; + } + _iHead = i; + } } void RingBuffer::clear() { - _iHead = 0; - _iTail = 0; + _iHead = 0; + _iTail = 0; } int RingBuffer::read_char() { - if(_iTail == _iHead) - return -1; - - uint8_t value; - if (_iTail < size) { - value = _aucBuffer[_iTail]; - } else { - value = additionalBuffer[_iTail - size]; - } - _iTail = nextIndex(_iTail); + if (_iTail == _iHead) + return -1; + + uint8_t value; + if (_iTail < size) + { + value = _aucBuffer[_iTail]; + } + else + { + value = additionalBuffer[_iTail - size]; + } + _iTail = nextIndex(_iTail); - return value; + return value; } int RingBuffer::available() { - int delta = _iHead - _iTail; + int delta = _iHead - _iTail; - if(delta < 0) - return size + additionalSize + delta; - else - return delta; + if (delta < 0) + return size + additionalSize + delta; + else + return delta; } int RingBuffer::availableForStore() @@ -88,25 +95,27 @@ int RingBuffer::availableForStore() return -delta - 1; } - int RingBuffer::peek() { - if(_iTail == _iHead) - return -1; + if (_iTail == _iHead) + return -1; - if (_iTail < size) { - return _aucBuffer[_iTail]; - } else { - return additionalBuffer[_iTail - size]; - } + if (_iTail < size) + { + return _aucBuffer[_iTail]; + } + else + { + return additionalBuffer[_iTail - size]; + } } rb_index_type RingBuffer::nextIndex(rb_index_type index) { - return (rb_index_type)(index + 1) % (size + additionalSize); + return (rb_index_type)(index + 1) % (size + additionalSize); } bool RingBuffer::isFull() { - return (nextIndex(_iHead) == _iTail); + return (nextIndex(_iHead) == _iTail); } diff --git a/megaavr/cores/coreX-corefiles/api/RingBuffer.h b/megaavr/cores/coreX-corefiles/api/RingBuffer.h index f7fc4a0..95c1baf 100644 --- a/megaavr/cores/coreX-corefiles/api/RingBuffer.h +++ b/megaavr/cores/coreX-corefiles/api/RingBuffer.h @@ -36,28 +36,29 @@ typedef unsigned int rb_index_type; class RingBuffer { - public: - RingBuffer( rb_index_type size = 64 ) ; - void store_char( uint8_t c ) ; - void clear(); - int read_char(); - int available(); - int availableForStore(); - int peek(); - bool isFull(); - void addStorage(uint8_t* _buffer, rb_index_type _size) { - additionalSize = _size; - additionalBuffer = _buffer; - }; - - private: - rb_index_type nextIndex(rb_index_type index); - uint8_t* additionalBuffer; - int additionalSize = 0; - rb_index_type size; - uint8_t* _aucBuffer; - volatile rb_index_type _iHead ; - volatile rb_index_type _iTail ; + public: + RingBuffer(rb_index_type size = 64); + void store_char(uint8_t c); + void clear(); + int read_char(); + int available(); + int availableForStore(); + int peek(); + bool isFull(); + void addStorage(uint8_t* _buffer, rb_index_type _size) + { + additionalSize = _size; + additionalBuffer = _buffer; + }; + + private: + rb_index_type nextIndex(rb_index_type index); + uint8_t* additionalBuffer; + int additionalSize = 0; + rb_index_type size; + uint8_t* _aucBuffer; + volatile rb_index_type _iHead; + volatile rb_index_type _iTail; }; #endif /* _RING_BUFFER_ */ diff --git a/megaavr/cores/coreX-corefiles/api/Server.h b/megaavr/cores/coreX-corefiles/api/Server.h index 8675682..fa4593c 100644 --- a/megaavr/cores/coreX-corefiles/api/Server.h +++ b/megaavr/cores/coreX-corefiles/api/Server.h @@ -21,8 +21,8 @@ #include "Print.h" -class Server : public Print { - public: - virtual void begin() = 0; +class Server : public Print +{ + public: + virtual void begin() = 0; }; - diff --git a/megaavr/cores/coreX-corefiles/api/Stream.cpp b/megaavr/cores/coreX-corefiles/api/Stream.cpp index c16d60f..287165e 100644 --- a/megaavr/cores/coreX-corefiles/api/Stream.cpp +++ b/megaavr/cores/coreX-corefiles/api/Stream.cpp @@ -25,18 +25,19 @@ #include "Common.h" #include "Stream.h" -#define PARSE_TIMEOUT 1000 // default number of milli-seconds to wait +#define PARSE_TIMEOUT 1000 // default number of milli-seconds to wait // private method to read stream with timeout int Stream::timedRead() { int c; _startMillis = millis(); - do { + do + { c = read(); if (c >= 0) return c; - } while(millis() - _startMillis < _timeout); - return -1; // -1 indicates timeout + } while (millis() - _startMillis < _timeout); + return -1; // -1 indicates timeout } // private method to peek stream with timeout @@ -44,11 +45,12 @@ int Stream::timedPeek() { int c; _startMillis = millis(); - do { + do + { c = peek(); if (c >= 0) return c; - } while(millis() - _startMillis < _timeout); - return -1; // -1 indicates timeout + } while (millis() - _startMillis < _timeout); + return -1; // -1 indicates timeout } // returns peek of the next digit in the stream or -1 if timeout @@ -56,41 +58,47 @@ int Stream::timedPeek() int Stream::peekNextDigit(LookaheadMode lookahead, bool detectDecimal) { int c; - while (1) { + while (1) + { c = timedPeek(); - if( c < 0 || + if (c < 0 || c == '-' || (c >= '0' && c <= '9') || (detectDecimal && c == '.')) return c; - switch( lookahead ){ - case SKIP_NONE: return -1; // Fail code. - case SKIP_WHITESPACE: - switch( c ){ - case ' ': - case '\t': - case '\r': - case '\n': break; - default: return -1; // Fail code. - } - case SKIP_ALL: + switch (lookahead) + { + case SKIP_NONE: + return -1; // Fail code. + case SKIP_WHITESPACE: + switch (c) + { + case ' ': + case '\t': + case '\r': + case '\n': break; + default: + return -1; // Fail code. + } + case SKIP_ALL: + break; } - read(); // discard non-numeric + read(); // discard non-numeric } } // Public Methods ////////////////////////////////////////////////////////////// -void Stream::setTimeout(unsigned long timeout) // sets the maximum number of milliseconds to wait +void Stream::setTimeout(unsigned long timeout) // sets the maximum number of milliseconds to wait { _timeout = timeout; } - // find returns true if the target string is found -bool Stream::find(char *target) +// find returns true if the target string is found +bool Stream::find(char *target) { return findUntil(target, strlen(target), NULL, 0); } @@ -103,7 +111,7 @@ bool Stream::find(char *target, size_t length) } // as find but search ends if the terminator string is found -bool Stream::findUntil(char *target, char *terminator) +bool Stream::findUntil(char *target, char *terminator) { return findUntil(target, strlen(target), terminator, strlen(terminator)); } @@ -113,10 +121,13 @@ bool Stream::findUntil(char *target, char *terminator) // returns true if target string is found, false if terminated or timed out bool Stream::findUntil(char *target, size_t targetLen, char *terminator, size_t termLen) { - if (terminator == NULL) { + if (terminator == NULL) + { MultiTarget t[1] = {{target, targetLen, 0}}; return findMulti(t, 1) == 0 ? true : false; - } else { + } + else + { MultiTarget t[2] = {{target, targetLen, 0}, {terminator, termLen, 0}}; return findMulti(t, 2) == 0 ? true : false; } @@ -135,22 +146,22 @@ long Stream::parseInt(LookaheadMode lookahead, char ignore) c = peekNextDigit(lookahead, false); // ignore non numeric leading characters - if(c < 0) + if (c < 0) return 0; // zero returned if timeout - do{ - if(c == ignore) + do + { + if (c == ignore) ; // ignore this character - else if(c == '-') + else if (c == '-') isNegative = true; - else if(c >= '0' && c <= '9') // is c a digit? + else if (c >= '0' && c <= '9') // is c a digit? value = value * 10 + c - '0'; - read(); // consume the character we got with peek + read(); // consume the character we got with peek c = timedPeek(); - } - while( (c >= '0' && c <= '9') || c == ignore ); + } while ((c >= '0' && c <= '9') || c == ignore); - if(isNegative) + if (isNegative) value = -value; return value; } @@ -165,30 +176,31 @@ float Stream::parseFloat(LookaheadMode lookahead, char ignore) float fraction = 1.0; c = peekNextDigit(lookahead, true); - // ignore non numeric leading characters - if(c < 0) + // ignore non numeric leading characters + if (c < 0) return 0; // zero returned if timeout - do{ - if(c == ignore) + do + { + if (c == ignore) ; // ignore - else if(c == '-') + else if (c == '-') isNegative = true; else if (c == '.') isFraction = true; - else if(c >= '0' && c <= '9') { // is c a digit? + else if (c >= '0' && c <= '9') + { // is c a digit? value = value * 10 + c - '0'; - if(isFraction) - fraction *= 0.1; + if (isFraction) + fraction *= 0.1; } - read(); // consume the character we got with peek + read(); // consume the character we got with peek c = timedPeek(); - } - while( (c >= '0' && c <= '9') || (c == '.' && !isFraction) || c == ignore ); + } while ((c >= '0' && c <= '9') || (c == '.' && !isFraction) || c == ignore); - if(isNegative) + if (isNegative) value = -value; - if(isFraction) + if (isFraction) return value * fraction; else return value; @@ -202,7 +214,8 @@ float Stream::parseFloat(LookaheadMode lookahead, char ignore) size_t Stream::readBytes(char *buffer, size_t length) { size_t count = 0; - while (count < length) { + while (count < length) + { int c = timedRead(); if (c < 0) break; *buffer++ = (char)c; @@ -211,7 +224,6 @@ size_t Stream::readBytes(char *buffer, size_t length) return count; } - // as readBytes with terminator character // terminates if length characters have been read, timeout, or if the terminator character detected // returns the number of characters placed in the buffer (0 means no valid data found) @@ -220,7 +232,8 @@ size_t Stream::readBytesUntil(char terminator, char *buffer, size_t length) { if (length < 1) return 0; size_t index = 0; - while (index < length) { + while (index < length) + { int c = timedRead(); if (c < 0 || c == terminator) break; *buffer++ = (char)c; @@ -253,22 +266,27 @@ String Stream::readStringUntil(char terminator) return ret; } -int Stream::findMulti( struct Stream::MultiTarget *targets, int tCount) { +int Stream::findMulti(struct Stream::MultiTarget *targets, int tCount) +{ // any zero length target string automatically matches and would make // a mess of the rest of the algorithm. - for (struct MultiTarget *t = targets; t < targets+tCount; ++t) { + for (struct MultiTarget *t = targets; t < targets + tCount; ++t) + { if (t->len <= 0) return t - targets; } - while (1) { + while (1) + { int c = timedRead(); if (c < 0) return -1; - for (struct MultiTarget *t = targets; t < targets+tCount; ++t) { + for (struct MultiTarget *t = targets; t < targets + tCount; ++t) + { // the simple case is if we match, deal with that first. - if (c == t->str[t->index]) { + if (c == t->str[t->index]) + { if (++t->index == t->len) return t - targets; else @@ -283,14 +301,16 @@ int Stream::findMulti( struct Stream::MultiTarget *targets, int tCount) { continue; int origIndex = t->index; - do { + do + { --t->index; // first check if current char works against the new current index if (c != t->str[t->index]) continue; // if it's the only char then we're good, nothing more to check - if (t->index == 0) { + if (t->index == 0) + { t->index++; break; } @@ -298,14 +318,16 @@ int Stream::findMulti( struct Stream::MultiTarget *targets, int tCount) { // otherwise we need to check the rest of the found string int diff = origIndex - t->index; size_t i; - for (i = 0; i < t->index; ++i) { + for (i = 0; i < t->index; ++i) + { if (t->str[i] != t->str[i + diff]) break; } // if we successfully got through the previous loop then our current // index is good. - if (i == t->index) { + if (i == t->index) + { t->index++; break; } diff --git a/megaavr/cores/coreX-corefiles/api/Stream.h b/megaavr/cores/coreX-corefiles/api/Stream.h index ef59370..dd0645e 100644 --- a/megaavr/cores/coreX-corefiles/api/Stream.h +++ b/megaavr/cores/coreX-corefiles/api/Stream.h @@ -22,6 +22,7 @@ #pragma once #include + #include "Print.h" // compatability macros for testing @@ -37,50 +38,51 @@ readBytesBetween( pre_string, terminator, buffer, length) // This enumeration provides the lookahead options for parseInt(), parseFloat() // The rules set out here are used until either the first valid character is found // or a time out occurs due to lack of input. -enum LookaheadMode{ - SKIP_ALL, // All invalid characters are ignored. - SKIP_NONE, // Nothing is skipped, and the stream is not touched unless the first waiting character is valid. - SKIP_WHITESPACE // Only tabs, spaces, line feeds & carriage returns are skipped. +enum LookaheadMode +{ + SKIP_ALL, // All invalid characters are ignored. + SKIP_NONE, // Nothing is skipped, and the stream is not touched unless the first waiting character is valid. + SKIP_WHITESPACE // Only tabs, spaces, line feeds & carriage returns are skipped. }; -#define NO_IGNORE_CHAR '\x01' // a char not found in a valid ASCII numeric field +#define NO_IGNORE_CHAR '\x01' // a char not found in a valid ASCII numeric field class Stream : public Print { - protected: - unsigned long _timeout; // number of milliseconds to wait for the next char before aborting timed read - unsigned long _startMillis; // used for timeout measurement - int timedRead(); // private method to read stream with timeout - int timedPeek(); // private method to peek stream with timeout - int peekNextDigit(LookaheadMode lookahead, bool detectDecimal); // returns the next numeric digit in the stream or -1 if timeout + protected: + unsigned long _timeout; // number of milliseconds to wait for the next char before aborting timed read + unsigned long _startMillis; // used for timeout measurement + int timedRead(); // private method to read stream with timeout + int timedPeek(); // private method to peek stream with timeout + int peekNextDigit(LookaheadMode lookahead, bool detectDecimal); // returns the next numeric digit in the stream or -1 if timeout - public: - virtual int available() = 0; - virtual int read() = 0; - virtual int peek() = 0; + public: + virtual int available() = 0; + virtual int read() = 0; + virtual int peek() = 0; - Stream() {_timeout=1000;} + Stream() { _timeout = 1000; } -// parsing methods + // parsing methods - void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second + void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second unsigned long getTimeout(void) { return _timeout; } - - bool find(char *target); // reads data from the stream until the target string is found - bool find(uint8_t *target) { return find ((char *)target); } + + bool find(char *target); // reads data from the stream until the target string is found + bool find(uint8_t *target) { return find((char *)target); } // returns true if target string is found, false if timed out (see setTimeout) - bool find(char *target, size_t length); // reads data from the stream until the target string of given length is found - bool find(uint8_t *target, size_t length) { return find ((char *)target, length); } + bool find(char *target, size_t length); // reads data from the stream until the target string of given length is found + bool find(uint8_t *target, size_t length) { return find((char *)target, length); } // returns true if target string is found, false if timed out - bool find(char target) { return find (&target, 1); } + bool find(char target) { return find(&target, 1); } - bool findUntil(char *target, char *terminator); // as find but search ends if the terminator string is found + bool findUntil(char *target, char *terminator); // as find but search ends if the terminator string is found bool findUntil(uint8_t *target, char *terminator) { return findUntil((char *)target, terminator); } - bool findUntil(char *target, size_t targetLen, char *terminate, size_t termLen); // as above but search ends if the terminate string is found - bool findUntil(uint8_t *target, size_t targetLen, char *terminate, size_t termLen) {return findUntil((char *)target, targetLen, terminate, termLen); } + bool findUntil(char *target, size_t targetLen, char *terminate, size_t termLen); // as above but search ends if the terminate string is found + bool findUntil(uint8_t *target, size_t targetLen, char *terminate, size_t termLen) { return findUntil((char *)target, targetLen, terminate, termLen); } long parseInt(LookaheadMode lookahead = SKIP_ALL, char ignore = NO_IGNORE_CHAR); // returns the first valid (long) integer value from the current position. @@ -92,13 +94,13 @@ class Stream : public Print float parseFloat(LookaheadMode lookahead = SKIP_ALL, char ignore = NO_IGNORE_CHAR); // float version of parseInt - size_t readBytes( char *buffer, size_t length); // read chars from stream into buffer - size_t readBytes( uint8_t *buffer, size_t length) { return readBytes((char *)buffer, length); } + size_t readBytes(char *buffer, size_t length); // read chars from stream into buffer + size_t readBytes(uint8_t *buffer, size_t length) { return readBytes((char *)buffer, length); } // terminates if length characters have been read or timeout (see setTimeout) // returns the number of characters placed in the buffer (0 means no valid data found) - size_t readBytesUntil( char terminator, char *buffer, size_t length); // as readBytes with terminator character - size_t readBytesUntil( char terminator, uint8_t *buffer, size_t length) { return readBytesUntil(terminator, (char *)buffer, length); } + size_t readBytesUntil(char terminator, char *buffer, size_t length); // as readBytes with terminator character + size_t readBytesUntil(char terminator, uint8_t *buffer, size_t length) { return readBytesUntil(terminator, (char *)buffer, length); } // terminates if length characters have been read, timeout, or if the terminator character detected // returns the number of characters placed in the buffer (0 means no valid data found) @@ -106,17 +108,18 @@ class Stream : public Print String readString(); String readStringUntil(char terminator); - protected: + protected: long parseInt(char ignore) { return parseInt(SKIP_ALL, ignore); } float parseFloat(char ignore) { return parseFloat(SKIP_ALL, ignore); } // These overload exists for compatibility with any class that has derived // Stream and used parseFloat/Int with a custom ignore character. To keep // the public API simple, these overload remains protected. - struct MultiTarget { - const char *str; // string you're searching for - size_t len; // length of string you're searching for - size_t index; // index used by the search routine. + struct MultiTarget + { + const char *str; // string you're searching for + size_t len; // length of string you're searching for + size_t index; // index used by the search routine. }; // This allows you to search for an arbitrary number of strings. diff --git a/megaavr/cores/coreX-corefiles/api/String.cpp b/megaavr/cores/coreX-corefiles/api/String.cpp index 5a5d710..6efc5f0 100644 --- a/megaavr/cores/coreX-corefiles/api/String.cpp +++ b/megaavr/cores/coreX-corefiles/api/String.cpp @@ -29,101 +29,101 @@ String::String(const char *cstr) { - init(); - if (cstr) copy(cstr, strlen(cstr)); + init(); + if (cstr) copy(cstr, strlen(cstr)); } String::String(const String &value) { - init(); - *this = value; + init(); + *this = value; } String::String(const __FlashStringHelper *pstr) { - init(); - *this = pstr; + init(); + *this = pstr; } #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) String::String(String &&rval) { - init(); - move(rval); + init(); + move(rval); } String::String(StringSumHelper &&rval) { - init(); - move(rval); + init(); + move(rval); } #endif String::String(char c) { - init(); - char buf[2]; - buf[0] = c; - buf[1] = 0; - *this = buf; + init(); + char buf[2]; + buf[0] = c; + buf[1] = 0; + *this = buf; } String::String(unsigned char value, unsigned char base) { - init(); - char buf[1 + 8 * sizeof(unsigned char)]; - utoa(value, buf, base); - *this = buf; + init(); + char buf[1 + 8 * sizeof(unsigned char)]; + utoa(value, buf, base); + *this = buf; } String::String(int value, unsigned char base) { - init(); - char buf[2 + 8 * sizeof(int)]; - itoa(value, buf, base); - *this = buf; + init(); + char buf[2 + 8 * sizeof(int)]; + itoa(value, buf, base); + *this = buf; } String::String(unsigned int value, unsigned char base) { - init(); - char buf[1 + 8 * sizeof(unsigned int)]; - utoa(value, buf, base); - *this = buf; + init(); + char buf[1 + 8 * sizeof(unsigned int)]; + utoa(value, buf, base); + *this = buf; } String::String(long value, unsigned char base) { - init(); - char buf[2 + 8 * sizeof(long)]; - ltoa(value, buf, base); - *this = buf; + init(); + char buf[2 + 8 * sizeof(long)]; + ltoa(value, buf, base); + *this = buf; } String::String(unsigned long value, unsigned char base) { - init(); - char buf[1 + 8 * sizeof(unsigned long)]; - ultoa(value, buf, base); - *this = buf; + init(); + char buf[1 + 8 * sizeof(unsigned long)]; + ultoa(value, buf, base); + *this = buf; } String::String(float value, unsigned char decimalPlaces) { - init(); - char buf[33]; - *this = dtostrf(value, (decimalPlaces + 2), decimalPlaces, buf); + init(); + char buf[33]; + *this = dtostrf(value, (decimalPlaces + 2), decimalPlaces, buf); } String::String(double value, unsigned char decimalPlaces) { - init(); - char buf[33]; - *this = dtostrf(value, (decimalPlaces + 2), decimalPlaces, buf); + init(); + char buf[33]; + *this = dtostrf(value, (decimalPlaces + 2), decimalPlaces, buf); } String::~String() { - free(buffer); + free(buffer); } /*********************************************/ @@ -132,125 +132,139 @@ String::~String() inline void String::init(void) { - buffer = NULL; - capacity = 0; - len = 0; + buffer = NULL; + capacity = 0; + len = 0; } void String::invalidate(void) { - if (buffer) free(buffer); - buffer = NULL; - capacity = len = 0; + if (buffer) free(buffer); + buffer = NULL; + capacity = len = 0; } unsigned char String::reserve(unsigned int size) { - if (buffer && capacity >= size) return 1; - if (changeBuffer(size)) { - if (len == 0) buffer[0] = 0; - return 1; - } - return 0; + if (buffer && capacity >= size) return 1; + if (changeBuffer(size)) + { + if (len == 0) buffer[0] = 0; + return 1; + } + return 0; } unsigned char String::changeBuffer(unsigned int maxStrLen) { - char *newbuffer = (char *)realloc(buffer, maxStrLen + 1); - if (newbuffer) { - buffer = newbuffer; - capacity = maxStrLen; - return 1; - } - return 0; + char *newbuffer = (char *)realloc(buffer, maxStrLen + 1); + if (newbuffer) + { + buffer = newbuffer; + capacity = maxStrLen; + return 1; + } + return 0; } /*********************************************/ /* Copy and Move */ /*********************************************/ -String & String::copy(const char *cstr, unsigned int length) +String &String::copy(const char *cstr, unsigned int length) { - if (!reserve(length)) { - invalidate(); - return *this; - } - len = length; - strcpy(buffer, cstr); - return *this; + if (!reserve(length)) + { + invalidate(); + return *this; + } + len = length; + strcpy(buffer, cstr); + return *this; } -String & String::copy(const __FlashStringHelper *pstr, unsigned int length) +String &String::copy(const __FlashStringHelper *pstr, unsigned int length) { - if (!reserve(length)) { - invalidate(); - return *this; - } - len = length; - strcpy_P(buffer, (PGM_P)pstr); - return *this; + if (!reserve(length)) + { + invalidate(); + return *this; + } + len = length; + strcpy_P(buffer, (PGM_P)pstr); + return *this; } #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) void String::move(String &rhs) { - if (buffer) { - if (rhs && capacity >= rhs.len) { - strcpy(buffer, rhs.buffer); - len = rhs.len; - rhs.len = 0; - return; - } else { - free(buffer); - } - } - buffer = rhs.buffer; - capacity = rhs.capacity; - len = rhs.len; - rhs.buffer = NULL; - rhs.capacity = 0; - rhs.len = 0; + if (buffer) + { + if (rhs && capacity >= rhs.len) + { + strcpy(buffer, rhs.buffer); + len = rhs.len; + rhs.len = 0; + return; + } + else + { + free(buffer); + } + } + buffer = rhs.buffer; + capacity = rhs.capacity; + len = rhs.len; + rhs.buffer = NULL; + rhs.capacity = 0; + rhs.len = 0; } #endif -String & String::operator = (const String &rhs) +String &String::operator=(const String &rhs) { - if (this == &rhs) return *this; - - if (rhs.buffer) copy(rhs.buffer, rhs.len); - else invalidate(); - - return *this; + if (this == &rhs) return *this; + + if (rhs.buffer) + copy(rhs.buffer, rhs.len); + else + invalidate(); + + return *this; } #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) -String & String::operator = (String &&rval) +String &String::operator=(String &&rval) { - if (this != &rval) move(rval); - return *this; + if (this != &rval) move(rval); + return *this; } -String & String::operator = (StringSumHelper &&rval) +String &String::operator=(StringSumHelper &&rval) { - if (this != &rval) move(rval); - return *this; + if (this != &rval) move(rval); + return *this; } #endif -String & String::operator = (const char *cstr) +String &String::operator=(const char *cstr) { - if (cstr) copy(cstr, strlen(cstr)); - else invalidate(); - - return *this; + if (cstr) + copy(cstr, strlen(cstr)); + else + invalidate(); + + return *this; } -String & String::operator = (const __FlashStringHelper *pstr) +String &String::operator=(const __FlashStringHelper *pstr) { - if (pstr) copy(pstr, strlen_P((PGM_P)pstr)); - else invalidate(); + if (pstr) + copy(pstr, strlen_P((PGM_P)pstr)); + else + invalidate(); - return *this; + return *this; } /*********************************************/ @@ -259,174 +273,174 @@ String & String::operator = (const __FlashStringHelper *pstr) unsigned char String::concat(const String &s) { - return concat(s.buffer, s.len); + return concat(s.buffer, s.len); } unsigned char String::concat(const char *cstr, unsigned int length) { - unsigned int newlen = len + length; - if (!cstr) return 0; - if (length == 0) return 1; - if (!reserve(newlen)) return 0; - strcpy(buffer + len, cstr); - len = newlen; - return 1; + unsigned int newlen = len + length; + if (!cstr) return 0; + if (length == 0) return 1; + if (!reserve(newlen)) return 0; + strcpy(buffer + len, cstr); + len = newlen; + return 1; } unsigned char String::concat(const char *cstr) { - if (!cstr) return 0; - return concat(cstr, strlen(cstr)); + if (!cstr) return 0; + return concat(cstr, strlen(cstr)); } unsigned char String::concat(char c) { - char buf[2]; - buf[0] = c; - buf[1] = 0; - return concat(buf, 1); + char buf[2]; + buf[0] = c; + buf[1] = 0; + return concat(buf, 1); } unsigned char String::concat(unsigned char num) { - char buf[1 + 3 * sizeof(unsigned char)]; - itoa(num, buf, 10); - return concat(buf, strlen(buf)); + char buf[1 + 3 * sizeof(unsigned char)]; + itoa(num, buf, 10); + return concat(buf, strlen(buf)); } unsigned char String::concat(int num) { - char buf[2 + 3 * sizeof(int)]; - itoa(num, buf, 10); - return concat(buf, strlen(buf)); + char buf[2 + 3 * sizeof(int)]; + itoa(num, buf, 10); + return concat(buf, strlen(buf)); } unsigned char String::concat(unsigned int num) { - char buf[1 + 3 * sizeof(unsigned int)]; - utoa(num, buf, 10); - return concat(buf, strlen(buf)); + char buf[1 + 3 * sizeof(unsigned int)]; + utoa(num, buf, 10); + return concat(buf, strlen(buf)); } unsigned char String::concat(long num) { - char buf[2 + 3 * sizeof(long)]; - ltoa(num, buf, 10); - return concat(buf, strlen(buf)); + char buf[2 + 3 * sizeof(long)]; + ltoa(num, buf, 10); + return concat(buf, strlen(buf)); } unsigned char String::concat(unsigned long num) { - char buf[1 + 3 * sizeof(unsigned long)]; - ultoa(num, buf, 10); - return concat(buf, strlen(buf)); + char buf[1 + 3 * sizeof(unsigned long)]; + ultoa(num, buf, 10); + return concat(buf, strlen(buf)); } unsigned char String::concat(float num) { - char buf[20]; - char* string = dtostrf(num, 4, 2, buf); - return concat(string, strlen(string)); + char buf[20]; + char *string = dtostrf(num, 4, 2, buf); + return concat(string, strlen(string)); } unsigned char String::concat(double num) { - char buf[20]; - char* string = dtostrf(num, 4, 2, buf); - return concat(string, strlen(string)); + char buf[20]; + char *string = dtostrf(num, 4, 2, buf); + return concat(string, strlen(string)); } -unsigned char String::concat(const __FlashStringHelper * str) +unsigned char String::concat(const __FlashStringHelper *str) { - if (!str) return 0; - int length = strlen_P((const char *) str); - if (length == 0) return 1; - unsigned int newlen = len + length; - if (!reserve(newlen)) return 0; - strcpy_P(buffer + len, (const char *) str); - len = newlen; - return 1; + if (!str) return 0; + int length = strlen_P((const char *)str); + if (length == 0) return 1; + unsigned int newlen = len + length; + if (!reserve(newlen)) return 0; + strcpy_P(buffer + len, (const char *)str); + len = newlen; + return 1; } /*********************************************/ /* Concatenate */ /*********************************************/ -StringSumHelper & operator + (const StringSumHelper &lhs, const String &rhs) +StringSumHelper &operator+(const StringSumHelper &lhs, const String &rhs) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(rhs.buffer, rhs.len)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(rhs.buffer, rhs.len)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, const char *cstr) +StringSumHelper &operator+(const StringSumHelper &lhs, const char *cstr) { - StringSumHelper &a = const_cast(lhs); - if (!cstr || !a.concat(cstr, strlen(cstr))) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!cstr || !a.concat(cstr, strlen(cstr))) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, char c) +StringSumHelper &operator+(const StringSumHelper &lhs, char c) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(c)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(c)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, unsigned char num) +StringSumHelper &operator+(const StringSumHelper &lhs, unsigned char num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, int num) +StringSumHelper &operator+(const StringSumHelper &lhs, int num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, unsigned int num) +StringSumHelper &operator+(const StringSumHelper &lhs, unsigned int num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, long num) +StringSumHelper &operator+(const StringSumHelper &lhs, long num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, unsigned long num) +StringSumHelper &operator+(const StringSumHelper &lhs, unsigned long num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, float num) +StringSumHelper &operator+(const StringSumHelper &lhs, float num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, double num) +StringSumHelper &operator+(const StringSumHelper &lhs, double num) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(num)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(num)) a.invalidate(); + return a; } -StringSumHelper & operator + (const StringSumHelper &lhs, const __FlashStringHelper *rhs) +StringSumHelper &operator+(const StringSumHelper &lhs, const __FlashStringHelper *rhs) { - StringSumHelper &a = const_cast(lhs); - if (!a.concat(rhs)) a.invalidate(); - return a; + StringSumHelper &a = const_cast(lhs); + if (!a.concat(rhs)) a.invalidate(); + return a; } /*********************************************/ @@ -435,75 +449,77 @@ StringSumHelper & operator + (const StringSumHelper &lhs, const __FlashStringHel int String::compareTo(const String &s) const { - if (!buffer || !s.buffer) { - if (s.buffer && s.len > 0) return 0 - *(unsigned char *)s.buffer; - if (buffer && len > 0) return *(unsigned char *)buffer; - return 0; - } - return strcmp(buffer, s.buffer); + if (!buffer || !s.buffer) + { + if (s.buffer && s.len > 0) return 0 - *(unsigned char *)s.buffer; + if (buffer && len > 0) return *(unsigned char *)buffer; + return 0; + } + return strcmp(buffer, s.buffer); } unsigned char String::equals(const String &s2) const { - return (len == s2.len && compareTo(s2) == 0); + return (len == s2.len && compareTo(s2) == 0); } unsigned char String::equals(const char *cstr) const { - if (len == 0) return (cstr == NULL || *cstr == 0); - if (cstr == NULL) return buffer[0] == 0; - return strcmp(buffer, cstr) == 0; + if (len == 0) return (cstr == NULL || *cstr == 0); + if (cstr == NULL) return buffer[0] == 0; + return strcmp(buffer, cstr) == 0; } unsigned char String::operator<(const String &rhs) const { - return compareTo(rhs) < 0; + return compareTo(rhs) < 0; } unsigned char String::operator>(const String &rhs) const { - return compareTo(rhs) > 0; + return compareTo(rhs) > 0; } unsigned char String::operator<=(const String &rhs) const { - return compareTo(rhs) <= 0; + return compareTo(rhs) <= 0; } unsigned char String::operator>=(const String &rhs) const { - return compareTo(rhs) >= 0; + return compareTo(rhs) >= 0; } -unsigned char String::equalsIgnoreCase( const String &s2 ) const +unsigned char String::equalsIgnoreCase(const String &s2) const { - if (this == &s2) return 1; - if (len != s2.len) return 0; - if (len == 0) return 1; - const char *p1 = buffer; - const char *p2 = s2.buffer; - while (*p1) { - if (tolower(*p1++) != tolower(*p2++)) return 0; - } - return 1; + if (this == &s2) return 1; + if (len != s2.len) return 0; + if (len == 0) return 1; + const char *p1 = buffer; + const char *p2 = s2.buffer; + while (*p1) + { + if (tolower(*p1++) != tolower(*p2++)) return 0; + } + return 1; } -unsigned char String::startsWith( const String &s2 ) const +unsigned char String::startsWith(const String &s2) const { - if (len < s2.len) return 0; - return startsWith(s2, 0); + if (len < s2.len) return 0; + return startsWith(s2, 0); } -unsigned char String::startsWith( const String &s2, unsigned int offset ) const +unsigned char String::startsWith(const String &s2, unsigned int offset) const { - if (offset > len - s2.len || !buffer || !s2.buffer) return 0; - return strncmp( &buffer[offset], s2.buffer, s2.len ) == 0; + if (offset > len - s2.len || !buffer || !s2.buffer) return 0; + return strncmp(&buffer[offset], s2.buffer, s2.len) == 0; } -unsigned char String::endsWith( const String &s2 ) const +unsigned char String::endsWith(const String &s2) const { - if ( len < s2.len || !buffer || !s2.buffer) return 0; - return strcmp(&buffer[len - s2.len], s2.buffer) == 0; + if (len < s2.len || !buffer || !s2.buffer) return 0; + return strcmp(&buffer[len - s2.len], s2.buffer) == 0; } /*********************************************/ @@ -512,41 +528,43 @@ unsigned char String::endsWith( const String &s2 ) const char String::charAt(unsigned int loc) const { - return operator[](loc); + return operator[](loc); } -void String::setCharAt(unsigned int loc, char c) +void String::setCharAt(unsigned int loc, char c) { - if (loc < len) buffer[loc] = c; + if (loc < len) buffer[loc] = c; } -char & String::operator[](unsigned int index) +char &String::operator[](unsigned int index) { - static char dummy_writable_char; - if (index >= len || !buffer) { - dummy_writable_char = 0; - return dummy_writable_char; - } - return buffer[index]; + static char dummy_writable_char; + if (index >= len || !buffer) + { + dummy_writable_char = 0; + return dummy_writable_char; + } + return buffer[index]; } -char String::operator[]( unsigned int index ) const +char String::operator[](unsigned int index) const { - if (index >= len || !buffer) return 0; - return buffer[index]; + if (index >= len || !buffer) return 0; + return buffer[index]; } void String::getBytes(unsigned char *buf, unsigned int bufsize, unsigned int index) const { - if (!bufsize || !buf) return; - if (index >= len) { - buf[0] = 0; - return; - } - unsigned int n = bufsize - 1; - if (n > len - index) n = len - index; - strncpy((char *)buf, buffer + index, n); - buf[n] = 0; + if (!bufsize || !buf) return; + if (index >= len) + { + buf[0] = 0; + return; + } + unsigned int n = bufsize - 1; + if (n > len - index) n = len - index; + strncpy((char *)buf, buffer + index, n); + buf[n] = 0; } /*********************************************/ @@ -555,79 +573,81 @@ void String::getBytes(unsigned char *buf, unsigned int bufsize, unsigned int ind int String::indexOf(char c) const { - return indexOf(c, 0); + return indexOf(c, 0); } -int String::indexOf( char ch, unsigned int fromIndex ) const +int String::indexOf(char ch, unsigned int fromIndex) const { - if (fromIndex >= len) return -1; - const char* temp = strchr(buffer + fromIndex, ch); - if (temp == NULL) return -1; - return temp - buffer; + if (fromIndex >= len) return -1; + const char *temp = strchr(buffer + fromIndex, ch); + if (temp == NULL) return -1; + return temp - buffer; } int String::indexOf(const String &s2) const { - return indexOf(s2, 0); + return indexOf(s2, 0); } int String::indexOf(const String &s2, unsigned int fromIndex) const { - if (fromIndex >= len) return -1; - const char *found = strstr(buffer + fromIndex, s2.buffer); - if (found == NULL) return -1; - return found - buffer; + if (fromIndex >= len) return -1; + const char *found = strstr(buffer + fromIndex, s2.buffer); + if (found == NULL) return -1; + return found - buffer; } -int String::lastIndexOf( char theChar ) const +int String::lastIndexOf(char theChar) const { - return lastIndexOf(theChar, len - 1); + return lastIndexOf(theChar, len - 1); } int String::lastIndexOf(char ch, unsigned int fromIndex) const { - if (fromIndex >= len) return -1; - char tempchar = buffer[fromIndex + 1]; - buffer[fromIndex + 1] = '\0'; - char* temp = strrchr( buffer, ch ); - buffer[fromIndex + 1] = tempchar; - if (temp == NULL) return -1; - return temp - buffer; + if (fromIndex >= len) return -1; + char tempchar = buffer[fromIndex + 1]; + buffer[fromIndex + 1] = '\0'; + char *temp = strrchr(buffer, ch); + buffer[fromIndex + 1] = tempchar; + if (temp == NULL) return -1; + return temp - buffer; } int String::lastIndexOf(const String &s2) const { - return lastIndexOf(s2, len - s2.len); + return lastIndexOf(s2, len - s2.len); } int String::lastIndexOf(const String &s2, unsigned int fromIndex) const { - if (s2.len == 0 || len == 0 || s2.len > len) return -1; - if (fromIndex >= len) fromIndex = len - 1; - int found = -1; - for (char *p = buffer; p <= buffer + fromIndex; p++) { - p = strstr(p, s2.buffer); - if (!p) break; - if ((unsigned int)(p - buffer) <= fromIndex) found = p - buffer; - } - return found; + if (s2.len == 0 || len == 0 || s2.len > len) return -1; + if (fromIndex >= len) fromIndex = len - 1; + int found = -1; + for (char *p = buffer; p <= buffer + fromIndex; p++) + { + p = strstr(p, s2.buffer); + if (!p) break; + if ((unsigned int)(p - buffer) <= fromIndex) found = p - buffer; + } + return found; } String String::substring(unsigned int left, unsigned int right) const { - if (left > right) { - unsigned int temp = right; - right = left; - left = temp; - } - String out; - if (left >= len) return out; - if (right > len) right = len; - char temp = buffer[right]; // save the replaced character - buffer[right] = '\0'; - out = buffer + left; // pointer arithmetic - buffer[right] = temp; //restore character - return out; + if (left > right) + { + unsigned int temp = right; + right = left; + left = temp; + } + String out; + if (left >= len) return out; + if (right > len) right = len; + char temp = buffer[right]; // save the replaced character + buffer[right] = '\0'; + out = buffer + left; // pointer arithmetic + buffer[right] = temp; //restore character + return out; } /*********************************************/ @@ -636,98 +656,121 @@ String String::substring(unsigned int left, unsigned int right) const void String::replace(char find, char replace) { - if (!buffer) return; - for (char *p = buffer; *p; p++) { - if (*p == find) *p = replace; - } -} - -void String::replace(const String& find, const String& replace) -{ - if (len == 0 || find.len == 0) return; - int diff = replace.len - find.len; - char *readFrom = buffer; - char *foundAt; - if (diff == 0) { - while ((foundAt = strstr(readFrom, find.buffer)) != NULL) { - memcpy(foundAt, replace.buffer, replace.len); - readFrom = foundAt + replace.len; - } - } else if (diff < 0) { - char *writeTo = buffer; - while ((foundAt = strstr(readFrom, find.buffer)) != NULL) { - unsigned int n = foundAt - readFrom; - memcpy(writeTo, readFrom, n); - writeTo += n; - memcpy(writeTo, replace.buffer, replace.len); - writeTo += replace.len; - readFrom = foundAt + find.len; - len += diff; - } - strcpy(writeTo, readFrom); - } else { - unsigned int size = len; // compute size needed for result - while ((foundAt = strstr(readFrom, find.buffer)) != NULL) { - readFrom = foundAt + find.len; - size += diff; - } - if (size == len) return; - if (size > capacity && !changeBuffer(size)) return; // XXX: tell user! - int index = len - 1; - while (index >= 0 && (index = lastIndexOf(find, index)) >= 0) { - readFrom = buffer + index + find.len; - memmove(readFrom + diff, readFrom, len - (readFrom - buffer)); - len += diff; - buffer[len] = 0; - memcpy(buffer + index, replace.buffer, replace.len); - index--; - } - } -} - -void String::remove(unsigned int index){ - // Pass the biggest integer as the count. The remove method - // below will take care of truncating it at the end of the - // string. - remove(index, (unsigned int)-1); -} - -void String::remove(unsigned int index, unsigned int count){ - if (index >= len) { return; } - if (count <= 0) { return; } - if (count > len - index) { count = len - index; } - char *writeTo = buffer + index; - len = len - count; - strncpy(writeTo, buffer + index + count,len - index); - buffer[len] = 0; + if (!buffer) return; + for (char *p = buffer; *p; p++) + { + if (*p == find) *p = replace; + } +} + +void String::replace(const String &find, const String &replace) +{ + if (len == 0 || find.len == 0) return; + int diff = replace.len - find.len; + char *readFrom = buffer; + char *foundAt; + if (diff == 0) + { + while ((foundAt = strstr(readFrom, find.buffer)) != NULL) + { + memcpy(foundAt, replace.buffer, replace.len); + readFrom = foundAt + replace.len; + } + } + else if (diff < 0) + { + char *writeTo = buffer; + while ((foundAt = strstr(readFrom, find.buffer)) != NULL) + { + unsigned int n = foundAt - readFrom; + memcpy(writeTo, readFrom, n); + writeTo += n; + memcpy(writeTo, replace.buffer, replace.len); + writeTo += replace.len; + readFrom = foundAt + find.len; + len += diff; + } + strcpy(writeTo, readFrom); + } + else + { + unsigned int size = len; // compute size needed for result + while ((foundAt = strstr(readFrom, find.buffer)) != NULL) + { + readFrom = foundAt + find.len; + size += diff; + } + if (size == len) return; + if (size > capacity && !changeBuffer(size)) return; // XXX: tell user! + int index = len - 1; + while (index >= 0 && (index = lastIndexOf(find, index)) >= 0) + { + readFrom = buffer + index + find.len; + memmove(readFrom + diff, readFrom, len - (readFrom - buffer)); + len += diff; + buffer[len] = 0; + memcpy(buffer + index, replace.buffer, replace.len); + index--; + } + } +} + +void String::remove(unsigned int index) +{ + // Pass the biggest integer as the count. The remove method + // below will take care of truncating it at the end of the + // string. + remove(index, (unsigned int)-1); +} + +void String::remove(unsigned int index, unsigned int count) +{ + if (index >= len) + { + return; + } + if (count <= 0) + { + return; + } + if (count > len - index) + { + count = len - index; + } + char *writeTo = buffer + index; + len = len - count; + strncpy(writeTo, buffer + index + count, len - index); + buffer[len] = 0; } void String::toLowerCase(void) { - if (!buffer) return; - for (char *p = buffer; *p; p++) { - *p = tolower(*p); - } + if (!buffer) return; + for (char *p = buffer; *p; p++) + { + *p = tolower(*p); + } } void String::toUpperCase(void) { - if (!buffer) return; - for (char *p = buffer; *p; p++) { - *p = toupper(*p); - } + if (!buffer) return; + for (char *p = buffer; *p; p++) + { + *p = toupper(*p); + } } void String::trim(void) { - if (!buffer || len == 0) return; - char *begin = buffer; - while (isspace(*begin)) begin++; - char *end = buffer + len - 1; - while (isspace(*end) && end >= begin) end--; - len = end + 1 - begin; - if (begin > buffer) memcpy(buffer, begin, len); - buffer[len] = 0; + if (!buffer || len == 0) return; + char *begin = buffer; + while (isspace(*begin)) begin++; + char *end = buffer + len - 1; + while (isspace(*end) && end >= begin) end--; + len = end + 1 - begin; + if (begin > buffer) memcpy(buffer, begin, len); + buffer[len] = 0; } /*********************************************/ @@ -736,17 +779,17 @@ void String::trim(void) long String::toInt(void) const { - if (buffer) return atol(buffer); - return 0; + if (buffer) return atol(buffer); + return 0; } float String::toFloat(void) const { - return float(toDouble()); + return float(toDouble()); } double String::toDouble(void) const { - if (buffer) return atof(buffer); - return 0; + if (buffer) return atof(buffer); + return 0; } diff --git a/megaavr/cores/coreX-corefiles/api/String.h b/megaavr/cores/coreX-corefiles/api/String.h index f2c6dd9..db5230e 100644 --- a/megaavr/cores/coreX-corefiles/api/String.h +++ b/megaavr/cores/coreX-corefiles/api/String.h @@ -48,185 +48,231 @@ class StringSumHelper; // The string class class String { - // use a function pointer to allow for "if (s)" without the - // complications of an operator bool(). for more information, see: - // http://www.artima.com/cppsource/safebool.html - typedef void (String::*StringIfHelperType)() const; - void StringIfHelper() const {} - -public: - // constructors - // creates a copy of the initial value. - // if the initial value is null or invalid, or if memory allocation - // fails, the string will be marked as invalid (i.e. "if (s)" will - // be false). - String(const char *cstr = ""); - String(const String &str); - String(const __FlashStringHelper *str); - #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) - String(String &&rval); - String(StringSumHelper &&rval); - #endif - explicit String(char c); - explicit String(unsigned char, unsigned char base=10); - explicit String(int, unsigned char base=10); - explicit String(unsigned int, unsigned char base=10); - explicit String(long, unsigned char base=10); - explicit String(unsigned long, unsigned char base=10); - explicit String(float, unsigned char decimalPlaces=2); - explicit String(double, unsigned char decimalPlaces=2); - ~String(void); - - // memory management - // return true on success, false on failure (in which case, the string - // is left unchanged). reserve(0), if successful, will validate an - // invalid string (i.e., "if (s)" will be true afterwards) - unsigned char reserve(unsigned int size); - inline unsigned int length(void) const {return len;} - - // creates a copy of the assigned value. if the value is null or - // invalid, or if the memory allocation fails, the string will be - // marked as invalid ("if (s)" will be false). - String & operator = (const String &rhs); - String & operator = (const char *cstr); - String & operator = (const __FlashStringHelper *str); - #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) - String & operator = (String &&rval); - String & operator = (StringSumHelper &&rval); - #endif - - // concatenate (works w/ built-in types) - - // returns true on success, false on failure (in which case, the string - // is left unchanged). if the argument is null or invalid, the - // concatenation is considered unsucessful. - unsigned char concat(const String &str); - unsigned char concat(const char *cstr); - unsigned char concat(char c); - unsigned char concat(unsigned char c); - unsigned char concat(int num); - unsigned char concat(unsigned int num); - unsigned char concat(long num); - unsigned char concat(unsigned long num); - unsigned char concat(float num); - unsigned char concat(double num); - unsigned char concat(const __FlashStringHelper * str); - - // if there's not enough memory for the concatenated value, the string - // will be left unchanged (but this isn't signalled in any way) - String & operator += (const String &rhs) {concat(rhs); return (*this);} - String & operator += (const char *cstr) {concat(cstr); return (*this);} - String & operator += (char c) {concat(c); return (*this);} - String & operator += (unsigned char num) {concat(num); return (*this);} - String & operator += (int num) {concat(num); return (*this);} - String & operator += (unsigned int num) {concat(num); return (*this);} - String & operator += (long num) {concat(num); return (*this);} - String & operator += (unsigned long num) {concat(num); return (*this);} - String & operator += (float num) {concat(num); return (*this);} - String & operator += (double num) {concat(num); return (*this);} - String & operator += (const __FlashStringHelper *str){concat(str); return (*this);} - - friend StringSumHelper & operator + (const StringSumHelper &lhs, const String &rhs); - friend StringSumHelper & operator + (const StringSumHelper &lhs, const char *cstr); - friend StringSumHelper & operator + (const StringSumHelper &lhs, char c); - friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned char num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, int num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned int num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, long num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned long num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, float num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, double num); - friend StringSumHelper & operator + (const StringSumHelper &lhs, const __FlashStringHelper *rhs); - - // comparison (only works w/ Strings and "strings") - operator StringIfHelperType() const { return buffer ? &String::StringIfHelper : 0; } - int compareTo(const String &s) const; - unsigned char equals(const String &s) const; - unsigned char equals(const char *cstr) const; - unsigned char operator == (const String &rhs) const {return equals(rhs);} - unsigned char operator == (const char *cstr) const {return equals(cstr);} - unsigned char operator != (const String &rhs) const {return !equals(rhs);} - unsigned char operator != (const char *cstr) const {return !equals(cstr);} - unsigned char operator < (const String &rhs) const; - unsigned char operator > (const String &rhs) const; - unsigned char operator <= (const String &rhs) const; - unsigned char operator >= (const String &rhs) const; - unsigned char equalsIgnoreCase(const String &s) const; - unsigned char startsWith( const String &prefix) const; - unsigned char startsWith(const String &prefix, unsigned int offset) const; - unsigned char endsWith(const String &suffix) const; - - // character acccess - char charAt(unsigned int index) const; - void setCharAt(unsigned int index, char c); - char operator [] (unsigned int index) const; - char& operator [] (unsigned int index); - void getBytes(unsigned char *buf, unsigned int bufsize, unsigned int index=0) const; - void toCharArray(char *buf, unsigned int bufsize, unsigned int index=0) const - { getBytes((unsigned char *)buf, bufsize, index); } - const char* c_str() const { return buffer; } - char* begin() { return buffer; } - char* end() { return buffer + length(); } - const char* begin() const { return c_str(); } - const char* end() const { return c_str() + length(); } - - // search - int indexOf( char ch ) const; - int indexOf( char ch, unsigned int fromIndex ) const; - int indexOf( const String &str ) const; - int indexOf( const String &str, unsigned int fromIndex ) const; - int lastIndexOf( char ch ) const; - int lastIndexOf( char ch, unsigned int fromIndex ) const; - int lastIndexOf( const String &str ) const; - int lastIndexOf( const String &str, unsigned int fromIndex ) const; - String substring( unsigned int beginIndex ) const { return substring(beginIndex, len); }; - String substring( unsigned int beginIndex, unsigned int endIndex ) const; - - // modification - void replace(char find, char replace); - void replace(const String& find, const String& replace); - void remove(unsigned int index); - void remove(unsigned int index, unsigned int count); - void toLowerCase(void); - void toUpperCase(void); - void trim(void); - - // parsing/conversion - long toInt(void) const; - float toFloat(void) const; - double toDouble(void) const; - -protected: - char *buffer; // the actual char array - unsigned int capacity; // the array length minus one (for the '\0') - unsigned int len; // the String length (not counting the '\0') -protected: - void init(void); - void invalidate(void); - unsigned char changeBuffer(unsigned int maxStrLen); - unsigned char concat(const char *cstr, unsigned int length); - - // copy and move - String & copy(const char *cstr, unsigned int length); - String & copy(const __FlashStringHelper *pstr, unsigned int length); - #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) - void move(String &rhs); - #endif + // use a function pointer to allow for "if (s)" without the + // complications of an operator bool(). for more information, see: + // http://www.artima.com/cppsource/safebool.html + typedef void (String::*StringIfHelperType)() const; + void StringIfHelper() const {} + + public: + // constructors + // creates a copy of the initial value. + // if the initial value is null or invalid, or if memory allocation + // fails, the string will be marked as invalid (i.e. "if (s)" will + // be false). + String(const char *cstr = ""); + String(const String &str); + String(const __FlashStringHelper *str); +#if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) + String(String &&rval); + String(StringSumHelper &&rval); +#endif + explicit String(char c); + explicit String(unsigned char, unsigned char base = 10); + explicit String(int, unsigned char base = 10); + explicit String(unsigned int, unsigned char base = 10); + explicit String(long, unsigned char base = 10); + explicit String(unsigned long, unsigned char base = 10); + explicit String(float, unsigned char decimalPlaces = 2); + explicit String(double, unsigned char decimalPlaces = 2); + ~String(void); + + // memory management + // return true on success, false on failure (in which case, the string + // is left unchanged). reserve(0), if successful, will validate an + // invalid string (i.e., "if (s)" will be true afterwards) + unsigned char reserve(unsigned int size); + inline unsigned int length(void) const { return len; } + + // creates a copy of the assigned value. if the value is null or + // invalid, or if the memory allocation fails, the string will be + // marked as invalid ("if (s)" will be false). + String &operator=(const String &rhs); + String &operator=(const char *cstr); + String &operator=(const __FlashStringHelper *str); +#if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) + String &operator=(String &&rval); + String &operator=(StringSumHelper &&rval); +#endif + + // concatenate (works w/ built-in types) + + // returns true on success, false on failure (in which case, the string + // is left unchanged). if the argument is null or invalid, the + // concatenation is considered unsucessful. + unsigned char concat(const String &str); + unsigned char concat(const char *cstr); + unsigned char concat(char c); + unsigned char concat(unsigned char c); + unsigned char concat(int num); + unsigned char concat(unsigned int num); + unsigned char concat(long num); + unsigned char concat(unsigned long num); + unsigned char concat(float num); + unsigned char concat(double num); + unsigned char concat(const __FlashStringHelper *str); + + // if there's not enough memory for the concatenated value, the string + // will be left unchanged (but this isn't signalled in any way) + String &operator+=(const String &rhs) + { + concat(rhs); + return (*this); + } + String &operator+=(const char *cstr) + { + concat(cstr); + return (*this); + } + String &operator+=(char c) + { + concat(c); + return (*this); + } + String &operator+=(unsigned char num) + { + concat(num); + return (*this); + } + String &operator+=(int num) + { + concat(num); + return (*this); + } + String &operator+=(unsigned int num) + { + concat(num); + return (*this); + } + String &operator+=(long num) + { + concat(num); + return (*this); + } + String &operator+=(unsigned long num) + { + concat(num); + return (*this); + } + String &operator+=(float num) + { + concat(num); + return (*this); + } + String &operator+=(double num) + { + concat(num); + return (*this); + } + String &operator+=(const __FlashStringHelper *str) + { + concat(str); + return (*this); + } + + friend StringSumHelper &operator+(const StringSumHelper &lhs, const String &rhs); + friend StringSumHelper &operator+(const StringSumHelper &lhs, const char *cstr); + friend StringSumHelper &operator+(const StringSumHelper &lhs, char c); + friend StringSumHelper &operator+(const StringSumHelper &lhs, unsigned char num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, int num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, unsigned int num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, long num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, unsigned long num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, float num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, double num); + friend StringSumHelper &operator+(const StringSumHelper &lhs, const __FlashStringHelper *rhs); + + // comparison (only works w/ Strings and "strings") + operator StringIfHelperType() const { return buffer ? &String::StringIfHelper : 0; } + int compareTo(const String &s) const; + unsigned char equals(const String &s) const; + unsigned char equals(const char *cstr) const; + unsigned char operator==(const String &rhs) const { return equals(rhs); } + unsigned char operator==(const char *cstr) const { return equals(cstr); } + unsigned char operator!=(const String &rhs) const { return !equals(rhs); } + unsigned char operator!=(const char *cstr) const { return !equals(cstr); } + unsigned char operator<(const String &rhs) const; + unsigned char operator>(const String &rhs) const; + unsigned char operator<=(const String &rhs) const; + unsigned char operator>=(const String &rhs) const; + unsigned char equalsIgnoreCase(const String &s) const; + unsigned char startsWith(const String &prefix) const; + unsigned char startsWith(const String &prefix, unsigned int offset) const; + unsigned char endsWith(const String &suffix) const; + + // character acccess + char charAt(unsigned int index) const; + void setCharAt(unsigned int index, char c); + char operator[](unsigned int index) const; + char &operator[](unsigned int index); + void getBytes(unsigned char *buf, unsigned int bufsize, unsigned int index = 0) const; + void toCharArray(char *buf, unsigned int bufsize, unsigned int index = 0) const + { + getBytes((unsigned char *)buf, bufsize, index); + } + const char *c_str() const { return buffer; } + char *begin() { return buffer; } + char *end() { return buffer + length(); } + const char *begin() const { return c_str(); } + const char *end() const { return c_str() + length(); } + + // search + int indexOf(char ch) const; + int indexOf(char ch, unsigned int fromIndex) const; + int indexOf(const String &str) const; + int indexOf(const String &str, unsigned int fromIndex) const; + int lastIndexOf(char ch) const; + int lastIndexOf(char ch, unsigned int fromIndex) const; + int lastIndexOf(const String &str) const; + int lastIndexOf(const String &str, unsigned int fromIndex) const; + String substring(unsigned int beginIndex) const { return substring(beginIndex, len); }; + String substring(unsigned int beginIndex, unsigned int endIndex) const; + + // modification + void replace(char find, char replace); + void replace(const String &find, const String &replace); + void remove(unsigned int index); + void remove(unsigned int index, unsigned int count); + void toLowerCase(void); + void toUpperCase(void); + void trim(void); + + // parsing/conversion + long toInt(void) const; + float toFloat(void) const; + double toDouble(void) const; + + protected: + char *buffer; // the actual char array + unsigned int capacity; // the array length minus one (for the '\0') + unsigned int len; // the String length (not counting the '\0') + protected: + void init(void); + void invalidate(void); + unsigned char changeBuffer(unsigned int maxStrLen); + unsigned char concat(const char *cstr, unsigned int length); + + // copy and move + String ©(const char *cstr, unsigned int length); + String ©(const __FlashStringHelper *pstr, unsigned int length); +#if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) + void move(String &rhs); +#endif }; class StringSumHelper : public String { -public: - StringSumHelper(const String &s) : String(s) {} - StringSumHelper(const char *p) : String(p) {} - StringSumHelper(char c) : String(c) {} - StringSumHelper(unsigned char num) : String(num) {} - StringSumHelper(int num) : String(num) {} - StringSumHelper(unsigned int num) : String(num) {} - StringSumHelper(long num) : String(num) {} - StringSumHelper(unsigned long num) : String(num) {} - StringSumHelper(float num) : String(num) {} - StringSumHelper(double num) : String(num) {} + public: + StringSumHelper(const String &s) : String(s) {} + StringSumHelper(const char *p) : String(p) {} + StringSumHelper(char c) : String(c) {} + StringSumHelper(unsigned char num) : String(num) {} + StringSumHelper(int num) : String(num) {} + StringSumHelper(unsigned int num) : String(num) {} + StringSumHelper(long num) : String(num) {} + StringSumHelper(unsigned long num) : String(num) {} + StringSumHelper(float num) : String(num) {} + StringSumHelper(double num) : String(num) {} }; -#endif // __cplusplus +#endif // __cplusplus diff --git a/megaavr/cores/coreX-corefiles/api/USBAPI.h b/megaavr/cores/coreX-corefiles/api/USBAPI.h index 8743ab4..3283106 100644 --- a/megaavr/cores/coreX-corefiles/api/USBAPI.h +++ b/megaavr/cores/coreX-corefiles/api/USBAPI.h @@ -30,17 +30,18 @@ typedef struct __attribute__((packed)) { union { uint8_t bmRequestType; - struct { + struct + { uint8_t direction : 5; uint8_t type : 2; uint8_t transferDirection : 1; }; }; - uint8_t bRequest; - uint8_t wValueL; - uint8_t wValueH; - uint16_t wIndex; - uint16_t wLength; + uint8_t bRequest; + uint8_t wValueL; + uint8_t wValueH; + uint16_t wIndex; + uint16_t wLength; } USBSetup; //================================================================================ @@ -50,11 +51,11 @@ int USB_SendControl(uint8_t flags, const void* d, int len); int USB_RecvControl(void* d, int len); int USB_RecvControlLong(void* d, int len); -uint8_t USB_Available(uint8_t ep); +uint8_t USB_Available(uint8_t ep); uint8_t USB_SendSpace(uint8_t ep); -int USB_Send(uint8_t ep, const void* data, int len); // blocking -int USB_Recv(uint8_t ep, void* data, int len); // non-blocking -int USB_Recv(uint8_t ep); // non-blocking +int USB_Send(uint8_t ep, const void* data, int len); // blocking +int USB_Recv(uint8_t ep, void* data, int len); // non-blocking +int USB_Recv(uint8_t ep); // non-blocking void USB_Flush(uint8_t ep); #endif \ No newline at end of file diff --git a/megaavr/cores/coreX-corefiles/api/Udp.h b/megaavr/cores/coreX-corefiles/api/Udp.h index 9058165..9c13995 100644 --- a/megaavr/cores/coreX-corefiles/api/Udp.h +++ b/megaavr/cores/coreX-corefiles/api/Udp.h @@ -37,50 +37,50 @@ #include "Stream.h" #include "IPAddress.h" -class UDP : public Stream { - -public: - virtual uint8_t begin(uint16_t) =0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use - virtual void stop() =0; // Finish with the UDP socket +class UDP : public Stream +{ + public: + virtual uint8_t begin(uint16_t) = 0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use + virtual void stop() = 0; // Finish with the UDP socket // Sending UDP packets - + // Start building up a packet to send to the remote host specific in ip and port // Returns 1 if successful, 0 if there was a problem with the supplied IP address or port - virtual int beginPacket(IPAddress ip, uint16_t port) =0; + virtual int beginPacket(IPAddress ip, uint16_t port) = 0; // Start building up a packet to send to the remote host specific in host and port // Returns 1 if successful, 0 if there was a problem resolving the hostname or port - virtual int beginPacket(const char *host, uint16_t port) =0; + virtual int beginPacket(const char* host, uint16_t port) = 0; // Finish off this packet and send it // Returns 1 if the packet was sent successfully, 0 if there was an error - virtual int endPacket() =0; + virtual int endPacket() = 0; // Write a single byte into the packet - virtual size_t write(uint8_t) =0; + virtual size_t write(uint8_t) = 0; // Write size bytes from buffer into the packet - virtual size_t write(const uint8_t *buffer, size_t size) =0; + virtual size_t write(const uint8_t* buffer, size_t size) = 0; // Start processing the next available incoming packet // Returns the size of the packet in bytes, or 0 if no packets are available - virtual int parsePacket() =0; + virtual int parsePacket() = 0; // Number of bytes remaining in the current packet - virtual int available() =0; + virtual int available() = 0; // Read a single byte from the current packet - virtual int read() =0; + virtual int read() = 0; // Read up to len bytes from the current packet and place them into buffer // Returns the number of bytes read, or 0 if none are available - virtual int read(unsigned char* buffer, size_t len) =0; + virtual int read(unsigned char* buffer, size_t len) = 0; // Read up to len characters from the current packet and place them into buffer // Returns the number of characters read, or 0 if none are available - virtual int read(char* buffer, size_t len) =0; + virtual int read(char* buffer, size_t len) = 0; // Return the next byte from the current packet without moving on to the next byte - virtual int peek() =0; - virtual void flush() =0; // Finish reading the current packet + virtual int peek() = 0; + virtual void flush() = 0; // Finish reading the current packet // Return the IP address of the host who sent the current incoming packet - virtual IPAddress remoteIP() =0; + virtual IPAddress remoteIP() = 0; // Return the port of the host who sent the current incoming packet - virtual uint16_t remotePort() =0; -protected: + virtual uint16_t remotePort() = 0; + + protected: uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); }; }; - diff --git a/megaavr/cores/coreX-corefiles/api/Udp.h.orig b/megaavr/cores/coreX-corefiles/api/Udp.h.orig index b695002..56c5f1d 100644 --- a/megaavr/cores/coreX-corefiles/api/Udp.h.orig +++ b/megaavr/cores/coreX-corefiles/api/Udp.h.orig @@ -42,7 +42,7 @@ namespace arduino { class UDP : public Stream { public: - virtual uint8_t begin(uint16_t) =0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use + virtual uint8_t begin(uint16_t) =0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use virtual void stop() =0; // Finish with the UDP socket // Sending UDP packets @@ -76,7 +76,7 @@ public: virtual int read(char* buffer, size_t len) =0; // Return the next byte from the current packet without moving on to the next byte virtual int peek() =0; - virtual void flush() =0; // Finish reading the current packet + virtual void flush() =0; // Finish reading the current packet // Return the IP address of the host who sent the current incoming packet virtual IPAddress remoteIP() =0; @@ -86,4 +86,4 @@ protected: uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); }; }; -} \ No newline at end of file +} diff --git a/megaavr/cores/coreX-corefiles/api/WCharacter.h b/megaavr/cores/coreX-corefiles/api/WCharacter.h index 4ce89ee..5db7d9b 100644 --- a/megaavr/cores/coreX-corefiles/api/WCharacter.h +++ b/megaavr/cores/coreX-corefiles/api/WCharacter.h @@ -38,131 +38,115 @@ inline bool isUpperCase(int c) __attribute__((always_inline)); inline bool isHexadecimalDigit(int c) __attribute__((always_inline)); inline int toAscii(int c) __attribute__((always_inline)); inline int toLowerCase(int c) __attribute__((always_inline)); -inline int toUpperCase(int c)__attribute__((always_inline)); +inline int toUpperCase(int c) __attribute__((always_inline)); - -// Checks for an alphanumeric character. +// Checks for an alphanumeric character. // It is equivalent to (isalpha(c) || isdigit(c)). -inline bool isAlphaNumeric(int c) +inline bool isAlphaNumeric(int c) { - return ( isalnum(c) == 0 ? false : true); + return (isalnum(c) == 0 ? false : true); } - -// Checks for an alphabetic character. +// Checks for an alphabetic character. // It is equivalent to (isupper(c) || islower(c)). inline bool isAlpha(int c) { - return ( isalpha(c) == 0 ? false : true); + return (isalpha(c) == 0 ? false : true); } - -// Checks whether c is a 7-bit unsigned char value +// Checks whether c is a 7-bit unsigned char value // that fits into the ASCII character set. inline bool isAscii(int c) { - return ( isascii (c) == 0 ? false : true); + return (isascii(c) == 0 ? false : true); } - // Checks for a blank character, that is, a space or a tab. inline bool isWhitespace(int c) { - return ( isblank (c) == 0 ? false : true); + return (isblank(c) == 0 ? false : true); } - // Checks for a control character. inline bool isControl(int c) { - return ( iscntrl (c) == 0 ? false : true); + return (iscntrl(c) == 0 ? false : true); } - // Checks for a digit (0 through 9). inline bool isDigit(int c) { - return ( isdigit (c) == 0 ? false : true); + return (isdigit(c) == 0 ? false : true); } - // Checks for any printable character except space. inline bool isGraph(int c) { - return ( isgraph (c) == 0 ? false : true); + return (isgraph(c) == 0 ? false : true); } - // Checks for a lower-case character. inline bool isLowerCase(int c) { - return (islower (c) == 0 ? false : true); + return (islower(c) == 0 ? false : true); } - // Checks for any printable character including space. inline bool isPrintable(int c) { - return ( isprint (c) == 0 ? false : true); + return (isprint(c) == 0 ? false : true); } - -// Checks for any printable character which is not a space +// Checks for any printable character which is not a space // or an alphanumeric character. inline bool isPunct(int c) { - return ( ispunct (c) == 0 ? false : true); + return (ispunct(c) == 0 ? false : true); } - -// Checks for white-space characters. For the avr-libc library, -// these are: space, formfeed ('\f'), newline ('\n'), carriage +// Checks for white-space characters. For the avr-libc library, +// these are: space, formfeed ('\f'), newline ('\n'), carriage // return ('\r'), horizontal tab ('\t'), and vertical tab ('\v'). inline bool isSpace(int c) { - return ( isspace (c) == 0 ? false : true); + return (isspace(c) == 0 ? false : true); } - // Checks for an uppercase letter. inline bool isUpperCase(int c) { - return ( isupper (c) == 0 ? false : true); + return (isupper(c) == 0 ? false : true); } - -// Checks for a hexadecimal digits, i.e. one of 0 1 2 3 4 5 6 7 +// Checks for a hexadecimal digits, i.e. one of 0 1 2 3 4 5 6 7 // 8 9 a b c d e f A B C D E F. inline bool isHexadecimalDigit(int c) { - return ( isxdigit (c) == 0 ? false : true); + return (isxdigit(c) == 0 ? false : true); } - -// Converts c to a 7-bit unsigned char value that fits into the +// Converts c to a 7-bit unsigned char value that fits into the // ASCII character set, by clearing the high-order bits. inline int toAscii(int c) { - return toascii (c); + return toascii(c); } - // Warning: -// Many people will be unhappy if you use this function. -// This function will convert accented letters into random +// Many people will be unhappy if you use this function. +// This function will convert accented letters into random // characters. // Converts the letter c to lower case, if possible. inline int toLowerCase(int c) { - return tolower (c); + return tolower(c); } - // Converts the letter c to upper case, if possible. inline int toUpperCase(int c) { - return toupper (c); + return toupper(c); } #endif \ No newline at end of file diff --git a/megaavr/cores/coreX-corefiles/api/itoa.h b/megaavr/cores/coreX-corefiles/api/itoa.h index 55b2849..c94f733 100644 --- a/megaavr/cores/coreX-corefiles/api/itoa.h +++ b/megaavr/cores/coreX-corefiles/api/itoa.h @@ -23,15 +23,15 @@ // core should supply an implementation of them. #ifdef __cplusplus -extern "C" { +extern "C" +{ #endif -extern char* itoa(int value, char *string, int radix); -extern char* ltoa(long value, char *string, int radix); -extern char* utoa(unsigned value, char *string, int radix); -extern char* ultoa(unsigned long value, char *string, int radix); + extern char* itoa(int value, char* string, int radix); + extern char* ltoa(long value, char* string, int radix); + extern char* utoa(unsigned value, char* string, int radix); + extern char* ultoa(unsigned long value, char* string, int radix); #ifdef __cplusplus } // extern "C" #endif - diff --git a/megaavr/cores/coreX-corefiles/hooks.c b/megaavr/cores/coreX-corefiles/hooks.c index 641eabc..a61b5ef 100644 --- a/megaavr/cores/coreX-corefiles/hooks.c +++ b/megaavr/cores/coreX-corefiles/hooks.c @@ -26,6 +26,6 @@ * real cooperative scheduler. */ static void __empty() { - // Empty + // Empty } void yield(void) __attribute__ ((weak, alias("__empty"))); diff --git a/megaavr/cores/coreX-corefiles/main.cpp b/megaavr/cores/coreX-corefiles/main.cpp index ef9f8f4..d79a464 100644 --- a/megaavr/cores/coreX-corefiles/main.cpp +++ b/megaavr/cores/coreX-corefiles/main.cpp @@ -20,28 +20,28 @@ #include // Declared weak in Arduino.h to allow user redefinitions. -int atexit(void (* /*func*/ )()) { return 0; } +int atexit(void (* /*func*/)()) { return 0; } void setupUSB() __attribute__((weak)); -void setupUSB() { } +void setupUSB() {} int main(void) { - init(); + init(); - initVariant(); + initVariant(); #if defined(USBCON) - USBDevice.attach(); + USBDevice.attach(); #endif - setup(); + setup(); - for (;;) { - loop(); - if (serialEventRun) serialEventRun(); - } + for (;;) + { + loop(); + if (serialEventRun) serialEventRun(); + } - return 0; + return 0; } - diff --git a/megaavr/cores/coreX-corefiles/new.cpp b/megaavr/cores/coreX-corefiles/new.cpp index cf6f89c..a265fd6 100644 --- a/megaavr/cores/coreX-corefiles/new.cpp +++ b/megaavr/cores/coreX-corefiles/new.cpp @@ -18,19 +18,22 @@ #include -void *operator new(size_t size) { +void *operator new(size_t size) +{ return malloc(size); } -void *operator new[](size_t size) { +void *operator new[](size_t size) +{ return malloc(size); } -void operator delete(void * ptr) { +void operator delete(void *ptr) +{ free(ptr); } -void operator delete[](void * ptr) { +void operator delete[](void *ptr) +{ free(ptr); } - diff --git a/megaavr/cores/coreX-corefiles/new.h b/megaavr/cores/coreX-corefiles/new.h index 6e1b68f..d1fc852 100644 --- a/megaavr/cores/coreX-corefiles/new.h +++ b/megaavr/cores/coreX-corefiles/new.h @@ -23,8 +23,7 @@ void * operator new(size_t size); void * operator new[](size_t size); -void operator delete(void * ptr); -void operator delete[](void * ptr); +void operator delete(void* ptr); +void operator delete[](void* ptr); #endif - diff --git a/megaavr/cores/coreX-corefiles/timers.h b/megaavr/cores/coreX-corefiles/timers.h index d380563..d468fbb 100644 --- a/megaavr/cores/coreX-corefiles/timers.h +++ b/megaavr/cores/coreX-corefiles/timers.h @@ -2,10 +2,10 @@ #define __TIMERS_H__ // The assumption is that we have a 16 bit timer fully available for timing purposes. -#define TIME_TRACKING_TIMER_DIVIDER 1 // Timer F_CPU Clock divider (can be 1 or 2) -#define TIME_TRACKING_TIMER_COUNT (F_CPU/(1000*TIME_TRACKING_TIMER_DIVIDER)) // Should correspond to exactly 1 ms, i.e. millis() +#define TIME_TRACKING_TIMER_DIVIDER 1 // Timer F_CPU Clock divider (can be 1 or 2) +#define TIME_TRACKING_TIMER_COUNT (F_CPU / (1000 * TIME_TRACKING_TIMER_DIVIDER)) // Should correspond to exactly 1 ms, i.e. millis() -#define PWM_TIMER_PERIOD 0xFE // For frequency -#define PWM_TIMER_COMPARE 0x80 // For duty cycle +#define PWM_TIMER_PERIOD 0xFE // For frequency +#define PWM_TIMER_COMPARE 0x80 // For duty cycle #endif diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 3ae5a7d..6de6bae 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -31,204 +31,216 @@ volatile uint32_t timer_millis = 0; -inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk){ - return ( (clk) / 1000000L ); +inline uint16_t clockCyclesPerMicrosecondComp(uint32_t clk) +{ + return ((clk) / 1000000L); } -inline uint16_t clockCyclesPerMicrosecond(){ - return clockCyclesPerMicrosecondComp(F_CPU); +inline uint16_t clockCyclesPerMicrosecond() +{ + return clockCyclesPerMicrosecondComp(F_CPU); } -inline unsigned long clockCyclesToMicroseconds(unsigned long cycles){ - return ( cycles / clockCyclesPerMicrosecond() ); +inline unsigned long clockCyclesToMicroseconds(unsigned long cycles) +{ + return (cycles / clockCyclesPerMicrosecond()); } -inline unsigned long microsecondsToClockCycles(unsigned long microseconds){ - return ( microseconds * clockCyclesPerMicrosecond() ); +inline unsigned long microsecondsToClockCycles(unsigned long microseconds) +{ + return (microseconds * clockCyclesPerMicrosecond()); } -static volatile TCB_t* _timer = +static volatile TCB_t *_timer = #if defined(MILLIS_USE_TIMERB0) - &TCB0; + &TCB0; #elif defined(MILLIS_USE_TIMERB1) - &TCB1; + &TCB1; #elif defined(MILLIS_USE_TIMERB2) - &TCB2; + &TCB2; #else // fallback or defined(MILLIS_USE_TIMERB3) - &TCB3; //TCB3 fallback + &TCB3; //TCB3 fallback #endif #if defined(MILLIS_USE_TIMERB0) - ISR(TCB0_INT_vect) +ISR(TCB0_INT_vect) #elif defined(MILLIS_USE_TIMERB1) - ISR(TCB1_INT_vect) +ISR(TCB1_INT_vect) #elif defined(MILLIS_USE_TIMERB2) - ISR(TCB2_INT_vect) +ISR(TCB2_INT_vect) #else // fallback or defined(MILLIS_USE_TIMERB3) - ISR(TCB3_INT_vect) +ISR(TCB3_INT_vect) #endif { - timer_millis++; + timer_millis++; - /* Clear flag */ - _timer->INTFLAGS = TCB_CAPT_bm; + /* Clear flag */ + _timer->INTFLAGS = TCB_CAPT_bm; } unsigned long millis() { - unsigned long m; + unsigned long m; - // disable interrupts while we read timer0_millis or we might get an - // inconsistent value (e.g. in the middle of a write to timer_millis) - uint8_t status = SREG; - cli(); + // disable interrupts while we read timer0_millis or we might get an + // inconsistent value (e.g. in the middle of a write to timer_millis) + uint8_t status = SREG; + cli(); - m = timer_millis; + m = timer_millis; - SREG = status; + SREG = status; - return m; + return m; } -unsigned long micros() { - uint32_t m; - uint16_t t; +unsigned long micros() +{ + uint32_t m; + uint16_t t; - /* Save current state and disable interrupts */ - uint8_t status = SREG; - cli(); + /* Save current state and disable interrupts */ + uint8_t status = SREG; + cli(); - /* Get current number of millis (i.e. overflows) and timer count */ - m = timer_millis; - t = _timer->CNT; + /* Get current number of millis (i.e. overflows) and timer count */ + m = timer_millis; + t = _timer->CNT; - /* If the timer overflow flag is raised, we just missed it, - increment to account for it, & read new ticks */ - if(_timer->INTFLAGS & TCB_CAPT_bm){ - m++; - t = _timer->CNT; - } + /* If the timer overflow flag is raised, we just missed it, + increment to account for it, & read new ticks */ + if (_timer->INTFLAGS & TCB_CAPT_bm) + { + m++; + t = _timer->CNT; + } - // Restore SREG - SREG = status; + // Restore SREG + SREG = status; - return (m * 1000L) + (t / (TIME_TRACKING_TIMER_COUNT / 1000)); + return (m * 1000L) + (t / (TIME_TRACKING_TIMER_COUNT / 1000)); } void delay(unsigned long ms) { - uint32_t start_time = micros(), delay_time = 1000*ms; + uint32_t start_time = micros(), delay_time = 1000 * ms; - /* Calculate future time to return */ - uint32_t return_time = start_time + delay_time; + /* Calculate future time to return */ + uint32_t return_time = start_time + delay_time; - /* If return time overflows */ - if(return_time < delay_time){ - /* Wait until micros overflows */ - while(micros() > return_time); - } - - /* Wait until return time */ - while(micros() < return_time); + /* If return time overflows */ + if (return_time < delay_time) + { + /* Wait until micros overflows */ + while (micros() > return_time) + ; + } + + /* Wait until return time */ + while (micros() < return_time) + ; } /* Delay for the given number of microseconds. Assumes a 1, 8, 12, 16, 20 or 24 MHz clock. */ // BUG: should really be implemented using _timer instead!!!!!!!!!! void delayMicroseconds(unsigned int us) { - // call = 4 cycles + 2 to 4 cycles to init us(2 for constant delay, 4 for variable) + // call = 4 cycles + 2 to 4 cycles to init us(2 for constant delay, 4 for variable) - // calling avrlib's delay_us() function with low values (e.g. 1 or - // 2 microseconds) gives delays longer than desired. - //delay_us(us); + // calling avrlib's delay_us() function with low values (e.g. 1 or + // 2 microseconds) gives delays longer than desired. + //delay_us(us); #if F_CPU >= 24000000L - // for the 24 MHz clock for the aventurous ones, trying to overclock + // for the 24 MHz clock for the aventurous ones, trying to overclock - // zero delay fix - if (!us) return; // = 3 cycles, (4 when true) + // zero delay fix + if (!us) return; // = 3 cycles, (4 when true) - // the following loop takes a 1/6 of a microsecond (4 cycles) - // per iteration, so execute it six times for each microsecond of - // delay requested. - us *= 6; // x6 us, = 7 cycles + // the following loop takes a 1/6 of a microsecond (4 cycles) + // per iteration, so execute it six times for each microsecond of + // delay requested. + us *= 6; // x6 us, = 7 cycles - // account for the time taken in the preceeding commands. - // we just burned 22 (24) cycles above, remove 5, (5*4=20) - // us is at least 6 so we can substract 5 - us -= 5; //=2 cycles + // account for the time taken in the preceeding commands. + // we just burned 22 (24) cycles above, remove 5, (5*4=20) + // us is at least 6 so we can substract 5 + us -= 5; //=2 cycles #elif F_CPU >= 20000000L - // for the 20 MHz clock on rare Arduino boards - - // for a one-microsecond delay, simply return. the overhead - // of the function call takes 18 (20) cycles, which is 1us - __asm__ __volatile__ ( - "nop" "\n\t" - "nop" "\n\t" - "nop" "\n\t" - "nop"); //just waiting 4 cycles - if (us <= 1) return; // = 3 cycles, (4 when true) - - // the following loop takes a 1/5 of a microsecond (4 cycles) - // per iteration, so execute it five times for each microsecond of - // delay requested. - us = (us << 2) + us; // x5 us, = 7 cycles - - // account for the time taken in the preceeding commands. - // we just burned 26 (28) cycles above, remove 7, (7*4=28) - // us is at least 10 so we can substract 7 - us -= 7; // 2 cycles + // for the 20 MHz clock on rare Arduino boards + + // for a one-microsecond delay, simply return. the overhead + // of the function call takes 18 (20) cycles, which is 1us + __asm__ __volatile__( + "nop" + "\n\t" + "nop" + "\n\t" + "nop" + "\n\t" + "nop"); //just waiting 4 cycles + if (us <= 1) return; // = 3 cycles, (4 when true) + + // the following loop takes a 1/5 of a microsecond (4 cycles) + // per iteration, so execute it five times for each microsecond of + // delay requested. + us = (us << 2) + us; // x5 us, = 7 cycles + + // account for the time taken in the preceeding commands. + // we just burned 26 (28) cycles above, remove 7, (7*4=28) + // us is at least 10 so we can substract 7 + us -= 7; // 2 cycles #elif F_CPU >= 16000000L - // for the 16 MHz clock on most Arduino boards + // for the 16 MHz clock on most Arduino boards - // for a one-microsecond delay, simply return. the overhead - // of the function call takes 14 (16) cycles, which is 1us - if (us <= 1) return; // = 3 cycles, (4 when true) + // for a one-microsecond delay, simply return. the overhead + // of the function call takes 14 (16) cycles, which is 1us + if (us <= 1) return; // = 3 cycles, (4 when true) - // the following loop takes 1/4 of a microsecond (4 cycles) - // per iteration, so execute it four times for each microsecond of - // delay requested. - us <<= 2; // x4 us, = 4 cycles + // the following loop takes 1/4 of a microsecond (4 cycles) + // per iteration, so execute it four times for each microsecond of + // delay requested. + us <<= 2; // x4 us, = 4 cycles - // account for the time taken in the preceeding commands. - // we just burned 19 (21) cycles above, remove 5, (5*4=20) - // us is at least 8 so we can substract 5 - us -= 5; // = 2 cycles, + // account for the time taken in the preceeding commands. + // we just burned 19 (21) cycles above, remove 5, (5*4=20) + // us is at least 8 so we can substract 5 + us -= 5; // = 2 cycles, #elif F_CPU >= 12000000L - // for the 12 MHz clock if somebody is working with USB + // for the 12 MHz clock if somebody is working with USB - // for a 1 microsecond delay, simply return. the overhead - // of the function call takes 14 (16) cycles, which is 1.5us - if (us <= 1) return; // = 3 cycles, (4 when true) + // for a 1 microsecond delay, simply return. the overhead + // of the function call takes 14 (16) cycles, which is 1.5us + if (us <= 1) return; // = 3 cycles, (4 when true) - // the following loop takes 1/3 of a microsecond (4 cycles) - // per iteration, so execute it three times for each microsecond of - // delay requested. - us = (us << 1) + us; // x3 us, = 5 cycles + // the following loop takes 1/3 of a microsecond (4 cycles) + // per iteration, so execute it three times for each microsecond of + // delay requested. + us = (us << 1) + us; // x3 us, = 5 cycles - // account for the time taken in the preceeding commands. - // we just burned 20 (22) cycles above, remove 5, (5*4=20) - // us is at least 6 so we can substract 5 - us -= 5; //2 cycles + // account for the time taken in the preceeding commands. + // we just burned 20 (22) cycles above, remove 5, (5*4=20) + // us is at least 6 so we can substract 5 + us -= 5; //2 cycles #elif F_CPU >= 8000000L - // for the 8 MHz internal clock + // for the 8 MHz internal clock - // for a 1 and 2 microsecond delay, simply return. the overhead - // of the function call takes 14 (16) cycles, which is 2us - if (us <= 2) return; // = 3 cycles, (4 when true) + // for a 1 and 2 microsecond delay, simply return. the overhead + // of the function call takes 14 (16) cycles, which is 2us + if (us <= 2) return; // = 3 cycles, (4 when true) - // the following loop takes 1/2 of a microsecond (4 cycles) - // per iteration, so execute it twice for each microsecond of - // delay requested. - us <<= 1; //x2 us, = 2 cycles + // the following loop takes 1/2 of a microsecond (4 cycles) + // per iteration, so execute it twice for each microsecond of + // delay requested. + us <<= 1; //x2 us, = 2 cycles - // account for the time taken in the preceeding commands. - // we just burned 17 (19) cycles above, remove 4, (4*4=16) - // us is at least 6 so we can substract 4 - us -= 4; // = 2 cycles + // account for the time taken in the preceeding commands. + // we just burned 17 (19) cycles above, remove 4, (4*4=16) + // us is at least 6 so we can substract 4 + us -= 4; // = 2 cycles #elif F_CPU >= 4000000L // The overhead of the function call is 14 (16) cycles which is 4 us @@ -252,151 +264,153 @@ void delayMicroseconds(unsigned int us) us = (us >> 1); // 3 cycles #else - // for the 1 MHz internal clock (default settings for common Atmega microcontrollers) + // for the 1 MHz internal clock (default settings for common Atmega microcontrollers) - // the overhead of the function calls is 14 (16) cycles - if (us <= 16) return; //= 3 cycles, (4 when true) - if (us <= 25) return; //= 3 cycles, (4 when true), (must be at least 25 if we want to substract 22) - - // compensate for the time taken by the preceeding and next commands (about 22 cycles) - us -= 22; // = 2 cycles - // the following loop takes 4 microseconds (4 cycles) - // per iteration, so execute it us/4 times - // us is at least 4, divided by 4 gives us 1 (no zero delay bug) - us >>= 2; // us div 4, = 4 cycles + // the overhead of the function calls is 14 (16) cycles + if (us <= 16) return; //= 3 cycles, (4 when true) + if (us <= 25) return; //= 3 cycles, (4 when true), (must be at least 25 if we want to substract 22) + // compensate for the time taken by the preceeding and next commands (about 22 cycles) + us -= 22; // = 2 cycles + // the following loop takes 4 microseconds (4 cycles) + // per iteration, so execute it us/4 times + // us is at least 4, divided by 4 gives us 1 (no zero delay bug) + us >>= 2; // us div 4, = 4 cycles #endif - // busy wait - __asm__ __volatile__ ( - "1: sbiw %0,1" "\n\t" // 2 cycles - "brne 1b" : "=w" (us) : "0" (us) // 2 cycles - ); - // return = 4 cycles + // busy wait + __asm__ __volatile__( + "1: sbiw %0,1" + "\n\t" // 2 cycles + "brne 1b" + : "=w"(us) + : "0"(us) // 2 cycles + ); + // return = 4 cycles } void init() { - // this needs to be called before setup() or some functions won't - // work there - -/******************************** CLOCK STUFF *********************************/ - - // Use external oscillator if already defined (in boards.txt, platformio.ini) - #if defined(USE_EXTERNAL_OSCILLATOR) - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLA, CLKCTRL_CLKSEL_EXTCLK_gc); - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); // Fallback to 16 MHz internal if no EXTCLK - - // Use internal oscillator if not defined. No need to manipulate the MCLKCTRLA register here - // because it's already done in the SYSCFG0 fuse byte - #else - #if (F_CPU == 20000000L) - /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU >= 16000000L) - /* No division on clock */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); - #elif (F_CPU >= 8000000L) - /* Clock DIV2 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); - #elif (F_CPU >= 4000000L) - /* Clock DIV4 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); - #elif (F_CPU >= 2000000L) - /* Clock DIV8 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); - #elif (F_CPU >= 1000000L) - /* Clock DIV16 */ - _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_16X_gc)); - #else - #assert "This internal CPU clock is not supported" - #endif - #endif - -/********************************* ADC ****************************************/ + // this needs to be called before setup() or some functions won't + // work there + + /******************************** CLOCK STUFF *********************************/ + +// Use external oscillator if already defined (in boards.txt, platformio.ini) +#if defined(USE_EXTERNAL_OSCILLATOR) + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLA, CLKCTRL_CLKSEL_EXTCLK_gc); + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); // Fallback to 16 MHz internal if no EXTCLK + +// Use internal oscillator if not defined. No need to manipulate the MCLKCTRLA register here +// because it's already done in the SYSCFG0 fuse byte +#else +#if (F_CPU == 20000000L) + /* No division on clock */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); +#elif (F_CPU >= 16000000L) + /* No division on clock */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); +#elif (F_CPU >= 8000000L) + /* Clock DIV2 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); +#elif (F_CPU >= 4000000L) + /* Clock DIV4 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); +#elif (F_CPU >= 2000000L) + /* Clock DIV8 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); +#elif (F_CPU >= 1000000L) + /* Clock DIV16 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_16X_gc)); +#else +#assert "This internal CPU clock is not supported" +#endif +#endif + + /********************************* ADC ****************************************/ #if defined(ADC0) - /* ADC clock between 50-200 kHz */ - - #if (F_CPU >= 20000000L) // 20 MHz / 128 = 156.250 kHz - ADC0.CTRLC |= ADC_PRESC_DIV128_gc; - #elif (F_CPU >= 16000000L) // 16 MHz / 128 = 125 kHz - ADC0.CTRLC |= ADC_PRESC_DIV128_gc; - #elif (F_CPU >= 8000000L) // 8 MHz / 64 = 125 kHz - ADC0.CTRLC |= ADC_PRESC_DIV64_gc; - #elif (F_CPU >= 4000000L) // 4 MHz / 32 = 125 kHz - ADC0.CTRLC |= ADC_PRESC_DIV32_gc; - #elif (F_CPU >= 2000000L) // 2 MHz / 16 = 125 kHz - ADC0.CTRLC |= ADC_PRESC_DIV16_gc; - #elif (F_CPU >= 1000000L) // 1 MHz / 8 = 125 kHz - ADC0.CTRLC |= ADC_PRESC_DIV8_gc; - #else // 128 kHz / 2 = 64 kHz -> This is the closest you can get, the prescaler is 2 - ADC0.CTRLC |= ADC_PRESC_DIV2_gc; - #endif - - /* Enable ADC */ - ADC0.CTRLA |= ADC_ENABLE_bm; - analogReference(VDD); + /* ADC clock between 50-200 kHz */ + +#if (F_CPU >= 20000000L) // 20 MHz / 128 = 156.250 kHz + ADC0.CTRLC |= ADC_PRESC_DIV128_gc; +#elif (F_CPU >= 16000000L) // 16 MHz / 128 = 125 kHz + ADC0.CTRLC |= ADC_PRESC_DIV128_gc; +#elif (F_CPU >= 8000000L) // 8 MHz / 64 = 125 kHz + ADC0.CTRLC |= ADC_PRESC_DIV64_gc; +#elif (F_CPU >= 4000000L) // 4 MHz / 32 = 125 kHz + ADC0.CTRLC |= ADC_PRESC_DIV32_gc; +#elif (F_CPU >= 2000000L) // 2 MHz / 16 = 125 kHz + ADC0.CTRLC |= ADC_PRESC_DIV16_gc; +#elif (F_CPU >= 1000000L) // 1 MHz / 8 = 125 kHz + ADC0.CTRLC |= ADC_PRESC_DIV8_gc; +#else // 128 kHz / 2 = 64 kHz -> This is the closest you can get, the prescaler is 2 + ADC0.CTRLC |= ADC_PRESC_DIV2_gc; +#endif + + /* Enable ADC */ + ADC0.CTRLA |= ADC_ENABLE_bm; + analogReference(VDD); #endif - PORTMUX.USARTROUTEA = 0; + PORTMUX.USARTROUTEA = 0; - setup_timers(); + setup_timers(); - /********************* TCB for system time tracking **************************/ + /********************* TCB for system time tracking **************************/ - // BUG: we can compensate for F_CPU by fine tuning value of TIME_TRACKING_TIMER_COUNT + // BUG: we can compensate for F_CPU by fine tuning value of TIME_TRACKING_TIMER_COUNT - /* Select vanilla 16 bit periodic interrupt mode */ - _timer->CTRLB = TCB_CNTMODE_INT_gc; + /* Select vanilla 16 bit periodic interrupt mode */ + _timer->CTRLB = TCB_CNTMODE_INT_gc; - /* TOP value for overflow every N clock cycles */ - _timer->CCMP = TIME_TRACKING_TIMER_COUNT - 1; + /* TOP value for overflow every N clock cycles */ + _timer->CCMP = TIME_TRACKING_TIMER_COUNT - 1; - /* Enable TCB interrupt */ - _timer->INTCTRL |= TCB_CAPT_bm; + /* Enable TCB interrupt */ + _timer->INTCTRL |= TCB_CAPT_bm; - /* Clock selection is F_CPU/N -- which is independent of TCA */ -#if TIME_TRACKING_TIMER_DIVIDER==1 - _timer->CTRLA = TCB_CLKSEL_CLKDIV1_gc; /* F_CPU */ -#elif TIME_TRACKING_TIMER_DIVIDER==2 - _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; /* F_CPU/2 */ + /* Clock selection is F_CPU/N -- which is independent of TCA */ +#if TIME_TRACKING_TIMER_DIVIDER == 1 + _timer->CTRLA = TCB_CLKSEL_CLKDIV1_gc; /* F_CPU */ +#elif TIME_TRACKING_TIMER_DIVIDER == 2 + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; /* F_CPU/2 */ #else #assert "TIME_TRACKING_TIMER_DIVIDER not supported" #endif - /* Enable & start */ - _timer->CTRLA |= TCB_ENABLE_bm; /* Keep this last before enabling interrupts to ensure tracking as accurate as possible */ + /* Enable & start */ + _timer->CTRLA |= TCB_ENABLE_bm; /* Keep this last before enabling interrupts to ensure tracking as accurate as possible */ -/*************************** ENABLE GLOBAL INTERRUPTS *************************/ + /*************************** ENABLE GLOBAL INTERRUPTS *************************/ - sei(); + sei(); } -void setup_timers() { - - // TYPE A TIMER +void setup_timers() +{ + // TYPE A TIMER // PORTMUX setting for TCA (defined in pins_arduino.h) - PORTMUX.TCAROUTEA = TCA0_PINS; + PORTMUX.TCAROUTEA = TCA0_PINS; // Enable split mode before anything else TCA0.SPLIT.CTRLD = TCA_SINGLE_SPLITM_bm; // Period setting, two 8 bit registers TCA0.SPLIT.LPER = - TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; + TCA0.SPLIT.HPER = PWM_TIMER_PERIOD; // Default duty 50%, will re-assign in analogWrite() TCA0.SPLIT.LCMP0 = - TCA0.SPLIT.LCMP1 = - TCA0.SPLIT.LCMP2 = - TCA0.SPLIT.HCMP0 = - TCA0.SPLIT.HCMP1 = - TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = PWM_TIMER_COMPARE; #if F_CPU <= 1000000L // Use DIV4 prescaler (giving 250kHz clock on 1MHz), enable TCA timer @@ -412,37 +426,37 @@ void setup_timers() { TCA0.SPLIT.CTRLA = (TCA_SPLIT_CLKSEL_DIV64_gc) | (TCA_SPLIT_ENABLE_bm); #endif - // TYPE B TIMERS - + // TYPE B TIMERS + // Set up routing (defined in pins_arduino.h) PORTMUX.TCBROUTEA = 0 - #if defined(TCB0) - | TCB0_PINS - #endif - #if defined(TCB1) - | TCB1_PINS - #endif - #if defined(TCB2) - | TCB2_PINS - #endif - #if defined(TCB3) - | TCB3_PINS - #endif - ; +#if defined(TCB0) + | TCB0_PINS +#endif +#if defined(TCB1) + | TCB1_PINS +#endif +#if defined(TCB2) + | TCB2_PINS +#endif +#if defined(TCB3) + | TCB3_PINS +#endif + ; // Start with TCB0 TCB_t *timer_B = (TCB_t *)&TCB0; - - // Find end timer - #if defined(TCB3) - TCB_t *timer_B_end = (TCB_t *)&TCB3; - #elif defined(TCB2) - TCB_t *timer_B_end = (TCB_t *)&TCB2; - #elif defined(TCB1) - TCB_t *timer_B_end = (TCB_t *)&TCB1; - #else - TCB_t *timer_B_end = (TCB_t *)&TCB0; - #endif + +// Find end timer +#if defined(TCB3) + TCB_t *timer_B_end = (TCB_t *)&TCB3; +#elif defined(TCB2) + TCB_t *timer_B_end = (TCB_t *)&TCB2; +#elif defined(TCB1) + TCB_t *timer_B_end = (TCB_t *)&TCB1; +#else + TCB_t *timer_B_end = (TCB_t *)&TCB0; +#endif // Timer B Setup loop for TCB[0:end] do @@ -459,33 +473,33 @@ void setup_timers() { // Use TCA clock (250kHz) and enable // (sync update commented out, might try to synchronize later timer_B->CTRLA = (TCB_CLKSEL_CLKTCA_gc) - //|(TCB_SYNCUPD_bm) - |(TCB_ENABLE_bm); + //|(TCB_SYNCUPD_bm) + | (TCB_ENABLE_bm); // Increment pointer to next TCB instance timer_B++; - // Stop when pointing to TCB3 + // Stop when pointing to TCB3 } while (timer_B <= timer_B_end); // Stuff for synchronizing PWM timers -// // Restart TCA to sync TCBs -// // should not be needed -// TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; -// TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; -// -// timer_B = (TCB_t *)&TCB0; -// -// // TCB are sync to TCA, remove setting -// for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); -// digitial_pin_timer < (TIMERB3 - TIMERB0); -// digitial_pin_timer++) -// { -// // disable sync with tca -// timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); -// -// // Add offset to register -// timer_B++; -// -// } + // // Restart TCA to sync TCBs + // // should not be needed + // TCA0.SINGLE.CTRLESET = TCA_SINGLE_CMD_RESTART_gc; + // TCA0.SINGLE.CTRLECLR = TCA_SINGLE_CMD_RESTART_gc; + // + // timer_B = (TCB_t *)&TCB0; + // + // // TCB are sync to TCA, remove setting + // for (uint8_t digitial_pin_timer = (TIMERB0 - TIMERB0); + // digitial_pin_timer < (TIMERB3 - TIMERB0); + // digitial_pin_timer++) + // { + // // disable sync with tca + // timer_B->CTRLA &= ~ (TCB_SYNCUPD_bm); + // + // // Add offset to register + // timer_B++; + // + // } } diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index ccd9c4c..dbcf46e 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -22,57 +22,58 @@ Modified 28 September 2010 by Mark Sproul */ -#include "wiring_private.h" -#include "pins_arduino.h" #include "Arduino.h" +#include "pins_arduino.h" +#include "wiring_private.h" void analogReference(uint8_t mode) { - switch (mode) - { - case EXTERNAL: - case VDD: - ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | mode | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... - // VREF.CTRLA does not need to be reconfigured, as the voltage references only supply their specified voltage when requested to do so by the ADC. - break; - case INTERNAL0V55: - VREF.CTRLA = VREF.CTRLA & ~(VREF_ADC0REFSEL_gm); // These bits are all 0 for 0.55v reference, so no need to do the mode << VREF_ADC0REFSEL_gp here; - ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm | ADC_SAMPCAP_bm)) | INTERNAL; // Per datasheet, recommended SAMPCAP=0 at ref < 1v - break; - case INTERNAL1V1: - case INTERNAL2V5: - case INTERNAL4V34: - case INTERNAL1V5: - VREF.CTRLA = (VREF.CTRLA & ~(VREF_ADC0REFSEL_gm)) | (mode << VREF_ADC0REFSEL_gp); - ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | INTERNAL | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - break; - default: - ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | VDD | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... - } + switch (mode) + { + case EXTERNAL: + case VDD: + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | mode | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... + // VREF.CTRLA does not need to be reconfigured, as the voltage references only supply their specified voltage when requested to do so by the ADC. + break; + case INTERNAL0V55: + VREF.CTRLA = VREF.CTRLA & ~(VREF_ADC0REFSEL_gm); // These bits are all 0 for 0.55v reference, so no need to do the mode << VREF_ADC0REFSEL_gp here; + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm | ADC_SAMPCAP_bm)) | INTERNAL; // Per datasheet, recommended SAMPCAP=0 at ref < 1v + break; + case INTERNAL1V1: + case INTERNAL2V5: + case INTERNAL4V34: + case INTERNAL1V5: + VREF.CTRLA = (VREF.CTRLA & ~(VREF_ADC0REFSEL_gm)) | (mode << VREF_ADC0REFSEL_gp); + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | INTERNAL | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v + break; + default: + ADC0.CTRLC = (ADC0.CTRLC & ~(ADC_REFSEL_gm)) | VDD | ADC_SAMPCAP_bm; // Per datasheet, recommended SAMPCAP=1 at ref > 1v - we don't *KNOW* the external reference will be >1v, but it's probably more likely... + } } int analogRead(uint8_t pin) { - pin = digitalPinToAnalogInput(pin); - if(pin > NUM_ANALOG_INPUTS) - return NOT_A_PIN; + pin = digitalPinToAnalogInput(pin); + if (pin > NUM_ANALOG_INPUTS) + return NOT_A_PIN; #if defined(ADC0) - /* Reference should be already set up */ - /* Select channel */ - ADC0.MUXPOS = (pin << ADC_MUXPOS_gp); + /* Reference should be already set up */ + /* Select channel */ + ADC0.MUXPOS = (pin << ADC_MUXPOS_gp); - /* Start conversion */ - ADC0.COMMAND = ADC_STCONV_bm; + /* Start conversion */ + ADC0.COMMAND = ADC_STCONV_bm; - /* Wait for result ready */ - while(!(ADC0.INTFLAGS & ADC_RESRDY_bm)); + /* Wait for result ready */ + while (!(ADC0.INTFLAGS & ADC_RESRDY_bm)) + ; - /* Combine two bytes */ - return ADC0.RES; + /* Combine two bytes */ + return ADC0.RES; -#else /* No ADC, return 0 */ - return 0; +#else /* No ADC, return 0 */ + return 0; #endif } @@ -82,84 +83,90 @@ int analogRead(uint8_t pin) // to digital output. void analogWrite(uint8_t pin, int val) { - - uint8_t bit_pos = digitalPinToBitPosition(pin); - if(bit_pos == NOT_A_PIN) - return; - - // We need to make sure the PWM output is enabled for those pins - // that support it, as we turn it off when digitally reading or - // writing with them. Also, make sure the pin is in output mode - // for consistently with Wiring, which doesn't require a pinMode - // call for the analog output pins. - pinMode(pin, OUTPUT); - - if(val <= 0){ /* if zero or negative drive digital low */ - - digitalWrite(pin, LOW); - - } else if(val >= 255){ /* if max or greater drive digital high */ - - digitalWrite(pin, HIGH); - - } else { /* handle pwm to generate analog value */ - - /* Get timer */ - uint8_t digital_pin_timer = digitalPinToTimer(pin); - - uint8_t* timer_cmp_out; - TCB_t *timer_B; - - /* Find out Port and Pin to correctly handle port mux, and timer. */ - switch (digital_pin_timer) { - - case TIMERA0: - /* Split mode, 2x3 8 bit registers. (chapter 19.7) */ - if (bit_pos >= 3) { - timer_cmp_out = ((uint8_t*) (&TCA0.SPLIT.HCMP0)) + 2*(bit_pos-3); - ++bit_pos; /* Upper 3 bits are shifted by 1 */ - } else { - /* Calculate correct compare buffer register */ - timer_cmp_out = ((uint8_t*) (&TCA0.SPLIT.LCMP0)) + 2*bit_pos; - } - - /* Configure duty cycle for correct compare channel */ - (*timer_cmp_out) = val; - - /* Enable output on pin */ - TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); - break; - - case TIMERB0: - case TIMERB1: - case TIMERB2: - case TIMERB3: - - /* Get pointer to timer, TIMERB0 order definition in Arduino.h*/ - //assert (((TIMERB0 - TIMERB3) == 2)); - timer_B = ((TCB_t *)&TCB0 + (digital_pin_timer - TIMERB0)); - - /* set duty cycle */ - timer_B->CCMPH = val; - - /* Enable Timer Output */ - timer_B->CTRLB |= (TCB_CCMPEN_bm); - - break; - - /* If non timer pin, or unknown timer definition. */ - /* do a digital write */ - - case NOT_ON_TIMER: - default: - if (val < 128) { - digitalWrite(pin, LOW); - } else { - digitalWrite(pin, HIGH); - } - break; - } - } + uint8_t bit_pos = digitalPinToBitPosition(pin); + if (bit_pos == NOT_A_PIN) + return; + + // We need to make sure the PWM output is enabled for those pins + // that support it, as we turn it off when digitally reading or + // writing with them. Also, make sure the pin is in output mode + // for consistently with Wiring, which doesn't require a pinMode + // call for the analog output pins. + pinMode(pin, OUTPUT); + + if (val <= 0) + { /* if zero or negative drive digital low */ + digitalWrite(pin, LOW); + } + else if (val >= 255) + { /* if max or greater drive digital high */ + digitalWrite(pin, HIGH); + } + else + { /* handle pwm to generate analog value */ + + /* Get timer */ + uint8_t digital_pin_timer = digitalPinToTimer(pin); + + uint8_t *timer_cmp_out; + TCB_t *timer_B; + + /* Find out Port and Pin to correctly handle port mux, and timer. */ + switch (digital_pin_timer) + { + case TIMERA0: + /* Split mode, 2x3 8 bit registers. (chapter 19.7) */ + if (bit_pos >= 3) + { + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.HCMP0)) + 2 * (bit_pos - 3); + ++bit_pos; /* Upper 3 bits are shifted by 1 */ + } + else + { + /* Calculate correct compare buffer register */ + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.LCMP0)) + 2 * bit_pos; + } + + /* Configure duty cycle for correct compare channel */ + (*timer_cmp_out) = val; + + /* Enable output on pin */ + TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); + break; + + case TIMERB0: + case TIMERB1: + case TIMERB2: + case TIMERB3: + + /* Get pointer to timer, TIMERB0 order definition in Arduino.h*/ + //assert (((TIMERB0 - TIMERB3) == 2)); + timer_B = ((TCB_t *)&TCB0 + (digital_pin_timer - TIMERB0)); + + /* set duty cycle */ + timer_B->CCMPH = val; + + /* Enable Timer Output */ + timer_B->CTRLB |= (TCB_CCMPEN_bm); + + break; + + /* If non timer pin, or unknown timer definition. */ + /* do a digital write */ + + case NOT_ON_TIMER: + default: + if (val < 128) + { + digitalWrite(pin, LOW); + } + else + { + digitalWrite(pin, HIGH); + } + break; + } + } } // Set PWM repeat frequency for all PWM outputs with @@ -167,29 +174,31 @@ void analogWrite(uint8_t pin, int val) // The argument is the desired frequency in kHz. A // best effort will be made to find something that matches. // -void analogWriteFrequency(uint8_t kHz) { - static const byte index2setting[] = { +void analogWriteFrequency(uint8_t kHz) +{ + static const byte index2setting[] = { #if F_CPU > 1000000L #if F_CPU > 2000000L #if F_CPU > 4000000L #if F_CPU > 8000000L - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // ~1 kHz PWM, ~250kHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV64_gc, // ~1 kHz PWM, ~250kHz clock #endif - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~2 kHz is not possible, use 4 #endif - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV16_gc, // ~4 kHz PWM, ~1MHz clock #endif - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV8_gc, // ~8 kHz PWM, ~2MHz clock #endif - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // ~16 kHz PWM, ~4MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // ~32 kHz PWM, ~8MHz clock - TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // ~64 kHz PWM, ~16MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV4_gc, // ~16 kHz PWM, ~4MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV2_gc, // ~32 kHz PWM, ~8MHz clock + TCA_SPLIT_ENABLE_bm | TCA_SPLIT_CLKSEL_DIV1_gc // ~64 kHz PWM, ~16MHz clock }; uint8_t index = 0; - while (kHz > 1) { // find approximate match - kHz >>= 1; - if (++index >= sizeof(index2setting) - 1) break; + while (kHz > 1) + { // find approximate match + kHz >>= 1; + if (++index >= sizeof(index2setting) - 1) break; } TCA0.SPLIT.CTRLA = index2setting[index]; diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index e66e28d..6672885 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -26,51 +26,52 @@ #include "wiring_private.h" #include "pins_arduino.h" - void pinMode(uint8_t pin, uint8_t mode) { - uint8_t bit_mask = digitalPinToBitMask(pin); - - if ((bit_mask == NOT_A_PIN) || (mode > INPUT_PULLUP)) - return; - - PORT_t* port = digitalPinToPortStruct(pin); - if(port == NULL) - return; - - if(mode == OUTPUT){ - - /* Configure direction as output */ - port->DIRSET = bit_mask; - - } else { /* mode == INPUT or INPUT_PULLUP */ - - uint8_t bit_pos = digitalPinToBitPosition(pin); - /* Calculate where pin control register is */ - volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); - - /* Save state */ - uint8_t status = SREG; - cli(); - - /* Configure direction as input */ - port->DIRCLR = bit_mask; - - /* Configure pull-up resistor */ - if(mode == INPUT_PULLUP){ - - /* Enable pull-up */ - *pin_ctrl_reg |= PORT_PULLUPEN_bm; - - } else { /* mode == INPUT (no pullup) */ - - /* Disable pull-up */ - *pin_ctrl_reg &= ~(PORT_PULLUPEN_bm); - } - - /* Restore state */ - SREG = status; - } + uint8_t bit_mask = digitalPinToBitMask(pin); + + if ((bit_mask == NOT_A_PIN) || (mode > INPUT_PULLUP)) + return; + + PORT_t *port = digitalPinToPortStruct(pin); + if (port == NULL) + return; + + if (mode == OUTPUT) + { + /* Configure direction as output */ + port->DIRSET = bit_mask; + } + else + { /* mode == INPUT or INPUT_PULLUP */ + + uint8_t bit_pos = digitalPinToBitPosition(pin); + /* Calculate where pin control register is */ + volatile uint8_t *pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); + + /* Save state */ + uint8_t status = SREG; + cli(); + + /* Configure direction as input */ + port->DIRCLR = bit_mask; + + /* Configure pull-up resistor */ + if (mode == INPUT_PULLUP) + { + /* Enable pull-up */ + *pin_ctrl_reg |= PORT_PULLUPEN_bm; + } + else + { /* mode == INPUT (no pullup) */ + + /* Disable pull-up */ + *pin_ctrl_reg &= ~(PORT_PULLUPEN_bm); + } + + /* Restore state */ + SREG = status; + } } // Forcing this inline keeps the callers from having to push their own stuff @@ -90,163 +91,170 @@ void pinMode(uint8_t pin, uint8_t mode) //static inline void turnOffPWM(uint8_t timer) static void turnOffPWM(uint8_t pin) { - /* Actually turn off compare channel, not the timer */ - - /* Get pin's timer */ - uint8_t timer = digitalPinToTimer(pin); - if(timer == NOT_ON_TIMER) - return; + /* Actually turn off compare channel, not the timer */ - uint8_t bit_pos; - TCB_t *timerB; + /* Get pin's timer */ + uint8_t timer = digitalPinToTimer(pin); + if (timer == NOT_ON_TIMER) + return; - switch (timer) { + uint8_t bit_pos; + TCB_t *timerB; - /* TCA0 */ - case TIMERA0: - /* Bit position will give output channel */ - bit_pos = digitalPinToBitPosition(pin); + switch (timer) + { + /* TCA0 */ + case TIMERA0: + /* Bit position will give output channel */ + bit_pos = digitalPinToBitPosition(pin); - /* Disable corresponding channel */ - if (bit_pos >= 3) ++bit_pos; /* Upper 3 bits are shifted by 1 */ - TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); + /* Disable corresponding channel */ + if (bit_pos >= 3) ++bit_pos; /* Upper 3 bits are shifted by 1 */ + TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); - break; + break; - /* TCB - only one output */ - case TIMERB0: - case TIMERB1: - case TIMERB2: - case TIMERB3: + /* TCB - only one output */ + case TIMERB0: + case TIMERB1: + case TIMERB2: + case TIMERB3: - timerB = (TCB_t *)&TCB0 + (timer - TIMERB0); + timerB = (TCB_t *)&TCB0 + (timer - TIMERB0); - /* Disable TCB compare channel */ - timerB->CTRLB &= ~(TCB_CCMPEN_bm); + /* Disable TCB compare channel */ + timerB->CTRLB &= ~(TCB_CCMPEN_bm); - break; - default: - break; - } + break; + default: + break; + } } void digitalWrite(uint8_t pin, uint8_t val) { - /* Get bit mask for pin */ - uint8_t bit_mask = digitalPinToBitMask(pin); - if(bit_mask == NOT_A_PIN) - return; - - /* Turn off PWM if applicable */ - - // If the pin that support PWM output, we need to turn it off - // before doing a digital write. - turnOffPWM(pin); - - /* Assuming the direction is already output !! */ - - /* Get port */ - PORT_t *port = digitalPinToPortStruct(pin); - - /* Output direction */ - if(port->DIR & bit_mask){ - - /* Set output to value */ - if (val == LOW) { /* If LOW */ - port->OUTCLR = bit_mask; - - } else if (val == CHANGE) { /* If TOGGLE */ - port->OUTTGL = bit_mask; - /* If HIGH OR > TOGGLE */ - } else { - port->OUTSET = bit_mask; - } - - /* Input direction */ - } else { - /* Old implementation has side effect when pin set as input - - pull up is enabled if this function is called. - Should we purposely implement this side effect? - */ - - /* Get bit position for getting pin ctrl reg */ - uint8_t bit_pos = digitalPinToBitPosition(pin); - - /* Calculate where pin control register is */ - volatile uint8_t* pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); - - /* Save system status and disable interrupts */ - uint8_t status = SREG; - cli(); - - if(val == LOW){ - /* Disable pullup */ - *pin_ctrl_reg &= ~PORT_PULLUPEN_bm; - - } else { - /* Enable pull-up */ - *pin_ctrl_reg |= PORT_PULLUPEN_bm; - } - - /* Restore system status */ - SREG = status; - } + /* Get bit mask for pin */ + uint8_t bit_mask = digitalPinToBitMask(pin); + if (bit_mask == NOT_A_PIN) + return; + + /* Turn off PWM if applicable */ + + // If the pin that support PWM output, we need to turn it off + // before doing a digital write. + turnOffPWM(pin); + + /* Assuming the direction is already output !! */ + + /* Get port */ + PORT_t *port = digitalPinToPortStruct(pin); + + /* Output direction */ + if (port->DIR & bit_mask) + { + /* Set output to value */ + if (val == LOW) + { /* If LOW */ + port->OUTCLR = bit_mask; + } + else if (val == CHANGE) + { /* If TOGGLE */ + port->OUTTGL = bit_mask; + /* If HIGH OR > TOGGLE */ + } + else + { + port->OUTSET = bit_mask; + } + + /* Input direction */ + } + else + { + /* Old implementation has side effect when pin set as input - + pull up is enabled if this function is called. + Should we purposely implement this side effect? + */ + + /* Get bit position for getting pin ctrl reg */ + uint8_t bit_pos = digitalPinToBitPosition(pin); + + /* Calculate where pin control register is */ + volatile uint8_t *pin_ctrl_reg = getPINnCTRLregister(port, bit_pos); + + /* Save system status and disable interrupts */ + uint8_t status = SREG; + cli(); + + if (val == LOW) + { + /* Disable pullup */ + *pin_ctrl_reg &= ~PORT_PULLUPEN_bm; + } + else + { + /* Enable pull-up */ + *pin_ctrl_reg |= PORT_PULLUPEN_bm; + } + + /* Restore system status */ + SREG = status; + } } - inline __attribute__((always_inline)) void _dwfast(uint8_t pin, uint8_t val) { - // Mega-0, Tiny-1 style IOPORTs - // Assumes VPORTs exist starting at 0 for each PORT structure - uint8_t mask = 1 << digital_pin_to_bit_position[pin]; - uint8_t port = digital_pin_to_port[pin]; - VPORT_t *vport; - - // Write pin value from VPORTx.OUT register - vport = (VPORT_t *)(port * 4); - - if (val == HIGH) - vport->OUT |= mask; - else if (val == LOW) - vport->OUT &= ~mask; - else // CHANGE - vport->IN = mask; + // Mega-0, Tiny-1 style IOPORTs + // Assumes VPORTs exist starting at 0 for each PORT structure + uint8_t mask = 1 << digital_pin_to_bit_position[pin]; + uint8_t port = digital_pin_to_port[pin]; + VPORT_t *vport; + + // Write pin value from VPORTx.OUT register + vport = (VPORT_t *)(port * 4); + + if (val == HIGH) + vport->OUT |= mask; + else if (val == LOW) + vport->OUT &= ~mask; + else // CHANGE + vport->IN = mask; } uint8_t digitalRead(uint8_t pin) { - /* Get bit mask and check valid pin */ - uint8_t bit_mask = digitalPinToBitMask(pin); - if(bit_mask == NOT_A_PIN) - return LOW; + /* Get bit mask and check valid pin */ + uint8_t bit_mask = digitalPinToBitMask(pin); + if (bit_mask == NOT_A_PIN) + return LOW; - // If the pin that support PWM output, we need to turn it off - // before getting a digital reading. - turnOffPWM(pin); + // If the pin that support PWM output, we need to turn it off + // before getting a digital reading. + turnOffPWM(pin); - /* Get port and check valid port */ - PORT_t *port = digitalPinToPortStruct(pin); + /* Get port and check valid port */ + PORT_t *port = digitalPinToPortStruct(pin); - /* Read pin value from PORTx.IN register */ - if(port->IN & bit_mask) - return HIGH; - else - return LOW; + /* Read pin value from PORTx.IN register */ + if (port->IN & bit_mask) + return HIGH; + else + return LOW; - return LOW; + return LOW; } -inline __attribute__((always_inline)) uint8_t _drfast(uint8_t pin) +inline __attribute__((always_inline)) uint8_t _drfast(uint8_t pin) { - // Mega-0, Tiny-1 style IOPORTs - // Assumes VPORTs exist starting at 0 for each PORT structure - uint8_t mask = 1 << digital_pin_to_bit_position[pin]; - uint8_t port = digital_pin_to_port[pin]; - VPORT_t *vport; + // Mega-0, Tiny-1 style IOPORTs + // Assumes VPORTs exist starting at 0 for each PORT structure + uint8_t mask = 1 << digital_pin_to_bit_position[pin]; + uint8_t port = digital_pin_to_port[pin]; + VPORT_t *vport; - // Old style port logic is a small integer 0 for PORTA, 1 for PORTB etc. - vport = (VPORT_t *)(port * 4); + // Old style port logic is a small integer 0 for PORTA, 1 for PORTB etc. + vport = (VPORT_t *)(port * 4); - // Read pin value from VPORTx.IN register - return !!(vport->IN & mask); + // Read pin value from VPORTx.IN register + return !!(vport->IN & mask); } diff --git a/megaavr/cores/coreX-corefiles/wiring_private.h b/megaavr/cores/coreX-corefiles/wiring_private.h index 9597ed8..a38e94e 100644 --- a/megaavr/cores/coreX-corefiles/wiring_private.h +++ b/megaavr/cores/coreX-corefiles/wiring_private.h @@ -23,20 +23,21 @@ #ifndef WiringPrivate_h #define WiringPrivate_h -#include #include -#include +#include #include +#include #include "Arduino.h" #ifdef __cplusplus -extern "C"{ +extern "C" +{ #endif -uint32_t countPulseASM(volatile uint8_t *port, uint8_t bit, uint8_t stateMask, unsigned long maxloops); + uint32_t countPulseASM(volatile uint8_t *port, uint8_t bit, uint8_t stateMask, unsigned long maxloops); -typedef void (*voidFuncPtr)(void); + typedef void (*voidFuncPtr)(void); #ifdef __cplusplus } // extern "C" diff --git a/megaavr/cores/coreX-corefiles/wiring_pulse.c b/megaavr/cores/coreX-corefiles/wiring_pulse.c index 3d75cd8..c4fd7e4 100644 --- a/megaavr/cores/coreX-corefiles/wiring_pulse.c +++ b/megaavr/cores/coreX-corefiles/wiring_pulse.c @@ -20,8 +20,8 @@ Boston, MA 02111-1307 USA */ -#include "wiring_private.h" #include "pins_arduino.h" +#include "wiring_private.h" /* Measures the length (in microseconds) of a pulse on the pin; state is HIGH * or LOW, the type of pulse to measure. Works on pulses from 2-3 microseconds @@ -32,24 +32,24 @@ */ unsigned long pulseIn(uint8_t pin, uint8_t state, unsigned long timeout) { - // cache the port and bit of the pin in order to speed up the - // pulse width measuring loop and achieve finer resolution. calling - // digitalRead() instead yields much coarser resolution. - uint8_t bit = digitalPinToBitMask(pin); - uint8_t port = digitalPinToPort(pin); - uint8_t stateMask = (state ? bit : 0); + // cache the port and bit of the pin in order to speed up the + // pulse width measuring loop and achieve finer resolution. calling + // digitalRead() instead yields much coarser resolution. + uint8_t bit = digitalPinToBitMask(pin); + uint8_t port = digitalPinToPort(pin); + uint8_t stateMask = (state ? bit : 0); - // convert the timeout from microseconds to a number of times through - // the initial loop; it takes approximately 16 clock cycles per iteration - unsigned long maxloops = microsecondsToClockCycles(timeout)/12; + // convert the timeout from microseconds to a number of times through + // the initial loop; it takes approximately 16 clock cycles per iteration + unsigned long maxloops = microsecondsToClockCycles(timeout) / 12; - unsigned long width = countPulseASM(portInputRegister(port), bit, stateMask, maxloops); + unsigned long width = countPulseASM(portInputRegister(port), bit, stateMask, maxloops); - // prevent clockCyclesToMicroseconds to return bogus values if countPulseASM timed out - if (width) - return clockCyclesToMicroseconds(width * 16 + 16); - else - return 0; + // prevent clockCyclesToMicroseconds to return bogus values if countPulseASM timed out + if (width) + return clockCyclesToMicroseconds(width * 16 + 16); + else + return 0; } /* Measures the length (in microseconds) of a pulse on the pin; state is HIGH @@ -62,32 +62,35 @@ unsigned long pulseIn(uint8_t pin, uint8_t state, unsigned long timeout) */ unsigned long pulseInLong(uint8_t pin, uint8_t state, unsigned long timeout) { - // cache the port and bit of the pin in order to speed up the - // pulse width measuring loop and achieve finer resolution. calling - // digitalRead() instead yields much coarser resolution. - uint8_t bit = digitalPinToBitMask(pin); - uint8_t port = digitalPinToPort(pin); - uint8_t stateMask = (state ? bit : 0); + // cache the port and bit of the pin in order to speed up the + // pulse width measuring loop and achieve finer resolution. calling + // digitalRead() instead yields much coarser resolution. + uint8_t bit = digitalPinToBitMask(pin); + uint8_t port = digitalPinToPort(pin); + uint8_t stateMask = (state ? bit : 0); - unsigned long startMicros = micros(); + unsigned long startMicros = micros(); - // wait for any previous pulse to end - while ((*portInputRegister(port) & bit) == stateMask) { - if (micros() - startMicros > timeout) - return 0; - } + // wait for any previous pulse to end + while ((*portInputRegister(port) & bit) == stateMask) + { + if (micros() - startMicros > timeout) + return 0; + } - // wait for the pulse to start - while ((*portInputRegister(port) & bit) != stateMask) { - if (micros() - startMicros > timeout) - return 0; - } + // wait for the pulse to start + while ((*portInputRegister(port) & bit) != stateMask) + { + if (micros() - startMicros > timeout) + return 0; + } - unsigned long start = micros(); - // wait for the pulse to stop - while ((*portInputRegister(port) & bit) == stateMask) { - if (micros() - startMicros > timeout) - return 0; - } - return micros() - start; + unsigned long start = micros(); + // wait for the pulse to stop + while ((*portInputRegister(port) & bit) == stateMask) + { + if (micros() - startMicros > timeout) + return 0; + } + return micros() - start; } \ No newline at end of file diff --git a/megaavr/cores/coreX-corefiles/wiring_shift.c b/megaavr/cores/coreX-corefiles/wiring_shift.c index 441fcd3..6819e7e 100644 --- a/megaavr/cores/coreX-corefiles/wiring_shift.c +++ b/megaavr/cores/coreX-corefiles/wiring_shift.c @@ -20,34 +20,37 @@ Boston, MA 02111-1307 USA */ -#include - -uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder) { - uint8_t value = 0; - uint8_t i; - - for (i = 0; i < 8; ++i) { - digitalWrite(clockPin, HIGH); - if (bitOrder == LSBFIRST) - value |= digitalRead(dataPin) << i; - else - value |= digitalRead(dataPin) << (7 - i); - digitalWrite(clockPin, LOW); - } - return value; +#include "Arduino.h" + +uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder) +{ + uint8_t value = 0; + uint8_t i; + + for (i = 0; i < 8; ++i) + { + digitalWrite(clockPin, HIGH); + if (bitOrder == LSBFIRST) + value |= digitalRead(dataPin) << i; + else + value |= digitalRead(dataPin) << (7 - i); + digitalWrite(clockPin, LOW); + } + return value; } void shiftOut(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder, uint8_t val) { - uint8_t i; - - for (i = 0; i < 8; i++) { - if (bitOrder == LSBFIRST) - digitalWrite(dataPin, !!(val & (1 << i))); - else - digitalWrite(dataPin, !!(val & (1 << (7 - i)))); - - digitalWrite(clockPin, HIGH); - digitalWrite(clockPin, LOW); - } + uint8_t i; + + for (i = 0; i < 8; i++) + { + if (bitOrder == LSBFIRST) + digitalWrite(dataPin, !!(val & (1 << i))); + else + digitalWrite(dataPin, !!(val & (1 << (7 - i)))); + + digitalWrite(clockPin, HIGH); + digitalWrite(clockPin, LOW); + } } diff --git a/megaavr/libraries/EEPROM/src/EEPROM.h b/megaavr/libraries/EEPROM/src/EEPROM.h index 906bfaa..d700217 100644 --- a/megaavr/libraries/EEPROM/src/EEPROM.h +++ b/megaavr/libraries/EEPROM/src/EEPROM.h @@ -20,8 +20,8 @@ #ifndef EEPROM_h #define EEPROM_h -#include #include +#include /*** EERef class. @@ -30,59 +30,62 @@ This class has an overhead of two bytes, similar to storing a pointer to an EEPROM cell. ***/ -#define nvm_read_byte(idx) *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) - -void nvm_write_byte(uint16_t idx, uint8_t dat) { - *(uint8_t*)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) = dat; - uint8_t oldSREG = SREG; - cli(); - _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_PAGEERASEWRITE_gc); - SREG = oldSREG; - while (NVMCTRL.STATUS & NVMCTRL_EEBUSY_bm); +#define nvm_read_byte(idx) *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) + +void nvm_write_byte(uint16_t idx, uint8_t dat) +{ + *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) = dat; + uint8_t oldSREG = SREG; + cli(); + _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_PAGEERASEWRITE_gc); + SREG = oldSREG; + while (NVMCTRL.STATUS & NVMCTRL_EEBUSY_bm) + ; } - -struct EERef{ - - EERef( const int index ) - : index( index ) {} - - //Access/read members. - uint8_t operator*() const { return nvm_read_byte( index ); } - operator uint8_t() const { return **this; } - - //Assignment/write members. - EERef &operator=( const EERef &ref ) { return *this = *ref; } - EERef &operator=( uint8_t in ) { return nvm_write_byte( index, in ), *this; } - EERef &operator +=( uint8_t in ) { return *this = **this + in; } - EERef &operator -=( uint8_t in ) { return *this = **this - in; } - EERef &operator *=( uint8_t in ) { return *this = **this * in; } - EERef &operator /=( uint8_t in ) { return *this = **this / in; } - EERef &operator ^=( uint8_t in ) { return *this = **this ^ in; } - EERef &operator %=( uint8_t in ) { return *this = **this % in; } - EERef &operator &=( uint8_t in ) { return *this = **this & in; } - EERef &operator |=( uint8_t in ) { return *this = **this | in; } - EERef &operator <<=( uint8_t in ) { return *this = **this << in; } - EERef &operator >>=( uint8_t in ) { return *this = **this >> in; } - - EERef &update( uint8_t in ) { return in != *this ? *this = in : *this; } - - /** Prefix increment/decrement **/ - EERef& operator++() { return *this += 1; } - EERef& operator--() { return *this -= 1; } - - /** Postfix increment/decrement **/ - uint8_t operator++ (int){ - uint8_t ret = **this; - return ++(*this), ret; - } - - uint8_t operator-- (int){ - uint8_t ret = **this; - return --(*this), ret; - } - - int index; //Index of current EEPROM cell. +struct EERef +{ + EERef(const int index) + : index(index) {} + + //Access/read members. + uint8_t operator*() const { return nvm_read_byte(index); } + operator uint8_t() const { return **this; } + + //Assignment/write members. + EERef &operator=(const EERef &ref) { return *this = *ref; } + EERef &operator=(uint8_t in) { return nvm_write_byte(index, in), *this; } + EERef &operator+=(uint8_t in) { return *this = **this + in; } + EERef &operator-=(uint8_t in) { return *this = **this - in; } + EERef &operator*=(uint8_t in) { return *this = **this * in; } + EERef &operator/=(uint8_t in) { return *this = **this / in; } + EERef &operator^=(uint8_t in) { return *this = **this ^ in; } + EERef &operator%=(uint8_t in) { return *this = **this % in; } + EERef &operator&=(uint8_t in) { return *this = **this & in; } + EERef &operator|=(uint8_t in) { return *this = **this | in; } + EERef &operator<<=(uint8_t in) { return *this = **this << in; } + EERef &operator>>=(uint8_t in) { return *this = **this >> in; } + + EERef &update(uint8_t in) { return in != *this ? *this = in : *this; } + + /** Prefix increment/decrement **/ + EERef &operator++() { return *this += 1; } + EERef &operator--() { return *this -= 1; } + + /** Postfix increment/decrement **/ + uint8_t operator++(int) + { + uint8_t ret = **this; + return ++(*this), ret; + } + + uint8_t operator--(int) + { + uint8_t ret = **this; + return --(*this), ret; + } + + int index; //Index of current EEPROM cell. }; /*** @@ -92,25 +95,25 @@ struct EERef{ increment/decrement operators. ***/ -struct EEPtr{ - - EEPtr( const int index ) - : index( index ) {} +struct EEPtr +{ + EEPtr(const int index) + : index(index) {} - operator int() const { return index; } - EEPtr &operator=( int in ) { return index = in, *this; } + operator int() const { return index; } + EEPtr &operator=(int in) { return index = in, *this; } - //Iterator functionality. - bool operator!=( const EEPtr &ptr ) { return index != ptr.index; } - EERef operator*() { return index; } + //Iterator functionality. + bool operator!=(const EEPtr &ptr) { return index != ptr.index; } + EERef operator*() { return index; } - /** Prefix & Postfix increment/decrement **/ - EEPtr& operator++() { return ++index, *this; } - EEPtr& operator--() { return --index, *this; } - EEPtr operator++ (int) { return index++; } - EEPtr operator-- (int) { return index--; } + /** Prefix & Postfix increment/decrement **/ + EEPtr &operator++() { return ++index, *this; } + EEPtr &operator--() { return --index, *this; } + EEPtr operator++(int) { return index++; } + EEPtr operator--(int) { return index--; } - int index; //Index of current EEPROM cell. + int index; //Index of current EEPROM cell. }; /*** @@ -120,33 +123,37 @@ struct EEPtr{ This class is also 100% backwards compatible with earlier Arduino core releases. ***/ -struct EEPROMClass{ - - //Basic user access methods. - EERef operator[]( const int idx ) { return idx; } - uint8_t read( int idx ) { return EERef( idx ); } - void write( int idx, uint8_t val ) { (EERef( idx )) = val; } - void update( int idx, uint8_t val ) { EERef( idx ).update( val ); } - - //STL and C++11 iteration capability. - EEPtr begin() { return 0x00; } - EEPtr end() { return length(); } //Standards requires this to be the item after the last valid entry. The returned pointer is invalid. - uint16_t length() { return EEPROM_SIZE; } - - //Functionality to 'get' and 'put' objects to and from EEPROM. - template< typename T > T &get( int idx, T &t ){ - EEPtr e = idx; - uint8_t *ptr = (uint8_t*) &t; - for( int count = sizeof(T) ; count ; --count, ++e ) *ptr++ = *e; - return t; - } - - template< typename T > const T &put( int idx, const T &t ){ - EEPtr e = idx; - const uint8_t *ptr = (const uint8_t*) &t; - for( int count = sizeof(T) ; count ; --count, ++e ) (*e).update( *ptr++ ); - return t; - } +struct EEPROMClass +{ + //Basic user access methods. + EERef operator[](const int idx) { return idx; } + uint8_t read(int idx) { return EERef(idx); } + void write(int idx, uint8_t val) { (EERef(idx)) = val; } + void update(int idx, uint8_t val) { EERef(idx).update(val); } + + //STL and C++11 iteration capability. + EEPtr begin() { return 0x00; } + EEPtr end() { return length(); } //Standards requires this to be the item after the last valid entry. The returned pointer is invalid. + uint16_t length() { return EEPROM_SIZE; } + + //Functionality to 'get' and 'put' objects to and from EEPROM. + template + T &get(int idx, T &t) + { + EEPtr e = idx; + uint8_t *ptr = (uint8_t *)&t; + for (int count = sizeof(T); count; --count, ++e) *ptr++ = *e; + return t; + } + + template + const T &put(int idx, const T &t) + { + EEPtr e = idx; + const uint8_t *ptr = (const uint8_t *)&t; + for (int count = sizeof(T); count; --count, ++e) (*e).update(*ptr++); + return t; + } }; static EEPROMClass EEPROM; diff --git a/megaavr/libraries/HID/src/HID.cpp b/megaavr/libraries/HID/src/HID.cpp index 21ede26..32ad860 100644 --- a/megaavr/libraries/HID/src/HID.cpp +++ b/megaavr/libraries/HID/src/HID.cpp @@ -22,141 +22,162 @@ HID_& HID() { - static HID_ obj; - return obj; + static HID_ obj; + return obj; } int HID_::getInterface(uint8_t* interfaceCount) { - *interfaceCount += 1; // uses 1 - HIDDescriptor hidInterface = { - D_INTERFACE(pluggedInterface, 1, USB_DEVICE_CLASS_HUMAN_INTERFACE, HID_SUBCLASS_NONE, HID_PROTOCOL_NONE), - D_HIDREPORT(descriptorSize), - D_ENDPOINT(USB_ENDPOINT_IN(pluggedEndpoint), USB_ENDPOINT_TYPE_INTERRUPT, USB_EP_SIZE, 0x01) - }; - return USB_SendControl(0, &hidInterface, sizeof(hidInterface)); + *interfaceCount += 1; // uses 1 + HIDDescriptor hidInterface = { + D_INTERFACE(pluggedInterface, 1, USB_DEVICE_CLASS_HUMAN_INTERFACE, HID_SUBCLASS_NONE, HID_PROTOCOL_NONE), + D_HIDREPORT(descriptorSize), + D_ENDPOINT(USB_ENDPOINT_IN(pluggedEndpoint), USB_ENDPOINT_TYPE_INTERRUPT, USB_EP_SIZE, 0x01)}; + return USB_SendControl(0, &hidInterface, sizeof(hidInterface)); } int HID_::getDescriptor(USBSetup& setup) { - // Check if this is a HID Class Descriptor request - if (setup.bmRequestType != REQUEST_DEVICETOHOST_STANDARD_INTERFACE) { return 0; } - if (setup.wValueH != HID_REPORT_DESCRIPTOR_TYPE) { return 0; } - - // In a HID Class Descriptor wIndex cointains the interface number - if (setup.wIndex != pluggedInterface) { return 0; } - - int total = 0; - HIDSubDescriptor* node; - for (node = rootNode; node; node = node->next) { - int res = USB_SendControl(TRANSFER_PGM, node->data, node->length); - if (res == -1) - return -1; - total += res; - } - - // Reset the protocol on reenumeration. Normally the host should not assume the state of the protocol - // due to the USB specs, but Windows and Linux just assumes its in report mode. - protocol = HID_REPORT_PROTOCOL; - - return total; + // Check if this is a HID Class Descriptor request + if (setup.bmRequestType != REQUEST_DEVICETOHOST_STANDARD_INTERFACE) + { + return 0; + } + if (setup.wValueH != HID_REPORT_DESCRIPTOR_TYPE) + { + return 0; + } + + // In a HID Class Descriptor wIndex cointains the interface number + if (setup.wIndex != pluggedInterface) + { + return 0; + } + + int total = 0; + HIDSubDescriptor* node; + for (node = rootNode; node; node = node->next) + { + int res = USB_SendControl(TRANSFER_PGM, node->data, node->length); + if (res == -1) + return -1; + total += res; + } + + // Reset the protocol on reenumeration. Normally the host should not assume the state of the protocol + // due to the USB specs, but Windows and Linux just assumes its in report mode. + protocol = HID_REPORT_PROTOCOL; + + return total; } -uint8_t HID_::getShortName(char *name) +uint8_t HID_::getShortName(char* name) { - name[0] = 'H'; - name[1] = 'I'; - name[2] = 'D'; - name[3] = 'A' + (descriptorSize & 0x0F); - name[4] = 'A' + ((descriptorSize >> 4) & 0x0F); - return 5; + name[0] = 'H'; + name[1] = 'I'; + name[2] = 'D'; + name[3] = 'A' + (descriptorSize & 0x0F); + name[4] = 'A' + ((descriptorSize >> 4) & 0x0F); + return 5; } -void HID_::AppendDescriptor(HIDSubDescriptor *node) +void HID_::AppendDescriptor(HIDSubDescriptor* node) { - if (!rootNode) { - rootNode = node; - } else { - HIDSubDescriptor *current = rootNode; - while (current->next) { - current = current->next; - } - current->next = node; - } - descriptorSize += node->length; + if (!rootNode) + { + rootNode = node; + } + else + { + HIDSubDescriptor* current = rootNode; + while (current->next) + { + current = current->next; + } + current->next = node; + } + descriptorSize += node->length; } int HID_::SendReport(uint8_t id, const void* data, int len) { - auto ret = USB_Send(pluggedEndpoint, &id, 1); - if (ret < 0) return ret; - auto ret2 = USB_Send(pluggedEndpoint | TRANSFER_RELEASE, data, len); - if (ret2 < 0) return ret2; - return ret + ret2; + auto ret = USB_Send(pluggedEndpoint, &id, 1); + if (ret < 0) return ret; + auto ret2 = USB_Send(pluggedEndpoint | TRANSFER_RELEASE, data, len); + if (ret2 < 0) return ret2; + return ret + ret2; } bool HID_::setup(USBSetup& setup) { - if (pluggedInterface != setup.wIndex) { - return false; - } - - uint8_t request = setup.bRequest; - uint8_t requestType = setup.bmRequestType; - - if (requestType == REQUEST_DEVICETOHOST_CLASS_INTERFACE) - { - if (request == HID_GET_REPORT) { - // TODO: HID_GetReport(); - return true; - } - if (request == HID_GET_PROTOCOL) { - // TODO: Send8(protocol); - return true; - } - if (request == HID_GET_IDLE) { - // TODO: Send8(idle); - } - } - - if (requestType == REQUEST_HOSTTODEVICE_CLASS_INTERFACE) - { - if (request == HID_SET_PROTOCOL) { - // The USB Host tells us if we are in boot or report mode. - // This only works with a real boot compatible device. - protocol = setup.wValueL; - return true; - } - if (request == HID_SET_IDLE) { - idle = setup.wValueL; - return true; - } - if (request == HID_SET_REPORT) - { - //uint8_t reportID = setup.wValueL; - //uint16_t length = setup.wLength; - //uint8_t data[length]; - // Make sure to not read more data than USB_EP_SIZE. - // You can read multiple times through a loop. - // The first byte (may!) contain the reportID on a multreport. - //USB_RecvControl(data, length); - } - } - - return false; + if (pluggedInterface != setup.wIndex) + { + return false; + } + + uint8_t request = setup.bRequest; + uint8_t requestType = setup.bmRequestType; + + if (requestType == REQUEST_DEVICETOHOST_CLASS_INTERFACE) + { + if (request == HID_GET_REPORT) + { + // TODO: HID_GetReport(); + return true; + } + if (request == HID_GET_PROTOCOL) + { + // TODO: Send8(protocol); + return true; + } + if (request == HID_GET_IDLE) + { + // TODO: Send8(idle); + } + } + + if (requestType == REQUEST_HOSTTODEVICE_CLASS_INTERFACE) + { + if (request == HID_SET_PROTOCOL) + { + // The USB Host tells us if we are in boot or report mode. + // This only works with a real boot compatible device. + protocol = setup.wValueL; + return true; + } + if (request == HID_SET_IDLE) + { + idle = setup.wValueL; + return true; + } + if (request == HID_SET_REPORT) + { + //uint8_t reportID = setup.wValueL; + //uint16_t length = setup.wLength; + //uint8_t data[length]; + // Make sure to not read more data than USB_EP_SIZE. + // You can read multiple times through a loop. + // The first byte (may!) contain the reportID on a multreport. + //USB_RecvControl(data, length); + } + } + + return false; } HID_::HID_(void) : PluggableUSBModule(1, 1, epType), - rootNode(NULL), descriptorSize(0), - protocol(HID_REPORT_PROTOCOL), idle(1) + rootNode(NULL), + descriptorSize(0), + protocol(HID_REPORT_PROTOCOL), + idle(1) { - epType[0] = EP_TYPE_INTERRUPT_IN; - PluggableUSB().plug(this); + epType[0] = EP_TYPE_INTERRUPT_IN; + PluggableUSB().plug(this); } int HID_::begin(void) { - return 0; + return 0; } #endif /* if defined(USBCON) */ diff --git a/megaavr/libraries/HID/src/HID.h b/megaavr/libraries/HID/src/HID.h index ad2b06b..2f7bbb8 100644 --- a/megaavr/libraries/HID/src/HID.h +++ b/megaavr/libraries/HID/src/HID.h @@ -19,8 +19,9 @@ #ifndef HID_h #define HID_h -#include #include +#include + #include "api/PluggableUSB.h" #if defined(USBCON) @@ -29,16 +30,16 @@ // HID 'Driver' // ------------ -#define HID_GET_REPORT 0x01 -#define HID_GET_IDLE 0x02 -#define HID_GET_PROTOCOL 0x03 -#define HID_SET_REPORT 0x09 -#define HID_SET_IDLE 0x0A -#define HID_SET_PROTOCOL 0x0B +#define HID_GET_REPORT 0x01 +#define HID_GET_IDLE 0x02 +#define HID_GET_PROTOCOL 0x03 +#define HID_SET_REPORT 0x09 +#define HID_SET_IDLE 0x0A +#define HID_SET_PROTOCOL 0x0B -#define HID_HID_DESCRIPTOR_TYPE 0x21 -#define HID_REPORT_DESCRIPTOR_TYPE 0x22 -#define HID_PHYSICAL_DESCRIPTOR_TYPE 0x23 +#define HID_HID_DESCRIPTOR_TYPE 0x21 +#define HID_REPORT_DESCRIPTOR_TYPE 0x22 +#define HID_PHYSICAL_DESCRIPTOR_TYPE 0x23 // HID subclass HID1.11 Page 8 4.2 Subclass #define HID_SUBCLASS_NONE 0 @@ -51,18 +52,18 @@ // Normal or bios protocol (Keyboard/Mouse) HID1.11 Page 54 7.2.5 Get_Protocol Request // "protocol" variable is used for this purpose. -#define HID_BOOT_PROTOCOL 0 -#define HID_REPORT_PROTOCOL 1 +#define HID_BOOT_PROTOCOL 0 +#define HID_REPORT_PROTOCOL 1 // HID Request Type HID1.11 Page 51 7.2.1 Get_Report Request -#define HID_REPORT_TYPE_INPUT 1 -#define HID_REPORT_TYPE_OUTPUT 2 +#define HID_REPORT_TYPE_INPUT 1 +#define HID_REPORT_TYPE_OUTPUT 2 #define HID_REPORT_TYPE_FEATURE 3 typedef struct { - uint8_t len; // 9 - uint8_t dtype; // 0x21 + uint8_t len; // 9 + uint8_t dtype; // 0x21 uint8_t addr; uint8_t versionL; // 0x101 uint8_t versionH; // 0x101 @@ -72,17 +73,18 @@ typedef struct uint8_t descLenH; } HIDDescDescriptor; -typedef struct +typedef struct { InterfaceDescriptor hid; - HIDDescDescriptor desc; - EndpointDescriptor in; + HIDDescDescriptor desc; + EndpointDescriptor in; } HIDDescriptor; -class HIDSubDescriptor { -public: - HIDSubDescriptor *next = NULL; - HIDSubDescriptor(const void *d, const uint16_t l) : data(d), length(l) { } +class HIDSubDescriptor +{ + public: + HIDSubDescriptor* next = NULL; + HIDSubDescriptor(const void* d, const uint16_t l) : data(d), length(l) {} const void* data; const uint16_t length; @@ -90,20 +92,20 @@ class HIDSubDescriptor { class HID_ : public PluggableUSBModule { -public: + public: HID_(void); int begin(void); int SendReport(uint8_t id, const void* data, int len); void AppendDescriptor(HIDSubDescriptor* node); -protected: + protected: // Implementation of the PluggableUSBModule int getInterface(uint8_t* interfaceCount); int getDescriptor(USBSetup& setup); bool setup(USBSetup& setup); uint8_t getShortName(char* name); -private: + private: unsigned int epType[1]; HIDSubDescriptor* rootNode; @@ -118,7 +120,10 @@ class HID_ : public PluggableUSBModule // https://isocpp.org/wiki/faq/ctors#static-init-order-on-first-use HID_& HID(); -#define D_HIDREPORT(length) { 9, 0x21, 0x01, 0x01, 0, 1, 0x22, lowByte(length), highByte(length) } +#define D_HIDREPORT(length) \ + { \ + 9, 0x21, 0x01, 0x01, 0, 1, 0x22, lowByte(length), highByte(length) \ + } #else diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index b8922fd..826a59e 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -20,11 +20,12 @@ Modified 2017 by Chuck Todd (ctodd@cableone.net) to correct Unconfigured Slave Mode reboot */ -extern "C" { - #include - #include - #include - #include "utility/twi.h" +extern "C" +{ +#include +#include +#include +#include "utility/twi.h" } #include "Wire.h" @@ -34,13 +35,13 @@ extern "C" { // Initialize Class Variables ////////////////////////////////////////////////// uint8_t TwoWire::rxBuffer[BUFFER_LENGTH]; -uint8_t TwoWire::rxBufferIndex = 0; //head -uint8_t TwoWire::rxBufferLength = 0; //tail +uint8_t TwoWire::rxBufferIndex = 0; //head +uint8_t TwoWire::rxBufferLength = 0; //tail uint8_t TwoWire::txAddress = 0; uint8_t TwoWire::txBuffer[BUFFER_LENGTH]; -uint8_t TwoWire::txBufferIndex = 0; //head -uint8_t TwoWire::txBufferLength = 0; //tail +uint8_t TwoWire::txBufferIndex = 0; //head +uint8_t TwoWire::txBufferLength = 0; //tail uint8_t TwoWire::transmitting = 0; void (*TwoWire::user_onRequest)(void); @@ -63,45 +64,44 @@ bool TwoWire::pins(uint8_t sda_pin, uint8_t scl_pin) if (sda_pin == PIN_WIRE_SDA_PINSWAP_1 && scl_pin == PIN_WIRE_SCL_PINSWAP_1) { // Use pin swap - PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } - else if(sda_pin == PIN_WIRE_SDA && scl_pin == PIN_WIRE_SCL) + else if (sda_pin == PIN_WIRE_SDA && scl_pin == PIN_WIRE_SCL) { // Use default configuration - PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } else { // Assume default configuration - PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return false; } - #endif } bool TwoWire::swap(uint8_t state) { #if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) - if(state == 1) + if (state == 1) { // Use pin swap - PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX_PINSWAP | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } - else if(state == 0) + else if (state == 0) { // Use default configuration - PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } else { // Assume default configuration - PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3<<4)); + PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } #endif @@ -110,71 +110,73 @@ bool TwoWire::swap(uint8_t state) void TwoWire::begin(void) { - rxBufferIndex = 0; - rxBufferLength = 0; + rxBufferIndex = 0; + rxBufferLength = 0; - txBufferIndex = 0; - txBufferLength = 0; + txBufferIndex = 0; + txBufferLength = 0; - TWI_MasterInit(DEFAULT_FREQUENCY); + TWI_MasterInit(DEFAULT_FREQUENCY); } void TwoWire::begin(uint8_t address) { - rxBufferIndex = 0; - rxBufferLength = 0; - - txBufferIndex = 0; - txBufferLength = 0; - - TWI_SlaveInit(address); - - TWI_attachSlaveTxEvent(onRequestService, txBuffer); // default callback must exist - TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, BUFFER_LENGTH); // default callback must exist + rxBufferIndex = 0; + rxBufferLength = 0; + + txBufferIndex = 0; + txBufferLength = 0; + + TWI_SlaveInit(address); + + TWI_attachSlaveTxEvent(onRequestService, txBuffer); // default callback must exist + TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, BUFFER_LENGTH); // default callback must exist } void TwoWire::begin(int address) { - begin((uint8_t)address); + begin((uint8_t)address); } void TwoWire::end(void) { - TWI_Disable(); + TWI_Disable(); } void TwoWire::setClock(uint32_t clock) { - TWI_MasterSetBaud(clock); + TWI_MasterSetBaud(clock); } -uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity, bool sendStop) { - if(quantity > BUFFER_LENGTH){ - quantity = BUFFER_LENGTH; - } - - uint8_t bytes_read = TWI_MasterRead(address, rxBuffer, quantity, sendStop); - - /* Initialize read variables */ - rxBufferIndex = 0; - rxBufferLength = bytes_read; - - return bytes_read; +uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity, bool sendStop) +{ + if (quantity > BUFFER_LENGTH) + { + quantity = BUFFER_LENGTH; + } + + uint8_t bytes_read = TWI_MasterRead(address, rxBuffer, quantity, sendStop); + + /* Initialize read variables */ + rxBufferIndex = 0; + rxBufferLength = bytes_read; + + return bytes_read; } uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity) { - return requestFrom(address, quantity, true); + return requestFrom(address, quantity, true); } uint8_t TwoWire::requestFrom(int address, int quantity) { - return requestFrom((uint8_t)address, (size_t)quantity, true); + return requestFrom((uint8_t)address, (size_t)quantity, true); } uint8_t TwoWire::requestFrom(int address, int quantity, int sendStop) { - return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); + return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); } void TwoWire::beginTransmission(uint8_t address) @@ -190,15 +192,15 @@ void TwoWire::beginTransmission(uint8_t address) void TwoWire::beginTransmission(int address) { - beginTransmission((uint8_t)address); + beginTransmission((uint8_t)address); } // // Originally, 'endTransmission' was an f(void) function. // It has been modified to take one parameter indicating // whether or not a STOP should be performed on the bus. -// Calling endTransmission(false) allows a sketch to -// perform a repeated start. +// Calling endTransmission(false) allows a sketch to +// perform a repeated start. // // WARNING: Nothing in the library keeps track of whether // the bus tenure has been properly ended with a STOP. It @@ -208,17 +210,17 @@ void TwoWire::beginTransmission(int address) // uint8_t TwoWire::endTransmission(bool sendStop) { - // transmit buffer (blocking) - uint8_t status = TWI_MasterWrite(txAddress, txBuffer, txBufferLength, sendStop); - - // reset tx buffer iterator vars - txBufferIndex = 0; - txBufferLength = 0; - - // indicate that we are done transmitting - transmitting = 0; - - return status; + // transmit buffer (blocking) + uint8_t status = TWI_MasterWrite(txAddress, txBuffer, txBufferLength, sendStop); + + // reset tx buffer iterator vars + txBufferIndex = 0; + txBufferLength = 0; + + // indicate that we are done transmitting + transmitting = 0; + + return status; } // This provides backwards compatibility with the original @@ -234,20 +236,21 @@ uint8_t TwoWire::endTransmission(void) // or after beginTransmission(address) size_t TwoWire::write(uint8_t data) { - /* Check if buffer is full */ - if(txBufferLength >= BUFFER_LENGTH){ - setWriteError(); - return 0; - } - - /* Put byte in txBuffer */ - txBuffer[txBufferIndex] = data; - txBufferIndex++; - - /* Update buffer length */ - txBufferLength = txBufferIndex; - - return 1; + /* Check if buffer is full */ + if (txBufferLength >= BUFFER_LENGTH) + { + setWriteError(); + return 0; + } + + /* Put byte in txBuffer */ + txBuffer[txBufferIndex] = data; + txBufferIndex++; + + /* Update buffer length */ + txBufferLength = txBufferIndex; + + return 1; } // must be called in: @@ -255,12 +258,12 @@ size_t TwoWire::write(uint8_t data) // or after beginTransmission(address) size_t TwoWire::write(const uint8_t *data, size_t quantity) { + for (size_t i = 0; i < quantity; i++) + { + write(*(data + i)); + } - for(size_t i = 0; i < quantity; i++){ - write(*(data + i)); - } - - return quantity; + return quantity; } // must be called in: @@ -268,7 +271,7 @@ size_t TwoWire::write(const uint8_t *data, size_t quantity) // or after requestFrom(address, numBytes) int TwoWire::available(void) { - return rxBufferLength - rxBufferIndex; + return rxBufferLength - rxBufferIndex; } // must be called in: @@ -276,15 +279,16 @@ int TwoWire::available(void) // or after requestFrom(address, numBytes) int TwoWire::read(void) { - int value = -1; - - // get each successive byte on each call - if(rxBufferIndex < rxBufferLength){ - value = rxBuffer[rxBufferIndex]; - rxBufferIndex++; - } - - return value; + int value = -1; + + // get each successive byte on each call + if (rxBufferIndex < rxBufferLength) + { + value = rxBuffer[rxBufferIndex]; + rxBufferIndex++; + } + + return value; } // must be called in: @@ -292,85 +296,89 @@ int TwoWire::read(void) // or after requestFrom(address, numBytes) int TwoWire::peek(void) { - int value = -1; - - if(rxBufferIndex < rxBufferLength){ - value = rxBuffer[rxBufferIndex]; - } + int value = -1; + + if (rxBufferIndex < rxBufferLength) + { + value = rxBuffer[rxBufferIndex]; + } - return value; + return value; } -// can be used to get out of an error state in TWI module +// can be used to get out of an error state in TWI module // e.g. when MDATA regsiter is written before MADDR void TwoWire::flush(void) { -// /* Clear buffers */ -// for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ -// txBuffer[i] = 0; -// rxBuffer[i] = 0; -// } -// -// /* Clear buffer variables */ -// txBufferIndex = 0; -// txBufferLength = 0; -// rxBufferIndex = 0; -// rxBufferLength = 0; -// -// /* Turn off and on TWI module */ -// TWI_Flush(); + // /* Clear buffers */ + // for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ + // txBuffer[i] = 0; + // rxBuffer[i] = 0; + // } + // + // /* Clear buffer variables */ + // txBufferIndex = 0; + // txBufferLength = 0; + // rxBufferIndex = 0; + // rxBufferLength = 0; + // + // /* Turn off and on TWI module */ + // TWI_Flush(); } // behind the scenes function that is called when data is received void TwoWire::onReceiveService(int numBytes) { - // don't bother if user hasn't registered a callback - if(!user_onReceive){ - return; - } - // don't bother if rx buffer is in use by a master requestFrom() op - // i know this drops data, but it allows for slight stupidity - // meaning, they may not have read all the master requestFrom() data yet - if(rxBufferIndex < rxBufferLength){ - return; - } - - // set rx iterator vars - rxBufferIndex = 0; - rxBufferLength = numBytes; - - // alert user program - user_onReceive(numBytes); + // don't bother if user hasn't registered a callback + if (!user_onReceive) + { + return; + } + // don't bother if rx buffer is in use by a master requestFrom() op + // i know this drops data, but it allows for slight stupidity + // meaning, they may not have read all the master requestFrom() data yet + if (rxBufferIndex < rxBufferLength) + { + return; + } + + // set rx iterator vars + rxBufferIndex = 0; + rxBufferLength = numBytes; + + // alert user program + user_onReceive(numBytes); } // behind the scenes function that is called when data is requested uint8_t TwoWire::onRequestService(void) { - // don't bother if user hasn't registered a callback - if(!user_onRequest){ - return 0; - } - - // reset slave write buffer iterator var - txBufferIndex = 0; - txBufferLength = 0; - - // alert user program - user_onRequest(); - - return txBufferLength; + // don't bother if user hasn't registered a callback + if (!user_onRequest) + { + return 0; + } + + // reset slave write buffer iterator var + txBufferIndex = 0; + txBufferLength = 0; + + // alert user program + user_onRequest(); + + return txBufferLength; } // sets function called on slave write -void TwoWire::onReceive( void (*function)(int) ) +void TwoWire::onReceive(void (*function)(int)) { - user_onReceive = function; + user_onReceive = function; } // sets function called on slave read -void TwoWire::onRequest( void (*function)(void) ) +void TwoWire::onRequest(void (*function)(void)) { - user_onRequest = function; + user_onRequest = function; } // Preinstantiate Objects ////////////////////////////////////////////////////// diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index e566e9c..6249b70 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -21,33 +21,34 @@ *****************************************************************************/ #include "twi.h" + #include "Arduino.h" /* Master variables */ -static register8_t master_slaveAddress; /*!< Slave address */ -static register8_t* master_writeData; /*!< Data to write */ -static register8_t* master_readData; /*!< Read data */ -static register8_t master_bytesToWrite; /*!< Number of bytes to write */ -static register8_t master_bytesToRead; /*!< Number of bytes to read */ -static register8_t master_bytesWritten; /*!< Number of bytes written */ -static register8_t master_bytesRead; /*!< Number of bytes read */ -static register8_t master_sendStop; /*!< To send a stop at the end of the transaction or not */ -static register8_t master_trans_status; /*!< Status of transaction */ -static register8_t master_result; /*!< Result of transaction */ +static register8_t master_slaveAddress; /*!< Slave address */ +static register8_t* master_writeData; /*!< Data to write */ +static register8_t* master_readData; /*!< Read data */ +static register8_t master_bytesToWrite; /*!< Number of bytes to write */ +static register8_t master_bytesToRead; /*!< Number of bytes to read */ +static register8_t master_bytesWritten; /*!< Number of bytes written */ +static register8_t master_bytesRead; /*!< Number of bytes read */ +static register8_t master_sendStop; /*!< To send a stop at the end of the transaction or not */ +static register8_t master_trans_status; /*!< Status of transaction */ +static register8_t master_result; /*!< Result of transaction */ /* Slave variables */ static uint8_t (*TWI_onSlaveTransmit)(void) __attribute__((unused)); static void (*TWI_onSlaveReceive)(int) __attribute__((unused)); static register8_t* slave_writeData; static register8_t* slave_readData; -static register8_t slave_bytesToWrite; -static register8_t slave_bytesWritten; -static register8_t slave_bytesToRead; -static register8_t slave_bytesRead; -static register8_t slave_trans_status; -static register8_t slave_result; -static register8_t slave_callUserReceive; -static register8_t slave_callUserRequest; +static register8_t slave_bytesToWrite; +static register8_t slave_bytesWritten; +static register8_t slave_bytesToRead; +static register8_t slave_bytesRead; +static register8_t slave_trans_status; +static register8_t slave_result; +static register8_t slave_callUserReceive; +static register8_t slave_callUserRequest; /* TWI module mode */ static volatile TWI_MODE_t twi_mode; @@ -62,32 +63,32 @@ static volatile TWI_MODE_t twi_mode; */ void TWI_MasterInit(uint32_t frequency) { - if(twi_mode != TWI_MODE_UNKNOWN) return; - - // Enable input pullup for the default or pin swapped pin position - if((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) - { - pinMode(PIN_WIRE_SDA, INPUT_PULLUP); - pinMode(PIN_WIRE_SCL, INPUT_PULLUP); - } + if (twi_mode != TWI_MODE_UNKNOWN) return; + + // Enable input pullup for the default or pin swapped pin position + if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) + { + pinMode(PIN_WIRE_SDA, INPUT_PULLUP); + pinMode(PIN_WIRE_SCL, INPUT_PULLUP); + } #if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) - else if((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX_PINSWAP) - { - pinMode(PIN_WIRE_SDA_PINSWAP_1, INPUT_PULLUP); - pinMode(PIN_WIRE_SCL_PINSWAP_1, INPUT_PULLUP); - } + else if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX_PINSWAP) + { + pinMode(PIN_WIRE_SDA_PINSWAP_1, INPUT_PULLUP); + pinMode(PIN_WIRE_SCL_PINSWAP_1, INPUT_PULLUP); + } #endif - twi_mode = TWI_MODE_MASTER; - - master_bytesRead = 0; - master_bytesWritten = 0; - master_trans_status = TWIM_STATUS_READY; - master_result = TWIM_RESULT_UNKNOWN; - - TWI0.MCTRLA = TWI_RIEN_bm | TWI_WIEN_bm | TWI_ENABLE_bm; - TWI_MasterSetBaud(frequency); - TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; + twi_mode = TWI_MODE_MASTER; + + master_bytesRead = 0; + master_bytesWritten = 0; + master_trans_status = TWIM_STATUS_READY; + master_result = TWIM_RESULT_UNKNOWN; + + TWI0.MCTRLA = TWI_RIEN_bm | TWI_WIEN_bm | TWI_ENABLE_bm; + TWI_MasterSetBaud(frequency); + TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; } /*! \brief Initialize the TWI module as a slave. @@ -101,26 +102,27 @@ void TWI_MasterInit(uint32_t frequency) */ void TWI_SlaveInit(uint8_t address) { - if(twi_mode != TWI_MODE_UNKNOWN) return; - - twi_mode = TWI_MODE_SLAVE; - - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_trans_status = TWIS_STATUS_READY; - slave_result = TWIS_RESULT_UNKNOWN; - slave_callUserRequest = 0; - slave_callUserReceive = 0; - - TWI0.SADDR = address << 1; - TWI0.SCTRLA = TWI_DIEN_bm | TWI_APIEN_bm | TWI_PIEN_bm | TWI_ENABLE_bm; - - /* Bus Error Detection circuitry needs Master enabled to work */ - TWI0.MCTRLA = TWI_ENABLE_bm; + if (twi_mode != TWI_MODE_UNKNOWN) return; + + twi_mode = TWI_MODE_SLAVE; + + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_trans_status = TWIS_STATUS_READY; + slave_result = TWIS_RESULT_UNKNOWN; + slave_callUserRequest = 0; + slave_callUserReceive = 0; + + TWI0.SADDR = address << 1; + TWI0.SCTRLA = TWI_DIEN_bm | TWI_APIEN_bm | TWI_PIEN_bm | TWI_ENABLE_bm; + + /* Bus Error Detection circuitry needs Master enabled to work */ + TWI0.MCTRLA = TWI_ENABLE_bm; } -void TWI_Flush(void){ - TWI0.MCTRLB |= TWI_FLUSH_bm; +void TWI_Flush(void) +{ + TWI0.MCTRLB |= TWI_FLUSH_bm; } /*! \brief Disable the TWI module. @@ -132,13 +134,13 @@ void TWI_Flush(void){ */ void TWI_Disable(void) { - TWI0.MCTRLA = 0x00; - TWI0.MBAUD = 0x00; - TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; - TWI0.SADDR = 0x00; - TWI0.SCTRLA = 0x00; + TWI0.MCTRLA = 0x00; + TWI0.MBAUD = 0x00; + TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; + TWI0.SADDR = 0x00; + TWI0.SCTRLA = 0x00; - twi_mode = TWI_MODE_UNKNOWN; + twi_mode = TWI_MODE_UNKNOWN; } /*! \brief Returns the TWI bus state. @@ -155,12 +157,11 @@ void TWI_Disable(void) */ TWI_BUSSTATE_t TWI_MasterState(void) { - TWI_BUSSTATE_t twi_status; - twi_status = (TWI_BUSSTATE_t) (TWI0.MSTATUS & TWI_BUSSTATE_gm); - return twi_status; + TWI_BUSSTATE_t twi_status; + twi_status = (TWI_BUSSTATE_t)(TWI0.MSTATUS & TWI_BUSSTATE_gm); + return twi_status; } - /*! \brief Returns true if transaction is ready. * * This function returns a boolean whether the TWI Master is ready @@ -173,8 +174,8 @@ TWI_BUSSTATE_t TWI_MasterState(void) */ uint8_t TWI_MasterReady(void) { - uint8_t twi_status = (master_trans_status & TWIM_STATUS_READY); - return twi_status; + uint8_t twi_status = (master_trans_status & TWIM_STATUS_READY); + return twi_status; } /*! \brief Set the TWI baud rate. @@ -183,34 +184,37 @@ uint8_t TWI_MasterReady(void) * * \param frequency The required baud. */ -void TWI_MasterSetBaud(uint32_t frequency){ - -// Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; -// Where T_RISE varies depending on operating frequency... -// From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz - - uint16_t t_rise; - - if(frequency < 200000){ - frequency = 100000; - t_rise = 1000; - - } else if (frequency < 800000){ - frequency = 400000; - t_rise = 300; - - } else if (frequency < 1200000){ - frequency = 1000000; - t_rise = 120; - - } else { - frequency = 100000; - t_rise = 1000; - } - - uint32_t baud = ((F_CPU/frequency) - (((F_CPU*t_rise)/1000)/1000)/1000 - 10)/2; - TWI0.MBAUD = (uint8_t)baud; - +void TWI_MasterSetBaud(uint32_t frequency) +{ + // Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; + // Where T_RISE varies depending on operating frequency... + // From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz + + uint16_t t_rise; + + if (frequency < 200000) + { + frequency = 100000; + t_rise = 1000; + } + else if (frequency < 800000) + { + frequency = 400000; + t_rise = 300; + } + else if (frequency < 1200000) + { + frequency = 1000000; + t_rise = 120; + } + else + { + frequency = 100000; + t_rise = 1000; + } + + uint32_t baud = ((F_CPU / frequency) - (((F_CPU * t_rise) / 1000) / 1000) / 1000 - 10) / 2; + TWI0.MBAUD = (uint8_t)baud; } /*! \brief TWI write transaction. @@ -226,18 +230,17 @@ void TWI_MasterSetBaud(uint32_t frequency){ * \retval false If transaction could not be started. */ uint8_t TWI_MasterWrite(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t send_stop) + uint8_t* write_data, + uint8_t bytes_to_write, + uint8_t send_stop) { - return TWI_MasterWriteRead(slave_address, - write_data, - bytes_to_write, - 0, - send_stop); + return TWI_MasterWriteRead(slave_address, + write_data, + bytes_to_write, + 0, + send_stop); } - /*! \brief TWI read transaction. * * This function is a TWI Master wrapper for read-only transaction. @@ -250,21 +253,20 @@ uint8_t TWI_MasterWrite(uint8_t slave_address, * \retval false If transaction could not be started. */ uint8_t TWI_MasterRead(uint8_t slave_address, - uint8_t* read_data, - uint8_t bytes_to_read, - uint8_t send_stop) + uint8_t* read_data, + uint8_t bytes_to_read, + uint8_t send_stop) { - master_readData = read_data; - - uint8_t bytes_read = TWI_MasterWriteRead(slave_address, - 0, - 0, - bytes_to_read, - send_stop); - return bytes_read; + master_readData = read_data; + + uint8_t bytes_read = TWI_MasterWriteRead(slave_address, + 0, + 0, + bytes_to_read, + send_stop); + return bytes_read; } - /*! \brief TWI write and/or read transaction. * * This function is a TWI Master write and/or read transaction. The function @@ -284,91 +286,102 @@ uint8_t TWI_MasterRead(uint8_t slave_address, * \retval 4:other error */ uint8_t TWI_MasterWriteRead(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t bytes_to_read, - uint8_t send_stop) + uint8_t* write_data, + uint8_t bytes_to_write, + uint8_t bytes_to_read, + uint8_t send_stop) { - if(twi_mode != TWI_MODE_MASTER) return false; + if (twi_mode != TWI_MODE_MASTER) return false; - /*Initiate transaction if bus is ready. */ - if (master_trans_status == TWIM_STATUS_READY) { - - master_trans_status = TWIM_STATUS_BUSY; - master_result = TWIM_RESULT_UNKNOWN; + /*Initiate transaction if bus is ready. */ + if (master_trans_status == TWIM_STATUS_READY) + { + master_trans_status = TWIM_STATUS_BUSY; + master_result = TWIM_RESULT_UNKNOWN; - master_writeData = write_data; + master_writeData = write_data; - master_bytesToWrite = bytes_to_write; - master_bytesToRead = bytes_to_read; - master_bytesWritten = 0; - master_bytesRead = 0; - master_sendStop = send_stop; - master_slaveAddress = slave_address<<1; + master_bytesToWrite = bytes_to_write; + master_bytesToRead = bytes_to_read; + master_bytesWritten = 0; + master_bytesRead = 0; + master_sendStop = send_stop; + master_slaveAddress = slave_address << 1; -trigger_action: + trigger_action: - /* If write command, send the START condition + Address + + /* If write command, send the START condition + Address + * 'R/_W = 0' */ - if (master_bytesToWrite > 0) { - twi_mode = TWI_MODE_MASTER_TRANSMIT; - uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); - TWI0.MADDR = writeAddress; - } - - /* If read command, send the START condition + Address + + if (master_bytesToWrite > 0) + { + twi_mode = TWI_MODE_MASTER_TRANSMIT; + uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); + TWI0.MADDR = writeAddress; + } + + /* If read command, send the START condition + Address + * 'R/_W = 1' */ - else if (master_bytesToRead > 0) { - twi_mode = TWI_MODE_MASTER_RECEIVE; - uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); - TWI0.MADDR = readAddress; - } - - else if (master_bytesToWrite == 0 && master_bytesToRead == 0) { - twi_mode = TWI_MODE_MASTER_TRANSMIT; - uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); - TWI0.MADDR = writeAddress; - } - - /* Arduino requires blocking function */ - while(master_result == TWIM_RESULT_UNKNOWN) {} - - // in case of arbitration lost, retry sending - if (master_result == TWIM_RESULT_ARBITRATION_LOST) { - goto trigger_action; - } - - uint8_t ret = 0; - if (master_bytesToRead > 0) { - // return bytes really read - ret = master_bytesRead; - } else { - // return 0 if success, >0 otherwise (follow classic AVR conventions) - switch (master_result) { - case TWIM_RESULT_OK: - ret = 0; - break; - case TWIM_RESULT_BUFFER_OVERFLOW: - ret = 1; - break; - case TWIM_RESULT_NACK_RECEIVED: - ret = 3; - break; - default: - ret = 4; - break; - } - } - - return ret; - } else { - return 1; - } + else if (master_bytesToRead > 0) + { + twi_mode = TWI_MODE_MASTER_RECEIVE; + uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); + TWI0.MADDR = readAddress; + } + + else if (master_bytesToWrite == 0 && master_bytesToRead == 0) + { + twi_mode = TWI_MODE_MASTER_TRANSMIT; + uint8_t writeAddress = ADD_WRITE_BIT(master_slaveAddress); + TWI0.MADDR = writeAddress; + } + + /* Arduino requires blocking function */ + while (master_result == TWIM_RESULT_UNKNOWN) + { + } + + // in case of arbitration lost, retry sending + if (master_result == TWIM_RESULT_ARBITRATION_LOST) + { + goto trigger_action; + } + + uint8_t ret = 0; + if (master_bytesToRead > 0) + { + // return bytes really read + ret = master_bytesRead; + } + else + { + // return 0 if success, >0 otherwise (follow classic AVR conventions) + switch (master_result) + { + case TWIM_RESULT_OK: + ret = 0; + break; + case TWIM_RESULT_BUFFER_OVERFLOW: + ret = 1; + break; + case TWIM_RESULT_NACK_RECEIVED: + ret = 3; + break; + default: + ret = 4; + break; + } + } + + return ret; + } + else + { + return 1; + } } - /*! \brief Common TWI master interrupt service routine. * * Check current status and calls the appropriate handler. @@ -376,29 +389,32 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, */ void TWI_MasterInterruptHandler() { - uint8_t currentStatus = TWI0.MSTATUS; - - /* If arbitration lost or bus error. */ - if ((currentStatus & TWI_ARBLOST_bm) || - (currentStatus & TWI_BUSERR_bm)) { - - TWI_MasterArbitrationLostBusErrorHandler(); - } - - /* If master write interrupt. */ - else if (currentStatus & TWI_WIF_bm) { - TWI_MasterWriteHandler(); - } - - /* If master read interrupt. */ - else if (currentStatus & TWI_RIF_bm) { - TWI_MasterReadHandler(); - } - - /* If unexpected state. */ - else { - TWI_MasterTransactionFinished(TWIM_RESULT_FAIL); - } + uint8_t currentStatus = TWI0.MSTATUS; + + /* If arbitration lost or bus error. */ + if ((currentStatus & TWI_ARBLOST_bm) || + (currentStatus & TWI_BUSERR_bm)) + { + TWI_MasterArbitrationLostBusErrorHandler(); + } + + /* If master write interrupt. */ + else if (currentStatus & TWI_WIF_bm) + { + TWI_MasterWriteHandler(); + } + + /* If master read interrupt. */ + else if (currentStatus & TWI_RIF_bm) + { + TWI_MasterReadHandler(); + } + + /* If unexpected state. */ + else + { + TWI_MasterTransactionFinished(TWIM_RESULT_FAIL); + } } /*! \brief TWI master arbitration lost and bus error interrupt handler. @@ -408,26 +424,27 @@ void TWI_MasterInterruptHandler() */ void TWI_MasterArbitrationLostBusErrorHandler() { - uint8_t currentStatus = TWI0.MSTATUS; - - /* If bus error. */ - if (currentStatus & TWI_BUSERR_bm) { - master_result = TWIM_RESULT_BUS_ERROR; - } - /* If arbitration lost. */ - else { - master_result = TWIM_RESULT_ARBITRATION_LOST; - } - - /* Clear all flags, abort operation */ - TWI0.MSTATUS = currentStatus; - - /* Wait for a new operation */ - twi_mode = TWI_MODE_MASTER; - master_trans_status = TWIM_STATUS_READY; + uint8_t currentStatus = TWI0.MSTATUS; + + /* If bus error. */ + if (currentStatus & TWI_BUSERR_bm) + { + master_result = TWIM_RESULT_BUS_ERROR; + } + /* If arbitration lost. */ + else + { + master_result = TWIM_RESULT_ARBITRATION_LOST; + } + + /* Clear all flags, abort operation */ + TWI0.MSTATUS = currentStatus; + + /* Wait for a new operation */ + twi_mode = TWI_MODE_MASTER; + master_trans_status = TWIM_STATUS_READY; } - /*! \brief TWI master write interrupt handler. * * Handles TWI transactions (master write) and responses to (N)ACK. @@ -435,49 +452,57 @@ void TWI_MasterArbitrationLostBusErrorHandler() */ void TWI_MasterWriteHandler() { - /* Local variables used in if tests to avoid compiler warning. */ - uint8_t bytesToWrite = master_bytesToWrite; - uint8_t bytesToRead = master_bytesToRead; - - /* If NOT acknowledged (NACK) by slave cancel the transaction. */ - if (TWI0.MSTATUS & TWI_RXACK_bm) { - if(master_sendStop){ - TWI0.MCTRLB = TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; - - } - TWI_MasterTransactionFinished(TWIM_RESULT_NACK_RECEIVED); - } - - /* If more bytes to write, send data. */ - else if (master_bytesWritten < bytesToWrite) { - uint8_t data = master_writeData[master_bytesWritten]; - TWI0.MDATA = data; - master_bytesWritten++; - } - - /* If bytes to read, send START condition + Address + + /* Local variables used in if tests to avoid compiler warning. */ + uint8_t bytesToWrite = master_bytesToWrite; + uint8_t bytesToRead = master_bytesToRead; + + /* If NOT acknowledged (NACK) by slave cancel the transaction. */ + if (TWI0.MSTATUS & TWI_RXACK_bm) + { + if (master_sendStop) + { + TWI0.MCTRLB = TWI_MCMD_STOP_gc; + } + else + { + TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; + } + TWI_MasterTransactionFinished(TWIM_RESULT_NACK_RECEIVED); + } + + /* If more bytes to write, send data. */ + else if (master_bytesWritten < bytesToWrite) + { + uint8_t data = master_writeData[master_bytesWritten]; + TWI0.MDATA = data; + master_bytesWritten++; + } + + /* If bytes to read, send START condition + Address + * 'R/_W = 1' */ - else if (master_bytesRead < bytesToRead) { - twi_mode = TWI_MODE_MASTER_RECEIVE; - uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); - TWI0.MADDR = readAddress; - } - - /* If transaction finished, send ACK/STOP condition if instructed and set RESULT OK. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; - } - TWI_MasterTransactionFinished(TWIM_RESULT_OK); - } + else if (master_bytesRead < bytesToRead) + { + twi_mode = TWI_MODE_MASTER_RECEIVE; + uint8_t readAddress = ADD_READ_BIT(master_slaveAddress); + TWI0.MADDR = readAddress; + } + + /* If transaction finished, send ACK/STOP condition if instructed and set RESULT OK. */ + else + { + if (master_sendStop) + { + TWI0.MCTRLB = TWI_MCMD_STOP_gc; + } + else + { + TWI0.MCTRLB = TWI_MCMD_REPSTART_gc; + } + TWI_MasterTransactionFinished(TWIM_RESULT_OK); + } } - /*! \brief TWI master read interrupt handler. * * This is the master read interrupt handler that takes care of @@ -487,47 +512,56 @@ void TWI_MasterWriteHandler() */ void TWI_MasterReadHandler() { - /* Fetch data if bytes to be read. */ - if (master_bytesRead < master_bytesToRead) { - uint8_t data = TWI0.MDATA; - master_readData[master_bytesRead] = data; - master_bytesRead++; - } - - /* If buffer overflow, issue NACK/STOP and BUFFER_OVERFLOW condition. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; - } - - TWI_MasterTransactionFinished(TWIM_RESULT_BUFFER_OVERFLOW); - master_bytesToRead = 0; - return; - } - - /* Local variable used in if test to avoid compiler warning. */ - uint8_t bytesToRead = master_bytesToRead; - - /* If more bytes to read, issue ACK and start a byte read. */ - if (master_bytesRead < bytesToRead) { - TWI0.MCTRLB = TWI_MCMD_RECVTRANS_gc; - } - - /* If transaction finished, issue NACK and STOP condition if instructed. */ - else { - if(master_sendStop){ - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; - } else { - TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; - } - - TWI_MasterTransactionFinished(TWIM_RESULT_OK); - } + /* Fetch data if bytes to be read. */ + if (master_bytesRead < master_bytesToRead) + { + uint8_t data = TWI0.MDATA; + master_readData[master_bytesRead] = data; + master_bytesRead++; + } + + /* If buffer overflow, issue NACK/STOP and BUFFER_OVERFLOW condition. */ + else + { + if (master_sendStop) + { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; + } + else + { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; + } + + TWI_MasterTransactionFinished(TWIM_RESULT_BUFFER_OVERFLOW); + master_bytesToRead = 0; + return; + } + + /* Local variable used in if test to avoid compiler warning. */ + uint8_t bytesToRead = master_bytesToRead; + + /* If more bytes to read, issue ACK and start a byte read. */ + if (master_bytesRead < bytesToRead) + { + TWI0.MCTRLB = TWI_MCMD_RECVTRANS_gc; + } + + /* If transaction finished, issue NACK and STOP condition if instructed. */ + else + { + if (master_sendStop) + { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_STOP_gc; + } + else + { + TWI0.MCTRLB = TWI_ACKACT_bm | TWI_MCMD_REPSTART_gc; + } + + TWI_MasterTransactionFinished(TWIM_RESULT_OK); + } } - /*! \brief TWI transaction finished handler. * * Prepares module for new transaction. @@ -536,81 +570,88 @@ void TWI_MasterReadHandler() */ void TWI_MasterTransactionFinished(uint8_t result) { - master_result = result; - master_trans_status = TWIM_STATUS_READY; - twi_mode = TWI_MODE_MASTER; + master_result = result; + master_trans_status = TWIM_STATUS_READY; + twi_mode = TWI_MODE_MASTER; } - /*! \brief Common TWI slave interrupt service routine. * * Check current status and calls the appropriate handler. * */ -void TWI_SlaveInterruptHandler(){ - uint8_t currentStatus = TWI0.SSTATUS; - - /* If bus error */ - if(currentStatus & TWI_BUSERR_bm){ - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_bytesToWrite = 0; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUS_ERROR); - } - - /* If Address or Stop */ - else if(currentStatus & TWI_APIF_bm){ - - /* Call user onReceive function if end of Master Write/Slave Read. +void TWI_SlaveInterruptHandler() +{ + uint8_t currentStatus = TWI0.SSTATUS; + + /* If bus error */ + if (currentStatus & TWI_BUSERR_bm) + { + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_bytesToWrite = 0; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUS_ERROR); + } + + /* If Address or Stop */ + else if (currentStatus & TWI_APIF_bm) + { + /* Call user onReceive function if end of Master Write/Slave Read. * This should be hit when there is a STOP or REPSTART */ - if(slave_callUserReceive == 1){ - TWI_onSlaveReceive(slave_bytesRead); - slave_callUserReceive = 0; - } - - /* If address match */ - if(currentStatus & TWI_AP_bm){ - TWI_SlaveAddressMatchHandler(); - } - - /* If stop */ - else { - TWI_SlaveStopHandler(); - - /* If CLKHOLD is high, we have missed an address match + if (slave_callUserReceive == 1) + { + TWI_onSlaveReceive(slave_bytesRead); + slave_callUserReceive = 0; + } + + /* If address match */ + if (currentStatus & TWI_AP_bm) + { + TWI_SlaveAddressMatchHandler(); + } + + /* If stop */ + else + { + TWI_SlaveStopHandler(); + + /* If CLKHOLD is high, we have missed an address match from a fast start after stop. Because the flag is shared we need to handle this here. */ - if(TWI0.SSTATUS & TWI_CLKHOLD_bm){ - - /* CLKHOLD will be cleared by servicing the address match */ - TWI_SlaveAddressMatchHandler(); - } - } - } - - /* If Data Interrupt */ - else if (currentStatus & TWI_DIF_bm){ - - /* If collision flag is raised, slave transmit unsuccessful */ - if (currentStatus & TWI_COLL_bm){ - slave_bytesRead = 0; - slave_bytesWritten = 0; - slave_bytesToWrite = 0; - TWI_SlaveTransactionFinished(TWIS_RESULT_TRANSMIT_COLLISION); - } - - /* Otherwise, normal data interrupt */ - else { - TWI_SlaveDataHandler(); - } - } - - /* If unexpected state */ - else { - TWI_SlaveTransactionFinished(TWIS_RESULT_FAIL); - } + if (TWI0.SSTATUS & TWI_CLKHOLD_bm) + { + /* CLKHOLD will be cleared by servicing the address match */ + TWI_SlaveAddressMatchHandler(); + } + } + } + + /* If Data Interrupt */ + else if (currentStatus & TWI_DIF_bm) + { + /* If collision flag is raised, slave transmit unsuccessful */ + if (currentStatus & TWI_COLL_bm) + { + slave_bytesRead = 0; + slave_bytesWritten = 0; + slave_bytesToWrite = 0; + TWI_SlaveTransactionFinished(TWIS_RESULT_TRANSMIT_COLLISION); + } + + /* Otherwise, normal data interrupt */ + else + { + TWI_SlaveDataHandler(); + } + } + + /* If unexpected state */ + else + { + TWI_SlaveTransactionFinished(TWIS_RESULT_FAIL); + } } /*! \brief TWI slave address interrupt handler. @@ -619,40 +660,42 @@ void TWI_SlaveInterruptHandler(){ * being addressed by a master * */ -void TWI_SlaveAddressMatchHandler(){ - slave_trans_status = TWIS_STATUS_BUSY; - slave_result = TWIS_RESULT_UNKNOWN; - - /* Send ACK, wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - - /* If Master Read/Slave Write */ - if(TWI0.SSTATUS & TWI_DIR_bm){ - slave_bytesWritten = 0; - /* Call user function */ - slave_bytesToWrite = TWI_onSlaveTransmit(); - twi_mode = TWI_MODE_SLAVE_TRANSMIT; - } - /* If Master Write/Slave Read */ - else { - slave_bytesRead = 0; - slave_callUserReceive = 1; - twi_mode = TWI_MODE_SLAVE_RECEIVE; - } - - /* Data interrupt to follow... */ +void TWI_SlaveAddressMatchHandler() +{ + slave_trans_status = TWIS_STATUS_BUSY; + slave_result = TWIS_RESULT_UNKNOWN; + + /* Send ACK, wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + + /* If Master Read/Slave Write */ + if (TWI0.SSTATUS & TWI_DIR_bm) + { + slave_bytesWritten = 0; + /* Call user function */ + slave_bytesToWrite = TWI_onSlaveTransmit(); + twi_mode = TWI_MODE_SLAVE_TRANSMIT; + } + /* If Master Write/Slave Read */ + else + { + slave_bytesRead = 0; + slave_callUserReceive = 1; + twi_mode = TWI_MODE_SLAVE_RECEIVE; + } + + /* Data interrupt to follow... */ } /*! \brief TWI slave stop interrupt handler. * */ -void TWI_SlaveStopHandler(){ - - /* Clear APIF, don't ACK or NACK */ - TWI0.SSTATUS = TWI_APIF_bm; - - TWI_SlaveTransactionFinished(TWIS_RESULT_OK); - +void TWI_SlaveStopHandler() +{ + /* Clear APIF, don't ACK or NACK */ + TWI0.SSTATUS = TWI_APIF_bm; + + TWI_SlaveTransactionFinished(TWIS_RESULT_OK); } /*! \brief TWI slave data interrupt handler. @@ -661,23 +704,22 @@ void TWI_SlaveStopHandler(){ * receiving data from a master * */ -void TWI_SlaveDataHandler(){ - - /* Enable stop interrupt */ - TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); - - /* If Master Read/Slave Write */ - if(TWI0.SSTATUS & TWI_DIR_bm){ - - TWI_SlaveWriteHandler(); - } - - /* If Master Write/Slave Read */ - else { - TWI_SlaveReadHandler(); - } - - +void TWI_SlaveDataHandler() +{ + /* Enable stop interrupt */ + TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); + + /* If Master Read/Slave Write */ + if (TWI0.SSTATUS & TWI_DIR_bm) + { + TWI_SlaveWriteHandler(); + } + + /* If Master Write/Slave Read */ + else + { + TWI_SlaveReadHandler(); + } } /*! \brief TWI slave data write interrupt handler. @@ -685,37 +727,35 @@ void TWI_SlaveDataHandler(){ * This is the slave data handler that takes care of sending data to a master * */ -void TWI_SlaveWriteHandler(){ - - /* If NACK, slave write transaction finished */ - if((slave_bytesWritten > 0) && (TWI0.SSTATUS & TWI_RXACK_bm)){ - - TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_OK); - } - - /* If ACK, master expects more data */ - else { - - if(slave_bytesWritten < slave_bytesToWrite){ - uint8_t data = slave_writeData[slave_bytesWritten]; - TWI0.SDATA = data; - slave_bytesWritten++; - - /* Send data, wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - - } - - /* If buffer overflow */ - else { - TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); - - } - - - } +void TWI_SlaveWriteHandler() +{ + /* If NACK, slave write transaction finished */ + if ((slave_bytesWritten > 0) && (TWI0.SSTATUS & TWI_RXACK_bm)) + { + TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_OK); + } + + /* If ACK, master expects more data */ + else + { + if (slave_bytesWritten < slave_bytesToWrite) + { + uint8_t data = slave_writeData[slave_bytesWritten]; + TWI0.SDATA = data; + slave_bytesWritten++; + + /* Send data, wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + } + + /* If buffer overflow */ + else + { + TWI0.SCTRLB = TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); + } + } } /*! \brief TWI slave data read interrupt handler. @@ -723,25 +763,26 @@ void TWI_SlaveWriteHandler(){ * This is the slave data handler that takes care of receiving data from a master * */ -void TWI_SlaveReadHandler(){ - - /* If free space in buffer */ - if(slave_bytesRead < slave_bytesToRead){ - - /* Fetch data */ - uint8_t data = TWI0.SDATA; - slave_readData[slave_bytesRead] = data; - slave_bytesRead++; - - /* Send ACK and wait for data interrupt */ - TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; - } - /* If buffer overflow, send NACK and wait for next START. +void TWI_SlaveReadHandler() +{ + /* If free space in buffer */ + if (slave_bytesRead < slave_bytesToRead) + { + /* Fetch data */ + uint8_t data = TWI0.SDATA; + slave_readData[slave_bytesRead] = data; + slave_bytesRead++; + + /* Send ACK and wait for data interrupt */ + TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; + } + /* If buffer overflow, send NACK and wait for next START. Set result buffer overflow */ - else { - TWI0.SCTRLB = TWI_ACKACT_bm | TWI_SCMD_COMPTRANS_gc; - TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); - } + else + { + TWI0.SCTRLB = TWI_ACKACT_bm | TWI_SCMD_COMPTRANS_gc; + TWI_SlaveTransactionFinished(TWIS_RESULT_BUFFER_OVERFLOW); + } } /* @@ -750,7 +791,8 @@ void TWI_SlaveReadHandler(){ * Input function: callback function to use * Output none */ -void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ){ +void TWI_attachSlaveRxEvent(void (*function)(int), uint8_t* read_data, uint8_t bytes_to_read) +{ TWI_onSlaveReceive = function; slave_readData = read_data; slave_bytesToRead = bytes_to_read; @@ -762,12 +804,12 @@ void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t * Input function: callback function to use * Output none */ -void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t* write_data ){ +void TWI_attachSlaveTxEvent(uint8_t (*function)(void), uint8_t* write_data) +{ TWI_onSlaveTransmit = function; slave_writeData = write_data; } - /*! \brief TWI slave transaction finished handler. * * Prepares module for new transaction. @@ -776,16 +818,18 @@ void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t* write_data ){ */ void TWI_SlaveTransactionFinished(uint8_t result) { - TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); - twi_mode = TWI_MODE_SLAVE; - slave_result = result; - slave_trans_status = TWIM_STATUS_READY; + TWI0.SCTRLA |= (TWI_APIEN_bm | TWI_PIEN_bm); + twi_mode = TWI_MODE_SLAVE; + slave_result = result; + slave_trans_status = TWIM_STATUS_READY; } -ISR(TWI0_TWIM_vect){ - TWI_MasterInterruptHandler(); +ISR(TWI0_TWIM_vect) +{ + TWI_MasterInterruptHandler(); } -ISR(TWI0_TWIS_vect){ - TWI_SlaveInterruptHandler(); +ISR(TWI0_TWIS_vect) +{ + TWI_SlaveInterruptHandler(); } \ No newline at end of file diff --git a/megaavr/libraries/Wire/src/utility/twi.h b/megaavr/libraries/Wire/src/utility/twi.h index 401f118..e58f524 100644 --- a/megaavr/libraries/Wire/src/utility/twi.h +++ b/megaavr/libraries/Wire/src/utility/twi.h @@ -26,49 +26,52 @@ #include "avr/io.h" /*! Transaction status defines. */ -#define TWIM_STATUS_READY 0 -#define TWIM_STATUS_BUSY 1 +#define TWIM_STATUS_READY 0 +#define TWIM_STATUS_BUSY 1 /* Transaction status defines.*/ -#define TWIS_STATUS_READY 0 -#define TWIS_STATUS_BUSY 1 +#define TWIS_STATUS_READY 0 +#define TWIS_STATUS_BUSY 1 /*! Transaction result enumeration. */ -typedef enum TWIM_RESULT_enum { - TWIM_RESULT_UNKNOWN = (0x00<<0), - TWIM_RESULT_OK = (0x01<<0), - TWIM_RESULT_BUFFER_OVERFLOW = (0x02<<0), - TWIM_RESULT_ARBITRATION_LOST = (0x03<<0), - TWIM_RESULT_BUS_ERROR = (0x04<<0), - TWIM_RESULT_NACK_RECEIVED = (0x05<<0), - TWIM_RESULT_FAIL = (0x06<<0), +typedef enum TWIM_RESULT_enum +{ + TWIM_RESULT_UNKNOWN = (0x00 << 0), + TWIM_RESULT_OK = (0x01 << 0), + TWIM_RESULT_BUFFER_OVERFLOW = (0x02 << 0), + TWIM_RESULT_ARBITRATION_LOST = (0x03 << 0), + TWIM_RESULT_BUS_ERROR = (0x04 << 0), + TWIM_RESULT_NACK_RECEIVED = (0x05 << 0), + TWIM_RESULT_FAIL = (0x06 << 0), } TWIM_RESULT_t; /* Transaction result enumeration */ -typedef enum TWIS_RESULT_enum { - TWIS_RESULT_UNKNOWN = (0x00<<0), - TWIS_RESULT_OK = (0x01<<0), - TWIS_RESULT_BUFFER_OVERFLOW = (0x02<<0), - TWIS_RESULT_TRANSMIT_COLLISION = (0x03<<0), - TWIS_RESULT_BUS_ERROR = (0x04<<0), - TWIS_RESULT_FAIL = (0x05<<0), - TWIS_RESULT_ABORTED = (0x06<<0), +typedef enum TWIS_RESULT_enum +{ + TWIS_RESULT_UNKNOWN = (0x00 << 0), + TWIS_RESULT_OK = (0x01 << 0), + TWIS_RESULT_BUFFER_OVERFLOW = (0x02 << 0), + TWIS_RESULT_TRANSMIT_COLLISION = (0x03 << 0), + TWIS_RESULT_BUS_ERROR = (0x04 << 0), + TWIS_RESULT_FAIL = (0x05 << 0), + TWIS_RESULT_ABORTED = (0x06 << 0), } TWIS_RESULT_t; /*! TWI Modes */ -typedef enum TWI_MODE_enum { - TWI_MODE_UNKNOWN = 0, - TWI_MODE_MASTER = 1, - TWI_MODE_SLAVE = 2, - TWI_MODE_MASTER_TRANSMIT = 3, - TWI_MODE_MASTER_RECEIVE = 4, - TWI_MODE_SLAVE_TRANSMIT = 5, - TWI_MODE_SLAVE_RECEIVE = 6 +typedef enum TWI_MODE_enum +{ + TWI_MODE_UNKNOWN = 0, + TWI_MODE_MASTER = 1, + TWI_MODE_SLAVE = 2, + TWI_MODE_MASTER_TRANSMIT = 3, + TWI_MODE_MASTER_RECEIVE = 4, + TWI_MODE_SLAVE_TRANSMIT = 5, + TWI_MODE_SLAVE_RECEIVE = 6 } TWI_MODE_t; /*! For adding R/_W bit to address */ -#define ADD_READ_BIT(address) (address | 0x01) -#define ADD_WRITE_BIT(address) (address & ~0x01) +#define ADD_READ_BIT(address) (address | 0x01) +#define ADD_WRITE_BIT(address) (address & ~0x01) void TWI_MasterInit(uint32_t frequency); void TWI_SlaveInit(uint8_t address); @@ -78,18 +81,18 @@ TWI_BUSSTATE_t TWI_MasterState(void); uint8_t TWI_MasterReady(void); void TWI_MasterSetBaud(uint32_t frequency); uint8_t TWI_MasterWrite(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t send_stop); + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t send_stop); uint8_t TWI_MasterRead(uint8_t slave_address, - uint8_t* read_data, - uint8_t bytes_to_read, - uint8_t send_stop); + uint8_t *read_data, + uint8_t bytes_to_read, + uint8_t send_stop); uint8_t TWI_MasterWriteRead(uint8_t slave_address, - uint8_t *write_data, - uint8_t bytes_to_write, - uint8_t bytes_to_read, - uint8_t send_stop); + uint8_t *write_data, + uint8_t bytes_to_write, + uint8_t bytes_to_read, + uint8_t send_stop); void TWI_MasterInterruptHandler(void); void TWI_MasterArbitrationLostBusErrorHandler(void); void TWI_MasterWriteHandler(void); @@ -102,8 +105,8 @@ void TWI_SlaveStopHandler(void); void TWI_SlaveDataHandler(void); void TWI_SlaveWriteHandler(void); void TWI_SlaveReadHandler(void); -void TWI_attachSlaveRxEvent( void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read ); -void TWI_attachSlaveTxEvent( uint8_t (*function)(void), uint8_t *write_data ); +void TWI_attachSlaveRxEvent(void (*function)(int), uint8_t *read_data, uint8_t bytes_to_read); +void TWI_attachSlaveTxEvent(uint8_t (*function)(void), uint8_t *write_data); void TWI_SlaveTransactionFinished(uint8_t result); /*! TWI master interrupt service routine. * @@ -112,16 +115,15 @@ void TWI_SlaveTransactionFinished(uint8_t result); * - ISR(TWI0_TWIM_vect){ - TWI_MasterInterruptHandler(); - } + ISR(TWI0_TWIM_vect){ + TWI_MasterInterruptHandler(); + } - ISR(TWI0_TWIS_vect){ - TWI_SlaveInterruptHandler(); - } + ISR(TWI0_TWIS_vect){ + TWI_SlaveInterruptHandler(); + } * - */ - + */ #endif /* TWI_DRIVER_H */ From c25a982594d54350e82698b2ad8fd232bce4a24e Mon Sep 17 00:00:00 2001 From: "Spence Konde (aka Dr. Azzy)" Date: Thu, 16 Apr 2020 22:53:46 -0400 Subject: [PATCH 138/351] Change wire to a Stream instead of HardwareI2C See https://github.com/SpenceKonde/megaTinyCore/pull/130 Losing the stupid HardwareI2C typing prevents it from pulling in a flash-wasting vtable., and as far as I can no libraries in circulation that depend on it being a HardwareI2C. --- megaavr/libraries/Wire/src/Wire.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index 8c30eae..3ff1272 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -28,7 +28,7 @@ // WIRE_HAS_END means Wire has end() #define WIRE_HAS_END 1 -class TwoWire : public HardwareI2C +class TwoWire : public Stream { private: static uint8_t rxBuffer[]; From 7714ac9053b540145ae3191f394fe605ba76798d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 17 Apr 2020 22:37:12 +0200 Subject: [PATCH 139/351] Improve micros() accuracy --- megaavr/cores/coreX-corefiles/wiring.c | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 6de6bae..2ba73b8 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -118,7 +118,28 @@ unsigned long micros() // Restore SREG SREG = status; - return (m * 1000L) + (t / (TIME_TRACKING_TIMER_COUNT / 1000)); +#if (F_CPU == 20000000L) + t = t >> 4; + return m * 1000 + (t - (t >> 2) + (t >> 4) - (t >> 6)); +#elif (F_CPU == 16000000L) + return m * 1000 + (t >> 4); +#elif (F_CPU == 10000000L) + t = t >> 3; + return m * 1000 + (t - (t >> 2) + (t >> 4) - (t >> 6)); +#elif (F_CPU == 8000000L) + return m * 1000 + (t >> 3); +#elif (F_CPU == 5000000L) + t = t >> 2; + return m * 1000 + (t - (t >> 2) + (t >> 4) - (t >> 6)); +#elif (F_CPU == 4000000L) + return m * 1000 + (t >> 2); +#elif (F_CPU == 2000000L) + return m * 1000 + (t >> 1); +#elif (F_CPU == 1000000L) + return m * 1000 + t; +#else + return 0; +#endif } void delay(unsigned long ms) From 7e1a09faaec6f3705f6c955a794e8a5f8cd5bc95 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 17 Apr 2020 22:47:33 +0200 Subject: [PATCH 140/351] Move pin macros Was not accessable when placed inside ARDUINO_MAIN --- .../variants/28pin-standard/pins_arduino.h | 50 +++++------ .../variants/32pin-standard/pins_arduino.h | 56 ++++++------ .../variants/48pin-standard/pins_arduino.h | 84 +++++++++--------- megaavr/variants/nano-every/pins_arduino.h | 84 +++++++++--------- megaavr/variants/uno-wifi/pins_arduino.h | 85 +++++++++---------- 5 files changed, 179 insertions(+), 180 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 49b7a8d..05b054d 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -136,7 +136,31 @@ static const uint8_t A5 = PIN_A5; static const uint8_t A6 = PIN_A6; static const uint8_t A7 = PIN_A7; -#define PINS_COUNT (27u) +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF6 22 + +#define PINS_COUNT (23u) #ifdef ARDUINO_MAIN @@ -220,30 +244,6 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 22 PF6 RESET }; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PC0 8 -#define PIN_PC1 9 -#define PIN_PC2 10 -#define PIN_PC3 11 -#define PIN_PD0 12 -#define PIN_PD1 13 -#define PIN_PD2 14 -#define PIN_PD3 15 -#define PIN_PD4 16 -#define PIN_PD5 17 -#define PIN_PD6 18 -#define PIN_PD7 19 -#define PIN_PF0 20 -#define PIN_PF1 21 -#define PIN_PF6 22 - const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index f9d29ef..816b2ee 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -151,6 +151,34 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF2 22 +#define PIN_PF3 23 +#define PIN_PF4 24 +#define PIN_PF5 25 +#define PIN_PF6 26 + #define PINS_COUNT (27u) #ifdef ARDUINO_MAIN @@ -247,34 +275,6 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 26 PF6 RESET }; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PC0 8 -#define PIN_PC1 9 -#define PIN_PC2 10 -#define PIN_PC3 11 -#define PIN_PD0 12 -#define PIN_PD1 13 -#define PIN_PD2 14 -#define PIN_PD3 15 -#define PIN_PD4 16 -#define PIN_PD5 17 -#define PIN_PD6 18 -#define PIN_PD7 19 -#define PIN_PF0 20 -#define PIN_PF1 21 -#define PIN_PF2 22 -#define PIN_PF3 23 -#define PIN_PF4 24 -#define PIN_PF5 25 -#define PIN_PF6 26 - const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index f7fb1e8..66fdd34 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -182,6 +182,48 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PB0 8 +#define PIN_PB1 9 +#define PIN_PB2 10 +#define PIN_PB3 11 +#define PIN_PB4 12 +#define PIN_PB5 13 +#define PIN_PC0 14 +#define PIN_PC1 15 +#define PIN_PC2 16 +#define PIN_PC3 17 +#define PIN_PC4 18 +#define PIN_PC5 19 +#define PIN_PC6 20 +#define PIN_PC7 21 +#define PIN_PD0 22 +#define PIN_PD1 23 +#define PIN_PD2 24 +#define PIN_PD3 25 +#define PIN_PD4 26 +#define PIN_PD5 27 +#define PIN_PD6 28 +#define PIN_PD7 29 +#define PIN_PE0 30 +#define PIN_PE1 31 +#define PIN_PE2 32 +#define PIN_PE3 33 +#define PIN_PF0 34 +#define PIN_PF1 35 +#define PIN_PF2 36 +#define PIN_PF3 37 +#define PIN_PF4 38 +#define PIN_PF5 39 +#define PIN_PF6 40 + #define PINS_COUNT (41u) @@ -321,48 +363,6 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PB0 8 -#define PIN_PB1 9 -#define PIN_PB2 10 -#define PIN_PB3 11 -#define PIN_PB4 12 -#define PIN_PB5 13 -#define PIN_PC0 14 -#define PIN_PC1 15 -#define PIN_PC2 16 -#define PIN_PC3 17 -#define PIN_PC4 18 -#define PIN_PC5 19 -#define PIN_PC6 20 -#define PIN_PC7 21 -#define PIN_PD0 22 -#define PIN_PD1 23 -#define PIN_PD2 24 -#define PIN_PD3 25 -#define PIN_PD4 26 -#define PIN_PD5 27 -#define PIN_PD6 28 -#define PIN_PD7 29 -#define PIN_PE0 30 -#define PIN_PE1 31 -#define PIN_PE2 32 -#define PIN_PE3 33 -#define PIN_PF0 34 -#define PIN_PF1 35 -#define PIN_PF2 36 -#define PIN_PF3 37 -#define PIN_PF4 38 -#define PIN_PF5 39 -#define PIN_PF6 40 - const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index d05539d..de51a6d 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -155,6 +155,48 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD3 14 +#define PIN_PD2 15 +#define PIN_PD1 16 +#define PIN_PD0 17 +#define PIN_PF2 18 +#define PIN_PF3 19 +#define PIN_PD4 20 +#define PIN_PD5 21 +#define PIN_PA2 22 +#define PIN_PA3 23 +#define PIN_PB5 24 +#define PIN_PB4 25 +#define PIN_PC3 26 +#define PIN_PA5 27 +#define PIN_PA4 28 +#define PIN_PD6 29 +#define PIN_PA6 30 +#define PIN_PA7 31 +#define PIN_PB3 32 +#define PIN_PC7 33 +#define PIN_PC0 34 +#define PIN_PC1 35 +#define PIN_PC2 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + #define PINS_COUNT (41u) #ifdef ARDUINO_MAIN @@ -293,48 +335,6 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm, // 40 PF6/RESET }; -#define PIN_PC5 0 -#define PIN_PC4 1 -#define PIN_PA0 2 -#define PIN_PF5 3 -#define PIN_PC6 4 -#define PIN_PB2 5 -#define PIN_PF4 6 -#define PIN_PA1 7 -#define PIN_PE3 8 -#define PIN_PB0 9 -#define PIN_PB1 10 -#define PIN_PE0 11 -#define PIN_PE1 12 -#define PIN_PE2 13 -#define PIN_PD3 14 -#define PIN_PD2 15 -#define PIN_PD1 16 -#define PIN_PD0 17 -#define PIN_PF2 18 -#define PIN_PF3 19 -#define PIN_PD4 20 -#define PIN_PD5 21 -#define PIN_PA2 22 -#define PIN_PA3 23 -#define PIN_PB5 24 -#define PIN_PB4 25 -#define PIN_PC3 26 -#define PIN_PA5 27 -#define PIN_PA4 28 -#define PIN_PD6 29 -#define PIN_PA6 30 -#define PIN_PA7 31 -#define PIN_PB3 32 -#define PIN_PC7 33 -#define PIN_PC0 34 -#define PIN_PC1 35 -#define PIN_PC2 36 -#define PIN_PF0 37 -#define PIN_PF1 38 -#define PIN_PD7 39 -#define PIN_PF6 40 - const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PC5/USART1_Rx_alt NOT_ON_TIMER, // 1 PC4/USART1_Tx_alt diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 49d59d6..05ca198 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -172,6 +172,48 @@ static const uint8_t A15 = PIN_A15; #define SPIIMU_SS (30u) #define SPIIMU_INT (31u) +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD0 14 +#define PIN_PD1 15 +#define PIN_PD2 16 +#define PIN_PD3 17 +#define PIN_PD4 18 +#define PIN_PD5 19 +#define PIN_PA2 20 +#define PIN_PA3 21 +#define PIN_PC3 22 +#define PIN_PA5 23 +#define PIN_PA4 24 +#define PIN_PD6 25 +#define PIN_PB5 26 +#define PIN_PB4 27 +#define PIN_PA6 28 +#define PIN_PA7 29 +#define PIN_PB3 30 +#define PIN_PC7 31 +#define PIN_PC0 32 +#define PIN_PC1 33 +#define PIN_PC2 34 +#define PIN_PF2 35 +#define PIN_PF3 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + #ifdef ARDUINO_MAIN // On the Arduino board, digital pins are also used @@ -339,49 +381,6 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN6_bm // 40 PF6 RESET }; - -#define PIN_PC5 0 -#define PIN_PC4 1 -#define PIN_PA0 2 -#define PIN_PF5 3 -#define PIN_PC6 4 -#define PIN_PB2 5 -#define PIN_PF4 6 -#define PIN_PA1 7 -#define PIN_PE3 8 -#define PIN_PB0 9 -#define PIN_PB1 10 -#define PIN_PE0 11 -#define PIN_PE1 12 -#define PIN_PE2 13 -#define PIN_PD0 14 -#define PIN_PD1 15 -#define PIN_PD2 16 -#define PIN_PD3 17 -#define PIN_PD4 18 -#define PIN_PD5 19 -#define PIN_PA2 20 -#define PIN_PA3 21 -#define PIN_PC3 22 -#define PIN_PA5 23 -#define PIN_PA4 24 -#define PIN_PD6 25 -#define PIN_PB5 26 -#define PIN_PB4 27 -#define PIN_PA6 28 -#define PIN_PA7 29 -#define PIN_PB3 30 -#define PIN_PC7 31 -#define PIN_PC0 32 -#define PIN_PC1 33 -#define PIN_PC2 34 -#define PIN_PF2 35 -#define PIN_PF3 36 -#define PIN_PF0 37 -#define PIN_PF1 38 -#define PIN_PD7 39 -#define PIN_PF6 40 - const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PC5/USART1_Rx NOT_ON_TIMER, // 1 PC4/USART1_Tx From 20ddca1e1feec9677932be67620a83d072a05373 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 27 Apr 2020 16:46:00 +0200 Subject: [PATCH 141/351] Fix missing weak attribute for 32-pin parts Closes #70 --- megaavr/variants/32pin-standard/pins_arduino.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 816b2ee..49566a0 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -307,6 +307,7 @@ const uint8_t digital_pin_to_timer[] = { #endif -void initVariant() {} +void initVariant() __attribute__((weak)); +void initVariant() { } #endif From fb893b8fc41dde0a0ca42f610fb789f6000184f1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 28 Apr 2020 14:11:17 +0200 Subject: [PATCH 142/351] Fix missing include for Uno Wifi --- megaavr/variants/uno-wifi/pins_arduino.h | 1 + 1 file changed, 1 insertion(+) diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 05ca198..c2a2dd4 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -23,6 +23,7 @@ #ifndef Pins_Arduino_h #define Pins_Arduino_h +#include #include #include "timers.h" From 6610c9a481f70fdb06bc042a0ce3514d95432131 Mon Sep 17 00:00:00 2001 From: Hans Date: Thu, 30 Apr 2020 19:14:11 +0200 Subject: [PATCH 143/351] Update README.md --- README.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 7d4acbd..6ea0c02 100644 --- a/README.md +++ b/README.md @@ -39,13 +39,14 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire | | Mega4809 | Mega4808 | Mega3209 | Mega3208 | Mega1609 | Mega1608 | Mega809 | Mega808 | |------------------|----------------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------| -| **Flash** | 48 kB | 48 kB | 32 kB | 32 kB | 16 kB | 16 kB | 8 kB | 8 kB | -| **RAM** | 6 kB | 6 kB | 4 kB | 4 kB | 2 kB | 2 kB | 1 kB | 1 kB | -| **EEPROM** | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | 256 B | +| **Flash** | 48 kiB | 48 kiB | 32 kiB | 32 kiB | 16 kiB | 16 kiB | 8 kiB | 8 kiB | +| **RAM** | 6 kiB | 6 kiB | 4 kiB | 4 kiB | 2 kiB | 2 kiB | 1 kiB | 1 kiB | +| **EEPROM** | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | | **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | | **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | | **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | + 64 bytes of USERROW, accessible from address 256 to 319 * TQFP32/QFN32 package ** SSOP28 package *** DIP40 package From b7456e7d444664194e9efc238dd4ea4a227fac2d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 30 Apr 2020 21:20:01 +0200 Subject: [PATCH 144/351] Change number of interrupt pins --- megaavr/variants/nano-every/pins_arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index de51a6d..3236e99 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -43,7 +43,7 @@ #define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation -#define EXTERNAL_NUM_INTERRUPTS (48) +#define EXTERNAL_NUM_INTERRUPTS (47) #define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) From ae940d606c85adce8c76d8af662a0e40af90af5b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 1 May 2020 08:29:10 +0200 Subject: [PATCH 145/351] Update Servo libraries Improvements stolen from @SpenceKonde's megaTinyCore --- megaavr/libraries/Servo/src/Servo.h | 56 +++++++++---------- megaavr/libraries/Servo/src/megaavr/Servo.cpp | 39 ++++++++----- .../libraries/Servo/src/megaavr/ServoTimers.h | 5 +- 3 files changed, 56 insertions(+), 44 deletions(-) diff --git a/megaavr/libraries/Servo/src/Servo.h b/megaavr/libraries/Servo/src/Servo.h index 4a58550..d3dc383 100644 --- a/megaavr/libraries/Servo/src/Servo.h +++ b/megaavr/libraries/Servo/src/Servo.h @@ -17,15 +17,15 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ -/* - A servo is activated by creating an instance of the Servo class passing +/* + A servo is activated by creating an instance of the Servo class passing the desired pin to the attach() method. - The servos are pulsed in the background using the value most recently + The servos are pulsed in the background using the value most recently written using the write() method. - Note that analogWrite of PWM on pins associated with the timer are + Note that analogWrite of PWM on pins associated with the timer are disabled when the first servo is attached. - Timers are seized as needed in groups of 12 servos - 24 servos use two + Timers are seized as needed in groups of 12 servos - 24 servos use two timers, 48 servos will use four. The sequence used to sieze timers is defined in timers.h @@ -35,14 +35,14 @@ attach(pin ) - Attaches a servo motor to an i/o pin. attach(pin, min, max ) - Attaches to a pin setting min and max values in microseconds - default min is 544, max is 2400 - + default min is 544, max is 2400 + write() - Sets the servo angle in degrees. (invalid angle that is valid as pulse in microseconds is treated as microseconds) - writeMicroseconds() - Sets the servo pulse width in microseconds - read() - Gets the last written servo pulse width as an angle between 0 and 180. + writeMicroseconds() - Sets the servo pulse width in microseconds + read() - Gets the last written servo pulse width as an angle between 0 and 180. readMicroseconds() - Gets the last written servo pulse width in microseconds. (was read_us() in first release) - attached() - Returns true if there is a servo attached. - detach() - Stops an attached servos from pulsing its i/o pin. + attached() - Returns true if there is a servo attached. + detach() - Stops an attached servos from pulsing its i/o pin. */ #ifndef Servo_h @@ -50,8 +50,8 @@ #include -/* - * Defines for 16 bit timers used with Servo library +/* + * Defines for 16 bit timers used with Servo library * * If _useTimerX is defined then TimerX is a 16 bit timer on the current board * timer16_Sequence_t enumerates the sequence that the timers should be allocated @@ -61,29 +61,29 @@ // Architecture specific include #if defined(ARDUINO_ARCH_MEGAAVR) #include "megaavr/ServoTimers.h" - #if (F_CPU==1000000L) + #if (F_CPU == 1000000L) #warning "Running at 1MHz results in unstable servo signal." #endif #else - #error "This library only supports boards with a megaAVR0 processor." + #error "This library only supports boards with a megaAVR-0 processor." #endif #define Servo_VERSION 2 // software version of this library -#define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo -#define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo +#define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo +#define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo #define DEFAULT_PULSE_WIDTH 1500 // default pulse width when servo is attached -#define REFRESH_INTERVAL 20000 // minumim time to refresh servos in microseconds +#define REFRESH_INTERVAL 20000 // minumim time to refresh servos in microseconds -#define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer +#define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer #define MAX_SERVOS (_Nbr_16timers * SERVOS_PER_TIMER) #define INVALID_SERVO 255 // flag indicating an invalid servo index typedef struct { uint8_t nbr :6 ; // a pin number from 0 to 63 - uint8_t isActive :1 ; // true if this channel is enabled, pin not pulsed if false -} ServoPin_t ; + uint8_t isActive :1 ; // true if this channel is enabled, pin not pulsed if false +} ServoPin_t ; typedef struct { ServoPin_t Pin; @@ -94,18 +94,18 @@ class Servo { public: Servo(); - uint8_t attach(int pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure - uint8_t attach(int pin, int min, int max); // as above but also sets min and max values for writes. + uint8_t attach(uint8_t pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure + uint8_t attach(uint8_t pin, int16_t min, int16_t max); // as above but also sets min and max values for writes. void detach(); - void write(int value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds - void writeMicroseconds(int value); // Write pulse width in microseconds + void write(int16_t value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds + void writeMicroseconds(int16_t value); // Write pulse width in microseconds int read(); // returns current pulse width as an angle between 0 and 180 degrees int readMicroseconds(); // returns current pulse width in microseconds for this servo (was read_us() in first release) - bool attached(); // return true if this servo is attached, otherwise false + bool attached(); // return true if this servo is attached, otherwise false private: uint8_t servoIndex; // index into the channel data for this servo - int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH - int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH + int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH + int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH }; #endif diff --git a/megaavr/libraries/Servo/src/megaavr/Servo.cpp b/megaavr/libraries/Servo/src/megaavr/Servo.cpp index bf46c43..92d0ad7 100644 --- a/megaavr/libraries/Servo/src/megaavr/Servo.cpp +++ b/megaavr/libraries/Servo/src/megaavr/Servo.cpp @@ -3,16 +3,21 @@ #include #include -#define usToTicks(_us) ((( _us / 16) * clockCyclesPerMicrosecond()) / 4) // converts microseconds to tick -#define ticksToUs(_ticks) (((unsigned) _ticks * 16 * 4) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds - -#define TRIM_DURATION 5 // compensation ticks to trim adjust for digitalWrite delays +#if (F_CPU > 10000000L) + #define usToTicks(_us) ((( _us / 2) * clockCyclesPerMicrosecond())) // converts microseconds to tick + #define ticksToUs(_ticks) (((unsigned) _ticks * 2) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds + #define TRIM_DURATION 37 // compensation ticks to trim adjust for digitalWrite delays +#else + #define usToTicks(_us) ((( _us ) * clockCyclesPerMicrosecond())) // converts microseconds to tick + #define ticksToUs(_ticks) (((unsigned) _ticks ) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds + #define TRIM_DURATION 74 // compensation ticks to trim adjust for digitalWrite delays +#endif -static servo_t servos[MAX_SERVOS]; // static array of servo structures +static servo_t servos[MAX_SERVOS]; // static array of servo structures -uint8_t ServoCount = 0; // the total number of attached servos +uint8_t ServoCount = 0; // the total number of attached servos -static volatile int8_t currentServoIndex[_Nbr_16timers]; // index for the servo being pulsed for each timer (or -1 if refresh interval) +static volatile int8_t currentServoIndex[_Nbr_16timers]; // index for the servo being pulsed for each timer (or -1 if refresh interval) // convenience macros #define SERVO_INDEX_TO_TIMER(_servo_nbr) ((timer16_Sequence_t)(_servo_nbr / SERVOS_PER_TIMER)) // returns the timer controlling this servo @@ -81,11 +86,17 @@ ISR(TCB3_INT_vect) static void initISR(__attribute__ ((unused)) timer16_Sequence_t timer) { - //TCA0.SINGLE.CTRLA = (TCA_SINGLE_CLKSEL_DIV16_gc) | (TCA_SINGLE_ENABLE_bm); - _timer->CTRLA = TCB_CLKSEL_CLKTCA_gc; + //divide CLK_PER by 2 instead of using TCA0-prescaled at 16/20MHz + #if (F_CPU > 10000000L) + _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; + #else // and don't divide it at all at lower clock speeds + _timer->CTRLA = TCB_CLKSEL_CLKDIV1_gc; + #endif // Timer to Periodic interrupt mode // This write will also disable any active PWM outputs _timer->CTRLB = TCB_CNTMODE_INT_gc; + + _timer->CCMP = 0x8000; //Experience has shown that without this, it goes off the rails // Enable interrupt _timer->INTCTRL = TCB_CAPTEI_bm; // Enable timer @@ -120,12 +131,12 @@ Servo::Servo() } } -uint8_t Servo::attach(int pin) +uint8_t Servo::attach(uint8_t pin) { return this->attach(pin, MIN_PULSE_WIDTH, MAX_PULSE_WIDTH); } -uint8_t Servo::attach(int pin, int min, int max) +uint8_t Servo::attach(uint8_t pin, int16_t min, int16_t max) { timer16_Sequence_t timer; @@ -156,7 +167,7 @@ void Servo::detach() } } -void Servo::write(int value) +void Servo::write(int16_t value) { // treat values less than 544 as angles in degrees (valid values in microseconds are handled as microseconds) if (value < MIN_PULSE_WIDTH) @@ -171,7 +182,7 @@ void Servo::write(int value) writeMicroseconds(value); } -void Servo::writeMicroseconds(int value) +void Servo::writeMicroseconds(int16_t value) { // calculate and store the values for the given channel byte channel = this->servoIndex; @@ -209,4 +220,4 @@ bool Servo::attached() return servos[this->servoIndex].Pin.isActive; } -#endif \ No newline at end of file +#endif diff --git a/megaavr/libraries/Servo/src/megaavr/ServoTimers.h b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h index fe5bdfd..3a64217 100644 --- a/megaavr/libraries/Servo/src/megaavr/ServoTimers.h +++ b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h @@ -49,8 +49,9 @@ __attribute__ ((used)) static volatile TCB_t* _timer = #endif typedef enum { - timer0, - _Nbr_16timers } timer16_Sequence_t; + timer0, + _Nbr_16timers +} timer16_Sequence_t; #endif /* __SERVO_TIMERS_H__ */ From 643ed0909686a07e5f87e8f8a324ab8ea29947cc Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 1 May 2020 08:56:30 +0200 Subject: [PATCH 146/351] Add analogReadResolution --- README.md | 26 ++++++++++++------- megaavr/cores/coreX-corefiles/api/Common.h | 1 + megaavr/cores/coreX-corefiles/wiring_analog.c | 15 +++++++++++ 3 files changed, 33 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 6ea0c02..10a5bf4 100644 --- a/README.md +++ b/README.md @@ -20,6 +20,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) + - [Analog read resolution](#analog-resolution) - [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) - [Analog Comparator (AC)](#analog-comparator-ac) - [Alternative pins](#alternative-pins) @@ -37,16 +38,16 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire ## Supported microcontrollers -| | Mega4809 | Mega4808 | Mega3209 | Mega3208 | Mega1609 | Mega1608 | Mega809 | Mega808 | -|------------------|----------------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------|------------------|-----------------------------------| -| **Flash** | 48 kiB | 48 kiB | 32 kiB | 32 kiB | 16 kiB | 16 kiB | 8 kiB | 8 kiB | -| **RAM** | 6 kiB | 6 kiB | 4 kiB | 4 kiB | 2 kiB | 2 kiB | 1 kiB | 1 kiB | -| **EEPROM** | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | 256 B + 64 B† | -| **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | -| **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | -| **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | +| | Mega4809 | Mega4808 | Mega3209 | Mega3208 | Mega1609 | Mega1608 | Mega809 | Mega808 | +|------------------|----------------------------|-----------------------------------|-------------------|-----------------------------------|-------------------|-----------------------------------|-------------------|-----------------------------------| +| **Flash** | 48 kiB | 48 kiB | 32 kiB | 32 kiB | 16 kiB | 16 kiB | 8 kiB | 8 kiB | +| **RAM** | 6 kiB | 6 kiB | 4 kiB | 4 kiB | 2 kiB | 2 kiB | 1 kiB | 1 kiB | +| **EEPROM** | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | +| **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | +| **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | +| **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | - 64 bytes of USERROW, accessible from address 256 to 319 + 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library * TQFP32/QFN32 package ** SSOP28 package *** DIP40 package @@ -170,6 +171,13 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. +### Analog read resolution +The default analog read resolution for these chips is 10 bit, which gives you values between 0 - 1023. If you need less resolution you can turn it down to 8 bits instead, which gives you values between 0 - 255. +Simply call `analogReadResolution` like this: +```c +analogReadResolution(8); // Set resolution to 8 bits +``` + ### Configurable Custom Logic (CCL) The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performance. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from each other, connected together or generate an interrupt to the CPU. I've made a [light weight, high-level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integration with the CCL hardware. diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index e5e7ee2..25cdca9 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -105,6 +105,7 @@ uint8_t _drfast(pin_size_t pinNumber); #define digitalReadFast(pin) \ (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _drfast(pin) : digitalRead(pin)) int analogRead(pin_size_t pinNumber); +uint8_t analogReadResolution(uint8_t res); void analogReference(uint8_t mode); void analogWrite(pin_size_t pinNumber, int value); void analogWriteFrequency(uint8_t kHz); diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index dbcf46e..f5abd04 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -77,6 +77,21 @@ int analogRead(uint8_t pin) #endif } +// analogReadResolution() has two legal values you can pass it, 8 or 10. +// According to the datasheet, you can clock the ADC faster if you set it to 8. +// Like the pinswap functions, if the user passes bogus values, we set it to the default and return false. +uint8_t analogReadResolution(uint8_t res) +{ + if (res==8) + { + ADC0.CTRLA&=~ADC_RESSEL_bm; + return 1; + } + // If argument wasn't 8, we'll be putting it to default value either way + ADC0.CTRLA |= ADC_RESSEL_bm; + return (res == 10); // Only return true if the value passed was the valid option, 10. +} + // Right now, PWM output only works on the pins with // hardware support. These are defined in the appropriate // pins_*.c file. For the rest of the pins, we default From 2ac45e07671342453b710cbd89914a63ecd51566 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 3 May 2020 15:39:55 +0200 Subject: [PATCH 147/351] Add dedicated 40-pin pinout #65 related --- README.md | 4 +- megaavr/boards.txt | 13 +- .../variants/40pin-standard/pins_arduino.h | 378 ++++++++++++++++++ 3 files changed, 390 insertions(+), 5 deletions(-) create mode 100644 megaavr/variants/40pin-standard/pins_arduino.h diff --git a/README.md b/README.md index 10a5bf4..58a50c6 100644 --- a/README.md +++ b/README.md @@ -131,6 +131,7 @@ digitalWrite(0, HIGH); ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. +- **40 pin standard**: This pinout is more or less identical to the 48 pin variant, but with a reduced pin number. Note that this pinout is only available on ATmega4809. - **32 pin standard**: This is the pinout for the 32 pin version of the ATmega3208/4808. Again, it will not be compatible with shields or anything like that, but it's clean and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. It will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. @@ -141,7 +142,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## Hardware features @@ -162,6 +163,7 @@ PWM output, `analogWrite()`, is available for the following pins: |-------------------|--------------------|------------------------------------| | *28 pin standard* | 4 | 8, 9, 10, 11 | | *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | +| *40 pin standard* | 8 | 8, 9, 10, 11, 12, 13, 30, 31 | | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | | *Nano Every* | 5 | 3, 5, 6, 9, 10 | diff --git a/megaavr/boards.txt b/megaavr/boards.txt index f0172b0..0a6d027 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -28,9 +28,14 @@ menu.bootloader=Bootloader 4809.bootloader.LOCKBIT=0xC5 # Pinouts -4809.menu.pinout.48pin_standard=40/48 pin standard +4809.menu.pinout.48pin_standard=48 pin standard 4809.menu.pinout.48pin_standard.build.variant=48pin-standard 4809.menu.pinout.48pin_standard.build.compat= + +4809.menu.pinout.40pin_standard=40 pin standard +4809.menu.pinout.40pin_standard.build.variant=40pin-standard +4809.menu.pinout.40pin_standard.build.compat= + 4809.menu.pinout.uno_wifi=Uno WiFi 4809.menu.pinout.uno_wifi.build.variant=uno-wifi 4809.menu.pinout.uno_wifi.build.compat= @@ -445,7 +450,7 @@ menu.bootloader=Bootloader 3209.bootloader.LOCKBIT=0xC5 # Pinouts -3209.menu.pinout.48pin_standard=40/48 pin standard +3209.menu.pinout.48pin_standard=48 pin standard 3209.menu.pinout.48pin_standard.build.variant=48pin-standard 3209.menu.pinout.48pin_standard.build.compat= 3209.menu.pinout.uno_wifi=Uno WiFi @@ -847,7 +852,7 @@ menu.bootloader=Bootloader 1609.bootloader.LOCKBIT=0xC5 # Pinouts -1609.menu.pinout.48pin_standard=40/48 pin standard +1609.menu.pinout.48pin_standard=48 pin standard 1609.menu.pinout.48pin_standard.build.variant=48pin-standard 1609.menu.pinout.48pin_standard.build.compat= 1609.menu.pinout.uno_wifi=Uno WiFi @@ -1249,7 +1254,7 @@ menu.bootloader=Bootloader 809.bootloader.LOCKBIT=0xC5 # Pinouts -809.menu.pinout.48pin_standard=40/48 pin standard +809.menu.pinout.48pin_standard=48 pin standard 809.menu.pinout.48pin_standard.build.variant=48pin-standard 809.menu.pinout.48pin_standard.build.compat= 809.menu.pinout.uno_wifi=Uno WiFi diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h new file mode 100644 index 0000000..a3ec17e --- /dev/null +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -0,0 +1,378 @@ +/****************************************************| +| 40-PIN STANDARD PINOUT | +| https://github.com/MCUdude/MegaCoreX | +| | +| COMPATIBLE WITH: | +| ATmega4809 | +| | +| Note that this pinout is not directly compatible | +| with the UNO Wifi Rev2 hardware without performing | +| pinswaps. This pinout is supposed to be as close | +| to the metal as possible. The only peripherals | +| that are swapped to other pins by default are the | +| PWM outputs. | +| | +|****************************************************/ + +#ifndef Pins_Arduino_h +#define Pins_Arduino_h + +#include +#include "timers.h" + +#define DEFAULT_40PIN_PINOUT + +// Pin macros +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PC4 12 +#define PIN_PC5 13 +#define PIN_PD0 14 +#define PIN_PD1 15 +#define PIN_PD2 16 +#define PIN_PD3 17 +#define PIN_PD4 18 +#define PIN_PD5 19 +#define PIN_PD6 20 +#define PIN_PD7 21 +#define PIN_PE0 22 +#define PIN_PE1 23 +#define PIN_PE2 24 +#define PIN_PE3 25 +#define PIN_PF0 26 +#define PIN_PF1 27 +#define PIN_PF2 28 +#define PIN_PF3 29 +#define PIN_PF4 30 +#define PIN_PF5 31 +#define PIN_PF6 32 + +#define PINS_COUNT 33 +#define NUM_DIGITAL_PINS (PINS_COUNT) +#define NUM_ANALOG_INPUTS 16 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 +#define NUM_SPI_PINS 3 +#define NUM_TOTAL_FREE_PINS (PINS_COUNT) +#define NUM_TOTAL_PINS (PINS_COUNT) +#define ANALOG_INPUT_OFFSET 14 +#define LED_BUILTIN PIN_PA7 +#define EXTERNAL_NUM_INTERRUPTS 47 +#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= PIN_PD0 && (p) <= PIN_PE3) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= PIN_PF2 && (p) <= PIN_PF5) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) ((p <= 11) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) <= 15) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 26 && (p) <= 31)) ? (p) : NOT_A_PIN) + +// Timer to use for millis/micros +#if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) || !defined(MILLIS_USE_TIMERB3) +#define MILLIS_USE_TIMERB2 // Use TCB2 for millis generation +#endif + +// PWM pins +#if defined(MILLIS_USE_TIMERB0) + #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF5) +#elif defined(MILLIS_USE_TIMERB1) + #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4) +#elif defined(MILLIS_USE_TIMERB2) + #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4 || (p) == PIN_PF5) +#else // default to MILLIS_USE_TIMERB3 + #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4 || (p) == PIN_PF5) +#endif + +// Timer pin swaps +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + +// SPI 0 +// No pinswap enabled by default +// Pinswap 2 not available +#define SPI_INTERFACES_COUNT 1 +#define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) +#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) +#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_ALT2_gc) +#define PIN_SPI_MISO (PIN_PA5) +#define PIN_SPI_SCK (PIN_PA6) +#define PIN_SPI_MOSI (PIN_PA4) +#define PIN_SPI_SS (PIN_PA7) +#define PIN_SPI_MISO_PINSWAP_1 (PIN_PC1) +#define PIN_SPI_SCK_PINSWAP_1 (PIN_PC2) +#define PIN_SPI_MOSI_PINSWAP_1 (PIN_PC0) +#define PIN_SPI_SS_PINSWAP_1 (PIN_PC3) +#define PIN_SPI_MISO_PINSWAP_2 (PIN_PE1) +#define PIN_SPI_SCK_PINSWAP_2 (PIN_PE2) +#define PIN_SPI_MOSI_PINSWAP_2 (PIN_PE0) +#define PIN_SPI_SS_PINSWAP_2 (PIN_PE3) +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; + +// TWI 0 +// No pinswap enabled by default +#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) +#define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) +#define PIN_WIRE_SDA (PIN_PA2) +#define PIN_WIRE_SCL (PIN_PA3) +#define PIN_WIRE_SDA_PINSWAP_1 (PIN_PC2) +#define PIN_WIRE_SCL_PINSWAP_1 (PIN_PC3) +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; + +// USART 0 +// No pinswap by default +#define HWSERIAL0 (&USART0) +#define HWSERIAL0_DRE_VECTOR (USART0_DRE_vect) +#define HWSERIAL0_DRE_VECTOR_NUM (USART0_DRE_vect_num) +#define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) +#define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) +#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) +#define PIN_WIRE_HWSERIAL0_TX (PIN_PA0) +#define PIN_WIRE_HWSERIAL0_RX (PIN_PA1) +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PA4) +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PA5) + +// USART1 +// No pinswap by default +#define HWSERIAL1 (&USART1) +#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) +#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) +#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) +#define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) +#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_ALT1_gc) +#define PIN_WIRE_HWSERIAL1_TX (PIN_PC0) +#define PIN_WIRE_HWSERIAL1_RX (PIN_PC1) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC4) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC5) + +// USART 2 +// No pinswap by default +#define HWSERIAL2 (&USART2) +#define HWSERIAL2_DRE_VECTOR (USART2_DRE_vect) +#define HWSERIAL2_DRE_VECTOR_NUM (USART2_DRE_vect_num) +#define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) +#define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) +#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) +#define PIN_WIRE_HWSERIAL2_TX (PIN_PF0) +#define PIN_WIRE_HWSERIAL2_RX (PIN_PF1) +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PF4) +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PF5) + +// Analog pins +#define PIN_A0 (PIN_PD0) +#define PIN_A1 (PIN_PD1) +#define PIN_A2 (PIN_PD2) +#define PIN_A3 (PIN_PD3) +#define PIN_A4 (PIN_PD4) +#define PIN_A5 (PIN_PD5) +#define PIN_A6 (PIN_PD6) +#define PIN_A7 (PIN_PD7) +#define PIN_A8 (PIN_PE0) +#define PIN_A9 (PIN_PE1) +#define PIN_A10 (PIN_PE2) +#define PIN_A11 (PIN_PE3) +#define PIN_A12 (PIN_PF2) +#define PIN_A13 (PIN_PF3) +#define PIN_A14 (PIN_PF4) +#define PIN_A15 (PIN_PF5) +static const uint8_t A0 = PIN_A0; +static const uint8_t A1 = PIN_A1; +static const uint8_t A2 = PIN_A2; +static const uint8_t A3 = PIN_A3; +static const uint8_t A4 = PIN_A4; +static const uint8_t A5 = PIN_A5; +static const uint8_t A6 = PIN_A6; +static const uint8_t A7 = PIN_A7; +static const uint8_t A8 = PIN_A8; +static const uint8_t A9 = PIN_A9; +static const uint8_t A10 = PIN_A10; +static const uint8_t A11 = PIN_A11; +static const uint8_t A12 = PIN_A12; +static const uint8_t A13 = PIN_A13; +static const uint8_t A14 = PIN_A14; +static const uint8_t A15 = PIN_A15; + +#ifdef ARDUINO_MAIN + +const uint8_t digital_pin_to_port[] = { + PA, // 0 PA0/USART0_Tx/CLKIN + PA, // 1 PA1/USART0_Rx + PA, // 2 PA2/SDA + PA, // 3 PA3/SCL + PA, // 4 PA4/MOSI + PA, // 5 PA5/MISO + PA, // 6 PA6/SCK + PA, // 7 PA7/SS/CLKOUT + PC, // 8 PC0/USART1_Tx/TCA0 PWM + PC, // 9 PC1/USART1_Rx/TCA0 PWM + PC, // 10 PC2/TCA0 PWM + PC, // 11 PC3/TCA0 PWM + PC, // 12 PC4/TCA0 PWM + PC, // 13 PC5/TCA0 PWM + PD, // 14 PD0/AIN0 + PD, // 15 PD1/AIN1 + PD, // 16 PD2/AIN2 + PD, // 17 PD3/AIN3 + PD, // 18 PD4/AIN4 + PD, // 19 PD5/AIN5 + PD, // 20 PD6/AIN6 + PD, // 21 PD7/AIN7/AREF + PE, // 22 PE0/AIN8 + PE, // 23 PE1/AIN9 + PE, // 24 PE2/AIN10 + PE, // 25 PE3/AIN11 + PF, // 26 PF0/USART2_Tx/TOSC1 + PF, // 27 PF1/USART2_Rx/TOSC2 + PF, // 28 PF2/AIN12 + PF, // 29 PF3/AIN13 + PF, // 30 PF4/AIN14/TCB0 PWM + PF, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PF // 32 PF6 RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_position[] = { + PIN0_bp, // 0 PIN_bp0/USART0_Tx/CLKIN + PIN1_bp, // 1 PA1/USART0_Rx + PIN2_bp, // 2 PA2/SDA + PIN3_bp, // 3 PA3/SCL + PIN4_bp, // 4 PA4/MOSI + PIN5_bp, // 5 PA5/MISO + PIN6_bp, // 6 PA6/SCK + PIN7_bp, // 7 PA7/SS/CLKOUT + PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM + PIN2_bp, // 10 PC2/TCA0 PWM + PIN3_bp, // 11 PC3/TCA0 PWM + PIN4_bp, // 12 PC4/TCA0 PWM + PIN5_bp, // 13 PC5/TCA0 PWM + PIN0_bp, // 14 PD0/AIN0 + PIN1_bp, // 15 PD1/AIN1 + PIN2_bp, // 16 PD2/AIN2 + PIN3_bp, // 17 PD3/AIN3 + PIN4_bp, // 18 PD4/AIN4 + PIN5_bp, // 19 PD5/AIN5 + PIN6_bp, // 20 PD6/AIN6 + PIN7_bp, // 21 PD7/AIN7/AREF + PIN0_bp, // 22 PE0/AIN8 + PIN1_bp, // 23 PE1/AIN9 + PIN2_bp, // 24 PE2/AIN10 + PIN3_bp, // 25 PE3/AIN11 + PIN0_bp, // 26 PF0/USART2_Tx/TOSC1 + PIN1_bp, // 27 PF1/USART2_Rx/TOSC2 + PIN2_bp, // 28 PF2/AIN12 + PIN3_bp, // 29 PF3/AIN13 + PIN4_bp, // 30 PF4/AIN14/TCB0 PWM + PIN5_bp, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN6_bp // 42 PF6 RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_mask[] = { + PIN0_bm, // 0 PIN_bp0/USART0_Tx/CLKIN + PIN1_bm, // 1 PA1/USART0_Rx + PIN2_bm, // 2 PA2/SDA + PIN3_bm, // 3 PA3/SCL + PIN4_bm, // 4 PA4/MOSI + PIN5_bm, // 5 PA5/MISO + PIN6_bm, // 6 PA6/SCK + PIN7_bm, // 7 PA7/SS/CLKOUT + PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM + PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM + PIN2_bm, // 10 PC2/TCA0 PWM + PIN3_bm, // 11 PC3/TCA0 PWM + PIN4_bm, // 12 PC4/TCA0 PWM + PIN5_bm, // 13 PC5/TCA0 PWM + PIN0_bm, // 14 PD0/AIN0 + PIN1_bm, // 15 PD1/AIN1 + PIN2_bm, // 16 PD2/AIN2 + PIN3_bm, // 17 PD3/AIN3 + PIN4_bm, // 18 PD4/AIN4 + PIN5_bm, // 19 PD5/AIN5 + PIN6_bm, // 20 PD6/AIN6 + PIN7_bm, // 21 PD7/AIN7/AREF + PIN0_bm, // 22 PE0/AIN8 + PIN1_bm, // 23 PE1/AIN9 + PIN2_bm, // 24 PE2/AIN10 + PIN3_bm, // 25 PE3/AIN11 + PIN0_bm, // 26 PF0/USART2_Tx/TOSC1 + PIN1_bm, // 27 PF1/USART2_Rx/TOSC2 + PIN2_bm, // 28 PF2/AIN12 + PIN3_bm, // 29 PF3/AIN13 + PIN4_bm, // 30 PF4/AIN14/TCB0 PWM + PIN5_bm, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN6_bm // 32 PF6 RESET +}; + +const uint8_t digital_pin_to_timer[] = { + NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN + NOT_ON_TIMER, // 1 PA1/USART0_Rx + NOT_ON_TIMER, // 2 PA2/SDA + NOT_ON_TIMER, // 3 PA3/SCL + NOT_ON_TIMER, // 4 PA4/MOSI + NOT_ON_TIMER, // 5 PA5/MISO + NOT_ON_TIMER, // 6 PA6/SCK + NOT_ON_TIMER, // 7 PA7/SS/CLKOUT + TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM + TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM + TIMERA0, // 10 PC2/TCA0 PWM + TIMERA0, // 11 PC3/TCA0 PWM + TIMERA0, // 12 PC4/TCA0 PWM + TIMERA0, // 13 PC5/TCA0 PWM + NOT_ON_TIMER, // 14 PD0/AIN0 + NOT_ON_TIMER, // 15 PD1/AIN1 + NOT_ON_TIMER, // 16 PD2/AIN2 + NOT_ON_TIMER, // 17 PD3/AIN3 + NOT_ON_TIMER, // 18 PD4/AIN4 + NOT_ON_TIMER, // 19 PD5/AIN5 + NOT_ON_TIMER, // 20 PD6/AIN6 + NOT_ON_TIMER, // 21 PD7/AIN7/AREF + NOT_ON_TIMER, // 22 PE0/AIN8 + NOT_ON_TIMER, // 23 PE1/AIN9 + NOT_ON_TIMER, // 24 PE2/AIN10 + NOT_ON_TIMER, // 25 PE3/AIN11 + NOT_ON_TIMER, // 26 PF0/USART2_Tx/TOSC1 + NOT_ON_TIMER, // 27 PF1/USART2_Rx/TOSC2 + NOT_ON_TIMER, // 28 PF2/AIN12 + NOT_ON_TIMER, // 29 PF3/AIN13 +#ifdef MILLIS_USE_TIMERB0 + NOT_ON_TIMER, // 30 PF4/AIN14 +#else + TIMERB0, // 30 PF4/AIN14/TCB0 PWM +#endif +#ifdef MILLIS_USE_TIMERB1 + NOT_ON_TIMER, // 31 PF5/AIN15/LED_BUILTIN +#else + TIMERB1, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN +#endif + NOT_ON_TIMER // 32 PF6 RESET +}; + +#endif + +void initVariant() __attribute__((weak)); +void initVariant() +{ + // Disable unavailable pins on the 40 pin package + PORTB.PIN0CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTB.PIN1CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTB.PIN2CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTB.PIN3CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTB.PIN4CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTB.PIN5CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTC.PIN6CTRL = PORT_ISC_INPUT_DISABLE_gc; + PORTC.PIN6CTRL = PORT_ISC_INPUT_DISABLE_gc; +} + +#endif From 5a3929bfbc210aa0b7feba4180b1502f28ab509d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 3 May 2020 17:18:12 +0200 Subject: [PATCH 148/351] Add assembler output --- megaavr/boards.txt | 8 +++++++ megaavr/platform.txt | 23 ++++++++++++++++++- .../scripts/create_disassembler_listing.sh | 8 +++++++ megaavr/scripts/delete_merged_output.bat | 2 ++ megaavr/scripts/delete_merged_output.sh | 4 ++++ 5 files changed, 44 insertions(+), 1 deletion(-) create mode 100755 megaavr/scripts/create_disassembler_listing.sh create mode 100644 megaavr/scripts/delete_merged_output.bat create mode 100755 megaavr/scripts/delete_merged_output.sh diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 0a6d027..1af2713 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -19,6 +19,7 @@ menu.bootloader=Bootloader 4809.build.board=AVR_ATmega4809 4809.build.mcu=atmega4809 4809.build.extra_flags={build.oscillator} {build.compat} +4809.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 4809.bootloader.WDTCFG=0x00 @@ -250,6 +251,7 @@ menu.bootloader=Bootloader 4808.build.board=AVR_ATmega4808 4808.build.mcu=atmega4808 4808.build.extra_flags={build.oscillator} +4808.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 4808.bootloader.WDTCFG=0x00 @@ -441,6 +443,7 @@ menu.bootloader=Bootloader 3209.build.board=AVR_ATmega3209 3209.build.mcu=atmega3209 3209.build.extra_flags={build.oscillator} {build.compat} +3209.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 3209.bootloader.WDTCFG=0x00 @@ -653,6 +656,7 @@ menu.bootloader=Bootloader 3208.build.board=AVR_ATmega3208 3208.build.mcu=atmega3208 3208.build.extra_flags={build.oscillator} +3208.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 3208.bootloader.WDTCFG=0x00 @@ -843,6 +847,7 @@ menu.bootloader=Bootloader 1609.build.board=AVR_ATmega1609 1609.build.mcu=atmega1609 1609.build.extra_flags={build.oscillator} {build.compat} +1609.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 1609.bootloader.WDTCFG=0x00 @@ -1055,6 +1060,7 @@ menu.bootloader=Bootloader 1608.build.board=AVR_ATmega1608 1608.build.mcu=atmega1608 1608.build.extra_flags={build.oscillator} +1608.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 1608.bootloader.WDTCFG=0x00 @@ -1245,6 +1251,7 @@ menu.bootloader=Bootloader 809.build.board=AVR_ATmega809 809.build.mcu=atmega809 809.build.extra_flags={build.oscillator} {build.compat} +809.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 809.bootloader.WDTCFG=0x00 @@ -1457,6 +1464,7 @@ menu.bootloader=Bootloader 808.build.board=AVR_ATmega808 808.build.mcu=atmega808 808.build.extra_flags={build.oscillator} +808.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 808.bootloader.WDTCFG=0x00 diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 97c18fa..84b9170 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -30,7 +30,10 @@ compiler.ar.cmd=avr-gcc-ar compiler.ar.flags=rcs compiler.objcopy.cmd=avr-objcopy compiler.objcopy.eep.flags=-O ihex -j .eeprom --set-section-flags=.eeprom=alloc,load --no-change-warnings --change-section-lma .eeprom=0 +compiler.objdump.cmd=avr-objdump +compiler.objdump.flags=--disassemble --source --line-numbers --demangle --section=.text compiler.elf2hex.flags=-O ihex -R .eeprom +compiler.elf2hex.bin.flags=-O binary -R .eeprom compiler.elf2hex.cmd=avr-objcopy compiler.ldflags= compiler.size.cmd=avr-size @@ -71,9 +74,27 @@ recipe.c.combine.pattern="{compiler.path}{compiler.c.elf.cmd}" {compiler.c.elf.f recipe.objcopy.eep.pattern="{compiler.path}{compiler.objcopy.cmd}" {compiler.objcopy.eep.flags} {compiler.objcopy.eep.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.eep" recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.hex" +## Save disassembler listing +recipe.hooks.objcopy.postobjcopy.1.pattern.windows=cmd /C "{compiler.path}{compiler.objdump.cmd}" {compiler.objdump.flags} "{build.path}/{build.project_name}.elf" > "{build.path}/{build.project_name}.lst" +recipe.hooks.objcopy.postobjcopy.1.pattern.linux=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" +recipe.hooks.objcopy.postobjcopy.1.pattern.macosx=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" +recipe.hooks.objcopy.postobjcopy.2.pattern.linux="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.lst" +recipe.hooks.objcopy.postobjcopy.2.pattern.macosx="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.lst" + ## Save hex recipe.output.tmp_file={build.project_name}.hex -recipe.output.save_file={build.project_name}.{build.variant}.hex +recipe.output.save_file={build.project_name}_{build.mcu}_{build.f_cpu}.hex + +## Save hex +recipe.hooks.savehex.presavehex.1.pattern.windows="{runtime.platform.path}/scripts/delete_merged_output.bat" {build.export_merged_output} "{build.path}\{build.project_name}.with_bootloader.hex" +recipe.hooks.savehex.presavehex.2.pattern.windows=cmd /C copy "{build.path}\{build.project_name}.lst" "{sketch_path}" +recipe.hooks.savehex.presavehex.1.pattern.linux=chmod +x "{runtime.platform.path}/scripts/delete_merged_output.sh" +recipe.hooks.savehex.presavehex.2.pattern.linux="{runtime.platform.path}/scripts/delete_merged_output.sh" {build.export_merged_output} "{build.path}/{build.project_name}.with_bootloader.hex" +recipe.hooks.savehex.presavehex.3.pattern.linux=cp "{build.path}/{build.project_name}.lst" "{sketch_path}" +recipe.hooks.savehex.presavehex.1.pattern.macosx=chmod +x "{runtime.platform.path}/scripts/delete_merged_output.sh" +recipe.hooks.savehex.presavehex.2.pattern.macosx="{runtime.platform.path}/scripts/delete_merged_output.sh" {build.export_merged_output} "{build.path}/{build.project_name}.with_bootloader.hex" +recipe.hooks.savehex.presavehex.3.pattern.macosx=cp "{build.path}/{build.project_name}.lst" "{sketch_path}" + ## Compute size recipe.size.pattern="{compiler.path}{compiler.size.cmd}" -A "{build.path}/{build.project_name}.elf" diff --git a/megaavr/scripts/create_disassembler_listing.sh b/megaavr/scripts/create_disassembler_listing.sh new file mode 100755 index 0000000..84e8b19 --- /dev/null +++ b/megaavr/scripts/create_disassembler_listing.sh @@ -0,0 +1,8 @@ +#!/bin/bash + +objdumpCommand="$1" +options="$2" +objfile="$3" +outputFile="$4" + +"$objdumpCommand" $options "$objfile" > "$outputFile" diff --git a/megaavr/scripts/delete_merged_output.bat b/megaavr/scripts/delete_merged_output.bat new file mode 100644 index 0000000..c0af51a --- /dev/null +++ b/megaavr/scripts/delete_merged_output.bat @@ -0,0 +1,2 @@ +@echo off +if "%1" == "false" del "%2" diff --git a/megaavr/scripts/delete_merged_output.sh b/megaavr/scripts/delete_merged_output.sh new file mode 100755 index 0000000..c2cc493 --- /dev/null +++ b/megaavr/scripts/delete_merged_output.sh @@ -0,0 +1,4 @@ +#!/bin/bash +if [ "$1" == "false" ]; then + rm "$2" +fi From 925b6a1e2de8de12826654bb783009b2ecb72d57 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 3 May 2020 21:12:54 +0200 Subject: [PATCH 149/351] Improve PWM layout for 28 and 32 pin parts Issue #66 related --- README.md | 13 +- .../variants/28pin-standard/pins_arduino.h | 261 ++++++++-------- .../variants/32pin-standard/pins_arduino.h | 295 +++++++++--------- 3 files changed, 302 insertions(+), 267 deletions(-) diff --git a/README.md b/README.md index 58a50c6..6bfa59a 100644 --- a/README.md +++ b/README.md @@ -20,7 +20,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) - - [Analog read resolution](#analog-resolution) + - [Analog read resolution](#analog-read-resolution) - [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) - [Analog Comparator (AC)](#analog-comparator-ac) - [Alternative pins](#alternative-pins) @@ -44,7 +44,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire | **RAM** | 6 kiB | 6 kiB | 4 kiB | 4 kiB | 2 kiB | 2 kiB | 1 kiB | 1 kiB | | **EEPROM** | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | 256 B +
64 B† | | **Serial ports** | 4 | 3 | 4 | 3 | 4 | 3 | 4 | 3 | -| **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | +| **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | | **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library @@ -117,7 +117,8 @@ Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. ## Pin macros -Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that maps "Arduino pins" to the port and port number: +Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that maps "Arduino pins" to the port and port number. +Note that all my Arduino cores has these macros if you prefer to use these rather than the default Arduino pin number. ```c++ // Use PIN_PA0 macro to refer to pin PA0 (Arduino pin 0) @@ -142,7 +143,7 @@ Please have a look at the pins_arduino.h files for detailed info.

| **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -|

|























| +|

|























| ## Hardware features @@ -161,8 +162,8 @@ PWM output, `analogWrite()`, is available for the following pins: | Pinout | Number of PWM pins | Available PWM pins | |-------------------|--------------------|------------------------------------| -| *28 pin standard* | 4 | 8, 9, 10, 11 | -| *32 pin standard* | 6 | 8, 9, 10, 11, 24, 25 | +| *28 pin standard* | 8 | 2, 3, 12, 13, 14, 15, 16, 17 | +| *32 pin standard* | 8 | 2, 3, 12, 13, 14, 15, 16, 17 | | *40 pin standard* | 8 | 8, 9, 10, 11, 12, 13, 30, 31 | | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 05b054d..1cc724b 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -20,113 +20,144 @@ #define DEFAULT_28PIN_PINOUT -#define NUM_DIGITAL_PINS 23 +// Arduino pin macros +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF6 22 + +#define PINS_COUNT 23 +#define NUM_DIGITAL_PINS PINS_COUNT #define NUM_ANALOG_INPUTS 8 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define NUM_I2C_PINS 2 +#define NUM_SPI_PINS 3 +#define NUM_TOTAL_FREE_PINS PINS_COUNT +#define NUM_TOTAL_PINS PINS_COUNT #define ANALOG_INPUT_OFFSET 12 -#define LED_BUILTIN 7 // PA7 +#define LED_BUILTIN PIN_PA7 +#define EXTERNAL_NUM_INTERRUPTS 47 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : (p) - 12) -#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 12 && (p) <= 19) ? (p) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 12 && (p) <= 19) ? (p) : NOT_A_PIN) +// Timer to use for millis/micros #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) -#define MILLIS_USE_TIMERB2 // use TCB2 +#define MILLIS_USE_TIMERB2 // Use TCB2 if nothing else if defined #endif -#define EXTERNAL_NUM_INTERRUPTS (47) - -#define digitalPinHasPWM(p) ((p) >= 8 && (p) <= 11) +// PWM pins +#if defined(MILLIS_USE_TIMERB0) + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA3 || (p) == PIN_PC0) +#elif defined(MILLIS_USE_TIMERB1) + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PC0) +#else // default to MILLIS_USE_TIMERB2 + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PA3) +#endif // Timer pin mapping -#define TCA0_PINS PORTMUX_TCA0_PORTC_gc -#define TCB0_PINS PORTMUX_TCB0_bm -#define TCB1_PINS PORTMUX_TCB1_bm -#define TCB2_PINS PORTMUX_TCB2_bm -#define TCB3_PINS 0x00 +#define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] +#define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 +#define TCB1_PINS 0x00 // TCB1 output on PA3 instead of PF5 +#define TCB2_PINS 0x00 // TCB2 output on PC0 instead of PB4 // SPI 0 // No pinswap by default // Pinswap 2 not available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) -#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define PIN_SPI_MISO (5) -#define PIN_SPI_SCK (6) -#define PIN_SPI_MOSI (4) -#define PIN_SPI_SS (7) -#define PIN_SPI_MISO_PINSWAP_1 (9) -#define PIN_SPI_SCK_PINSWAP_1 (10) -#define PIN_SPI_MOSI_PINSWAP_1 (8) -#define PIN_SPI_SS_PINSWAP_1 (11) - -static const uint8_t SS = PIN_SPI_SS; -static const uint8_t MOSI = PIN_SPI_MOSI; -static const uint8_t MISO = PIN_SPI_MISO; -static const uint8_t SCK = PIN_SPI_SCK; +#define SPI_MUX PORTMUX_SPI0_DEFAULT_gc +#define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_ALT1_gc +#define PIN_SPI_MISO PIN_PA5 +#define PIN_SPI_SCK PIN_PA6 +#define PIN_SPI_MOSI PIN_PA4 +#define PIN_SPI_SS PIN_PA7 +#define PIN_SPI_MISO_PINSWAP_1 PIN_PC1 +#define PIN_SPI_SCK_PINSWAP_1 PIN_PC2 +#define PIN_SPI_MOSI_PINSWAP_1 PIN_PC0 +#define PIN_SPI_SS_PINSWAP_1 PIN_PC3 +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) -#define PIN_WIRE_SDA (2) -#define PIN_WIRE_SCL (3) -#define PIN_WIRE_SDA_PINSWAP_1 (10) -#define PIN_WIRE_SCL_PINSWAP_1 (11) -static const uint8_t SDA = PIN_WIRE_SDA; -static const uint8_t SCL = PIN_WIRE_SCL; +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define TWI_MUX_PINSWAP PORTMUX_TWI0_ALT2_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 +#define PIN_WIRE_SDA_PINSWAP_1 PIN_PC2 +#define PIN_WIRE_SCL_PINSWAP_1 PIN_PC3 +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; // USART 0 // No pinswap by default -#define HWSERIAL0 (&USART0) -#define HWSERIAL0_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_WIRE_HWSERIAL0_TX (0) -#define PIN_WIRE_HWSERIAL0_RX (1) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (4) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (5) +#define HWSERIAL0 &USART0 +#define HWSERIAL0_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 +#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap available -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (8) -#define PIN_WIRE_HWSERIAL1_RX (9) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (8) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (9) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc +#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 +#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 // USART 2 // No pinswap by default -#define HWSERIAL2 (&USART2) -#define HWSERIAL2_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) -#define PIN_WIRE_HWSERIAL2_TX (20) -#define PIN_WIRE_HWSERIAL2_RX (21) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (24) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (25) - -#define PIN_A0 (12) -#define PIN_A1 (13) -#define PIN_A2 (14) -#define PIN_A3 (15) -#define PIN_A4 (16) -#define PIN_A5 (17) -#define PIN_A6 (18) -#define PIN_A7 (19) +#define HWSERIAL2 &USART2 +#define HWSERIAL2_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc +#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 +#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF0 +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF1 +// Analog pins +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PD4 +#define PIN_A5 PIN_PD5 +#define PIN_A6 PIN_PD6 +#define PIN_A7 PIN_PD7 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; @@ -136,32 +167,6 @@ static const uint8_t A5 = PIN_A5; static const uint8_t A6 = PIN_A6; static const uint8_t A7 = PIN_A7; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PC0 8 -#define PIN_PC1 9 -#define PIN_PC2 10 -#define PIN_PC3 11 -#define PIN_PD0 12 -#define PIN_PD1 13 -#define PIN_PD2 14 -#define PIN_PD3 15 -#define PIN_PD4 16 -#define PIN_PD5 17 -#define PIN_PD6 18 -#define PIN_PD7 19 -#define PIN_PF0 20 -#define PIN_PF1 21 -#define PIN_PF6 22 - -#define PINS_COUNT (23u) - #ifdef ARDUINO_MAIN const uint8_t digital_pin_to_port[] = { @@ -200,10 +205,10 @@ const uint8_t digital_pin_to_bit_position[] = { PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK PIN7_bp, // 7 PA7/SS/CLKOUT - PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bp, // 10 PC2/TCA0 PWM - PIN3_bp, // 11 PC3/TCA0 PWM + PIN0_bp, // 8 PC0/USART1_Tx + PIN1_bp, // 9 PC1/USART1_Rx + PIN2_bp, // 10 PC2 + PIN3_bp, // 11 PC3 PIN0_bp, // 12 PD0/AIN0 PIN1_bp, // 13 PD1/AIN1 PIN2_bp, // 14 PD2/AIN2 @@ -227,10 +232,10 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK PIN7_bm, // 7 PA7/SS/CLKOUT - PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bm, // 10 PC2/TCA0 PWM - PIN3_bm, // 11 PC3/TCA0 PWM + PIN0_bm, // 8 PC0/USART1_Tx + PIN1_bm, // 9 PC1/USART1_Rx + PIN2_bm, // 10 PC2 + PIN3_bm, // 11 PC3 PIN0_bm, // 12 PD0/AIN0 PIN1_bm, // 13 PD1/AIN1 PIN2_bm, // 14 PD2/AIN2 @@ -247,22 +252,34 @@ const uint8_t digital_pin_to_bit_mask[] = { const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx +#if !defined(MILLIS_USE_TIMERB0) + TIMERB0, // 2 PA2/SDA +#else NOT_ON_TIMER, // 2 PA2/SDA +#endif +#if !defined(MILLIS_USE_TIMERB1) + TIMERB1, // 3 PA3/SCL +#else NOT_ON_TIMER, // 3 PA3/SCL +#endif NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK NOT_ON_TIMER, // 7 PA7/SS/CLKOUT - TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM - TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM - TIMERA0, // 10 PC2/TCA0 PWM - TIMERA0, // 11 PC3/TCA0 PWM - NOT_ON_TIMER, // 12 PD0/AIN0 - NOT_ON_TIMER, // 13 PD1/AIN1 - NOT_ON_TIMER, // 14 PD2/AIN2 - NOT_ON_TIMER, // 15 PD3/AIN3/LED_BUILTIN - NOT_ON_TIMER, // 16 PD4/AIN4 - NOT_ON_TIMER, // 17 PD5/AIN5 +#if !defined(MILLIS_USE_TIMERB2) + TIMERB2, // 8 PC0/USART1_Tx +#else + NOT_ON_TIMER, // 8 PC0/USART1_Tx +#endif + NOT_ON_TIMER, // 9 PC1/USART1_Rx + NOT_ON_TIMER, // 10 PC2 + NOT_ON_TIMER, // 11 PC3 + TIMERA0, // 12 PD0/AIN0 + TIMERA0, // 13 PD1/AIN1 + TIMERA0, // 14 PD2/AIN2 + TIMERA0, // 15 PD3/AIN3/LED_BUILTIN + TIMERA0, // 16 PD4/AIN4 + TIMERA0, // 17 PD5/AIN5 NOT_ON_TIMER, // 18 PD6/AIN6 NOT_ON_TIMER, // 19 PD7/AIN7/AREF NOT_ON_TIMER, // 20 PF0/USART2_Tx/TOSC1 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 49566a0..08e534e 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -20,120 +20,155 @@ #define DEFAULT_32PIN_PINOUT -#define NUM_DIGITAL_PINS 27 +// Arduino pin macros +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PC0 8 +#define PIN_PC1 9 +#define PIN_PC2 10 +#define PIN_PC3 11 +#define PIN_PD0 12 +#define PIN_PD1 13 +#define PIN_PD2 14 +#define PIN_PD3 15 +#define PIN_PD4 16 +#define PIN_PD5 17 +#define PIN_PD6 18 +#define PIN_PD7 19 +#define PIN_PF0 20 +#define PIN_PF1 21 +#define PIN_PF2 22 +#define PIN_PF3 23 +#define PIN_PF4 24 +#define PIN_PF5 25 +#define PIN_PF6 26 + +#define PINS_COUNT 27 +#define NUM_DIGITAL_PINS PINS_COUNT #define NUM_ANALOG_INPUTS 12 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define NUM_I2C_PINS 2 +#define NUM_SPI_PINS 3 +#define NUM_TOTAL_FREE_PINS PINS_COUNT +#define NUM_TOTAL_PINS PINS_COUNT #define ANALOG_INPUT_OFFSET 12 -#define LED_BUILTIN 7 // PA7 +#define LED_BUILTIN PIN_PA7 +#define EXTERNAL_NUM_INTERRUPTS 47 #define digitalPinToAnalogInput(p) ((p < 8) ? (p) : ((p) < 12) ? ((p) + 4) : ((p) < 20) ? ((p) - 12) : ((p) >= 22 && (p) <=25) ? ((p) - 10) : NOT_A_PIN) -#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 8 && (p) <= 11) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 12 && (p) <= 19) || ((p) >= 22 && (p) <= 25)) ? (p) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) ((p < 8) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) >= 8 && (p) <= 11) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 12 && (p) <= 19) || ((p) >= 22 && (p) <= 25)) ? (p) : NOT_A_PIN) #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) -#define MILLIS_USE_TIMERB2 // use TCB2 +#define MILLIS_USE_TIMERB2 // Use TCB2 if nothing else if defined #endif -#define EXTERNAL_NUM_INTERRUPTS (47) - -#define digitalPinHasPWM(p) (((p) >= 8 && (p) <= 11) || (p) == 24 || (p) == 25) +// PWM pins +#if defined(MILLIS_USE_TIMERB0) + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA3 || (p) == PIN_PC0) +#elif defined(MILLIS_USE_TIMERB1) + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PC0) +#else // default to MILLIS_USE_TIMERB2 + #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PA3) +#endif // Timer pin mapping -#define TCA0_PINS PORTMUX_TCA0_PORTC_gc -#define TCB0_PINS PORTMUX_TCB0_bm -#define TCB1_PINS PORTMUX_TCB1_bm -#define TCB2_PINS PORTMUX_TCB2_bm -#define TCB3_PINS 0x00 +#define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] +#define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 +#define TCB1_PINS 0x00 // TCB1 output on PA3 instead of PF5 +#define TCB2_PINS 0x00 // TCB2 output on PC0 instead of PB4 // SPI 0 // No pinswap enabled by default // Pinswap 2 not available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) -#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define PIN_SPI_MISO (5) -#define PIN_SPI_SCK (6) -#define PIN_SPI_MOSI (4) -#define PIN_SPI_SS (7) -#define PIN_SPI_MISO_PINSWAP_1 (9) -#define PIN_SPI_SCK_PINSWAP_1 (10) -#define PIN_SPI_MOSI_PINSWAP_1 (8) -#define PIN_SPI_SS_PINSWAP_1 (11) -static const uint8_t SS = PIN_SPI_SS; -static const uint8_t MOSI = PIN_SPI_MOSI; -static const uint8_t MISO = PIN_SPI_MISO; -static const uint8_t SCK = PIN_SPI_SCK; +#define SPI_MUX PORTMUX_SPI0_DEFAULT_gc +#define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_ALT1_gc +#define PIN_SPI_MISO PIN_PA5 +#define PIN_SPI_SCK PIN_PA6 +#define PIN_SPI_MOSI PIN_PA4 +#define PIN_SPI_SS PIN_PA7 +#define PIN_SPI_MISO_PINSWAP_1 PIN_PC1 +#define PIN_SPI_SCK_PINSWAP_1 PIN_PC2 +#define PIN_SPI_MOSI_PINSWAP_1 PIN_PC0 +#define PIN_SPI_SS_PINSWAP_1 PIN_PC3 +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) -#define PIN_WIRE_SDA (2) -#define PIN_WIRE_SCL (3) -#define PIN_WIRE_SDA_PINSWAP_1 (10) -#define PIN_WIRE_SCL_PINSWAP_1 (11) -static const uint8_t SDA = PIN_WIRE_SDA; -static const uint8_t SCL = PIN_WIRE_SCL; +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define TWI_MUX_PINSWAP PORTMUX_TWI0_ALT2_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 +#define PIN_WIRE_SDA_PINSWAP_1 PIN_PC2 +#define PIN_WIRE_SCL_PINSWAP_1 PIN_PC3 +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; // USART 0 // No pinswap enabled by default -#define HWSERIAL0 (&USART0) -#define HWSERIAL0_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_WIRE_HWSERIAL0_TX (0) -#define PIN_WIRE_HWSERIAL0_RX (1) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (4) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (5) +#define HWSERIAL0 &USART0 +#define HWSERIAL0_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 +#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap available -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (8) -#define PIN_WIRE_HWSERIAL1_RX (9) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (8) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (9) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc +#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 +#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 // USART 2 // No pinswap enabled by default -#define HWSERIAL2 (&USART2) -#define HWSERIAL2_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) -#define PIN_WIRE_HWSERIAL2_TX (20) -#define PIN_WIRE_HWSERIAL2_RX (21) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (24) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (25) - -#define PIN_A0 (12) -#define PIN_A1 (13) -#define PIN_A2 (14) -#define PIN_A3 (15) -#define PIN_A4 (16) -#define PIN_A5 (17) -#define PIN_A6 (18) -#define PIN_A7 (19) -#define PIN_A8 (22) -#define PIN_A9 (23) -#define PIN_A10 (24) -#define PIN_A11 (25) -#define PIN_A12 (22) -#define PIN_A13 (23) -#define PIN_A14 (24) -#define PIN_A15 (25) +#define HWSERIAL2 &USART2 +#define HWSERIAL2_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc +#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 +#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +// Analog pins +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PD4 +#define PIN_A5 PIN_PD5 +#define PIN_A6 PIN_PD6 +#define PIN_A7 PIN_PD7 +#define PIN_A8 PIN_PF2 +#define PIN_A9 PIN_PF3 +#define PIN_A10 PIN_PF4 +#define PIN_A11 PIN_PF5 +#define PIN_A12 PIN_PF2 +#define PIN_A13 PIN_PF3 +#define PIN_A14 PIN_PF4 +#define PIN_A15 PIN_PF5 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; @@ -151,36 +186,6 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PC0 8 -#define PIN_PC1 9 -#define PIN_PC2 10 -#define PIN_PC3 11 -#define PIN_PD0 12 -#define PIN_PD1 13 -#define PIN_PD2 14 -#define PIN_PD3 15 -#define PIN_PD4 16 -#define PIN_PD5 17 -#define PIN_PD6 18 -#define PIN_PD7 19 -#define PIN_PF0 20 -#define PIN_PF1 21 -#define PIN_PF2 22 -#define PIN_PF3 23 -#define PIN_PF4 24 -#define PIN_PF5 25 -#define PIN_PF6 26 - -#define PINS_COUNT (27u) - #ifdef ARDUINO_MAIN const uint8_t digital_pin_to_port[] = { @@ -192,10 +197,10 @@ const uint8_t digital_pin_to_port[] = { PA, // 5 PA5/MISO PA, // 6 PA6/SCK PA, // 7 PA7/SS/CLKOUT - PC, // 8 PC0/USART1_Tx/TCA0 PWM - PC, // 9 PC1/USART1_Rx/TCA0 PWM - PC, // 10 PC2/TCA0 PWM - PC, // 11 PC3/TCA0 PWM + PC, // 8 PC0/USART1_Tx + PC, // 9 PC1/USART1_Rx + PC, // 10 PC2 + PC, // 11 PC3 PD, // 12 PD0/AIN0 PD, // 13 PD1/AIN1 PD, // 14 PD2/AIN2 @@ -223,10 +228,10 @@ const uint8_t digital_pin_to_bit_position[] = { PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK PIN7_bp, // 7 PA7/SS/CLKOUT - PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bp, // 10 PC2/TCA0 PWM - PIN3_bp, // 11 PC3/TCA0 PWM + PIN0_bp, // 8 PC0/USART1_Tx + PIN1_bp, // 9 PC1/USART1_Rx + PIN2_bp, // 10 PC2 + PIN3_bp, // 11 PC3 PIN0_bp, // 12 PD0/AIN0 PIN1_bp, // 13 PD1/AIN1 PIN2_bp, // 14 PD2/AIN2 @@ -254,10 +259,10 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK PIN7_bm, // 7 PA7/SS/CLKOUT - PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bm, // 10 PC2/TCA0 PWM - PIN3_bm, // 11 PC3/TCA0 PWM + PIN0_bm, // 8 PC0/USART1_Tx + PIN1_bm, // 9 PC1/USART1_Rx + PIN2_bm, // 10 PC2 + PIN3_bm, // 11 PC3 PIN0_bm, // 12 PD0/AIN0 PIN1_bm, // 13 PD1/AIN1 PIN2_bm, // 14 PD2/AIN2 @@ -278,30 +283,42 @@ const uint8_t digital_pin_to_bit_mask[] = { const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 0 PA0/USART0_Tx/CLKIN NOT_ON_TIMER, // 1 PA1/USART0_Rx +#if !defined(MILLIS_USE_TIMERB0) + TIMERB0, // 2 PA2/SDA +#else NOT_ON_TIMER, // 2 PA2/SDA +#endif +#if !defined(MILLIS_USE_TIMERB1) + TIMERB1, // 3 PA3/SCL +#else NOT_ON_TIMER, // 3 PA3/SCL +#endif NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK NOT_ON_TIMER, // 7 PA7/SS/CLKOUT - TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM - TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM - TIMERA0, // 10 PC2/TCA0 PWM - TIMERA0, // 11 PC3/TCA0 PWM - NOT_ON_TIMER, // 12 PD0/AIN0 - NOT_ON_TIMER, // 13 PD1/AIN1 - NOT_ON_TIMER, // 14 PD2/AIN2 - NOT_ON_TIMER, // 15 PD3/AIN3/LED_BUILTIN - NOT_ON_TIMER, // 16 PD4/AIN4 - NOT_ON_TIMER, // 17 PD5/AIN5 +#if !defined(MILLIS_USE_TIMERB2) + TIMERB2, // 8 PC0/USART1_Tx +#else + NOT_ON_TIMER, // 8 PC0/USART1_Tx +#endif + NOT_ON_TIMER, // 9 PC1/USART1_Rx + NOT_ON_TIMER, // 10 PC2/ + NOT_ON_TIMER, // 11 PC3/ + TIMERA0, // 12 PD0/AIN0 + TIMERA0, // 13 PD1/AIN1 + TIMERA0, // 14 PD2/AIN2 + TIMERA0, // 15 PD3/AIN3/LED_BUILTIN + TIMERA0, // 16 PD4/AIN4 + TIMERA0, // 17 PD5/AIN5 NOT_ON_TIMER, // 18 PD6/AIN6 NOT_ON_TIMER, // 19 PD7/AIN7/AREF NOT_ON_TIMER, // 20 PF0/USART2_Tx/TOSC1 NOT_ON_TIMER, // 21 PF1/USART2_Rx/TOSC2 NOT_ON_TIMER, // 22 PF2/AIN12 NOT_ON_TIMER, // 23 PF3/AIN13 - TIMERB0, // 24 PF4/AIN14/TCB0 PWM - TIMERB1, // 25 PF5/AIN15/TCB1 PWM + NOT_ON_TIMER, // 24 PF4/AIN14 + NOT_ON_TIMER, // 25 PF5/AIN15 NOT_ON_TIMER // 26 PF6 RESET }; From 9271e6cff149ce0fa36cf4fed72c44b85dc8aae6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 3 May 2020 22:19:48 +0200 Subject: [PATCH 150/351] Formatting --- .../variants/28pin-standard/pins_arduino.h | 9 +- .../variants/32pin-standard/pins_arduino.h | 9 +- .../variants/40pin-standard/pins_arduino.h | 86 ++-- .../variants/48pin-standard/pins_arduino.h | 388 +++++++++--------- 4 files changed, 253 insertions(+), 239 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 1cc724b..e851a8d 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -67,11 +67,14 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA3 || (p) == PIN_PC0) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PC0) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) #else // default to MILLIS_USE_TIMERB2 - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PA3) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif // Timer pin mapping diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 08e534e..06635e0 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -70,11 +70,14 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA3 || (p) == PIN_PC0) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PC0) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) #else // default to MILLIS_USE_TIMERB2 - #define digitalPinHasPWM(p) (((p) >= PIN_PD0 && (p) <= PIN_PD5) || (p) == PIN_PA2 || (p) == PIN_PA3) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif // Timer pin mapping diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index a3ec17e..ef6e786 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -79,21 +79,25 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF5) + #define digitalPinHasPWM(p) (((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF5)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4) + #define digitalPinHasPWM(p) (((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4)) #elif defined(MILLIS_USE_TIMERB2) - #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4 || (p) == PIN_PF5) + #define digitalPinHasPWM(p) (((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #else // default to MILLIS_USE_TIMERB3 - #define digitalPinHasPWM(p) (((p) >= PIN_PC0 && (p) <= PIN_PC5) || (p) == PIN_PF4 || (p) == PIN_PF5) + #define digitalPinHasPWM(p) (((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #endif // Timer pin swaps -#define TCA0_PINS PORTMUX_TCA0_PORTC_gc -#define TCB0_PINS PORTMUX_TCB0_bm -#define TCB1_PINS PORTMUX_TCB1_bm -#define TCB2_PINS PORTMUX_TCB2_bm -#define TCB3_PINS 0x00 +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] +#define TCB0_PINS PORTMUX_TCB0_bm // TCB0 output on PF4 instead of PA2 +#define TCB1_PINS PORTMUX_TCB1_bm // TCB1 output on PF5 instead of PA3 +#define TCB2_PINS PORTMUX_TCB2_bm // TCB2 output on PB4 instead of PC0 +#define TCB3_PINS 0x00 // TCB3 output on PB5 instead of PC1 // SPI 0 // No pinswap enabled by default @@ -214,12 +218,12 @@ const uint8_t digital_pin_to_port[] = { PA, // 5 PA5/MISO PA, // 6 PA6/SCK PA, // 7 PA7/SS/CLKOUT - PC, // 8 PC0/USART1_Tx/TCA0 PWM - PC, // 9 PC1/USART1_Rx/TCA0 PWM - PC, // 10 PC2/TCA0 PWM - PC, // 11 PC3/TCA0 PWM - PC, // 12 PC4/TCA0 PWM - PC, // 13 PC5/TCA0 PWM + PC, // 8 PC0/USART1_Tx + PC, // 9 PC1/USART1_Rx + PC, // 10 PC2 + PC, // 11 PC3 + PC, // 12 PC4 + PC, // 13 PC5 PD, // 14 PD0/AIN0 PD, // 15 PD1/AIN1 PD, // 16 PD2/AIN2 @@ -236,8 +240,8 @@ const uint8_t digital_pin_to_port[] = { PF, // 27 PF1/USART2_Rx/TOSC2 PF, // 28 PF2/AIN12 PF, // 29 PF3/AIN13 - PF, // 30 PF4/AIN14/TCB0 PWM - PF, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PF, // 30 PF4/AIN14 + PF, // 31 PF5/AIN15/LED_BUILTIN PF // 32 PF6 RESET }; @@ -251,12 +255,12 @@ const uint8_t digital_pin_to_bit_position[] = { PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK PIN7_bp, // 7 PA7/SS/CLKOUT - PIN0_bp, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bp, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bp, // 10 PC2/TCA0 PWM - PIN3_bp, // 11 PC3/TCA0 PWM - PIN4_bp, // 12 PC4/TCA0 PWM - PIN5_bp, // 13 PC5/TCA0 PWM + PIN0_bp, // 8 PC0/USART1_Tx + PIN1_bp, // 9 PC1/USART1_Rx + PIN2_bp, // 10 PC2 + PIN3_bp, // 11 PC3 + PIN4_bp, // 12 PC4 + PIN5_bp, // 13 PC5 PIN0_bp, // 14 PD0/AIN0 PIN1_bp, // 15 PD1/AIN1 PIN2_bp, // 16 PD2/AIN2 @@ -273,8 +277,8 @@ const uint8_t digital_pin_to_bit_position[] = { PIN1_bp, // 27 PF1/USART2_Rx/TOSC2 PIN2_bp, // 28 PF2/AIN12 PIN3_bp, // 29 PF3/AIN13 - PIN4_bp, // 30 PF4/AIN14/TCB0 PWM - PIN5_bp, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN4_bp, // 30 PF4/AIN14 + PIN5_bp, // 31 PF5/AIN15/LED_BUILTIN PIN6_bp // 42 PF6 RESET }; @@ -288,12 +292,12 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK PIN7_bm, // 7 PA7/SS/CLKOUT - PIN0_bm, // 8 PC0/USART1_Tx/TCA0 PWM - PIN1_bm, // 9 PC1/USART1_Rx/TCA0 PWM - PIN2_bm, // 10 PC2/TCA0 PWM - PIN3_bm, // 11 PC3/TCA0 PWM - PIN4_bm, // 12 PC4/TCA0 PWM - PIN5_bm, // 13 PC5/TCA0 PWM + PIN0_bm, // 8 PC0/USART1_Tx + PIN1_bm, // 9 PC1/USART1_Rx + PIN2_bm, // 10 PC2 + PIN3_bm, // 11 PC3 + PIN4_bm, // 12 PC4 + PIN5_bm, // 13 PC5 PIN0_bm, // 14 PD0/AIN0 PIN1_bm, // 15 PD1/AIN1 PIN2_bm, // 16 PD2/AIN2 @@ -310,8 +314,8 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN1_bm, // 27 PF1/USART2_Rx/TOSC2 PIN2_bm, // 28 PF2/AIN12 PIN3_bm, // 29 PF3/AIN13 - PIN4_bm, // 30 PF4/AIN14/TCB0 PWM - PIN5_bm, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN4_bm, // 30 PF4/AIN14 + PIN5_bm, // 31 PF5/AIN15/LED_BUILTIN PIN6_bm // 32 PF6 RESET }; @@ -324,12 +328,12 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK NOT_ON_TIMER, // 7 PA7/SS/CLKOUT - TIMERA0, // 8 PC0/USART1_Tx/TCA0 PWM - TIMERA0, // 9 PC1/USART1_Rx/TCA0 PWM - TIMERA0, // 10 PC2/TCA0 PWM - TIMERA0, // 11 PC3/TCA0 PWM - TIMERA0, // 12 PC4/TCA0 PWM - TIMERA0, // 13 PC5/TCA0 PWM + TIMERA0, // 8 PC0/USART1_Tx + TIMERA0, // 9 PC1/USART1_Rx + TIMERA0, // 10 PC2 + TIMERA0, // 11 PC3 + TIMERA0, // 12 PC4 + TIMERA0, // 13 PC5 NOT_ON_TIMER, // 14 PD0/AIN0 NOT_ON_TIMER, // 15 PD1/AIN1 NOT_ON_TIMER, // 16 PD2/AIN2 @@ -349,12 +353,12 @@ const uint8_t digital_pin_to_timer[] = { #ifdef MILLIS_USE_TIMERB0 NOT_ON_TIMER, // 30 PF4/AIN14 #else - TIMERB0, // 30 PF4/AIN14/TCB0 PWM + TIMERB0, // 30 PF4/AIN14 #endif #ifdef MILLIS_USE_TIMERB1 NOT_ON_TIMER, // 31 PF5/AIN15/LED_BUILTIN #else - TIMERB1, // 31 PF5/AIN15/TCB1 PWM/LED_BUILTIN + TIMERB1, // 31 PF5/AIN15/LED_BUILTIN #endif NOT_ON_TIMER // 32 PF6 RESET }; diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 66fdd34..ba7a6fe 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -25,146 +25,195 @@ #define DEFAULT_48PIN_PINOUT -#define NUM_DIGITAL_PINS 41 +// Arduino pin macros +#define PIN_PA0 0 +#define PIN_PA1 1 +#define PIN_PA2 2 +#define PIN_PA3 3 +#define PIN_PA4 4 +#define PIN_PA5 5 +#define PIN_PA6 6 +#define PIN_PA7 7 +#define PIN_PB0 8 +#define PIN_PB1 9 +#define PIN_PB2 10 +#define PIN_PB3 11 +#define PIN_PB4 12 +#define PIN_PB5 13 +#define PIN_PC0 14 +#define PIN_PC1 15 +#define PIN_PC2 16 +#define PIN_PC3 17 +#define PIN_PC4 18 +#define PIN_PC5 19 +#define PIN_PC6 20 +#define PIN_PC7 21 +#define PIN_PD0 22 +#define PIN_PD1 23 +#define PIN_PD2 24 +#define PIN_PD3 25 +#define PIN_PD4 26 +#define PIN_PD5 27 +#define PIN_PD6 28 +#define PIN_PD7 29 +#define PIN_PE0 30 +#define PIN_PE1 31 +#define PIN_PE2 32 +#define PIN_PE3 33 +#define PIN_PF0 34 +#define PIN_PF1 35 +#define PIN_PF2 36 +#define PIN_PF3 37 +#define PIN_PF4 38 +#define PIN_PF5 39 +#define PIN_PF6 40 + +#define PINS_COUNT 41 +#define NUM_DIGITAL_PINS PINS_COUNT #define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 -#define NUM_I2C_PINS 2 // (SDA / SCL) -#define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) -#define NUM_TOTAL_PINS (NUM_DIGITAL_PINS) +#define NUM_I2C_PINS 2 +#define NUM_SPI_PINS 3 +#define NUM_TOTAL_FREE_PINS NUM_DIGITAL_PINS +#define NUM_TOTAL_PINS NUM_DIGITAL_PINS #define ANALOG_INPUT_OFFSET 22 -#define LED_BUILTIN 7 // PA7 +#define LED_BUILTIN PIN_PA7 +#define EXTERNAL_NUM_INTERRUPTS 47 #define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= 22 && (p) <= 33) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= 36 && (p) <=39) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) ((p <= 11) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) <= 15) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 22 && (p) <= 33) || ((p) >= 36 && (p) <= 39)) ? (p) : NOT_A_PIN) +// Timer to use for millis/micros #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) || !defined(MILLIS_USE_TIMERB3) -#define MILLIS_USE_TIMERB2 // Use TCB2 for millis generation +#define MILLIS_USE_TIMERB2 // Use TCB2 if nothing else if defined #endif -#define EXTERNAL_NUM_INTERRUPTS (47) - +// PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) >= 12 && (p) <= 19) || (p) == 39) + #define digitalPinHasPWM(p) (((p) == PIN_PB4) || ((p) == PIN_PB5) || ((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || \ + ((p) == PIN_PC3) || ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF5)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) >= 12 && (p) <= 19) || (p) == 38) + #define digitalPinHasPWM(p) (((p) == PIN_PB4) || ((p) == PIN_PB5) || ((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || \ + ((p) == PIN_PC3) || ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4)) #elif defined(MILLIS_USE_TIMERB2) - #define digitalPinHasPWM(p) (((p) >= 13 && (p) <= 19) || (p) == 38 || (p) == 39) + #define digitalPinHasPWM(p) (((p) == PIN_PB5) || ((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #else // default to MILLIS_USE_TIMERB3 - #define digitalPinHasPWM(p) ((p) == 12 || ((p) >= 14 && (p) <= 19) || (p) == 38 || (p) == 39) + #define digitalPinHasPWM(p) (((p) == PIN_PB4) || ((p) == PIN_PC0) || ((p) == PIN_PC1) || ((p) == PIN_PC2) || ((p) == PIN_PC3) || \ + ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #endif // Timer pin swaps -#define TCA0_PINS PORTMUX_TCA0_PORTC_gc -#define TCB0_PINS PORTMUX_TCB0_bm -#define TCB1_PINS PORTMUX_TCB1_bm -#define TCB2_PINS PORTMUX_TCB2_bm -#define TCB3_PINS 0x00 +#define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] +#define TCB0_PINS PORTMUX_TCB0_bm // TCB0 output on PF4 instead of PA2 +#define TCB1_PINS PORTMUX_TCB1_bm // TCB1 output on PF5 instead of PA3 +#define TCB2_PINS PORTMUX_TCB2_bm // TCB2 output on PB4 instead of PC0 +#define TCB3_PINS 0x00 // TCB3 output on PB5 instead of PC1 // SPI 0 // No pinswap enabled by default // Pinswap 2 not available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) -#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_ALT2_gc) -#define PIN_SPI_MISO (5) -#define PIN_SPI_SCK (6) -#define PIN_SPI_MOSI (4) -#define PIN_SPI_SS (7) -#define PIN_SPI_MISO_PINSWAP_1 (15) -#define PIN_SPI_SCK_PINSWAP_1 (16) -#define PIN_SPI_MOSI_PINSWAP_1 (14) -#define PIN_SPI_SS_PINSWAP_1 (17) -#define PIN_SPI_MISO_PINSWAP_2 (31) -#define PIN_SPI_SCK_PINSWAP_2 (32) -#define PIN_SPI_MOSI_PINSWAP_2 (30) -#define PIN_SPI_SS_PINSWAP_2 (33) -static const uint8_t SS = PIN_SPI_SS; -static const uint8_t MOSI = PIN_SPI_MOSI; -static const uint8_t MISO = PIN_SPI_MISO; -static const uint8_t SCK = PIN_SPI_SCK; +#define SPI_MUX PORTMUX_SPI0_DEFAULT_gc +#define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_ALT1_gc +#define SPI_MUX_PINSWAP_2 PORTMUX_SPI0_ALT2_gc +#define PIN_SPI_MISO PIN_PA5 +#define PIN_SPI_SCK PIN_PA6 +#define PIN_SPI_MOSI PIN_PA4 +#define PIN_SPI_SS PIN_PA7 +#define PIN_SPI_MISO_PINSWAP_1 PIN_PC1 +#define PIN_SPI_SCK_PINSWAP_1 PIN_PC2 +#define PIN_SPI_MOSI_PINSWAP_1 PIN_PC0 +#define PIN_SPI_SS_PINSWAP_1 PIN_PC3 +#define PIN_SPI_MISO_PINSWAP_2 PIN_PE1 +#define PIN_SPI_SCK_PINSWAP_2 PIN_PE2 +#define PIN_SPI_MOSI_PINSWAP_2 PIN_PE0 +#define PIN_SPI_SS_PINSWAP_2 PIN_PE3 +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) -#define PIN_WIRE_SDA (2) -#define PIN_WIRE_SCL (3) -#define PIN_WIRE_SDA_PINSWAP_1 (16) -#define PIN_WIRE_SCL_PINSWAP_1 (17) -static const uint8_t SDA = PIN_WIRE_SDA; -static const uint8_t SCL = PIN_WIRE_SCL; +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define TWI_MUX_PINSWAP PORTMUX_TWI0_ALT2_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 +#define PIN_WIRE_SDA_PINSWAP_1 PIN_PC2 +#define PIN_WIRE_SCL_PINSWAP_1 PIN_PC3 +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; // USART 0 // No pinswap by default -#define HWSERIAL0 (&USART0) -#define HWSERIAL0_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_WIRE_HWSERIAL0_TX (0) -#define PIN_WIRE_HWSERIAL0_RX (1) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (4) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (5) +#define HWSERIAL0 &USART0 +#define HWSERIAL0_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 +#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap by default -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_ALT1_gc) -#define PIN_WIRE_HWSERIAL1_TX (14) -#define PIN_WIRE_HWSERIAL1_RX (15) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (18) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (19) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_ALT1_gc +#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 +#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC4 +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC5 // USART 2 // No pinswap by default -#define HWSERIAL2 (&USART2) -#define HWSERIAL2_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) -#define PIN_WIRE_HWSERIAL2_TX (34) -#define PIN_WIRE_HWSERIAL2_RX (35) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (38) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (39) +#define HWSERIAL2 &USART2 +#define HWSERIAL2_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc +#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 +#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 // USART 3 // No pinswap by default -#define HWSERIAL3 (&USART3) -#define HWSERIAL3_DRE_VECTOR (USART3_DRE_vect) -#define HWSERIAL3_DRE_VECTOR_NUM (USART3_DRE_vect_num) -#define HWSERIAL3_RXC_VECTOR (USART3_RXC_vect) -#define HWSERIAL3_MUX (PORTMUX_USART3_DEFAULT_gc) -#define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART3_ALT1_gc) -#define PIN_WIRE_HWSERIAL3_TX (8) -#define PIN_WIRE_HWSERIAL3_RX (9) -#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 (12) -#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 (13) - -#define PIN_A0 (22) -#define PIN_A1 (23) -#define PIN_A2 (24) -#define PIN_A3 (25) -#define PIN_A4 (26) -#define PIN_A5 (27) -#define PIN_A6 (28) -#define PIN_A7 (29) -#define PIN_A8 (30) -#define PIN_A9 (31) -#define PIN_A10 (32) -#define PIN_A11 (33) -#define PIN_A12 (36) -#define PIN_A13 (37) -#define PIN_A14 (38) -#define PIN_A15 (39) +#define HWSERIAL3 &USART3 +#define HWSERIAL3_DRE_VECTOR USART3_DRE_vect +#define HWSERIAL3_DRE_VECTOR_NUM USART3_DRE_vect_num +#define HWSERIAL3_RXC_VECTOR USART3_RXC_vect +#define HWSERIAL3_MUX PORTMUX_USART3_DEFAULT_gc +#define HWSERIAL3_MUX_PINSWAP_1 PORTMUX_USART3_ALT1_gc +#define PIN_WIRE_HWSERIAL3_TX PIN_PB0 +#define PIN_WIRE_HWSERIAL3_RX PIN_PB1 +#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 PIN_PB4 +#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 PIN_PB5 +// Analog pins +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PD4 +#define PIN_A5 PIN_PD5 +#define PIN_A6 PIN_PD6 +#define PIN_A7 PIN_PD7 +#define PIN_A8 PIN_PE0 +#define PIN_A9 PIN_PE1 +#define PIN_A10 PIN_PE2 +#define PIN_A11 PIN_PE3 +#define PIN_A12 PIN_PF2 +#define PIN_A13 PIN_PF3 +#define PIN_A14 PIN_PF4 +#define PIN_A15 PIN_PF5 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; @@ -182,51 +231,6 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; -#define PIN_PA0 0 -#define PIN_PA1 1 -#define PIN_PA2 2 -#define PIN_PA3 3 -#define PIN_PA4 4 -#define PIN_PA5 5 -#define PIN_PA6 6 -#define PIN_PA7 7 -#define PIN_PB0 8 -#define PIN_PB1 9 -#define PIN_PB2 10 -#define PIN_PB3 11 -#define PIN_PB4 12 -#define PIN_PB5 13 -#define PIN_PC0 14 -#define PIN_PC1 15 -#define PIN_PC2 16 -#define PIN_PC3 17 -#define PIN_PC4 18 -#define PIN_PC5 19 -#define PIN_PC6 20 -#define PIN_PC7 21 -#define PIN_PD0 22 -#define PIN_PD1 23 -#define PIN_PD2 24 -#define PIN_PD3 25 -#define PIN_PD4 26 -#define PIN_PD5 27 -#define PIN_PD6 28 -#define PIN_PD7 29 -#define PIN_PE0 30 -#define PIN_PE1 31 -#define PIN_PE2 32 -#define PIN_PE3 33 -#define PIN_PF0 34 -#define PIN_PF1 35 -#define PIN_PF2 36 -#define PIN_PF3 37 -#define PIN_PF4 38 -#define PIN_PF5 39 -#define PIN_PF6 40 - -#define PINS_COUNT (41u) - - #ifdef ARDUINO_MAIN const uint8_t digital_pin_to_port[] = { @@ -243,13 +247,13 @@ const uint8_t digital_pin_to_port[] = { PB, // 10 PB2 PB, // 11 PB3 PB, // 12 PB4/(TCB2 PWM) - PB, // 13 PB5/TCB3 PWM - PC, // 14 PC0/USART1_Tx/TCA0 PWM - PC, // 15 PC1/USART1_Rx/TCA0 PWM - PC, // 16 PC2/TCA0 PWM - PC, // 17 PC3/TCA0 PWM - PC, // 18 PC4/TCA0 PWM - PC, // 19 PC5/TCA0 PWM + PB, // 13 PB5 + PC, // 14 PC0/USART1_Tx + PC, // 15 PC1/USART1_Rx + PC, // 16 PC2 + PC, // 17 PC3 + PC, // 18 PC4 + PC, // 19 PC5 PC, // 20 PC6 PC, // 21 PC7 PD, // 22 PD0/AIN0 @@ -268,8 +272,8 @@ const uint8_t digital_pin_to_port[] = { PF, // 35 PF1/USART2_Rx/TOSC2 PF, // 36 PF2/AIN12 PF, // 37 PF3/AIN13 - PF, // 38 PF4/AIN14/TCB0 PWM - PF, // 39 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PF, // 38 PF4/AIN14 + PF, // 39 PF5/AIN15/LED_BUILTIN PF // 40 PF6 RESET }; @@ -288,13 +292,13 @@ const uint8_t digital_pin_to_bit_position[] = { PIN2_bp, // 10 PB2 PIN3_bp, // 11 PB3 PIN4_bp, // 12 PB4/(TCB2 PWM) - PIN5_bp, // 13 PB5/TCB3 PWM - PIN0_bp, // 14 PC0/USART1_Tx/TCA0 PWM - PIN1_bp, // 15 PC1/USART1_Rx/TCA0 PWM - PIN2_bp, // 16 PC2/TCA0 PWM - PIN3_bp, // 17 PC3/TCA0 PWM - PIN4_bp, // 18 PC4/TCA0 PWM - PIN5_bp, // 19 PC5/TCA0 PWM + PIN5_bp, // 13 PB5 + PIN0_bp, // 14 PC0/USART1_Tx + PIN1_bp, // 15 PC1/USART1_Rx + PIN2_bp, // 16 PC2 + PIN3_bp, // 17 PC3 + PIN4_bp, // 18 PC4 + PIN5_bp, // 19 PC5 PIN6_bp, // 20 PC6 PIN7_bp, // 21 PC7 PIN0_bp, // 22 PD0/AIN0 @@ -313,8 +317,8 @@ const uint8_t digital_pin_to_bit_position[] = { PIN1_bp, // 35 PF1/USART2_Rx/TOSC2 PIN2_bp, // 36 PF2/AIN12 PIN3_bp, // 37 PF3/AIN13 - PIN4_bp, // 38 PF4/AIN14/TCB0 PWM - PIN5_bp, // 39 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN4_bp, // 38 PF4/AIN14 + PIN5_bp, // 39 PF5/AIN15/LED_BUILTIN PIN6_bp // 40 PF6 RESET }; @@ -333,13 +337,13 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN2_bm, // 10 PB2 PIN3_bm, // 11 PB3 PIN4_bm, // 12 PB4/(TCB2 PWM) - PIN5_bm, // 13 PB5/TCB3 PWM - PIN0_bm, // 14 PC0/USART1_Tx/TCA0 PWM - PIN1_bm, // 15 PC1/USART1_Rx/TCA0 PWM - PIN2_bm, // 16 PC2/TCA0 PWM - PIN3_bm, // 17 PC3/TCA0 PWM - PIN4_bm, // 18 PC4/TCA0 PWM - PIN5_bm, // 19 PC5/TCA0 PWM + PIN5_bm, // 13 PB5 + PIN0_bm, // 14 PC0/USART1_Tx + PIN1_bm, // 15 PC1/USART1_Rx + PIN2_bm, // 16 PC2 + PIN3_bm, // 17 PC3 + PIN4_bm, // 18 PC4 + PIN5_bm, // 19 PC5 PIN6_bm, // 20 PC6 PIN7_bm, // 21 PC7 PIN0_bm, // 22 PD0/AIN0 @@ -358,8 +362,8 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN1_bm, // 35 PF1/USART2_Rx/TOSC2 PIN2_bm, // 36 PF2/AIN12 PIN3_bm, // 37 PF3/AIN13 - PIN4_bm, // 38 PF4/AIN14/TCB0 PWM - PIN5_bm, // 39 PF5/AIN15/TCB1 PWM/LED_BUILTIN + PIN4_bm, // 38 PF4/AIN14 + PIN5_bm, // 39 PF5/AIN15/LED_BUILTIN PIN6_bm // 40 PF6 RESET }; @@ -376,22 +380,22 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 9 PB1/USART3_Rx NOT_ON_TIMER, // 10 PB2 NOT_ON_TIMER, // 11 PB3 -#ifdef MILLIS_USE_TIMERB2 - NOT_ON_TIMER, // 12 PB4 +#if !defined(MILLIS_USE_TIMERB2) + TIMERB2, // 12 PB4 #else - TIMERB2, // 12 PB4/TCB2 PWM + NOT_ON_TIMER, // 12 PB4 #endif -#ifdef MILLIS_USE_TIMERB3 - NOT_ON_TIMER, // 13 PB5 +#if !defined(MILLIS_USE_TIMERB3) + TIMERB3, // 13 PB5 #else - TIMERB3, // 13 PB5/TCB3 PWM + NOT_ON_TIMER, // 13 PB5 #endif - TIMERA0, // 14 PC0/USART1_Tx/TCA0 PWM - TIMERA0, // 15 PC1/USART1_Rx/TCA0 PWM - TIMERA0, // 16 PC2/TCA0 PWM - TIMERA0, // 17 PC3/TCA0 PWM - TIMERA0, // 18 PC4/TCA0 PWM - TIMERA0, // 19 PC5/TCA0 PWM + TIMERA0, // 14 PC0/USART1_Tx + TIMERA0, // 15 PC1/USART1_Rx + TIMERA0, // 16 PC2 + TIMERA0, // 17 PC3 + TIMERA0, // 18 PC4 + TIMERA0, // 19 PC5 NOT_ON_TIMER, // 20 PC6 NOT_ON_TIMER, // 21 PC7 NOT_ON_TIMER, // 22 PD0/AIN0 @@ -410,15 +414,15 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 35 PF1/USART2_Rx/TOSC2 NOT_ON_TIMER, // 36 PF2/AIN12 NOT_ON_TIMER, // 37 PF3/AIN13 -#ifdef MILLIS_USE_TIMERB0 - NOT_ON_TIMER, // 38 PF4/AIN14 +#if !defined(MILLIS_USE_TIMERB0) + TIMERB0, // 38 PF4/AIN14 #else - TIMERB0, // 38 PF4/AIN14/TCB0 PWM + NOT_ON_TIMER, // 38 PF4/AIN14 #endif -#ifdef MILLIS_USE_TIMERB1 - NOT_ON_TIMER, // 39 PF5/AIN15/LED_BUILTIN +#if !defined(MILLIS_USE_TIMERB1) + TIMERB1, // 39 PF5/AIN15/LED_BUILTIN #else - TIMERB1, // 39 PF5/AIN15/TCB1 PWM/LED_BUILTIN + NOT_ON_TIMER, // 39 PF5/AIN15/LED_BUILTIN #endif NOT_ON_TIMER // 40 PF6 RESET }; From 1746f4df0a43fe1de4491bf0dd546277147da9f6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 4 May 2020 14:04:45 +0200 Subject: [PATCH 151/351] Improve Wire library Lots on improvements have been borrowed from megaTinyCore --- megaavr/libraries/Wire/src/Wire.cpp | 76 ++++++++----- megaavr/libraries/Wire/src/Wire.h | 17 ++- megaavr/libraries/Wire/src/utility/twi.c | 139 ++++++++++------------- megaavr/libraries/Wire/src/utility/twi.h | 36 +++--- 4 files changed, 144 insertions(+), 124 deletions(-) diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index 826a59e..be88af6 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -15,7 +15,7 @@ You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - + Modified 2012 by Todd Krein (todd@krein.org) to implement repeated starts Modified 2017 by Chuck Todd (ctodd@cableone.net) to correct Unconfigured Slave Mode reboot */ @@ -119,7 +119,7 @@ void TwoWire::begin(void) TWI_MasterInit(DEFAULT_FREQUENCY); } -void TwoWire::begin(uint8_t address) +void TwoWire::begin(uint8_t address, bool receive_broadcast, uint8_t second_address) { rxBufferIndex = 0; rxBufferLength = 0; @@ -127,15 +127,35 @@ void TwoWire::begin(uint8_t address) txBufferIndex = 0; txBufferLength = 0; - TWI_SlaveInit(address); + TWI_SlaveInit(address, receive_broadcast, second_address); TWI_attachSlaveTxEvent(onRequestService, txBuffer); // default callback must exist TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, BUFFER_LENGTH); // default callback must exist } +void TwoWire::begin(int address, bool receive_broadcast, uint8_t second_address) +{ + begin((uint8_t)address, receive_broadcast, second_address); +} + +void TwoWire::begin(uint8_t address, bool receive_broadcast) +{ + begin(address, receive_broadcast, 0); +} + +void TwoWire::begin(int address, bool receive_broadcast) +{ + begin((uint8_t)address, receive_broadcast, 0); +} + +void TwoWire::begin(uint8_t address) +{ + begin(address, 0, 0); +} + void TwoWire::begin(int address) { - begin((uint8_t)address); + begin((uint8_t)address, 0, 0); } void TwoWire::end(void) @@ -196,17 +216,17 @@ void TwoWire::beginTransmission(int address) } // -// Originally, 'endTransmission' was an f(void) function. -// It has been modified to take one parameter indicating -// whether or not a STOP should be performed on the bus. -// Calling endTransmission(false) allows a sketch to -// perform a repeated start. +// Originally, 'endTransmission' was an f(void) function. +// It has been modified to take one parameter indicating +// whether or not a STOP should be performed on the bus. +// Calling endTransmission(false) allows a sketch to +// perform a repeated start. // -// WARNING: Nothing in the library keeps track of whether -// the bus tenure has been properly ended with a STOP. It -// is very possible to leave the bus in a hung state if -// no call to endTransmission(true) is made. Some I2C -// devices will behave oddly if they do not see a STOP. +// WARNING: Nothing in the library keeps track of whether +// the bus tenure has been properly ended with a STOP. It +// is very possible to leave the bus in a hung state if +// no call to endTransmission(true) is made. Some I2C +// devices will behave oddly if they do not see a STOP. // uint8_t TwoWire::endTransmission(bool sendStop) { @@ -223,8 +243,8 @@ uint8_t TwoWire::endTransmission(bool sendStop) return status; } -// This provides backwards compatibility with the original -// definition, and expected behaviour, of endTransmission +// This provides backwards compatibility with the original +// definition, and expected behaviour, of endTransmission // uint8_t TwoWire::endTransmission(void) { @@ -310,20 +330,20 @@ int TwoWire::peek(void) // e.g. when MDATA regsiter is written before MADDR void TwoWire::flush(void) { - // /* Clear buffers */ - // for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ - // txBuffer[i] = 0; - // rxBuffer[i] = 0; - // } + // /* Clear buffers */ + // for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ + // txBuffer[i] = 0; + // rxBuffer[i] = 0; + // } // - // /* Clear buffer variables */ - // txBufferIndex = 0; - // txBufferLength = 0; - // rxBufferIndex = 0; - // rxBufferLength = 0; + // /* Clear buffer variables */ + // txBufferIndex = 0; + // txBufferLength = 0; + // rxBufferIndex = 0; + // rxBufferLength = 0; // - // /* Turn off and on TWI module */ - // TWI_Flush(); + // /* Turn off and on TWI module */ + // TWI_Flush(); } // behind the scenes function that is called when data is received diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index 3ff1272..dc2f0c2 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -24,7 +24,15 @@ #include +#if ((RAMEND - RAMSTART) < 1023) +#define BUFFER_LENGTH 16 +#elif ((RAMEND - RAMSTART) < 4095) +#define BUFFER_LENGTH 32 +#elif ((RAMEND - RAMSTART) < 8191) +#define BUFFER_LENGTH 64 +#else #define BUFFER_LENGTH 128 +#endif // WIRE_HAS_END means Wire has end() #define WIRE_HAS_END 1 @@ -45,6 +53,7 @@ class TwoWire : public Stream static void (*user_onReceive)(int); static uint8_t onRequestService(void); static void onReceiveService(int); + public: TwoWire(); bool pins(uint8_t sda_pin, uint8_t scl_pin); @@ -52,6 +61,10 @@ class TwoWire : public Stream void begin(); void begin(uint8_t); void begin(int); + void begin(uint8_t, bool, uint8_t); + void begin(int, bool, uint8_t); + void begin(uint8_t, bool); + void begin(int, bool); void end(); void setClock(uint32_t); void beginTransmission(uint8_t); @@ -68,8 +81,8 @@ class TwoWire : public Stream virtual int read(void); virtual int peek(void); virtual void flush(void); - void onReceive( void (*)(int) ); - void onRequest( void (*)(void) ); + void onReceive(void (*)(int)); + void onRequest(void (*)(void)); inline size_t write(unsigned long n) { return write((uint8_t)n); } inline size_t write(long n) { return write((uint8_t)n); } diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 6249b70..28743c5 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -1,27 +1,26 @@ /****************************************************************************** * (c) 2018 Microchip Technology Inc. and its subsidiaries. -* -* Subject to your compliance with these terms, you may use Microchip software -* and any derivatives exclusively with Microchip products. It is your -* responsibility to comply with third party license terms applicable to your -* use of third party software (including open source software) that may +* +* Subject to your compliance with these terms, you may use Microchip software +* and any derivatives exclusively with Microchip products. It is your +* responsibility to comply with third party license terms applicable to your +* use of third party software (including open source software) that may * accompany Microchip software. * -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER -* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED -* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR -* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, -* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY -* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP -* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE -* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN -* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, +* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER +* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED +* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR +* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, +* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY +* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP +* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE +* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN +* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, * THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. * *****************************************************************************/ #include "twi.h" - #include "Arduino.h" /* Master variables */ @@ -59,13 +58,14 @@ static volatile TWI_MODE_t twi_mode; * Enables master read and write interrupts. * Remember to enable interrupts globally from the main application. * - * \param frequency The required baud. + * \param frequency The required baud. */ void TWI_MasterInit(uint32_t frequency) { - if (twi_mode != TWI_MODE_UNKNOWN) return; + if (twi_mode != TWI_MODE_UNKNOWN) + return; - // Enable input pullup for the default or pin swapped pin position +// Enable input pullup for the default or pin swapped pin position if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) { pinMode(PIN_WIRE_SDA, INPUT_PULLUP); @@ -98,11 +98,12 @@ void TWI_MasterInit(uint32_t frequency) * Assigns slave's own address. * Remember to enable interrupts globally from the main application. * - * \param address The TWI Slave's own address. + * \param address The TWI Slave's own address. */ -void TWI_SlaveInit(uint8_t address) +void TWI_SlaveInit(uint8_t address, uint8_t receive_broadcast, uint8_t second_address) { - if (twi_mode != TWI_MODE_UNKNOWN) return; + if (twi_mode != TWI_MODE_UNKNOWN) + return; twi_mode = TWI_MODE_SLAVE; @@ -113,7 +114,8 @@ void TWI_SlaveInit(uint8_t address) slave_callUserRequest = 0; slave_callUserReceive = 0; - TWI0.SADDR = address << 1; + TWI0.SADDR = address << 1 | receive_broadcast; + TWI0.SADDRMASK = second_address; TWI0.SCTRLA = TWI_DIEN_bm | TWI_APIEN_bm | TWI_PIEN_bm | TWI_ENABLE_bm; /* Bus Error Detection circuitry needs Master enabled to work */ @@ -130,7 +132,7 @@ void TWI_Flush(void) * TWI module disable function. * Disables both master and slave modes * - * \param frequency The required baud. + * \param frequency The required baud. */ void TWI_Disable(void) { @@ -139,7 +141,7 @@ void TWI_Disable(void) TWI0.MSTATUS = TWI_BUSSTATE_IDLE_gc; TWI0.SADDR = 0x00; TWI0.SCTRLA = 0x00; - + TWI0.SADDRMASK = 0; twi_mode = TWI_MODE_UNKNOWN; } @@ -182,38 +184,39 @@ uint8_t TWI_MasterReady(void) * * Sets the baud rate used by TWI Master. * - * \param frequency The required baud. + * \param frequency The required baud. */ void TWI_MasterSetBaud(uint32_t frequency) { - // Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; - // Where T_RISE varies depending on operating frequency... - // From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz + // Formula is: BAUD = ((F_CLKPER/frequency) - F_CLKPER*T_RISE - 10)/2; + // Where T_RISE varies depending on operating frequency... + // From 1617 DS: 1000ns @ 100kHz / 300ns @ 400kHz / 120ns @ 1MHz uint16_t t_rise; + uint16_t freq_khz = frequency / 1000; - if (frequency < 200000) + if (freq_khz < 200) { - frequency = 100000; + freq_khz = 100; t_rise = 1000; } - else if (frequency < 800000) + else if (freq_khz < 800) { - frequency = 400000; + freq_khz = 400; t_rise = 300; } - else if (frequency < 1200000) + else if (freq_khz < 1200) { - frequency = 1000000; + freq_khz = 1000; t_rise = 120; } else { - frequency = 100000; + freq_khz = 100; t_rise = 1000; } - uint32_t baud = ((F_CPU / frequency) - (((F_CPU * t_rise) / 1000) / 1000) / 1000 - 10) / 2; + uint32_t baud = ((F_CPU / 1000 / freq_khz) - (((F_CPU * t_rise) / 1000) / 1000) / 1000 - 10) / 2; TWI0.MBAUD = (uint8_t)baud; } @@ -279,11 +282,8 @@ uint8_t TWI_MasterRead(uint8_t slave_address, * \param bytesToWrite Number of bytes to write. * \param bytesToRead Number of bytes to read. * - * \retval 0:success - * \retval 1:data too long to fit in transmit buffer - * \retval 2:received NACK on transmit of address - * \retval 3:received NACK on transmit of data - * \retval 4:other error + * \retval true If transaction could be started. + * \retval false If transaction could not be started. */ uint8_t TWI_MasterWriteRead(uint8_t slave_address, uint8_t* write_data, @@ -291,7 +291,8 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, uint8_t bytes_to_read, uint8_t send_stop) { - if (twi_mode != TWI_MODE_MASTER) return false; + if (twi_mode != TWI_MODE_MASTER) + return false; /*Initiate transaction if bus is ready. */ if (master_trans_status == TWIM_STATUS_READY) @@ -311,8 +312,8 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, trigger_action: /* If write command, send the START condition + Address + - * 'R/_W = 0' - */ + * 'R/_W = 0' + */ if (master_bytesToWrite > 0) { twi_mode = TWI_MODE_MASTER_TRANSMIT; @@ -321,8 +322,8 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, } /* If read command, send the START condition + Address + - * 'R/_W = 1' - */ + * 'R/_W = 1' + */ else if (master_bytesToRead > 0) { twi_mode = TWI_MODE_MASTER_RECEIVE; @@ -356,22 +357,8 @@ uint8_t TWI_MasterWriteRead(uint8_t slave_address, } else { - // return 0 if success, >0 otherwise (follow classic AVR conventions) - switch (master_result) - { - case TWIM_RESULT_OK: - ret = 0; - break; - case TWIM_RESULT_BUFFER_OVERFLOW: - ret = 1; - break; - case TWIM_RESULT_NACK_RECEIVED: - ret = 3; - break; - default: - ret = 4; - break; - } + // return 0 if success, 1 otherwise + ret = (master_result == TWIM_RESULT_OK ? 0 : 1); } return ret; @@ -479,8 +466,8 @@ void TWI_MasterWriteHandler() } /* If bytes to read, send START condition + Address + - * 'R/_W = 1' - */ + * 'R/_W = 1' + */ else if (master_bytesRead < bytesToRead) { twi_mode = TWI_MODE_MASTER_RECEIVE; @@ -597,8 +584,8 @@ void TWI_SlaveInterruptHandler() else if (currentStatus & TWI_APIF_bm) { /* Call user onReceive function if end of Master Write/Slave Read. - * This should be hit when there is a STOP or REPSTART - */ + * This should be hit when there is a STOP or REPSTART + */ if (slave_callUserReceive == 1) { TWI_onSlaveReceive(slave_bytesRead); @@ -616,10 +603,10 @@ void TWI_SlaveInterruptHandler() { TWI_SlaveStopHandler(); - /* If CLKHOLD is high, we have missed an address match - from a fast start after stop. - Because the flag is shared we need to handle this here. - */ + /* If CLKHOLD is high, we have missed an address match + from a fast start after stop. + Because the flag is shared we need to handle this here. + */ if (TWI0.SSTATUS & TWI_CLKHOLD_bm) { /* CLKHOLD will be cleared by servicing the address match */ @@ -700,7 +687,7 @@ void TWI_SlaveStopHandler() /*! \brief TWI slave data interrupt handler. * - * This is the slave data handler that takes care of sending data to or + * This is the slave data handler that takes care of sending data to or * receiving data from a master * */ @@ -776,8 +763,8 @@ void TWI_SlaveReadHandler() /* Send ACK and wait for data interrupt */ TWI0.SCTRLB = TWI_SCMD_RESPONSE_gc; } - /* If buffer overflow, send NACK and wait for next START. - Set result buffer overflow */ + /* If buffer overflow, send NACK and wait for next START. + Set result buffer overflow */ else { TWI0.SCTRLB = TWI_ACKACT_bm | TWI_SCMD_COMPTRANS_gc; @@ -785,7 +772,7 @@ void TWI_SlaveReadHandler() } } -/* +/* * Function twi_attachSlaveRxEvent * Desc sets function called before a slave read operation * Input function: callback function to use @@ -798,7 +785,7 @@ void TWI_attachSlaveRxEvent(void (*function)(int), uint8_t* read_data, uint8_t b slave_bytesToRead = bytes_to_read; } -/* +/* * Function twi_attachSlaveTxEvent * Desc sets function called before a slave write operation * Input function: callback function to use @@ -832,4 +819,4 @@ ISR(TWI0_TWIM_vect) ISR(TWI0_TWIS_vect) { TWI_SlaveInterruptHandler(); -} \ No newline at end of file +} diff --git a/megaavr/libraries/Wire/src/utility/twi.h b/megaavr/libraries/Wire/src/utility/twi.h index e58f524..9663c27 100644 --- a/megaavr/libraries/Wire/src/utility/twi.h +++ b/megaavr/libraries/Wire/src/utility/twi.h @@ -1,21 +1,21 @@ /****************************************************************************** * (c) 2018 Microchip Technology Inc. and its subsidiaries. -* -* Subject to your compliance with these terms, you may use Microchip software -* and any derivatives exclusively with Microchip products. It is your -* responsibility to comply with third party license terms applicable to your -* use of third party software (including open source software) that may +* +* Subject to your compliance with these terms, you may use Microchip software +* and any derivatives exclusively with Microchip products. It is your +* responsibility to comply with third party license terms applicable to your +* use of third party software (including open source software) that may * accompany Microchip software. * -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER -* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED -* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR -* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, -* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY -* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP -* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE -* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN -* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, +* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER +* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED +* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A PARTICULAR +* PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, +* PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY +* KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP +* HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE +* FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN +* ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY, * THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. * *****************************************************************************/ @@ -34,7 +34,7 @@ #define TWIS_STATUS_BUSY 1 /*! Transaction result enumeration. */ -typedef enum TWIM_RESULT_enum +typedef enum __attribute__((packed)) TWIM_RESULT_enum { TWIM_RESULT_UNKNOWN = (0x00 << 0), TWIM_RESULT_OK = (0x01 << 0), @@ -46,7 +46,7 @@ typedef enum TWIM_RESULT_enum } TWIM_RESULT_t; /* Transaction result enumeration */ -typedef enum TWIS_RESULT_enum +typedef enum __attribute__((packed)) TWIS_RESULT_enum { TWIS_RESULT_UNKNOWN = (0x00 << 0), TWIS_RESULT_OK = (0x01 << 0), @@ -58,7 +58,7 @@ typedef enum TWIS_RESULT_enum } TWIS_RESULT_t; /*! TWI Modes */ -typedef enum TWI_MODE_enum +typedef enum __attribute__((packed)) TWI_MODE_enum { TWI_MODE_UNKNOWN = 0, TWI_MODE_MASTER = 1, @@ -74,7 +74,7 @@ typedef enum TWI_MODE_enum #define ADD_WRITE_BIT(address) (address & ~0x01) void TWI_MasterInit(uint32_t frequency); -void TWI_SlaveInit(uint8_t address); +void TWI_SlaveInit(uint8_t address, uint8_t receive_broadcast, uint8_t second_address); void TWI_Flush(void); void TWI_Disable(void); TWI_BUSSTATE_t TWI_MasterState(void); From 4e712716f00bb66337dee3efd58518fa7c788820 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 5 May 2020 21:22:15 +0200 Subject: [PATCH 152/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 84b9170..8ae5e4b 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.1 +version=1.0.4 # AVR compile variables # --------------------- From 3f133bd2852e5e9d0029936fec35dced66d5f5c1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 19 May 2020 11:27:14 +0200 Subject: [PATCH 153/351] Fix LED_BUILTIN comment Closes #72 --- megaavr/variants/28pin-standard/pins_arduino.h | 16 ++++++++-------- megaavr/variants/32pin-standard/pins_arduino.h | 16 ++++++++-------- megaavr/variants/40pin-standard/pins_arduino.h | 18 +++++++++--------- megaavr/variants/48pin-standard/pins_arduino.h | 18 +++++++++--------- megaavr/variants/nano-every/pins_arduino.h | 8 ++++---- 5 files changed, 38 insertions(+), 38 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index e851a8d..8b0bc2b 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -180,7 +180,7 @@ const uint8_t digital_pin_to_port[] = { PA, // 4 PA4/MOSI PA, // 5 PA5/MISO PA, // 6 PA6/SCK - PA, // 7 PA7/SS/CLKOUT + PA, // 7 PA7/SS/CLKOUT/LED_BUILTIN PC, // 8 PC0/USART1_Tx/TCA0 PWM PC, // 9 PC1/USART1_Rx/TCA0 PWM PC, // 10 PC2/TCA0 PWM @@ -188,7 +188,7 @@ const uint8_t digital_pin_to_port[] = { PD, // 12 PD0/AIN0 PD, // 13 PD1/AIN1 PD, // 14 PD2/AIN2 - PD, // 15 PD3/AIN3/LED_BUILTIN + PD, // 15 PD3/AIN3 PD, // 16 PD4/AIN4 PD, // 17 PD5/AIN5 PD, // 18 PD6/AIN6 @@ -207,7 +207,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN4_bp, // 4 PA4/MOSI PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK - PIN7_bp, // 7 PA7/SS/CLKOUT + PIN7_bp, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bp, // 8 PC0/USART1_Tx PIN1_bp, // 9 PC1/USART1_Rx PIN2_bp, // 10 PC2 @@ -215,7 +215,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN0_bp, // 12 PD0/AIN0 PIN1_bp, // 13 PD1/AIN1 PIN2_bp, // 14 PD2/AIN2 - PIN3_bp, // 15 PD3/AIN3/LED_BUILTIN + PIN3_bp, // 15 PD3/AIN3 PIN4_bp, // 16 PD4/AIN4 PIN5_bp, // 17 PD5/AIN5 PIN6_bp, // 18 PD6/AIN6 @@ -234,7 +234,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN4_bm, // 4 PA4/MOSI PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK - PIN7_bm, // 7 PA7/SS/CLKOUT + PIN7_bm, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bm, // 8 PC0/USART1_Tx PIN1_bm, // 9 PC1/USART1_Rx PIN2_bm, // 10 PC2 @@ -242,7 +242,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN0_bm, // 12 PD0/AIN0 PIN1_bm, // 13 PD1/AIN1 PIN2_bm, // 14 PD2/AIN2 - PIN3_bm, // 15 PD3/AIN3/LED_BUILTIN + PIN3_bm, // 15 PD3/AIN3 PIN4_bm, // 16 PD4/AIN4 PIN5_bm, // 17 PD5/AIN5 PIN6_bm, // 18 PD6/AIN6 @@ -268,7 +268,7 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK - NOT_ON_TIMER, // 7 PA7/SS/CLKOUT + NOT_ON_TIMER, // 7 PA7/SS/CLKOUT/LED_BUILTIN #if !defined(MILLIS_USE_TIMERB2) TIMERB2, // 8 PC0/USART1_Tx #else @@ -280,7 +280,7 @@ const uint8_t digital_pin_to_timer[] = { TIMERA0, // 12 PD0/AIN0 TIMERA0, // 13 PD1/AIN1 TIMERA0, // 14 PD2/AIN2 - TIMERA0, // 15 PD3/AIN3/LED_BUILTIN + TIMERA0, // 15 PD3/AIN3 TIMERA0, // 16 PD4/AIN4 TIMERA0, // 17 PD5/AIN5 NOT_ON_TIMER, // 18 PD6/AIN6 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 06635e0..e1e884a 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -199,7 +199,7 @@ const uint8_t digital_pin_to_port[] = { PA, // 4 PA4/MOSI PA, // 5 PA5/MISO PA, // 6 PA6/SCK - PA, // 7 PA7/SS/CLKOUT + PA, // 7 PA7/SS/CLKOUT/LED_BUILTIN PC, // 8 PC0/USART1_Tx PC, // 9 PC1/USART1_Rx PC, // 10 PC2 @@ -207,7 +207,7 @@ const uint8_t digital_pin_to_port[] = { PD, // 12 PD0/AIN0 PD, // 13 PD1/AIN1 PD, // 14 PD2/AIN2 - PD, // 15 PD3/AIN3/LED_BUILTIN + PD, // 15 PD3/AIN3 PD, // 16 PD4/AIN4 PD, // 17 PD5/AIN5 PD, // 18 PD6/AIN6 @@ -230,7 +230,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN4_bp, // 4 PA4/MOSI PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK - PIN7_bp, // 7 PA7/SS/CLKOUT + PIN7_bp, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bp, // 8 PC0/USART1_Tx PIN1_bp, // 9 PC1/USART1_Rx PIN2_bp, // 10 PC2 @@ -238,7 +238,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN0_bp, // 12 PD0/AIN0 PIN1_bp, // 13 PD1/AIN1 PIN2_bp, // 14 PD2/AIN2 - PIN3_bp, // 15 PD3/AIN3/LED_BUILTIN + PIN3_bp, // 15 PD3/AIN3 PIN4_bp, // 16 PD4/AIN4 PIN5_bp, // 17 PD5/AIN5 PIN6_bp, // 18 PD6/AIN6 @@ -261,7 +261,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN4_bm, // 4 PA4/MOSI PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK - PIN7_bm, // 7 PA7/SS/CLKOUT + PIN7_bm, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bm, // 8 PC0/USART1_Tx PIN1_bm, // 9 PC1/USART1_Rx PIN2_bm, // 10 PC2 @@ -269,7 +269,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN0_bm, // 12 PD0/AIN0 PIN1_bm, // 13 PD1/AIN1 PIN2_bm, // 14 PD2/AIN2 - PIN3_bm, // 15 PD3/AIN3/LED_BUILTIN + PIN3_bm, // 15 PD3/AIN3 PIN4_bm, // 16 PD4/AIN4 PIN5_bm, // 17 PD5/AIN5 PIN6_bm, // 18 PD6/AIN6 @@ -299,7 +299,7 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK - NOT_ON_TIMER, // 7 PA7/SS/CLKOUT + NOT_ON_TIMER, // 7 PA7/SS/CLKOUT/LED_BUILTIN #if !defined(MILLIS_USE_TIMERB2) TIMERB2, // 8 PC0/USART1_Tx #else @@ -311,7 +311,7 @@ const uint8_t digital_pin_to_timer[] = { TIMERA0, // 12 PD0/AIN0 TIMERA0, // 13 PD1/AIN1 TIMERA0, // 14 PD2/AIN2 - TIMERA0, // 15 PD3/AIN3/LED_BUILTIN + TIMERA0, // 15 PD3/AIN3 TIMERA0, // 16 PD4/AIN4 TIMERA0, // 17 PD5/AIN5 NOT_ON_TIMER, // 18 PD6/AIN6 diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index ef6e786..6c03291 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -217,7 +217,7 @@ const uint8_t digital_pin_to_port[] = { PA, // 4 PA4/MOSI PA, // 5 PA5/MISO PA, // 6 PA6/SCK - PA, // 7 PA7/SS/CLKOUT + PA, // 7 PA7/SS/CLKOUT/LED_BUILTIN PC, // 8 PC0/USART1_Tx PC, // 9 PC1/USART1_Rx PC, // 10 PC2 @@ -241,7 +241,7 @@ const uint8_t digital_pin_to_port[] = { PF, // 28 PF2/AIN12 PF, // 29 PF3/AIN13 PF, // 30 PF4/AIN14 - PF, // 31 PF5/AIN15/LED_BUILTIN + PF, // 31 PF5/AIN15 PF // 32 PF6 RESET }; @@ -254,7 +254,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN4_bp, // 4 PA4/MOSI PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK - PIN7_bp, // 7 PA7/SS/CLKOUT + PIN7_bp, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bp, // 8 PC0/USART1_Tx PIN1_bp, // 9 PC1/USART1_Rx PIN2_bp, // 10 PC2 @@ -278,7 +278,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN2_bp, // 28 PF2/AIN12 PIN3_bp, // 29 PF3/AIN13 PIN4_bp, // 30 PF4/AIN14 - PIN5_bp, // 31 PF5/AIN15/LED_BUILTIN + PIN5_bp, // 31 PF5/AIN15 PIN6_bp // 42 PF6 RESET }; @@ -291,7 +291,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN4_bm, // 4 PA4/MOSI PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK - PIN7_bm, // 7 PA7/SS/CLKOUT + PIN7_bm, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bm, // 8 PC0/USART1_Tx PIN1_bm, // 9 PC1/USART1_Rx PIN2_bm, // 10 PC2 @@ -315,7 +315,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN2_bm, // 28 PF2/AIN12 PIN3_bm, // 29 PF3/AIN13 PIN4_bm, // 30 PF4/AIN14 - PIN5_bm, // 31 PF5/AIN15/LED_BUILTIN + PIN5_bm, // 31 PF5/AIN15 PIN6_bm // 32 PF6 RESET }; @@ -327,7 +327,7 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK - NOT_ON_TIMER, // 7 PA7/SS/CLKOUT + NOT_ON_TIMER, // 7 PA7/SS/CLKOUT/LED_BUILTIN TIMERA0, // 8 PC0/USART1_Tx TIMERA0, // 9 PC1/USART1_Rx TIMERA0, // 10 PC2 @@ -356,9 +356,9 @@ const uint8_t digital_pin_to_timer[] = { TIMERB0, // 30 PF4/AIN14 #endif #ifdef MILLIS_USE_TIMERB1 - NOT_ON_TIMER, // 31 PF5/AIN15/LED_BUILTIN + NOT_ON_TIMER, // 31 PF5/AIN15 #else - TIMERB1, // 31 PF5/AIN15/LED_BUILTIN + TIMERB1, // 31 PF5/AIN15 #endif NOT_ON_TIMER // 32 PF6 RESET }; diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index ba7a6fe..7000e0a 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -241,7 +241,7 @@ const uint8_t digital_pin_to_port[] = { PA, // 4 PA4/MOSI PA, // 5 PA5/MISO PA, // 6 PA6/SCK - PA, // 7 PA7/SS/CLKOUT + PA, // 7 PA7/SS/CLKOUT/LED_BUILTIN PB, // 8 PB0/USART3_Tx PB, // 9 PB1/USART3_Rx PB, // 10 PB2 @@ -273,7 +273,7 @@ const uint8_t digital_pin_to_port[] = { PF, // 36 PF2/AIN12 PF, // 37 PF3/AIN13 PF, // 38 PF4/AIN14 - PF, // 39 PF5/AIN15/LED_BUILTIN + PF, // 39 PF5/AIN15 PF // 40 PF6 RESET }; @@ -286,7 +286,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN4_bp, // 4 PA4/MOSI PIN5_bp, // 5 PA5/MISO PIN6_bp, // 6 PA6/SCK - PIN7_bp, // 7 PA7/SS/CLKOUT + PIN7_bp, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bp, // 8 PB0/USART3_Tx PIN1_bp, // 9 PB1/USART3_Rx PIN2_bp, // 10 PB2 @@ -318,7 +318,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN2_bp, // 36 PF2/AIN12 PIN3_bp, // 37 PF3/AIN13 PIN4_bp, // 38 PF4/AIN14 - PIN5_bp, // 39 PF5/AIN15/LED_BUILTIN + PIN5_bp, // 39 PF5/AIN15 PIN6_bp // 40 PF6 RESET }; @@ -331,7 +331,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN4_bm, // 4 PA4/MOSI PIN5_bm, // 5 PA5/MISO PIN6_bm, // 6 PA6/SCK - PIN7_bm, // 7 PA7/SS/CLKOUT + PIN7_bm, // 7 PA7/SS/CLKOUT/LED_BUILTIN PIN0_bm, // 8 PB0/USART3_Tx PIN1_bm, // 9 PB1/USART3_Rx PIN2_bm, // 10 PB2 @@ -363,7 +363,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN2_bm, // 36 PF2/AIN12 PIN3_bm, // 37 PF3/AIN13 PIN4_bm, // 38 PF4/AIN14 - PIN5_bm, // 39 PF5/AIN15/LED_BUILTIN + PIN5_bm, // 39 PF5/AIN15 PIN6_bm // 40 PF6 RESET }; @@ -375,7 +375,7 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 4 PA4/MOSI NOT_ON_TIMER, // 5 PA5/MISO NOT_ON_TIMER, // 6 PA6/SCK - NOT_ON_TIMER, // 7 PA7/SS/CLKOUT + NOT_ON_TIMER, // 7 PA7/SS/CLKOUT/LED_BUILTIN NOT_ON_TIMER, // 8 PB0/USART3_Tx NOT_ON_TIMER, // 9 PB1/USART3_Rx NOT_ON_TIMER, // 10 PB2 @@ -420,9 +420,9 @@ const uint8_t digital_pin_to_timer[] = { NOT_ON_TIMER, // 38 PF4/AIN14 #endif #if !defined(MILLIS_USE_TIMERB1) - TIMERB1, // 39 PF5/AIN15/LED_BUILTIN + TIMERB1, // 39 PF5/AIN15 #else - NOT_ON_TIMER, // 39 PF5/AIN15/LED_BUILTIN + NOT_ON_TIMER, // 39 PF5/AIN15 #endif NOT_ON_TIMER // 40 PF6 RESET }; diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index 3236e99..d5c0620 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -215,7 +215,7 @@ const uint8_t digital_pin_to_port[] = { PB, // 10 PB1/USART3_Rx PE, // 11 PE0/AIN8 PE, // 12 PE1/AIN9 - PE, // 13 PE2/AIN10 + PE, // 13 PE2/AIN10/LED_BUILTIN PD, // 14 PD3/AIN3 PD, // 15 PD2/AIN2 PD, // 16 PD1/AIN1 @@ -260,7 +260,7 @@ const uint8_t digital_pin_to_bit_position[] = { PIN1_bp, // 10 PB1/USART3_Rx PIN0_bp, // 11 PE0/AIN8 PIN1_bp, // 12 PE1/AIN9 - PIN2_bp, // 13 PE2/AIN10 + PIN2_bp, // 13 PE2/AIN10/LED_BUILTIN PIN3_bp, // 14 PD3/AIN3 PIN2_bp, // 15 PD2/AIN2 PIN1_bp, // 16 PD1/AIN1 @@ -305,7 +305,7 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN1_bm, // 10 PB1/USART3_Rx PIN0_bm, // 11 PE0/AIN8 PIN1_bm, // 12 PE1/AIN9 - PIN2_bm, // 13 PE2/AIN19 + PIN2_bm, // 13 PE2/AIN10/LED_BUILTIN PIN3_bm, // 14 PD3/AIN3 PIN2_bm, // 15 PD2/AIN2 PIN1_bm, // 16 PD1/AIN1 @@ -349,7 +349,7 @@ const uint8_t digital_pin_to_timer[] = { TIMERA0, // 10 PB1/USART3_Rx NOT_ON_TIMER, // 11 PE0/AIN8 NOT_ON_TIMER, // 12 PE1/AIN9 - NOT_ON_TIMER, // 13 PE2/AIN10 + NOT_ON_TIMER, // 13 PE2/AIN10/LED_BUILTIN NOT_ON_TIMER, // 14 PD3/AIN3 NOT_ON_TIMER, // 15 PD2/AIN2 NOT_ON_TIMER, // 16 PD1/AIN1 From f136a98407637b35cc7e109ade5a22dc8f87db9d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 29 May 2020 10:23:40 +0200 Subject: [PATCH 154/351] Load user application + bootloader when uploading using programmer This means that the IDE won't wipe the bootloader anymore if you're uploading with a dedicated programmer --- megaavr/bootloaders/empty/empty.hex | 1 - megaavr/platform.txt | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/megaavr/bootloaders/empty/empty.hex b/megaavr/bootloaders/empty/empty.hex index 0bb9243..7ef5593 100644 --- a/megaavr/bootloaders/empty/empty.hex +++ b/megaavr/bootloaders/empty/empty.hex @@ -1,2 +1 @@ -:0200000002C03C :00000001FF \ No newline at end of file diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 8ae5e4b..69e65ce 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -137,7 +137,7 @@ tools.avrdude.program.params.quiet=-q -q # tools.avrdude.program.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value tools.avrdude.program.verify= tools.avrdude.program.params.noverify=-V -tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.with_bootloader.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q From 1ba38300fc02d93b6831375d79ae5aa5d381ed15 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 29 May 2020 13:30:07 +0200 Subject: [PATCH 155/351] Improve assembly listing output --- megaavr/boards.txt | 72 +++++++++++++++++++++++++++++++++++++++----- megaavr/platform.txt | 12 ++++---- 2 files changed, 70 insertions(+), 14 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 1af2713..4219cc7 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -19,7 +19,6 @@ menu.bootloader=Bootloader 4809.build.board=AVR_ATmega4809 4809.build.mcu=atmega4809 4809.build.extra_flags={build.oscillator} {build.compat} -4809.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 4809.bootloader.WDTCFG=0x00 @@ -153,6 +152,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.no_bootloader.upload.maximum_size=49152 4809.menu.bootloader.no_bootloader.upload.extra_params= 4809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +4809.menu.bootloader.no_bootloader.build.export_merged_output=false 4809.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 4809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -162,6 +162,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_default.upload.port=UART0_DEF 4809.menu.bootloader.uart0_default.upload.extra_params= 4809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart0_default.build.export_merged_output=true 4809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -172,6 +173,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4809.menu.bootloader.uart0_alternative.upload.extra_params= 4809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart0_alternative.build.export_merged_output=true 4809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -182,6 +184,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_default.upload.port=UART1_DEF 4809.menu.bootloader.uart1_default.upload.extra_params= 4809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart1_default.build.export_merged_output=true 4809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -192,6 +195,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4809.menu.bootloader.uart1_alternative.upload.extra_params= 4809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart1_alternative.build.export_merged_output=true 4809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -202,6 +206,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_default.upload.port=UART2_DEF 4809.menu.bootloader.uart2_default.upload.extra_params= 4809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart2_default.build.export_merged_output=true 4809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -212,6 +217,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4809.menu.bootloader.uart2_alternative.upload.extra_params= 4809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart2_alternative.build.export_merged_output=true 4809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -222,6 +228,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_default.upload.port=UART3_DEF 4809.menu.bootloader.uart3_default.upload.extra_params= 4809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart3_default.build.export_merged_output=true 4809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -232,6 +239,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 4809.menu.bootloader.uart3_alternative.upload.extra_params= 4809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +4809.menu.bootloader.uart3_alternative.build.export_merged_output=true 4809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -251,7 +259,6 @@ menu.bootloader=Bootloader 4808.build.board=AVR_ATmega4808 4808.build.mcu=atmega4808 4808.build.extra_flags={build.oscillator} -4808.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 4808.bootloader.WDTCFG=0x00 @@ -364,6 +371,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.no_bootloader.upload.maximum_size=49152 4808.menu.bootloader.no_bootloader.upload.extra_params= 4808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +4808.menu.bootloader.no_bootloader.build.export_merged_output=false 4808.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 4808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -373,6 +381,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_default.upload.port=UART0_DEF 4808.menu.bootloader.uart0_default.upload.extra_params= 4808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart0_default.build.export_merged_output=true 4808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -383,6 +392,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 4808.menu.bootloader.uart0_alternative.upload.extra_params= 4808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart0_alternative.build.export_merged_output=true 4808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -393,6 +403,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_default.upload.port=UART1_DEF 4808.menu.bootloader.uart1_default.upload.extra_params= 4808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart1_default.build.export_merged_output=true 4808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -403,6 +414,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 4808.menu.bootloader.uart1_alternative.upload.extra_params= 4808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart1_alternative.build.export_merged_output=true 4808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -413,6 +425,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_default.upload.port=UART2_DEF 4808.menu.bootloader.uart2_default.upload.extra_params= 4808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart2_default.build.export_merged_output=true 4808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -423,6 +436,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 4808.menu.bootloader.uart2_alternative.upload.extra_params= 4808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +4808.menu.bootloader.uart2_alternative.build.export_merged_output=true 4808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -443,7 +457,6 @@ menu.bootloader=Bootloader 3209.build.board=AVR_ATmega3209 3209.build.mcu=atmega3209 3209.build.extra_flags={build.oscillator} {build.compat} -3209.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 3209.bootloader.WDTCFG=0x00 @@ -558,6 +571,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.no_bootloader.upload.maximum_size=32768 3209.menu.bootloader.no_bootloader.upload.extra_params= 3209.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +3209.menu.bootloader.no_bootloader.build.export_merged_output=false 3209.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 3209.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -567,6 +581,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_default.upload.port=UART0_DEF 3209.menu.bootloader.uart0_default.upload.extra_params= 3209.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart0_default.build.export_merged_output=true 3209.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -577,6 +592,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3209.menu.bootloader.uart0_alternative.upload.extra_params= 3209.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart0_alternative.build.export_merged_output=true 3209.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -587,6 +603,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_default.upload.port=UART1_DEF 3209.menu.bootloader.uart1_default.upload.extra_params= 3209.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart1_default.build.export_merged_output=true 3209.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -597,6 +614,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3209.menu.bootloader.uart1_alternative.upload.extra_params= 3209.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart1_alternative.build.export_merged_output=true 3209.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -607,6 +625,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_default.upload.port=UART2_DEF 3209.menu.bootloader.uart2_default.upload.extra_params= 3209.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart2_default.build.export_merged_output=true 3209.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -617,6 +636,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3209.menu.bootloader.uart2_alternative.upload.extra_params= 3209.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart2_alternative.build.export_merged_output=true 3209.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -627,6 +647,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_default.upload.port=UART3_DEF 3209.menu.bootloader.uart3_default.upload.extra_params= 3209.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart3_default.build.export_merged_output=true 3209.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -637,6 +658,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 3209.menu.bootloader.uart3_alternative.upload.extra_params= 3209.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +3209.menu.bootloader.uart3_alternative.build.export_merged_output=true 3209.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -656,7 +678,6 @@ menu.bootloader=Bootloader 3208.build.board=AVR_ATmega3208 3208.build.mcu=atmega3208 3208.build.extra_flags={build.oscillator} -3208.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 3208.bootloader.WDTCFG=0x00 @@ -769,6 +790,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.no_bootloader.upload.maximum_size=32768 3208.menu.bootloader.no_bootloader.upload.extra_params= 3208.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +3208.menu.bootloader.no_bootloader.build.export_merged_output=false 3208.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 3208.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -778,6 +800,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_default.upload.port=UART0_DEF 3208.menu.bootloader.uart0_default.upload.extra_params= 3208.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart0_default.build.export_merged_output=true 3208.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -788,6 +811,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 3208.menu.bootloader.uart0_alternative.upload.extra_params= 3208.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart0_alternative.build.export_merged_output=true 3208.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -798,6 +822,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_default.upload.port=UART1_DEF 3208.menu.bootloader.uart1_default.upload.extra_params= 3208.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart1_default.build.export_merged_output=true 3208.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -808,6 +833,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 3208.menu.bootloader.uart1_alternative.upload.extra_params= 3208.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart1_alternative.build.export_merged_output=true 3208.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -818,6 +844,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_default.upload.port=UART2_DEF 3208.menu.bootloader.uart2_default.upload.extra_params= 3208.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart2_default.build.export_merged_output=true 3208.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -828,6 +855,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 3208.menu.bootloader.uart2_alternative.upload.extra_params= 3208.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +3208.menu.bootloader.uart2_alternative.build.export_merged_output=true 3208.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -847,7 +875,6 @@ menu.bootloader=Bootloader 1609.build.board=AVR_ATmega1609 1609.build.mcu=atmega1609 1609.build.extra_flags={build.oscillator} {build.compat} -1609.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 1609.bootloader.WDTCFG=0x00 @@ -962,6 +989,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.no_bootloader.upload.maximum_size=16384 1609.menu.bootloader.no_bootloader.upload.extra_params= 1609.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +1609.menu.bootloader.no_bootloader.build.export_merged_output=false 1609.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 1609.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -971,6 +999,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_default.upload.port=UART0_DEF 1609.menu.bootloader.uart0_default.upload.extra_params= 1609.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart0_default.build.export_merged_output=true 1609.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -981,6 +1010,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1609.menu.bootloader.uart0_alternative.upload.extra_params= 1609.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart0_alternative.build.export_merged_output=true 1609.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -991,6 +1021,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_default.upload.port=UART1_DEF 1609.menu.bootloader.uart1_default.upload.extra_params= 1609.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart1_default.build.export_merged_output=true 1609.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1001,6 +1032,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1609.menu.bootloader.uart1_alternative.upload.extra_params= 1609.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart1_alternative.build.export_merged_output=true 1609.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1011,6 +1043,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_default.upload.port=UART2_DEF 1609.menu.bootloader.uart2_default.upload.extra_params= 1609.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart2_default.build.export_merged_output=true 1609.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1021,6 +1054,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1609.menu.bootloader.uart2_alternative.upload.extra_params= 1609.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart2_alternative.build.export_merged_output=true 1609.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1031,6 +1065,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_default.upload.port=UART3_DEF 1609.menu.bootloader.uart3_default.upload.extra_params= 1609.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart3_default.build.export_merged_output=true 1609.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -1041,6 +1076,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 1609.menu.bootloader.uart3_alternative.upload.extra_params= 1609.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +1609.menu.bootloader.uart3_alternative.build.export_merged_output=true 1609.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1060,7 +1096,6 @@ menu.bootloader=Bootloader 1608.build.board=AVR_ATmega1608 1608.build.mcu=atmega1608 1608.build.extra_flags={build.oscillator} -1608.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 1608.bootloader.WDTCFG=0x00 @@ -1173,6 +1208,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.no_bootloader.upload.maximum_size=16384 1608.menu.bootloader.no_bootloader.upload.extra_params= 1608.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +1608.menu.bootloader.no_bootloader.build.export_merged_output=false 1608.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 1608.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -1182,6 +1218,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_default.upload.port=UART0_DEF 1608.menu.bootloader.uart0_default.upload.extra_params= 1608.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart0_default.build.export_merged_output=true 1608.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1192,6 +1229,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 1608.menu.bootloader.uart0_alternative.upload.extra_params= 1608.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart0_alternative.build.export_merged_output=true 1608.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1202,6 +1240,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_default.upload.port=UART1_DEF 1608.menu.bootloader.uart1_default.upload.extra_params= 1608.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart1_default.build.export_merged_output=true 1608.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1212,6 +1251,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 1608.menu.bootloader.uart1_alternative.upload.extra_params= 1608.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart1_alternative.build.export_merged_output=true 1608.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1222,6 +1262,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_default.upload.port=UART2_DEF 1608.menu.bootloader.uart2_default.upload.extra_params= 1608.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart2_default.build.export_merged_output=true 1608.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1232,6 +1273,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 1608.menu.bootloader.uart2_alternative.upload.extra_params= 1608.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +1608.menu.bootloader.uart2_alternative.build.export_merged_output=true 1608.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1251,7 +1293,6 @@ menu.bootloader=Bootloader 809.build.board=AVR_ATmega809 809.build.mcu=atmega809 809.build.extra_flags={build.oscillator} {build.compat} -809.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 809.bootloader.WDTCFG=0x00 @@ -1366,6 +1407,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.no_bootloader.upload.maximum_size=8192 809.menu.bootloader.no_bootloader.upload.extra_params= 809.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +809.menu.bootloader.no_bootloader.build.export_merged_output=false 809.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 809.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -1375,6 +1417,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_default.upload.port=UART0_DEF 809.menu.bootloader.uart0_default.upload.extra_params= 809.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart0_default.build.export_merged_output=true 809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1385,6 +1428,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 809.menu.bootloader.uart0_alternative.upload.extra_params= 809.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart0_alternative.build.export_merged_output=true 809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1395,6 +1439,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_default.upload.port=UART1_DEF 809.menu.bootloader.uart1_default.upload.extra_params= 809.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart1_default.build.export_merged_output=true 809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1405,6 +1450,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 809.menu.bootloader.uart1_alternative.upload.extra_params= 809.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart1_alternative.build.export_merged_output=true 809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1415,6 +1461,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_default.upload.port=UART2_DEF 809.menu.bootloader.uart2_default.upload.extra_params= 809.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart2_default.build.export_merged_output=true 809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1425,6 +1472,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 809.menu.bootloader.uart2_alternative.upload.extra_params= 809.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart2_alternative.build.export_merged_output=true 809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 @@ -1435,6 +1483,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_default.upload.port=UART3_DEF 809.menu.bootloader.uart3_default.upload.extra_params= 809.menu.bootloader.uart3_default.build.text_section_start=.text=0x200 +809.menu.bootloader.uart3_default.build.export_merged_output=true 809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 @@ -1445,6 +1494,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_alternative.upload.port=UART3_ALT 809.menu.bootloader.uart3_alternative.upload.extra_params= 809.menu.bootloader.uart3_alternative.build.text_section_start=.text=0x200 +809.menu.bootloader.uart3_alternative.build.export_merged_output=true 809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 @@ -1464,7 +1514,6 @@ menu.bootloader=Bootloader 808.build.board=AVR_ATmega808 808.build.mcu=atmega808 808.build.extra_flags={build.oscillator} -808.build.export_merged_output=false # Fuses we don't need to modify in the tools menu 808.bootloader.WDTCFG=0x00 @@ -1577,6 +1626,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.no_bootloader.upload.maximum_size=8192 808.menu.bootloader.no_bootloader.upload.extra_params= 808.menu.bootloader.no_bootloader.build.text_section_start=.text=0x0 +808.menu.bootloader.no_bootloader.build.export_merged_output=false 808.menu.bootloader.no_bootloader.bootloader.file=empty/empty.hex 808.menu.bootloader.no_bootloader.bootloader.BOOTEND=0x00 @@ -1586,6 +1636,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_default.upload.port=UART0_DEF 808.menu.bootloader.uart0_default.upload.extra_params= 808.menu.bootloader.uart0_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart0_default.build.export_merged_output=true 808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 @@ -1596,6 +1647,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_alternative.upload.port=UART0_ALT 808.menu.bootloader.uart0_alternative.upload.extra_params= 808.menu.bootloader.uart0_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart0_alternative.build.export_merged_output=true 808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 @@ -1606,6 +1658,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_default.upload.port=UART1_DEF 808.menu.bootloader.uart1_default.upload.extra_params= 808.menu.bootloader.uart1_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart1_default.build.export_merged_output=true 808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 @@ -1616,6 +1669,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_alternative.upload.port=UART1_ALT 808.menu.bootloader.uart1_alternative.upload.extra_params= 808.menu.bootloader.uart1_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart1_alternative.build.export_merged_output=true 808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 @@ -1626,6 +1680,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_default.upload.port=UART2_DEF 808.menu.bootloader.uart2_default.upload.extra_params= 808.menu.bootloader.uart2_default.build.text_section_start=.text=0x200 +808.menu.bootloader.uart2_default.build.export_merged_output=true 808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 @@ -1636,6 +1691,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_alternative.upload.port=UART2_ALT 808.menu.bootloader.uart2_alternative.upload.extra_params= 808.menu.bootloader.uart2_alternative.build.text_section_start=.text=0x200 +808.menu.bootloader.uart2_alternative.build.export_merged_output=true 808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 69e65ce..be13b07 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -75,11 +75,11 @@ recipe.objcopy.eep.pattern="{compiler.path}{compiler.objcopy.cmd}" {compiler.obj recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.hex" ## Save disassembler listing -recipe.hooks.objcopy.postobjcopy.1.pattern.windows=cmd /C "{compiler.path}{compiler.objdump.cmd}" {compiler.objdump.flags} "{build.path}/{build.project_name}.elf" > "{build.path}/{build.project_name}.lst" +recipe.hooks.objcopy.postobjcopy.1.pattern.windows=cmd /C "{compiler.path}{compiler.objdump.cmd}" {compiler.objdump.flags} "{build.path}/{build.project_name}.elf" > "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" recipe.hooks.objcopy.postobjcopy.1.pattern.linux=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" recipe.hooks.objcopy.postobjcopy.1.pattern.macosx=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" -recipe.hooks.objcopy.postobjcopy.2.pattern.linux="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.lst" -recipe.hooks.objcopy.postobjcopy.2.pattern.macosx="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.lst" +recipe.hooks.objcopy.postobjcopy.2.pattern.linux="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" +recipe.hooks.objcopy.postobjcopy.2.pattern.macosx="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" ## Save hex recipe.output.tmp_file={build.project_name}.hex @@ -87,13 +87,13 @@ recipe.output.save_file={build.project_name}_{build.mcu}_{build.f_cpu}.hex ## Save hex recipe.hooks.savehex.presavehex.1.pattern.windows="{runtime.platform.path}/scripts/delete_merged_output.bat" {build.export_merged_output} "{build.path}\{build.project_name}.with_bootloader.hex" -recipe.hooks.savehex.presavehex.2.pattern.windows=cmd /C copy "{build.path}\{build.project_name}.lst" "{sketch_path}" +recipe.hooks.savehex.presavehex.2.pattern.windows=cmd /C copy "{build.path}\{build.project_name}_{build.mcu}_{build.f_cpu}.lst" "{sketch_path}" recipe.hooks.savehex.presavehex.1.pattern.linux=chmod +x "{runtime.platform.path}/scripts/delete_merged_output.sh" recipe.hooks.savehex.presavehex.2.pattern.linux="{runtime.platform.path}/scripts/delete_merged_output.sh" {build.export_merged_output} "{build.path}/{build.project_name}.with_bootloader.hex" -recipe.hooks.savehex.presavehex.3.pattern.linux=cp "{build.path}/{build.project_name}.lst" "{sketch_path}" +recipe.hooks.savehex.presavehex.3.pattern.linux=cp "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" "{sketch_path}" recipe.hooks.savehex.presavehex.1.pattern.macosx=chmod +x "{runtime.platform.path}/scripts/delete_merged_output.sh" recipe.hooks.savehex.presavehex.2.pattern.macosx="{runtime.platform.path}/scripts/delete_merged_output.sh" {build.export_merged_output} "{build.path}/{build.project_name}.with_bootloader.hex" -recipe.hooks.savehex.presavehex.3.pattern.macosx=cp "{build.path}/{build.project_name}.lst" "{sketch_path}" +recipe.hooks.savehex.presavehex.3.pattern.macosx=cp "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" "{sketch_path}" ## Compute size From 4ecd828b4f8dd76751a455042466114fcc791a97 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 3 Jun 2020 07:12:41 +0200 Subject: [PATCH 156/351] Add 5 and 10 MHz internal clock option Closes #74 --- README.md | 2 + megaavr/boards.txt | 96 ++++++++++++++++++++++++++ megaavr/cores/coreX-corefiles/wiring.c | 55 +++++++++++---- 3 files changed, 139 insertions(+), 14 deletions(-) diff --git a/README.md b/README.md index 6bfa59a..d61b682 100644 --- a/README.md +++ b/README.md @@ -69,7 +69,9 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol |-----------|---------------------|--------------------------| | 20 MHz | Internal oscillator | | | 16 MHz | Internal oscillator | **Default option** | +| 10 MHz | Internal oscillator | Derived from 20 MHz osc. | | 8 MHz | Internal oscillator | Derived from 16 MHz osc. | +| 5 MHz | Internal oscillator | Derived from 20 MHz osc. | | 4 MHz | Internal oscillator | Derived from 16 MHz osc. | | 2 MHz | Internal oscillator | Derived from 16 MHz osc. | | 1 MHz | Internal oscillator | Derived from 16 MHz osc. | diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 4219cc7..8a2a196 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -87,12 +87,24 @@ menu.bootloader=Bootloader 4809.menu.clock.internal_20MHz.build.oscillator= 4809.menu.clock.internal_20MHz.build.f_cpu=20000000L +4809.menu.clock.internal_10MHz_div=Internal 10 MHz +4809.menu.clock.internal_10MHz_div.upload.speed=115200 +4809.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_10MHz_div.build.oscillator= +4809.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 4809.menu.clock.internal_8MHz_div=Internal 8 MHz 4809.menu.clock.internal_8MHz_div.upload.speed=115200 4809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 4809.menu.clock.internal_8MHz_div.build.oscillator= 4809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +4809.menu.clock.internal_5MHz_div=Internal 5 MHz +4809.menu.clock.internal_5MHz_div.upload.speed=115200 +4809.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_5MHz_div.build.oscillator= +4809.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 4809.menu.clock.internal_4MHz_div=Internal 4 MHz 4809.menu.clock.internal_4MHz_div.upload.speed=115200 4809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -312,12 +324,24 @@ menu.bootloader=Bootloader 4808.menu.clock.internal_20MHz.build.oscillator= 4808.menu.clock.internal_20MHz.build.f_cpu=20000000L +4808.menu.clock.internal_10MHz_div=Internal 10 MHz +4808.menu.clock.internal_10MHz_div.upload.speed=115200 +4808.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_10MHz_div.build.oscillator= +4808.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 4808.menu.clock.internal_8MHz_div=Internal 8 MHz 4808.menu.clock.internal_8MHz_div.upload.speed=115200 4808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 4808.menu.clock.internal_8MHz_div.build.oscillator= 4808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +4808.menu.clock.internal_5MHz_div=Internal 5 MHz +4808.menu.clock.internal_5MHz_div.upload.speed=115200 +4808.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_5MHz_div.build.oscillator= +4808.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 4808.menu.clock.internal_4MHz_div=Internal 4 MHz 4808.menu.clock.internal_4MHz_div.upload.speed=115200 4808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -512,12 +536,24 @@ menu.bootloader=Bootloader 3209.menu.clock.internal_20MHz.build.oscillator= 3209.menu.clock.internal_20MHz.build.f_cpu=20000000L +3209.menu.clock.internal_10MHz_div=Internal 10 MHz +3209.menu.clock.internal_10MHz_div.upload.speed=115200 +3209.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_10MHz_div.build.oscillator= +3209.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 3209.menu.clock.internal_8MHz_div=Internal 8 MHz 3209.menu.clock.internal_8MHz_div.upload.speed=115200 3209.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 3209.menu.clock.internal_8MHz_div.build.oscillator= 3209.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +3209.menu.clock.internal_5MHz_div=Internal 5 MHz +3209.menu.clock.internal_5MHz_div.upload.speed=115200 +3209.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_5MHz_div.build.oscillator= +3209.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 3209.menu.clock.internal_4MHz_div=Internal 4 MHz 3209.menu.clock.internal_4MHz_div.upload.speed=115200 3209.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -731,12 +767,24 @@ menu.bootloader=Bootloader 3208.menu.clock.internal_20MHz.build.oscillator= 3208.menu.clock.internal_20MHz.build.f_cpu=20000000L +3208.menu.clock.internal_10MHz_div=Internal 10 MHz +3208.menu.clock.internal_10MHz_div.upload.speed=115200 +3208.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_10MHz_div.build.oscillator= +3208.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 3208.menu.clock.internal_8MHz_div=Internal 8 MHz 3208.menu.clock.internal_8MHz_div.upload.speed=115200 3208.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 3208.menu.clock.internal_8MHz_div.build.oscillator= 3208.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +3208.menu.clock.internal_5MHz_div=Internal 5 MHz +3208.menu.clock.internal_5MHz_div.upload.speed=115200 +3208.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_5MHz_div.build.oscillator= +3208.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 3208.menu.clock.internal_4MHz_div=Internal 4 MHz 3208.menu.clock.internal_4MHz_div.upload.speed=115200 3208.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -930,12 +978,24 @@ menu.bootloader=Bootloader 1609.menu.clock.internal_20MHz.build.oscillator= 1609.menu.clock.internal_20MHz.build.f_cpu=20000000L +1609.menu.clock.internal_10MHz_div=Internal 10 MHz +1609.menu.clock.internal_10MHz_div.upload.speed=115200 +1609.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_10MHz_div.build.oscillator= +1609.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 1609.menu.clock.internal_8MHz_div=Internal 8 MHz 1609.menu.clock.internal_8MHz_div.upload.speed=115200 1609.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 1609.menu.clock.internal_8MHz_div.build.oscillator= 1609.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +1609.menu.clock.internal_5MHz_div=Internal 5 MHz +1609.menu.clock.internal_5MHz_div.upload.speed=115200 +1609.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_5MHz_div.build.oscillator= +1609.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 1609.menu.clock.internal_4MHz_div=Internal 4 MHz 1609.menu.clock.internal_4MHz_div.upload.speed=115200 1609.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -1149,12 +1209,24 @@ menu.bootloader=Bootloader 1608.menu.clock.internal_20MHz.build.oscillator= 1608.menu.clock.internal_20MHz.build.f_cpu=20000000L +1608.menu.clock.internal_10MHz_div=Internal 10 MHz +1608.menu.clock.internal_10MHz_div.upload.speed=115200 +1608.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_10MHz_div.build.oscillator= +1608.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 1608.menu.clock.internal_8MHz_div=Internal 8 MHz 1608.menu.clock.internal_8MHz_div.upload.speed=115200 1608.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 1608.menu.clock.internal_8MHz_div.build.oscillator= 1608.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +1608.menu.clock.internal_5MHz_div=Internal 5 MHz +1608.menu.clock.internal_5MHz_div.upload.speed=115200 +1608.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_5MHz_div.build.oscillator= +1608.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 1608.menu.clock.internal_4MHz_div=Internal 4 MHz 1608.menu.clock.internal_4MHz_div.upload.speed=115200 1608.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -1348,12 +1420,24 @@ menu.bootloader=Bootloader 809.menu.clock.internal_20MHz.build.oscillator= 809.menu.clock.internal_20MHz.build.f_cpu=20000000L +809.menu.clock.internal_10MHz_div=Internal 10 MHz +809.menu.clock.internal_10MHz_div.upload.speed=115200 +809.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +809.menu.clock.internal_10MHz_div.build.oscillator= +809.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 809.menu.clock.internal_8MHz_div=Internal 8 MHz 809.menu.clock.internal_8MHz_div.upload.speed=115200 809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 809.menu.clock.internal_8MHz_div.build.oscillator= 809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +809.menu.clock.internal_5MHz_div=Internal 5 MHz +809.menu.clock.internal_5MHz_div.upload.speed=115200 +809.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +809.menu.clock.internal_5MHz_div.build.oscillator= +809.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 809.menu.clock.internal_4MHz_div=Internal 4 MHz 809.menu.clock.internal_4MHz_div.upload.speed=115200 809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 @@ -1567,12 +1651,24 @@ menu.bootloader=Bootloader 808.menu.clock.internal_20MHz.build.oscillator= 808.menu.clock.internal_20MHz.build.f_cpu=20000000L +808.menu.clock.internal_10MHz_div=Internal 10 MHz +808.menu.clock.internal_10MHz_div.upload.speed=115200 +808.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 +808.menu.clock.internal_10MHz_div.build.oscillator= +808.menu.clock.internal_10MHz_div.build.f_cpu=10000000L + 808.menu.clock.internal_8MHz_div=Internal 8 MHz 808.menu.clock.internal_8MHz_div.upload.speed=115200 808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 808.menu.clock.internal_8MHz_div.build.oscillator= 808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L +808.menu.clock.internal_5MHz_div=Internal 5 MHz +808.menu.clock.internal_5MHz_div.upload.speed=115200 +808.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 +808.menu.clock.internal_5MHz_div.build.oscillator= +808.menu.clock.internal_5MHz_div.build.f_cpu=5000000L + 808.menu.clock.internal_4MHz_div=Internal 4 MHz 808.menu.clock.internal_4MHz_div.upload.speed=115200 808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 diff --git a/megaavr/cores/coreX-corefiles/wiring.c b/megaavr/cores/coreX-corefiles/wiring.c index 2ba73b8..a04037f 100644 --- a/megaavr/cores/coreX-corefiles/wiring.c +++ b/megaavr/cores/coreX-corefiles/wiring.c @@ -188,7 +188,6 @@ void delayMicroseconds(unsigned int us) us -= 5; //=2 cycles #elif F_CPU >= 20000000L - // for the 20 MHz clock on rare Arduino boards // for a one-microsecond delay, simply return. the overhead // of the function call takes 18 (20) cycles, which is 1us @@ -213,7 +212,6 @@ void delayMicroseconds(unsigned int us) us -= 7; // 2 cycles #elif F_CPU >= 16000000L - // for the 16 MHz clock on most Arduino boards // for a one-microsecond delay, simply return. the overhead // of the function call takes 14 (16) cycles, which is 1us @@ -230,7 +228,6 @@ void delayMicroseconds(unsigned int us) us -= 5; // = 2 cycles, #elif F_CPU >= 12000000L - // for the 12 MHz clock if somebody is working with USB // for a 1 microsecond delay, simply return. the overhead // of the function call takes 14 (16) cycles, which is 1.5us @@ -246,8 +243,23 @@ void delayMicroseconds(unsigned int us) // us is at least 6 so we can substract 5 us -= 5; //2 cycles +#elif F_CPU >= 10000000L + + // for a 1 microsecond delay, simply return. the overhead + // of the function call takes 14 (16) cycles, which is 1.5us + if (us <= 1) return; // = 3 cycles, (4 when true) + + // the following loop takes 2/5 of a microsecond (4 cycles) + // per iteration, so execute it 2.5 times for each microsecond of + // delay requested. + us = (us << 1) + (us >> 1); // x2.5 us, = 5 cycles + + // account for the time taken in the preceding commands. + // we just burned 20 (22) cycles above, remove 5, (5*4=20) + // us is at least 6 so we can subtract 5 + us -= 5; //2 cycles + #elif F_CPU >= 8000000L - // for the 8 MHz internal clock // for a 1 and 2 microsecond delay, simply return. the overhead // of the function call takes 14 (16) cycles, which is 2us @@ -263,10 +275,21 @@ void delayMicroseconds(unsigned int us) // us is at least 6 so we can substract 4 us -= 4; // = 2 cycles +#elif F_CPU >= 5000000L + + // For a 1 ~ 3 microsecond delay, simply return. The overhead + // of the function call takes 14 (16) cycles, which is 3us + if (us <= 3) return; // = 3 cycles, (4 when true) + + // The following loop takes 4/5th microsecond (4 cycles) + // per iteration, so we want to add it to 1/4th of itself + us += (us >> 2); + + us -= 2; // = 2 cycles + #elif F_CPU >= 4000000L // The overhead of the function call is 14 (16) cycles which is 4 us - if (us <= 2) - return; + if (us <= 2) return; // Subtract microseconds that were wasted in this function us -= 2; @@ -276,8 +299,7 @@ void delayMicroseconds(unsigned int us) #elif F_CPU >= 2000000L // The overhead of the function call is 14 (16) cycles which is 8.68 us // Plus the if-statement that takes 3 cycles (4 when true): ~11us - if (us <= 13) - return; + if (us <= 13) return; // Subtract microseconds that were wasted in this function us -= 11; // 2 cycles @@ -285,7 +307,6 @@ void delayMicroseconds(unsigned int us) us = (us >> 1); // 3 cycles #else - // for the 1 MHz internal clock (default settings for common Atmega microcontrollers) // the overhead of the function calls is 14 (16) cycles if (us <= 16) return; //= 3 cycles, (4 when true) @@ -329,19 +350,25 @@ void init() #if (F_CPU == 20000000L) /* No division on clock */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); -#elif (F_CPU >= 16000000L) +#elif (F_CPU == 16000000L) /* No division on clock */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, 0x00); -#elif (F_CPU >= 8000000L) +#elif (F_CPU == 10000000L) + /* Clock DIV2 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); +#elif (F_CPU == 8000000L) /* Clock DIV2 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_2X_gc)); -#elif (F_CPU >= 4000000L) +#elif (F_CPU == 5000000L) + /* Clock DIV4 */ + _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); +#elif (F_CPU == 4000000L) /* Clock DIV4 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_4X_gc)); -#elif (F_CPU >= 2000000L) +#elif (F_CPU == 2000000L) /* Clock DIV8 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_8X_gc)); -#elif (F_CPU >= 1000000L) +#elif (F_CPU == 1000000L) /* Clock DIV16 */ _PROTECTED_WRITE(CLKCTRL_MCLKCTRLB, (CLKCTRL_PEN_bm | CLKCTRL_PDIV_16X_gc)); #else From f27154293a9c306867e0b6d3f1e269b79c31da95 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 30 Jun 2020 20:25:03 +0200 Subject: [PATCH 157/351] Update README Fix BOD typo --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index d61b682..c129ce8 100644 --- a/README.md +++ b/README.md @@ -92,7 +92,7 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol | BOD threshold | |--------------------------------| -| 4.2 V | +| 4.3 V | | 4.0 V | | 3.7 V | | 3.3 V | @@ -104,7 +104,7 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol ## Reset pin -None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. Note that the reset pin cannot be usd as a GPIO when using a bootloader +None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. Note that the reset pin cannot be usd as a GPIO when using a bootloader. ## Printf support From db2cfe32e36bef11c3e30cfb304ce518f954dfbf Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 30 Jun 2020 20:25:46 +0200 Subject: [PATCH 158/351] Don't set unused fuse Closes #79 --- megaavr/boards.txt | 48 +++++++++++++++++++++++----------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index 8a2a196..c4bd61a 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -52,13 +52,13 @@ menu.bootloader=Bootloader 4809.menu.resetpin.reset=Reset 4809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 4809.menu.resetpin.gpio=GPIO -4809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +4809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 4809.menu.BOD.2v6=BOD 2.6V 4809.menu.BOD.2v6.bootloader.BODCFG=0x54 -4809.menu.BOD.4v2=BOD 4.2V -4809.menu.BOD.4v2.bootloader.BODCFG=0xF4 +4809.menu.BOD.4v3=BOD 4.3V +4809.menu.BOD.4v3.bootloader.BODCFG=0xF4 4809.menu.BOD.4v0=BOD 4.0V 4809.menu.BOD.4v0.bootloader.BODCFG=0xD4 4809.menu.BOD.3v7=BOD 3.7V @@ -289,13 +289,13 @@ menu.bootloader=Bootloader 4808.menu.resetpin.reset=Reset 4808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 4808.menu.resetpin.gpio=GPIO -4808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +4808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 4808.menu.BOD.2v6=BOD 2.6V 4808.menu.BOD.2v6.bootloader.BODCFG=0x54 -4808.menu.BOD.4v2=BOD 4.2V -4808.menu.BOD.4v2.bootloader.BODCFG=0xF4 +4808.menu.BOD.4v3=BOD 4.3V +4808.menu.BOD.4v3.bootloader.BODCFG=0xF4 4808.menu.BOD.4v0=BOD 4.0V 4808.menu.BOD.4v0.bootloader.BODCFG=0xD4 4808.menu.BOD.3v7=BOD 3.7V @@ -501,13 +501,13 @@ menu.bootloader=Bootloader 3209.menu.resetpin.reset=Reset 3209.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 3209.menu.resetpin.gpio=GPIO -3209.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +3209.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 3209.menu.BOD.2v6=BOD 2.6V 3209.menu.BOD.2v6.bootloader.BODCFG=0x54 -3209.menu.BOD.4v2=BOD 4.2V -3209.menu.BOD.4v2.bootloader.BODCFG=0xF4 +3209.menu.BOD.4v3=BOD 4.3V +3209.menu.BOD.4v3.bootloader.BODCFG=0xF4 3209.menu.BOD.4v0=BOD 4.0V 3209.menu.BOD.4v0.bootloader.BODCFG=0xD4 3209.menu.BOD.3v7=BOD 3.7V @@ -732,13 +732,13 @@ menu.bootloader=Bootloader 3208.menu.resetpin.reset=Reset 3208.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 3208.menu.resetpin.gpio=GPIO -3208.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +3208.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 3208.menu.BOD.2v6=BOD 2.6V 3208.menu.BOD.2v6.bootloader.BODCFG=0x54 -3208.menu.BOD.4v2=BOD 4.2V -3208.menu.BOD.4v2.bootloader.BODCFG=0xF4 +3208.menu.BOD.4v3=BOD 4.3V +3208.menu.BOD.4v3.bootloader.BODCFG=0xF4 3208.menu.BOD.4v0=BOD 4.0V 3208.menu.BOD.4v0.bootloader.BODCFG=0xD4 3208.menu.BOD.3v7=BOD 3.7V @@ -943,13 +943,13 @@ menu.bootloader=Bootloader 1609.menu.resetpin.reset=Reset 1609.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 1609.menu.resetpin.gpio=GPIO -1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 1609.menu.BOD.2v6=BOD 2.6V 1609.menu.BOD.2v6.bootloader.BODCFG=0x54 -1609.menu.BOD.4v2=BOD 4.2V -1609.menu.BOD.4v2.bootloader.BODCFG=0xF4 +1609.menu.BOD.4v3=BOD 4.3V +1609.menu.BOD.4v3.bootloader.BODCFG=0xF4 1609.menu.BOD.4v0=BOD 4.0V 1609.menu.BOD.4v0.bootloader.BODCFG=0xD4 1609.menu.BOD.3v7=BOD 3.7V @@ -1174,13 +1174,13 @@ menu.bootloader=Bootloader 1608.menu.resetpin.reset=Reset 1608.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 1608.menu.resetpin.gpio=GPIO -1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 1608.menu.BOD.2v6=BOD 2.6V 1608.menu.BOD.2v6.bootloader.BODCFG=0x54 -1608.menu.BOD.4v2=BOD 4.2V -1608.menu.BOD.4v2.bootloader.BODCFG=0xF4 +1608.menu.BOD.4v3=BOD 4.3V +1608.menu.BOD.4v3.bootloader.BODCFG=0xF4 1608.menu.BOD.4v0=BOD 4.0V 1608.menu.BOD.4v0.bootloader.BODCFG=0xD4 1608.menu.BOD.3v7=BOD 3.7V @@ -1385,13 +1385,13 @@ menu.bootloader=Bootloader 809.menu.resetpin.reset=Reset 809.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 809.menu.resetpin.gpio=GPIO -809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 809.menu.BOD.2v6=BOD 2.6V 809.menu.BOD.2v6.bootloader.BODCFG=0x54 -809.menu.BOD.4v2=BOD 4.2V -809.menu.BOD.4v2.bootloader.BODCFG=0xF4 +809.menu.BOD.4v3=BOD 4.3V +809.menu.BOD.4v3.bootloader.BODCFG=0xF4 809.menu.BOD.4v0=BOD 4.0V 809.menu.BOD.4v0.bootloader.BODCFG=0xD4 809.menu.BOD.3v7=BOD 3.7V @@ -1616,13 +1616,13 @@ menu.bootloader=Bootloader 808.menu.resetpin.reset=Reset 808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD 808.menu.resetpin.gpio=GPIO -808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC5 +808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 # Brown out detection 808.menu.BOD.2v6=BOD 2.6V 808.menu.BOD.2v6.bootloader.BODCFG=0x54 -808.menu.BOD.4v2=BOD 4.2V -808.menu.BOD.4v2.bootloader.BODCFG=0xF4 +808.menu.BOD.4v3=BOD 4.3V +808.menu.BOD.4v3.bootloader.BODCFG=0xF4 808.menu.BOD.4v0=BOD 4.0V 808.menu.BOD.4v0.bootloader.BODCFG=0xD4 808.menu.BOD.3v7=BOD 3.7V From 86f18ddc72b5ac28cab52852d5fc2da58643eff1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 2 Jul 2020 10:48:25 +0200 Subject: [PATCH 159/351] Update parent ID for ATmega808/809/1608/1609 Now the usersig (or USERROW) size is correct --- megaavr/avrdude.conf | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 10c32a1..14437b3 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -15797,7 +15797,7 @@ part parent ".avr8x_tiny" # ATmega808 #------------------------------------------------------------ -part parent ".avr8x_mega" +part parent ".avr8x_tiny" id = "m808"; desc = "ATmega808"; signature = 0x1E 0x93 0x26; @@ -15821,7 +15821,7 @@ part parent ".avr8x_mega" # ATmega809 #------------------------------------------------------------ -part parent ".avr8x_mega" +part parent ".avr8x_tiny" id = "m809"; desc = "ATmega809"; signature = 0x1E 0x93 0x2A; @@ -15845,7 +15845,7 @@ part parent ".avr8x_mega" # ATmega1608 #------------------------------------------------------------ -part parent ".avr8x_mega" +part parent ".avr8x_tiny" id = "m1608"; desc = "ATmega1608"; signature = 0x1E 0x94 0x27; @@ -15869,7 +15869,7 @@ part parent ".avr8x_mega" # ATmega1609 #------------------------------------------------------------ -part parent ".avr8x_mega" +part parent ".avr8x_tiny" id = "m1609"; desc = "ATmega1609"; signature = 0x1E 0x94 0x26; From 87f7f42b27825a5714cace7c4836426e090fa018 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 6 Jul 2020 12:26:17 +0200 Subject: [PATCH 160/351] Fix typos --- README.md | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index c129ce8..9b6f054 100644 --- a/README.md +++ b/README.md @@ -114,13 +114,13 @@ If you're using a serial port, simply use `Serial.printf("Milliseconds since sta ## Fast IO -For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compiles down to a single instruction. +For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compile down to a single instruction. Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that in order to gain any speed improvements, the pin number has to be a constant. ## Pin macros -Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that maps "Arduino pins" to the port and port number. -Note that all my Arduino cores has these macros if you prefer to use these rather than the default Arduino pin number. +Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that map "Arduino pins" to the port and port number. +Note that all my Arduino cores have these macros if you prefer to use these rather than the default Arduino pin number. ```c++ // Use PIN_PA0 macro to refer to pin PA0 (Arduino pin 0) @@ -149,7 +149,7 @@ Please have a look at the pins_arduino.h files for detailed info.

## Hardware features -Here's some hardware spesific features that differs from the older AVR families. +Here's some hardware specific features that differ from the older AVR families. ### Interrupt pins Unlike older AVRs the megaAVR-0 microcontrollers have fully featured interrupts on every pin. @@ -191,16 +191,16 @@ The megaAVR-0 microcontrollers are equipped with an analog comparator. It compar Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. ### Alternative pins -The megaAVR-0 microcontrollers support alternative pin assignments for some of its built-in peripherals. +The megaAVR-0 microcontrollers support alternative pin assignments for some of their built-in peripherals. This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. They will return `true` if that swap or pin combination is supported. For `Serial` peripherals the method is `pins(tx,rx)`, for `Wire` it's `pins(sda,scl)` and for `SPI` it's `pins(mosi,miso,sck,ss)`. (Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) -Note that `swap()` and `pins()` does the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. +Note that `swap()` and `pins()` do the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral, -mote that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. +note that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. `swap()` or `pins()` are called like this. **Use either `swap()` or `pins()`, not both!** @@ -223,8 +223,8 @@ Available pin combinations for the *48 pin standard* pinout are: | Peripheral | Default | Alternative 1 | Alternative 2 | |------------|------------------------------- |------------------------------------|------------------------------------| | Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | | -| Serial1 | swap(0) **or** pins(12,13) | swap(1) **or** pins(14,15) | | -| Serial2 | swap(0) **or** pins(32,35) | swap(1) **or** pins(38,39) | | +| Serial1 | swap(0) **or** pins(14,15) | swap(1) **or** pins(18,19) | | +| Serial2 | swap(0) **or** pins(34,35) | swap(1) **or** pins(38,39) | | | Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | | | Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | | | SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(14,15,16,17) | swap(2) **or** pins(30,31,32,33) | From e6c658af37daa0cf75da32dbd1bab051db64f585 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 22 Jul 2020 10:50:58 +0200 Subject: [PATCH 161/351] Add macros to identify chip type Needed for some libraries to distinguish between MegaCoreX and the official megaavr core --- megaavr/variants/28pin-standard/pins_arduino.h | 3 ++- megaavr/variants/32pin-standard/pins_arduino.h | 3 ++- megaavr/variants/40pin-standard/pins_arduino.h | 3 ++- megaavr/variants/48pin-standard/pins_arduino.h | 3 ++- 4 files changed, 8 insertions(+), 4 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 8b0bc2b..18703b4 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -18,7 +18,8 @@ #include #include "timers.h" -#define DEFAULT_28PIN_PINOUT +#define MEGACOREX_DEFAULT_28PIN_PINOUT +#define __AVR_ATmegax08__ // Arduino pin macros #define PIN_PA0 0 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index e1e884a..7cdd0a1 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -18,7 +18,8 @@ #include #include "timers.h" -#define DEFAULT_32PIN_PINOUT +#define MEGACOREX_DEFAULT_32PIN_PINOUT +#define __AVR_ATmegax08__ // Arduino pin macros #define PIN_PA0 0 diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index 6c03291..b6e4dc5 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -20,7 +20,8 @@ #include #include "timers.h" -#define DEFAULT_40PIN_PINOUT +#define MEGACOREX_DEFAULT_40PIN_PINOUT +#define __AVR_ATmegax09__ // Pin macros #define PIN_PA0 0 diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 7000e0a..a129b6f 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -23,7 +23,8 @@ #include #include "timers.h" -#define DEFAULT_48PIN_PINOUT +#define MEGACOREX_DEFAULT_48PIN_PINOUT +#define __AVR_ATmegax09__ // Arduino pin macros #define PIN_PA0 0 From a16ef7cab5aae4a8afd84d87a7c246aafe4636c4 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 26 Jul 2020 11:08:35 +0200 Subject: [PATCH 162/351] Fix and improve Nano Every pinout Fix an issue where USART0 were incorrectly routed. Closes #80. Swap Serial2 (hardware USART0) so the default RX and TX pins are routed to pins that are broken put --- README.md | 12 +- megaavr/variants/nano-every/pins_arduino.h | 182 +++++++++++---------- 2 files changed, 98 insertions(+), 96 deletions(-) diff --git a/README.md b/README.md index 9b6f054..0074575 100644 --- a/README.md +++ b/README.md @@ -250,11 +250,11 @@ Available pin combinations for the *Uno WiFi* pinout are: Available pin combinations for the *Nano Every* pinout are: -| Peripheral | Default | Alternative | -|------------|------------------------------------|------------------------------| -| Serial | swap(0) **or** pins(25,24) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) | -| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | +| Peripheral | Default | Alternative | +|------------|------------------------------------|-----------------------------------------------| +| Serial | swap(0) **or** pins(25,24) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | +| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | ## How to install @@ -290,7 +290,7 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he [The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Arduino Nano Every [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index d5c0620..53e9dbe 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -28,8 +28,53 @@ #define NANO_EVERY_PINOUT #define NONA4809_PINOUT +#define __AVR_ATmegax09__ -#define NUM_DIGITAL_PINS 41 +// Arduino pin macros +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD3 14 +#define PIN_PD2 15 +#define PIN_PD1 16 +#define PIN_PD0 17 +#define PIN_PF2 18 +#define PIN_PF3 19 +#define PIN_PD4 20 +#define PIN_PD5 21 +#define PIN_PA2 22 +#define PIN_PA3 23 +#define PIN_PB5 24 +#define PIN_PB4 25 +#define PIN_PC3 26 +#define PIN_PA5 27 +#define PIN_PA4 28 +#define PIN_PD6 29 +#define PIN_PA6 30 +#define PIN_PA7 31 +#define PIN_PB3 32 +#define PIN_PC7 33 +#define PIN_PC0 34 +#define PIN_PC1 35 +#define PIN_PC2 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + +#define PINS_COUNT 41 +#define NUM_DIGITAL_PINS PINS_COUNT #define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 @@ -38,14 +83,16 @@ #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) #define ANALOG_INPUT_OFFSET 14 +#define LED_BUILTIN 13 +#define EXTERNAL_NUM_INTERRUPTS 47 #define digitalPinToAnalogInput(p) (((p) == A0) ? (3) : ((p) == A1) ? (2) : ((p) == A2) ? (1): ((p) == A3) ? (0): ((p) == A4) ? (12): ((p) == A5) ? (13): ((p) == A6) ? (4): ((p) == A7) ? (5): ((p) == A8) ? (7): ((p) == A9) ? (10) : ((p) == A10) ? (9): ((p) == A11) ? (8): ((p) == A12) ? (11): ((p) == A13) ? (14): ((p) == A14) ? (15) :((p) == A15) ? (29) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) -#define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation - -#define EXTERNAL_NUM_INTERRUPTS (47) +// Timer to use for millis/micros +#define MILLIS_USE_TIMERB3 -#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) +// PWM pins +#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTB_gc @@ -58,10 +105,10 @@ // Pinswap enabled by default and no alternative available #define SPI_INTERFACES_COUNT 1 #define SPI_MUX (PORTMUX_SPI0_ALT2_gc) -#define PIN_SPI_MISO (12) -#define PIN_SPI_SCK (13) -#define PIN_SPI_MOSI (11) -#define PIN_SPI_SS (8) +#define PIN_SPI_MISO (PIN_PE1) +#define PIN_SPI_SCK (PIN_PE2) +#define PIN_SPI_MOSI (PIN_PE0) +#define PIN_SPI_SS (PIN_PE3) static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; @@ -70,8 +117,8 @@ static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default, and no alternative available #define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define PIN_WIRE_SDA (22) -#define PIN_WIRE_SCL (23) +#define PIN_WIRE_SDA (PIN_PA2) +#define PIN_WIRE_SCL (PIN_PA3) static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; @@ -84,10 +131,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL0_TX (25) -#define PIN_WIRE_HWSERIAL0_RX (24) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (9) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) +#define PIN_WIRE_HWSERIAL0_TX (PIN_PB4) +#define PIN_WIRE_HWSERIAL0_RX (PIN_PB5) +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) // Nano every main USART available on Arduino header pins // USART1 on mega4809 (alternative pins) @@ -98,46 +145,45 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (1) -#define PIN_WIRE_HWSERIAL1_RX (0) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (34) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (35) +#define PIN_WIRE_HWSERIAL1_TX (PIN_PC4) +#define PIN_WIRE_HWSERIAL1_RX (PIN_PC5) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) // Nano Every pare USART available on testpoints -// USART0 on mega4809 (alternative pins) +// USART0 on mega4809 (default pins) // Mapped to HWSERIAL2 in Serial library #define HWSERIAL2 (&USART0) #define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) #define HWSERIAL2_DRE_VECTOR_NUM (USART0_DRE_vect_num) #define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL2_TX (24) -#define PIN_WIRE_HWSERIAL2_RX (23) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (2) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) - +#define HWSERIAL2_MUX (PORTMUX_USART0_DEFAULT_gc) +#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) +#define PIN_WIRE_HWSERIAL2_TX (PIN_PA0) +#define PIN_WIRE_HWSERIAL2_RX (PIN_PA1) +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PA4) +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PA5) + +// Hardware USART2 not in use because no pins are broken out #define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) -#define LED_BUILTIN 13 - -#define PIN_A0 (14) // AIN3 -#define PIN_A1 (15) // AIN2 -#define PIN_A2 (16) // AIN1 -#define PIN_A3 (17) // AIN0 -#define PIN_A4 (18) // AIN12 -#define PIN_A5 (19) // AIN13 -#define PIN_A6 (20) // AIN4 -#define PIN_A7 (21) // AIN5 -#define PIN_A8 (39) // AIN7 -#define PIN_A9 (13) // AIN10 -#define PIN_A10 (12) // AIN9 -#define PIN_A11 (11) // AIN8 -#define PIN_A12 (8) // AIN11 -#define PIN_A13 (6) // AIN14 -#define PIN_A14 (3) // AIN15 -#define PIN_A15 (29) // AIN6 - +// Analog pins +#define PIN_A0 PIN_PD3 // AIN3 +#define PIN_A1 PIN_PD2 // AIN2 +#define PIN_A2 PIN_PD1 // AIN1 +#define PIN_A3 PIN_PD0 // AIN0 +#define PIN_A4 PIN_PF2 // AIN12 +#define PIN_A5 PIN_PF3 // AIN13 +#define PIN_A6 PIN_PD4 // AIN4 +#define PIN_A7 PIN_PD5 // AIN5 +#define PIN_A8 PIN_PD7 // AIN7 +#define PIN_A9 PIN_PE2 // AIN10 +#define PIN_A10 PIN_PE1 // AIN9 +#define PIN_A11 PIN_PE0 // AIN8 +#define PIN_A12 PIN_PE3 // AIN11 +#define PIN_A13 PIN_PF4 // AIN14 +#define PIN_A14 PIN_PF5 // AIN15 +#define PIN_A15 PIN_PD6 // AIN6 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; @@ -155,50 +201,6 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; -#define PIN_PC5 0 -#define PIN_PC4 1 -#define PIN_PA0 2 -#define PIN_PF5 3 -#define PIN_PC6 4 -#define PIN_PB2 5 -#define PIN_PF4 6 -#define PIN_PA1 7 -#define PIN_PE3 8 -#define PIN_PB0 9 -#define PIN_PB1 10 -#define PIN_PE0 11 -#define PIN_PE1 12 -#define PIN_PE2 13 -#define PIN_PD3 14 -#define PIN_PD2 15 -#define PIN_PD1 16 -#define PIN_PD0 17 -#define PIN_PF2 18 -#define PIN_PF3 19 -#define PIN_PD4 20 -#define PIN_PD5 21 -#define PIN_PA2 22 -#define PIN_PA3 23 -#define PIN_PB5 24 -#define PIN_PB4 25 -#define PIN_PC3 26 -#define PIN_PA5 27 -#define PIN_PA4 28 -#define PIN_PD6 29 -#define PIN_PA6 30 -#define PIN_PA7 31 -#define PIN_PB3 32 -#define PIN_PC7 33 -#define PIN_PC0 34 -#define PIN_PC1 35 -#define PIN_PC2 36 -#define PIN_PF0 37 -#define PIN_PF1 38 -#define PIN_PD7 39 -#define PIN_PF6 40 - -#define PINS_COUNT (41u) - #ifdef ARDUINO_MAIN const uint8_t digital_pin_to_port[] = { From 8b4bd31df95be19a3fbaa90ea62542cbba5bb565 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 26 Jul 2020 11:49:26 +0200 Subject: [PATCH 163/351] Add another hardware serial port for Nano Every --- README.md | 5 ++-- megaavr/variants/nano-every/pins_arduino.h | 31 ++++++++++++++++------ 2 files changed, 26 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 0074575..2e09040 100644 --- a/README.md +++ b/README.md @@ -255,6 +255,7 @@ Available pin combinations for the *Nano Every* pinout are: | Serial | swap(0) **or** pins(25,24) | swap(1) **or** pins(9,10) | | Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | | Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | ## How to install @@ -290,13 +291,13 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he [The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Arduino Nano Every [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index 53e9dbe..01b3cc1 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -122,8 +122,9 @@ static const uint8_t SCK = PIN_SPI_SCK; static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -// Nano Every debug USART (not available on headers, only via the SAMD11 virtual COM port) -// USART3 on mega4809 (alternative pins) +// Nano Every debug USART (Serial) +// USART3 on mega4809 +// Maps to alternative pins by default // Mapped to HWSERIAL0 in Serial library #define HWSERIAL0 (&USART3) #define HWSERIAL0_DRE_VECTOR (USART3_DRE_vect) @@ -136,8 +137,9 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) #define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) -// Nano every main USART available on Arduino header pins -// USART1 on mega4809 (alternative pins) +// Nano every USART (Serial1) +// USART1 on mega4809 +// Maps to alternative pins by default // Mapped to HWSERIAL1 in Serial library #define HWSERIAL1 (&USART1) #define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) @@ -150,8 +152,9 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) #define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) -// Nano Every pare USART available on testpoints -// USART0 on mega4809 (default pins) +// Nano Every USART (Serial2) +// USART0 on mega4809 +// Maps to default pins by default // Mapped to HWSERIAL2 in Serial library #define HWSERIAL2 (&USART0) #define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) @@ -164,8 +167,20 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PA4) #define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PA5) -// Hardware USART2 not in use because no pins are broken out -#define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) +// Nano Every USART (Serial3) +// USART2 on mega4809 +// Maps to alternative pins by default +// Mapped to HWSERIAL3 in Serial library +#define HWSERIAL3 (&USART2) +#define HWSERIAL3_DRE_VECTOR (USART2_DRE_vect) +#define HWSERIAL3_DRE_VECTOR_NUM (USART2_DRE_vect_num) +#define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) +#define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) +#define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL3_TX (PIN_PF4) +#define PIN_WIRE_HWSERIAL3_RX (PIN_PF5) +#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) +#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) // Analog pins #define PIN_A0 PIN_PD3 // AIN3 From 7487bfbabe712a10a6b3a14da79b169390581f55 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 26 Jul 2020 13:28:27 +0200 Subject: [PATCH 164/351] Improve Uno Wifi Rev2 pinout pins_arduino.h cleanup + Serial3 is now available --- README.md | 27 +-- megaavr/variants/uno-wifi/pins_arduino.h | 260 ++++++++++++----------- 2 files changed, 153 insertions(+), 134 deletions(-) diff --git a/README.md b/README.md index 2e09040..0d59118 100644 --- a/README.md +++ b/README.md @@ -240,22 +240,25 @@ Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: | Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | | SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(8,9,10,11) | + Available pin combinations for the *Uno WiFi* pinout are: -| Peripheral | Default | Alternative | -|------------|------------------------------------|------------------------------| -| Serial | swap(0) **or** pins(27,26) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) | -| Serial2 | swap(0) **or** pins(24,23) | swap(1) **or** pins(2,7) | +| Peripheral | Default | Alternative | +|------------|---------------------------------------------------------|--------------------------------------------------------| +| Serial | swap(0) **or** pins(27,26) (connected to mEDBG) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) (available on SPI header) | +| Serial2 | swap(0) **or** pins(24,23) (connected to Wifi module) | swap(1) **or** pins(2,7) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | + Available pin combinations for the *Nano Every* pinout are: -| Peripheral | Default | Alternative | -|------------|------------------------------------|-----------------------------------------------| -| Serial | swap(0) **or** pins(25,24) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | -| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | -| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | +| Peripheral | Default | Alternative | +|------------|-------------------------------------------------------------|-----------------------------------------------| +| Serial | swap(0) **or** pins(25,24) (connected to USB-serial chip) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | +| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | ## How to install @@ -291,7 +294,7 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he [The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: - + ### Arduino Nano Every [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index c2a2dd4..96f8b3f 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -29,7 +29,52 @@ #define UNO_WIFI_REV2_PINOUT #define UNO2018_PINOUT +#define __AVR_ATmegax09__ +// Arduino pin macros +#define PIN_PC5 0 +#define PIN_PC4 1 +#define PIN_PA0 2 +#define PIN_PF5 3 +#define PIN_PC6 4 +#define PIN_PB2 5 +#define PIN_PF4 6 +#define PIN_PA1 7 +#define PIN_PE3 8 +#define PIN_PB0 9 +#define PIN_PB1 10 +#define PIN_PE0 11 +#define PIN_PE1 12 +#define PIN_PE2 13 +#define PIN_PD0 14 +#define PIN_PD1 15 +#define PIN_PD2 16 +#define PIN_PD3 17 +#define PIN_PD4 18 +#define PIN_PD5 19 +#define PIN_PA2 20 +#define PIN_PA3 21 +#define PIN_PC3 22 +#define PIN_PA5 23 +#define PIN_PA4 24 +#define PIN_PD6 25 +#define PIN_PB5 26 +#define PIN_PB4 27 +#define PIN_PA6 28 +#define PIN_PA7 29 +#define PIN_PB3 30 +#define PIN_PC7 31 +#define PIN_PC0 32 +#define PIN_PC1 33 +#define PIN_PC2 34 +#define PIN_PF2 35 +#define PIN_PF3 36 +#define PIN_PF0 37 +#define PIN_PF1 38 +#define PIN_PD7 39 +#define PIN_PF6 40 + +#define PINS_COUNT 41 #define NUM_DIGITAL_PINS 20 // (14 on digital headers + 6 on analog headers) #define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 6 // (TOSC1/2, VREF, RESET, DEBUG USART Rx/Tx) @@ -39,30 +84,46 @@ #define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) #define ANALOG_INPUT_OFFSET 14 +#define LED_BUILTIN PIN_PD6 +#define EXTERNAL_NUM_INTERRUPTS 47 #define digitalPinToAnalogInput(p) (((p) <= 5 && (p) != 3) ? (p) : ((p) >= 14 && (p) <= 19) ? ((p) - 14) : ((p) == 25) ? ((p) - 19) : ((p) == 39) ? ((p) - 32) : ((p) >= 11 && (p) <= 13) ? ((p) - 3) : ((p) == 8) ? ((p) + 3) : ((p) >= 35 && (p) <= 36) ? ((p) - 23) : ((p) == 6) ? ((p) + 8) : ((p) == 3) ? ((p) + 12) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) +// Timer to use for millis/micros #define MILLIS_USE_TIMERB3 // Use TCB3 for millis generation -#define EXTERNAL_NUM_INTERRUPTS (47) - -#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) +// PWM pins +#define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) // Timer pin mapping -#define TCA0_PINS PORTMUX_TCA0_PORTB_gc -#define TCB0_PINS PORTMUX_TCB0_bm -#define TCB1_PINS PORTMUX_TCB1_bm -#define TCB2_PINS PORTMUX_TCB2_bm -#define TCB3_PINS 0x00 +#define TCA0_PINS PORTMUX_TCA0_PORTB_gc +#define TCB0_PINS PORTMUX_TCB0_bm +#define TCB1_PINS PORTMUX_TCB1_bm +#define TCB2_PINS PORTMUX_TCB2_bm +#define TCB3_PINS 0x00 + +// Wiring to Wifi NINA module +#define NINA_GPIO0 PIN_PA6 +#define NINA_RESETN PIN_PA7 +#define NINA_ACK PIN_PF3 +#define NINA_CTS NINA_ACK +#define NINA_RTS NINA_GPIO0 +#define SPIWIFI_SS PIN_PF2 +#define SPIWIFI_ACK NINA_ACK +#define SPIWIFI_RESET ~NINA_RESETN + +// Wiring to IMU +#define SPIIMU_SS PIN_PB3 +#define SPIIMU_INT PIN_PC7 // SPI 0 // Pinswap enabled by default and no alternative available #define SPI_INTERFACES_COUNT 1 #define SPI_MUX (PORTMUX_SPI0_ALT1_gc) -#define PIN_SPI_MISO (33) -#define PIN_SPI_SCK (34) -#define PIN_SPI_MOSI (32) -#define PIN_SPI_SS (10) +#define PIN_SPI_MISO (PIN_PC1) +#define PIN_SPI_SCK (PIN_PC2) +#define PIN_SPI_MOSI (PIN_PC0) +#define PIN_SPI_SS (PIN_PB1) static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; @@ -71,41 +132,44 @@ static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default, and no alternative available #define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define PIN_WIRE_SDA (20) -#define PIN_WIRE_SCL (21) +#define PIN_WIRE_SDA (PIN_PA2) +#define PIN_WIRE_SCL (PIN_PA3) static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; -// Uno2 Main USART available on Arduino header pins -// USART1 on mega4809 (alternative pins) +// Uno Wifi Rev2 debug USART (Serial) +// USART3 on mega4809 +// Maps to alternative pins by default // Mapped to HWSERIAL0 in Serial library -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (1) -#define PIN_WIRE_HWSERIAL1_RX (0) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (32) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (33) - -// Uno2 Debug USART (not available on headers, only via the mEDGB virtual COM port) -// USART3 on mega4809 (alternative pins) -// Mapped to HWSERIAL1 in Serial library #define HWSERIAL0 (&USART3) #define HWSERIAL0_DRE_VECTOR (USART3_DRE_vect) #define HWSERIAL0_DRE_VECTOR_NUM (USART3_DRE_vect_num) #define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL0_TX (27) -#define PIN_WIRE_HWSERIAL0_RX (26) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (9) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (10) - -// Uno2 Spare USART available on testpoints -// USART0 on mega4809 (alternative pins) +#define PIN_WIRE_HWSERIAL0_TX (PIN_PB4) +#define PIN_WIRE_HWSERIAL0_RX (PIN_PB5) +#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) +#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) + +// Uno Wifi Rev2 USART (Serial1) +// USART1 on mega4809 +// Maps to alternative pins by default +// Mapped to HWSERIAL1 in Serial library +#define HWSERIAL1 (&USART1) +#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) +#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) +#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) +#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) +#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL1_TX (PIN_PC4) +#define PIN_WIRE_HWSERIAL1_RX (PIN_PC5) +#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) +#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) + +// Uno Wifi Rev2 USART for communicating with Wifi NINA (Serial2) +// USART0 on mega4809 +// Maps to alternative pins by default // Mapped to HWSERIAL2 in Serial library #define HWSERIAL2 (&USART0) #define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) @@ -113,32 +177,43 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) #define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) #define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL2_TX (24) -#define PIN_WIRE_HWSERIAL2_RX (23) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (2) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (7) - -#define HWSERIAL3_MUX (PORTMUX_USART2_NONE_gc) - -#define LED_BUILTIN 25 - -#define PIN_A0 (14) -#define PIN_A1 (15) -#define PIN_A2 (16) -#define PIN_A3 (17) -#define PIN_A4 (18) -#define PIN_A5 (19) -#define PIN_A6 (25) -#define PIN_A7 (39) -#define PIN_A8 (11) -#define PIN_A9 (12) -#define PIN_A10 (13) -#define PIN_A11 (8) -#define PIN_A12 (35) -#define PIN_A13 (36) -#define PIN_A14 (6) -#define PIN_A15 (3) - +#define PIN_WIRE_HWSERIAL2_TX (PIN_PA4) +#define PIN_WIRE_HWSERIAL2_RX (PIN_PA5) +#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PA0) +#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PA1) + +// Uno Wifi Rev2 USART (Serial3) +// USART2 on mega4809 +// Maps to alternative pins by default +// Mapped to HWSERIAL3 in Serial library +#define HWSERIAL3 (&USART2) +#define HWSERIAL3_DRE_VECTOR (USART2_DRE_vect) +#define HWSERIAL3_DRE_VECTOR_NUM (USART2_DRE_vect_num) +#define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) +#define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) +#define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) +#define PIN_WIRE_HWSERIAL3_TX (PIN_PF4) +#define PIN_WIRE_HWSERIAL3_RX (PIN_PF5) +#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) +#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) + +// Analog pins +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PD4 +#define PIN_A5 PIN_PD5 +#define PIN_A6 PIN_PD6 +#define PIN_A7 PIN_PD7 +#define PIN_A8 PIN_PE0 +#define PIN_A9 PIN_PE1 +#define PIN_A10 PIN_PE2 +#define PIN_A11 PIN_PE3 +#define PIN_A12 PIN_PF2 +#define PIN_A13 PIN_PF3 +#define PIN_A14 PIN_PF4 +#define PIN_A15 PIN_PF5 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; @@ -156,65 +231,6 @@ static const uint8_t A13 = PIN_A13; static const uint8_t A14 = PIN_A14; static const uint8_t A15 = PIN_A15; -#define PINS_COUNT (40u) - -//NINA -#define NINA_GPIO0 (28u) -#define NINA_RESETN (29u) -#define NINA_ACK (36u) -#define NINA_CTS NINA_ACK -#define NINA_RTS NINA_GPIO0 - -#define SPIWIFI_SS (35u) -#define SPIWIFI_ACK NINA_ACK -#define SPIWIFI_RESET (~NINA_RESETN) - -//IMU -#define SPIIMU_SS (30u) -#define SPIIMU_INT (31u) - -#define PIN_PC5 0 -#define PIN_PC4 1 -#define PIN_PA0 2 -#define PIN_PF5 3 -#define PIN_PC6 4 -#define PIN_PB2 5 -#define PIN_PF4 6 -#define PIN_PA1 7 -#define PIN_PE3 8 -#define PIN_PB0 9 -#define PIN_PB1 10 -#define PIN_PE0 11 -#define PIN_PE1 12 -#define PIN_PE2 13 -#define PIN_PD0 14 -#define PIN_PD1 15 -#define PIN_PD2 16 -#define PIN_PD3 17 -#define PIN_PD4 18 -#define PIN_PD5 19 -#define PIN_PA2 20 -#define PIN_PA3 21 -#define PIN_PC3 22 -#define PIN_PA5 23 -#define PIN_PA4 24 -#define PIN_PD6 25 -#define PIN_PB5 26 -#define PIN_PB4 27 -#define PIN_PA6 28 -#define PIN_PA7 29 -#define PIN_PB3 30 -#define PIN_PC7 31 -#define PIN_PC0 32 -#define PIN_PC1 33 -#define PIN_PC2 34 -#define PIN_PF2 35 -#define PIN_PF3 36 -#define PIN_PF0 37 -#define PIN_PF1 38 -#define PIN_PD7 39 -#define PIN_PF6 40 - #ifdef ARDUINO_MAIN // On the Arduino board, digital pins are also used From 8a20da11e0d439c60695840447d7ffe03232e689 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 26 Jul 2020 13:31:43 +0200 Subject: [PATCH 165/351] Table formatting --- README.md | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 0d59118..bb67f9b 100644 --- a/README.md +++ b/README.md @@ -243,22 +243,22 @@ Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: Available pin combinations for the *Uno WiFi* pinout are: -| Peripheral | Default | Alternative | -|------------|---------------------------------------------------------|--------------------------------------------------------| -| Serial | swap(0) **or** pins(27,26) (connected to mEDBG) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) (available on SPI header) | -| Serial2 | swap(0) **or** pins(24,23) (connected to Wifi module) | swap(1) **or** pins(2,7) | -| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | +| Peripheral | Default | Alternative | +|------------|--------------------------------------------------------------|--------------------------------------------------------| +| Serial | swap(0) **or** pins(27,26)
(connected to mEDBG) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) (available on SPI header) | +| Serial2 | swap(0) **or** pins(24,23)
(connected to Wifi module) | swap(1) **or** pins(2,7) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | Available pin combinations for the *Nano Every* pinout are: -| Peripheral | Default | Alternative | -|------------|-------------------------------------------------------------|-----------------------------------------------| -| Serial | swap(0) **or** pins(25,24) (connected to USB-serial chip) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | -| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | -| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | +| Peripheral | Default | Alternative | +|------------|------------------------------------------------------------------|-----------------------------------------------| +| Serial | swap(0) **or** pins(25,24)
(connected to USB-serial chip) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | +| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | ## How to install From 4d3af09c12186aad63fb4e0b493f4f8492489232 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 14 Aug 2020 21:42:25 +0200 Subject: [PATCH 166/351] Update Logic library Incorporate improvements @SpenceKonde has added Closes #83 --- megaavr/libraries/Logic/README.md | 140 +++++++-- megaavr/libraries/Logic/library.properties | 4 +- megaavr/libraries/Logic/src/Logic.cpp | 340 +++++++++++++-------- megaavr/libraries/Logic/src/Logic.h | 121 +++++++- 4 files changed, 433 insertions(+), 172 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index 4d754e0..1ffe616 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -1,12 +1,14 @@ # Logic A library for interfacing with the CCL (Configurable Custom Logic) peripherals of the megaAVR-0 MCUs. -Developed by MCUdude for use with [MegaCoreX](https://github.com/MCUdude/MegaCoreX). +Developed by MCUdude for use with [MegaCoreX](https://github.com/MCUdude/MegaCoreX), adapted to megaAVR ATtiny parts by [Tadashi G. Takaoka](https://github.com/tgtakaoka), and to DA-series by [Spence Konde](https://github.com/SpenceKonde) The megaAVR-0 has four independent internal logic blocks that can be individually customized. -More useful information about CCL can be found in the [Microchip Application Note TB3218](http://ww1.microchip.com/downloads/en/AppNotes/TB3218-Getting-Started-with-CCL-90003218A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). +All of the megaTiny parts have 2 blocks of CCL available. The examples included assume the use of megaTinyCore in their defines to detect the applicable part. +More useful information about CCL can be found in the [Microchip Application Note TB3218](http://ww1.microchip.com/downloads/en/AppNotes/TB3218-Getting-Started-with-CCL-90003218A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf), part in question. ## Logic -Class for interfacing with the built-in logic block. use the predefined objects `Logic0`, `Logic1`, `Logic2` and `Logic3`. +Class for interfacing with the built-in logic block. use the predefined objects `Logic0`, `Logic1`, `Logic2` and `Logic3`. +`Logic2` and `Logic3` are only available on the ATmega parts, `Logic4` and `Logic5` only on AVR-DA. Each object contains register pointers for interfacing with the right registers. Some of these variables are available to the user. @@ -26,27 +28,80 @@ Logic0.enable = true; // Enable logic block 0 ##### Default state `Logic0.enable` defaults to `false` if not specified in the user program. - ### input0..input2 -Variable for setting what mode input 0..2 on a logic block should have. -Accepted values: +Variable for setting what mode input 0..2 on a logic block should have. + +Notes for all parts: +* The datasheets give different names for the event channels for ATtiny and ATmega parts, both are supported by library: event 0 and event a are the same, as are event 1 and event b. These can be generated using the event system, see the relevant datasheet and examples for more information. +* Timer WO channels correspond to the specified timer's PWM Output channels. They are true when the specified timer's value is higher than the compare register for that output channel. +* Type-B timers can only generate an output under circumstances where they could drive an output pin if CCMPEN in TCBn.CTRLA is set. + +Accepted values for DA-series and megaAVR 0-series parts: +``` c++ +in::masked; // Pin not in use +in::unused; // Pin not in use +in::disable; // Pin not in use +in::feedback; // Connect output of the logic block to this input +in::link; // Connect output of logic block n+1 to this input +in::event_0; // Connect input to event a +in::event_a; // Connect input to event a +in::event_1; // Connect input to event b +in::event_b; // Connect input to event b +in::pin; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, do not change pinMode +in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup on +in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +in::ac; // Connect input to the output of the internal analog comparator (input 0,1,2 from AC0,1,2) +in::zcd; // Connect input to the output of the zero crossing detector (input 0,1,2 from ZCD0,1,2) - DA-series only +in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX +in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK +in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 +in::tca1; // Connect input to TCA1. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 - DA-series only +in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO. +in::tcd; // Connect input to TCD0. Input 0 connects to WOA, input 1 to WOB and input2 to WOC - DA-series only +``` + +Notes specific to ATmega parts +* The 48-pin and 64-pin DA-series parts have 6 LUTs. No pins for CCL5 are available in the 48-pin package. +* On 28-pin versions of the ATmega 4808, 3208, 1608, and 808, IN1 and IN2 inputs for logic3 are not available. If all input pins for all logic blocks are needed, the event system workaround shown for the ATtiny parts in the examples can be used, though note that register names and values are different. Same principle applies to the DA-series devices with fewer pins. +* According to the datasheet for SPI as input source, inputs 0 and 1 connect to MOSI. Thus, on these parts, there is no input to the logic blocks for MISO. Note also that the order is different from the ATtiny parts. +* If input on the highest-number Logic block is set to link, it will use the output of Logic0 (unless it's an early production DA-series - see the errata) +* If you need to link input to logic block other than the n+1 block, you can use the event system for that. + +Accepted values for tinyAVR 0/1-series parts: + ``` c++ -in::masked; // Pin not in use -in::unused; // Pin not in use -in::disable; // Pin not in use -in::feedback; // Connect output of the logic block to this input -in::link; // Connect output of logic block n+1 to this input -in::event_a; // Connect input to event A -in::event_b; // Connect input to event B -in::input; // Connect input to GPIO -in::ac; // Connect input to the output of the internal analog comparator -in::input_pullup; // Connect input to GPIO and enable the internal pullup resistor -in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX -in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK -in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 -in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO +in::masked; // Pin not in use +in::unused; // Pin not in use +in::disable; // Pin not in use +in::feedback; // Connect output of the logic block to this input +in::link; // Connect output of the other logic block to this input +in::event_0; // Connect input to event 0 +in::event_a; // Connect input to event 0 +in::event_1; // Connect input to event 1 +in::event_b; // Connect input to event 1 +in::pin; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, do not change pinMode +in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup on +in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +in::ac0; // Connect input to AC0 OUT +in::tcb0; // Connect input to TCB0 WO +in::tca; // Connect input to TCA0 WO0~2 for input 0~2 +in::tca0; // Connect input to TCA0 WO0~2 for input 0~2 +in::tcd; // Connect input to TCD WOAn, WOB, WOA for input 0, 1, 2 +in::usart; // Connect input to U(S)ART0 XCK and TXD for input 0, 1 +in::spi; // Connect input to SPI0 SCK, MOSI, MISO for input 0, 1, 2 +in::ac1; // Connect input to AC1 OUT (input 0, 1 only) +in::tcb1; // Connect input to TCB1 WO (input 0, 1 only) +in::ac2; // Connect input to AC2 OUT (input 0, 1 only) ``` +Notes specific to ATtiny: +* It is not clear what TCD0 WOAn is. I suspect it is true when TCD0 count is greater than TCD0.COMPSET0 and TCD0.CMPCLR0, ie, when WOA turns on and off, which can be individually controlled; the timer continues counting until reaching TCD0.CMPCLR1 when WOB turns off (TCD0 is a very strange timer). +* Not all inputs are available on all parts - only input sources corresponding to peripherals on that device are available. Not all options are avalable for input 2, as noted above. +* On CCL1 (logic1), IN0 I/O input is available only on the 20 and-24 pin parts, and IN1 and IN2 only on 24-pin parts. The event inputs can be used with pin events to take input from a diferent pins for up to two inputs. This is demonstrated in the five input example. +* CCL0's IN0 pin is on PA0, which is nominally the UPDI pin. It can only be used as input when that pin is set as GPIO. This limits the usefulness of CCL0 on the ATtiny parts; configuring UPDI as GPIO prevents further programming via UPDI except via HV programming. Configuring this option is only supported on megaTinyCore with Optiboot bootloader (from 1.1.6 on), and prevents further modification of the fuses or bootloader without HV programming, however, as noted above, input0 can be used via the event inputs to take input from another pin. This is demonstrated in the three input examples. + ##### Usage ``` c++ Logic0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 @@ -97,8 +152,8 @@ Variable to connecting a filter or synchronizer to the logic block output. Usefu Accepted values: ```c++ filter::disable; // No filter used -filter::synchronizer; // Connect synchronizer to output -filter::filter; // Connect filter to output +filter::synchronizer; // Connect synchronizer to output; delays output by 2 clock cycles. +filter::filter; // Connect filter to output; delays output by 4 clock cycles, only passes output that is stable for >2 clock cycles. ``` ##### Usage @@ -110,8 +165,45 @@ Logic0.filter = filter::filter; // Enable filter on output of block 0 `LogicN.filter` defaults to `filter::disable` if not specified in the user program. +### clocksource +Variable set the clock source for the LUT. The inputs are checked and output updated on the rising edge of this clock. Except on the Dx-series parts, only clk_per (peripheral clock, ie, the system clock) and in2 are available. If you don't know what this means, you want clk_per. If sequential logic is used, this is also used to clock that. +Accepted values: +```c++ +clocksource::clk_per; // Clock from the peripheral clock (ie, system clock) +clocksource::in2; // Clock from the selected input2; it is treated as a 0 in the truth table. +clocksource::oschf; // Clock from the **unprescaled** internal HF oscillator. Same as clk_per if system clock not prescaled. +clocksource::osc32k; // Clock from the internal 32.768 kHz oscillator +clocksource::osc1l; // Clock from the internal 32.768 kHz oscillator prescaled by 32 +``` + +#### Usage +```c++ +Logic0.clocksource = clocksource::clk_per; +``` + +##### Default state +`LogicN.clocksource` defaults to `clocksource::clk_per` if not specified in the user program. + + +### edgedetect +Variable for controlling use of the edge detector. The edge detector can be used to generate a pulse when detecting a rising edge on its input. To detect a falling edge, the TRUTH table should be programmed to provide inverted output. In order to avoid unpredictable behavior, a valid filter option must be enabled. Note that this is likely only of use when the output is being used for sequential logic or as the input to another logic block; it looks particularly useful on the odd LUT input to a J-K flip-flop sequential logic unit. + +```c++ +edgedetect::disable; // No edge detection used +edgedetect::enable; // Edge detection used +``` + +#### Usage +```c++ +Logic0.edgedetect = edgedetect::enable; +``` + +##### Default state +`LogicN.edgedetect` defaults to `edgedetect::disable` if not specified in the user program. + + ### sequencer -Variable for connecting a sequencer to the logic block output. +Variable for connecting a sequencer to the logic block output. There is 1 sequencer per 2 CCLs; this option is ignored for the odd-numbered logic blocks. Accepted values: ```c++ sequencer::disable; // No sequencer connected @@ -178,7 +270,7 @@ Logic::stop(); // Stop CCL ## attachInterrupt() Method for enabling interrupts for a specific block. Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. -This method ins't available on tinyAVR series. +This method ins't available on tinyAVR series, as these parts cannot generate an interrupt from the CCL blocks. ##### Usage ```c++ diff --git a/megaavr/libraries/Logic/library.properties b/megaavr/libraries/Logic/library.properties index 984a10c..e3bb320 100644 --- a/megaavr/libraries/Logic/library.properties +++ b/megaavr/libraries/Logic/library.properties @@ -1,8 +1,8 @@ name=Logic -version=1.0.0 +version=1.0.2 author=MCUdude maintainer=MCUdude -sentence=A library for interfacing with the customizable logic in megaAVR chips +sentence=A library for interfacing with the customizable logic in megaAVR 0-series, tinyAVR 0/1-series, and Dx-series chips paragraph= category=Signal Input/Output url=https://github.com/MCUdude/MegaCoreX diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 7036022..428186b 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -1,47 +1,52 @@ #include "Logic.h" -#if defined(CCL_CCL_vect) // Array for storing ISR function pointers +#if defined(CCL_CCL_vect) +#if defined(TRUTH5) +static volatile voidFuncPtr intFuncCCL[6]; +#else static volatile voidFuncPtr intFuncCCL[4]; #endif +#endif struct Logic::CCLBlock { - const uint8_t number; - const uint8_t input0_bm; - const uint8_t input1_bm; - const uint8_t input2_bm; - const uint8_t output_bm; - const uint8_t output_alt_bm; - PORT_t& PORT_IN; - PORT_t& PORT_OUT; - PORT_t& PORT_ALT_OUT; - volatile register8_t& SEQCTRL; - volatile register8_t& LUTCTRLA; - volatile register8_t& LUTCTRLB; - volatile register8_t& LUTCTRLC; - volatile register8_t& TRUTH; + const uint8_t number; + const uint8_t input0_bm; + const uint8_t input1_bm; + const uint8_t input2_bm; + const uint8_t output_bm; + const uint8_t output_alt_bm; + PORT_t& PORT_IN; + PORT_t& PORT_OUT; + PORT_t& PORT_ALT_OUT; + volatile register8_t& SEQCTRL; + volatile register8_t& LUTCTRLA; + volatile register8_t& LUTCTRLB; + volatile register8_t& LUTCTRLC; + volatile register8_t& TRUTH; }; -static const struct Logic::CCLBlock blocks[] = { +static const struct Logic::CCLBlock blocks[] = +{ #if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - 0, 0, 0, PIN7_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, 0, 0, PIN7_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, #endif #if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ defined(__AVR_ATtiny1606__) || \ @@ -49,94 +54,116 @@ static const struct Logic::CCLBlock blocks[] = { defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) #define PORTMUX_CCL PORTMUX.CTRLA #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, #endif #if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) #define PORTMUX_CCL PORTMUX.CTRLA #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, #endif -#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ - defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) +#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__)|| \ + defined(__AVR_AVR128DA32__)|| defined(__AVR_AVR128DA28__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) #define PORTMUX_CCL PORTMUX.CCLROUTEA #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTC, PORTC, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { // Note: 28-Pin version doesn't have input2 and output_alt. - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { // Note: 28-Pin version doesn't have input2 and output_alt + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, #endif -#if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ - defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) +#if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ + defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) #define PORTMUX_CCL PORTMUX.CCLROUTEA #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { // Note: 40-Pin version doesn't have output_alt. - 1, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTC, PORTC, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { // Note: 40-Pin version doesn't have output_alt + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, +#endif +#if defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) + { + 4, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTB, PORTB, PORTB, + CCL.SEQCTRL2, CCL.LUT4CTRLA, CCL.LUT4CTRLB, CCL.LUT4CTRLC, CCL.TRUTH4, + }, + { + 5, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTG, PORTG, PORTG, + CCL.SEQCTRL2, CCL.LUT5CTRLA, CCL.LUT5CTRLB, CCL.LUT5CTRLC, CCL.TRUTH5, + }, #endif }; @@ -152,6 +179,12 @@ Logic Logic2(2); #if defined(CCL_TRUTH3) Logic Logic3(3); #endif +#if defined(CCL_TRUTH4) +Logic Logic4(4); +#endif +#if defined(CCL_TRUTH5) +Logic Logic5(5); +#endif Logic::Logic(const uint8_t block_number) : enable(false), @@ -161,8 +194,10 @@ Logic::Logic(const uint8_t block_number) output(out::disable), output_swap(out::no_swap), filter(filter::disable), + edgedetect(edgedetect::disable), truth(0x00), sequencer(sequencer::disable), + clocksource(clocksource::clk_per), block(blocks[block_number]) { } @@ -192,38 +227,39 @@ static volatile register8_t& PINCTRL(PORT_t& port, const uint8_t pin_bm) return port.PIN7CTRL; } - void Logic::initInput(in::input_t& input, PORT_t& port, const uint8_t pin_bm) { - if(input == in::input && pin_bm) + if((input & 0x30) && pin_bm) // Input pin is either set to input or input with pullup { port.DIRCLR = pin_bm; - PINCTRL(port, pin_bm) &= ~PORT_PULLUPEN_bm; - } - else if (input == in::input_pullup && pin_bm) - { - port.DIRCLR = pin_bm; - PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; + + if(input == in::input) + PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; + else + PINCTRL(port, pin_bm) &= ~PORT_PULLUPEN_bm; + input = in::input; } } - void Logic::init() { initInput(input0, block.PORT_IN, block.input0_bm); initInput(input1, block.PORT_IN, block.input1_bm); initInput(input2, block.PORT_IN, block.input2_bm); - + // Set inputs modes block.LUTCTRLB = (input1 << CCL_INSEL1_gp) | (input0 << CCL_INSEL0_gp); block.LUTCTRLC = (input2 << CCL_INSEL2_gp); // Set truth table block.TRUTH = truth; - + // Set sequencer - block.SEQCTRL = sequencer; + if (!(block.number & 0x01)) + { + block.SEQCTRL = sequencer; + } // Set output pin state and output pin swap if(output == out::enable) @@ -243,19 +279,20 @@ void Logic::init() block.PORT_ALT_OUT.DIRSET = block.output_bm; } } - + // Set logic output state and output filter block.LUTCTRLA = (output ? CCL_OUTEN_bm : 0) - | (filter << CCL_FILTSEL_gp) - | (enable ? CCL_ENABLE_bm : 0); + | (edgedetect ? CCL_EDGEDET_EN_gc : 0 ) + | (filter << CCL_FILTSEL_gp) + | (clocksource << CCL_CLKSRC_gp) + | (enable ? CCL_ENABLE_bm : 0); } - #if defined(CCL_CCL_vect) void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) { CCL_INTMODE0_t intmode; - switch (mode) + switch (mode) { // Set RISING, FALLING or CHANGE interrupt trigger for a block output case RISING: @@ -271,27 +308,43 @@ void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) // Only RISING, FALLING and CHANGE is supported return; } - const int intmode_bp = block.number * 2; - CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) - | (intmode << intmode_bp); - +#if defined(CCL_TRUTH4) + if (block.number > 3) + { + const int16_t intmode_bp = (block.number & 0x03) * 2; + CCL.INTCTRL1 = (CCL.INTCTRL1 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); + } + else + { + const int16_t intmode_bp = (block.number & 0x03) * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); + } +#else + const int16_t intmode_bp = block.number * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); +#endif // Store function pointer intFuncCCL[block.number] = userFunc; } - void Logic::detachInterrupt() { // Disable interrupt for a given block output +#if defined(CCL_TRUTH4) + if(block_number > 4) + CCL.INTCTRL1 &= ~(CCL_INTMODE1_gm << ((block.number & 3) * 2)); + else + CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); +#else CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); +#endif } - // CCL interrupt service routine // Use attachIntterupt to activate this. ISR(CCL_CCL_vect) { - // Cleck for block 0 interrupt + // Check for block 0 interrupt if(CCL.INTFLAGS & CCL_INT0_bm) { // Run user function @@ -299,17 +352,23 @@ ISR(CCL_CCL_vect) // Clear flag CCL.INTFLAGS |= CCL_INT0_bm; } + // Check for block 1 interrupt if(CCL.INTFLAGS & CCL_INT1_bm) { + // Run user function intFuncCCL[CCL_INT1_bp](); + // Clear flag CCL.INTFLAGS |= CCL_INT1_bm; } + // Check for block 2 interrupt if(CCL.INTFLAGS & CCL_INT2_bm) { + // Run user function intFuncCCL[CCL_INT2_bp](); + // Clear flag CCL.INTFLAGS |= CCL_INT2_bm; } - // Cleck for block 3 interrupt + // Check for block 3 interrupt if(CCL.INTFLAGS & CCL_INT3_bm) { // Run user function @@ -317,5 +376,26 @@ ISR(CCL_CCL_vect) // Clear flag CCL.INTFLAGS |= CCL_INT3_bm; } -} +#if defined(TRUTH4) + // Check for block 4 interrupt + if(CCL.INTFLAGS & CCL_INT4_bm) + { + // Run user function + intFuncCCL[CCL_INT4_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT4_bm; + } +#endif +#if defined(TRUTH5) + // Check for block 5 interrupt + if(CCL.INTFLAGS & CCL_INT5_bm) + { + // Run user function + intFuncCCL[CCL_INT5_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT5_bm; + } #endif // CCL_CCL_vect +} + +#endif diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 68d671c..cadd322 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -3,25 +3,83 @@ #include -//Use in:: when working with logic inputs namespace in { enum input_t : uint8_t { - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_a = 0x03, - event_b = 0x04, - input = 0x05, - ac = 0x06, - input_pullup = 0x07, - usart = 0x08, - spi = 0x09, - tca0 = 0x0A, - tcb = 0x0C, +#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__)|| \ + defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tcb = 0x0C, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, +#elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA32__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + zcd = 0x07, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca1 = 0x0B, + tcb = 0x0C, + tcd = 0x0D, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, +#else //megaAVR-0 and 1 ATtiny + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac0 = 0x06, + tcb0 = 0x07, + tca = 0x08, + tcd0 = 0x09, + usart = 0x0A, + spi = 0x0B, + ac1 = 0x0C, + tcb1 = 0x0D, + ac2 = 0x0E, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, +#endif }; }; @@ -38,7 +96,7 @@ namespace out no_swap = 0x00, pin_swap = 0x01, }; -}; +}; // Use filter:: when working with logic output filter namespace filter @@ -51,6 +109,29 @@ namespace filter }; }; +// Use clocksource:: when working with logic clock source +namespace clocksource +{ + enum clocksource_t : uint8_t + { + clk_per = 0x00, + in2 = 0x01, + oschf = 0x04, + osc32k = 0x05, + osc1k = 0x06, + }; +}; + +// Use edgedetect:: when using edge detection with filter +namespace edgedetect +{ + enum edgedet_t : uint8_t + { + disable = 0x00, + enable = 0x01 + }; +}; + // Use sequencer:: when working with LUT sequencer namespace sequencer { @@ -85,8 +166,10 @@ class Logic out::output_t output; out::pinswap_t output_swap; filter::filter_t filter; + edgedetect::edgedet_t edgedetect; uint8_t truth; sequencer::sequencer_t sequencer; + clocksource::clocksource_t clocksource; struct CCLBlock; @@ -108,5 +191,11 @@ extern Logic Logic2; #if defined(CCL_TRUTH3) extern Logic Logic3; #endif +#if defined(CCL_TRUTH4) +extern Logic Logic4; +#endif +#if defined(CCL_TRUTH5) +extern Logic Logic5; +#endif #endif From 76d92fc04d73b400c28b4042debd455cdfe0c97d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 15 Aug 2020 12:01:33 +0200 Subject: [PATCH 167/351] Fix typo and missing literals --- megaavr/libraries/Logic/keywords.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt index 720da20..8e167c1 100644 --- a/megaavr/libraries/Logic/keywords.txt +++ b/megaavr/libraries/Logic/keywords.txt @@ -1,5 +1,5 @@ ####################################### -# Syntax Coloring Map For Wire +# Syntax Coloring Map For Logic ####################################### ####################################### @@ -34,4 +34,6 @@ Logic3 KEYWORD2 in LITERAL1 out LITERAL1 filter LITERAL1 +clocksource LITERAL1 +edgedetect LITERAL1 sequencer LITERAL1 From 5adb16a17e59d88dd9a19cdb05395d5d4b413be8 Mon Sep 17 00:00:00 2001 From: Alejandro Solano <54044412+soranoalejandro@users.noreply.github.com> Date: Thu, 20 Aug 2020 08:33:19 +0000 Subject: [PATCH 168/351] Fixed incorrect compiler error message Shows correct error message when HWSERIAL0_DRE_VECTOR is not defined. I have verified and this copy/paste error is not present in the files for UART1 to UART3, only in this file. --- megaavr/cores/coreX-corefiles/UART0.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/UART0.cpp b/megaavr/cores/coreX-corefiles/UART0.cpp index 72e93c6..28f1aaa 100644 --- a/megaavr/cores/coreX-corefiles/UART0.cpp +++ b/megaavr/cores/coreX-corefiles/UART0.cpp @@ -51,7 +51,7 @@ ISR(HWSERIAL0_DRE_VECTOR) Serial._tx_data_empty_irq(); } #else -#error "Don't know what the Data Received interrupt vector is called for Serial" +#error "Don't know what the Data Register Empty interrupt vector is called for Serial" #endif #if defined(HWSERIAL0) From 142245ede244c8304fdcaf23e5db696859e9593a Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 31 Aug 2020 09:21:28 +0200 Subject: [PATCH 169/351] Update README.md Add info about the microUPDI programmer --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index bb67f9b..2c03f97 100644 --- a/README.md +++ b/README.md @@ -5,6 +5,9 @@ Compared to older AVR families they also have more advanced and accurate interna For programming, these chips use a UPDI programming interface. This is a bi-directional single wire interface and requires a programmer that supports UPDI. If you rather prefer uploading using a USB to serial adapter there is an option to use the Optiboot bootloader. Read more about UPDI and bootloaders in the [Programming](#programming) section below. +If you're looking for a sleek, reliable UPDI programmer that also acts as a USB to serial adapter, check out the microUPDI programmer! It's a small breakout board where you add your own Arduino Pro Micro board, and flash it with the right firmware using Arduino IDE. You can buy the microUPDI programmer over at my [Tindie store](https://www.tindie.com/products/MCUdude/microupdi-programmer/), and you can flash your Arduino Pro Micro with the correct firmware by installing [microUPDIcore](https://github.com/MCUdude/microUPDI). + + # Table of contents * [Supported microcontrollers](#supported-microcontrollers) From 94f657f3c98dc3c862b8f06731e20d549229683e Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 31 Aug 2020 16:39:42 +0200 Subject: [PATCH 170/351] Fix image size --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 2c03f97..1b1281d 100644 --- a/README.md +++ b/README.md @@ -7,7 +7,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire If you're looking for a sleek, reliable UPDI programmer that also acts as a USB to serial adapter, check out the microUPDI programmer! It's a small breakout board where you add your own Arduino Pro Micro board, and flash it with the right firmware using Arduino IDE. You can buy the microUPDI programmer over at my [Tindie store](https://www.tindie.com/products/MCUdude/microupdi-programmer/), and you can flash your Arduino Pro Micro with the correct firmware by installing [microUPDIcore](https://github.com/MCUdude/microUPDI). - + # Table of contents * [Supported microcontrollers](#supported-microcontrollers) From 1c9663ce1b9277ce75d12e8660dcd664cee2e28c Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 31 Aug 2020 16:40:37 +0200 Subject: [PATCH 171/351] Fix image size again --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 1b1281d..67a85ac 100644 --- a/README.md +++ b/README.md @@ -7,7 +7,7 @@ For programming, these chips use a UPDI programming interface. This is a bi-dire If you're looking for a sleek, reliable UPDI programmer that also acts as a USB to serial adapter, check out the microUPDI programmer! It's a small breakout board where you add your own Arduino Pro Micro board, and flash it with the right firmware using Arduino IDE. You can buy the microUPDI programmer over at my [Tindie store](https://www.tindie.com/products/MCUdude/microupdi-programmer/), and you can flash your Arduino Pro Micro with the correct firmware by installing [microUPDIcore](https://github.com/MCUdude/microUPDI). - + # Table of contents * [Supported microcontrollers](#supported-microcontrollers) From d62556794f2b80ab408b67fd88684dcde279a932 Mon Sep 17 00:00:00 2001 From: Hans Date: Fri, 4 Sep 2020 19:56:25 +0200 Subject: [PATCH 172/351] Fix DACREF formula --- megaavr/libraries/Comparator/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index c389366..a2d1ba1 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -73,7 +73,7 @@ Comparator.reference = ref::vref_2v5; // Use the internal 2.5V reference for th Variable for setting the DACREF value. The DACREF voltage is the voltage that the comparator uses as it's reference. This is the formula for the DACREF output voltage: - + ##### Usage ``` c++ From 7cbb9d03785d5c7d1b524d37d17c9bd4a30bc4bb Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 15 Sep 2020 22:18:28 +0200 Subject: [PATCH 173/351] Rename HWSERIAL macros Somehow, somewhere WIRE_* snuck into these macros. Probably a copy/paste error from the official megaavr repo --- megaavr/cores/coreX-corefiles/UART0.cpp | 2 +- megaavr/cores/coreX-corefiles/UART1.cpp | 2 +- megaavr/cores/coreX-corefiles/UART2.cpp | 2 +- megaavr/cores/coreX-corefiles/UART3.cpp | 2 +- .../variants/28pin-standard/pins_arduino.h | 24 +++++++------- .../variants/32pin-standard/pins_arduino.h | 24 +++++++------- .../variants/40pin-standard/pins_arduino.h | 24 +++++++------- .../variants/48pin-standard/pins_arduino.h | 32 +++++++++---------- megaavr/variants/nano-every/pins_arduino.h | 32 +++++++++---------- megaavr/variants/uno-wifi/pins_arduino.h | 32 +++++++++---------- 10 files changed, 88 insertions(+), 88 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART0.cpp b/megaavr/cores/coreX-corefiles/UART0.cpp index 28f1aaa..9f8686a 100644 --- a/megaavr/cores/coreX-corefiles/UART0.cpp +++ b/megaavr/cores/coreX-corefiles/UART0.cpp @@ -55,7 +55,7 @@ ISR(HWSERIAL0_DRE_VECTOR) #endif #if defined(HWSERIAL0) -UartClass Serial(HWSERIAL0, PIN_WIRE_HWSERIAL0_RX, PIN_WIRE_HWSERIAL0_TX, PIN_WIRE_HWSERIAL0_RX_PINSWAP_1, PIN_WIRE_HWSERIAL0_TX_PINSWAP_1, HWSERIAL0_DRE_VECTOR_NUM, HWSERIAL0_MUX, HWSERIAL0_MUX_PINSWAP_1); +UartClass Serial(HWSERIAL0, PIN_HWSERIAL0_RX, PIN_HWSERIAL0_TX, PIN_HWSERIAL0_RX_PINSWAP_1, PIN_HWSERIAL0_TX_PINSWAP_1, HWSERIAL0_DRE_VECTOR_NUM, HWSERIAL0_MUX, HWSERIAL0_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent diff --git a/megaavr/cores/coreX-corefiles/UART1.cpp b/megaavr/cores/coreX-corefiles/UART1.cpp index 68610e3..99cc22e 100644 --- a/megaavr/cores/coreX-corefiles/UART1.cpp +++ b/megaavr/cores/coreX-corefiles/UART1.cpp @@ -55,7 +55,7 @@ ISR(HWSERIAL1_DRE_VECTOR) #endif #if defined(HWSERIAL1) -UartClass Serial1(HWSERIAL1, PIN_WIRE_HWSERIAL1_RX, PIN_WIRE_HWSERIAL1_TX, PIN_WIRE_HWSERIAL1_RX_PINSWAP_1, PIN_WIRE_HWSERIAL1_TX_PINSWAP_1, HWSERIAL1_DRE_VECTOR_NUM, HWSERIAL1_MUX, HWSERIAL1_MUX_PINSWAP_1); +UartClass Serial1(HWSERIAL1, PIN_HWSERIAL1_RX, PIN_HWSERIAL1_TX, PIN_HWSERIAL1_RX_PINSWAP_1, PIN_HWSERIAL1_TX_PINSWAP_1, HWSERIAL1_DRE_VECTOR_NUM, HWSERIAL1_MUX, HWSERIAL1_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent diff --git a/megaavr/cores/coreX-corefiles/UART2.cpp b/megaavr/cores/coreX-corefiles/UART2.cpp index 6a1c86c..203f0a3 100644 --- a/megaavr/cores/coreX-corefiles/UART2.cpp +++ b/megaavr/cores/coreX-corefiles/UART2.cpp @@ -55,7 +55,7 @@ ISR(HWSERIAL2_DRE_VECTOR) #endif #if defined(HWSERIAL2) -UartClass Serial2(HWSERIAL2, PIN_WIRE_HWSERIAL2_RX, PIN_WIRE_HWSERIAL2_TX, PIN_WIRE_HWSERIAL2_RX_PINSWAP_1, PIN_WIRE_HWSERIAL2_TX_PINSWAP_1, HWSERIAL2_DRE_VECTOR_NUM, HWSERIAL2_MUX, HWSERIAL2_MUX_PINSWAP_1); +UartClass Serial2(HWSERIAL2, PIN_HWSERIAL2_RX, PIN_HWSERIAL2_TX, PIN_HWSERIAL2_RX_PINSWAP_1, PIN_HWSERIAL2_TX_PINSWAP_1, HWSERIAL2_DRE_VECTOR_NUM, HWSERIAL2_MUX, HWSERIAL2_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent diff --git a/megaavr/cores/coreX-corefiles/UART3.cpp b/megaavr/cores/coreX-corefiles/UART3.cpp index 45f0c78..6a12e55 100644 --- a/megaavr/cores/coreX-corefiles/UART3.cpp +++ b/megaavr/cores/coreX-corefiles/UART3.cpp @@ -55,7 +55,7 @@ ISR(HWSERIAL3_DRE_VECTOR) #endif #if defined(HWSERIAL3) -UartClass Serial3(HWSERIAL3, PIN_WIRE_HWSERIAL3_RX, PIN_WIRE_HWSERIAL3_TX, PIN_WIRE_HWSERIAL3_RX_PINSWAP_1, PIN_WIRE_HWSERIAL3_TX_PINSWAP_1, HWSERIAL3_DRE_VECTOR_NUM, HWSERIAL3_MUX, HWSERIAL3_MUX_PINSWAP_1); +UartClass Serial3(HWSERIAL3, PIN_HWSERIAL3_RX, PIN_HWSERIAL3_TX, PIN_HWSERIAL3_RX_PINSWAP_1, PIN_HWSERIAL3_TX_PINSWAP_1, HWSERIAL3_DRE_VECTOR_NUM, HWSERIAL3_MUX, HWSERIAL3_MUX_PINSWAP_1); #endif // Function that can be weakly referenced by serialEventRun to prevent diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 18703b4..57042c8 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -122,10 +122,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR USART0_RXC_vect #define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc -#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 -#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_TX PIN_PA0 +#define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap available @@ -135,10 +135,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR USART1_RXC_vect #define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc -#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 -#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_TX PIN_PC0 +#define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 // USART 2 // No pinswap by default @@ -148,10 +148,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR USART2_RXC_vect #define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc -#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 -#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF0 -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF1 +#define PIN_HWSERIAL2_TX PIN_PF0 +#define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF0 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF1 // Analog pins #define PIN_A0 PIN_PD0 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 7cdd0a1..ddb5532 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -125,10 +125,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR USART0_RXC_vect #define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc -#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 -#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_TX PIN_PA0 +#define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap available @@ -138,10 +138,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR USART1_RXC_vect #define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc -#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 -#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_TX PIN_PC0 +#define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 // USART 2 // No pinswap enabled by default @@ -151,10 +151,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR USART2_RXC_vect #define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc -#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 -#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL2_TX PIN_PF0 +#define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 // Analog pins #define PIN_A0 PIN_PD0 diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index b6e4dc5..d5890b2 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -143,10 +143,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_WIRE_HWSERIAL0_TX (PIN_PA0) -#define PIN_WIRE_HWSERIAL0_RX (PIN_PA1) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PA4) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PA5) +#define PIN_HWSERIAL0_TX (PIN_PA0) +#define PIN_HWSERIAL0_RX (PIN_PA1) +#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PA4) +#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PA5) // USART1 // No pinswap by default @@ -156,10 +156,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_ALT1_gc) -#define PIN_WIRE_HWSERIAL1_TX (PIN_PC0) -#define PIN_WIRE_HWSERIAL1_RX (PIN_PC1) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC4) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC5) +#define PIN_HWSERIAL1_TX (PIN_PC0) +#define PIN_HWSERIAL1_RX (PIN_PC1) +#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC4) +#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC5) // USART 2 // No pinswap by default @@ -169,10 +169,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) #define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) #define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) -#define PIN_WIRE_HWSERIAL2_TX (PIN_PF0) -#define PIN_WIRE_HWSERIAL2_RX (PIN_PF1) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PF4) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PF5) +#define PIN_HWSERIAL2_TX (PIN_PF0) +#define PIN_HWSERIAL2_RX (PIN_PF1) +#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PF4) +#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PF5) // Analog pins #define PIN_A0 (PIN_PD0) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index a129b6f..09ca362 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -154,10 +154,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR USART0_RXC_vect #define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc -#define PIN_WIRE_HWSERIAL0_TX PIN_PA0 -#define PIN_WIRE_HWSERIAL0_RX PIN_PA1 -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_TX PIN_PA0 +#define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 // USART1 // No pinswap by default @@ -167,10 +167,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR USART1_RXC_vect #define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_ALT1_gc -#define PIN_WIRE_HWSERIAL1_TX PIN_PC0 -#define PIN_WIRE_HWSERIAL1_RX PIN_PC1 -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 PIN_PC4 -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 PIN_PC5 +#define PIN_HWSERIAL1_TX PIN_PC0 +#define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC4 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC5 // USART 2 // No pinswap by default @@ -180,10 +180,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR USART2_RXC_vect #define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc -#define PIN_WIRE_HWSERIAL2_TX PIN_PF0 -#define PIN_WIRE_HWSERIAL2_RX PIN_PF1 -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL2_TX PIN_PF0 +#define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 // USART 3 // No pinswap by default @@ -193,10 +193,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL3_RXC_VECTOR USART3_RXC_vect #define HWSERIAL3_MUX PORTMUX_USART3_DEFAULT_gc #define HWSERIAL3_MUX_PINSWAP_1 PORTMUX_USART3_ALT1_gc -#define PIN_WIRE_HWSERIAL3_TX PIN_PB0 -#define PIN_WIRE_HWSERIAL3_RX PIN_PB1 -#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 PIN_PB4 -#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 PIN_PB5 +#define PIN_HWSERIAL3_TX PIN_PB0 +#define PIN_HWSERIAL3_RX PIN_PB1 +#define PIN_HWSERIAL3_TX_PINSWAP_1 PIN_PB4 +#define PIN_HWSERIAL3_RX_PINSWAP_1 PIN_PB5 // Analog pins #define PIN_A0 PIN_PD0 diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index 01b3cc1..a54e3a8 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -132,10 +132,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL0_TX (PIN_PB4) -#define PIN_WIRE_HWSERIAL0_RX (PIN_PB5) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) +#define PIN_HWSERIAL0_TX (PIN_PB4) +#define PIN_HWSERIAL0_RX (PIN_PB5) +#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) +#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) // Nano every USART (Serial1) // USART1 on mega4809 @@ -147,10 +147,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (PIN_PC4) -#define PIN_WIRE_HWSERIAL1_RX (PIN_PC5) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) +#define PIN_HWSERIAL1_TX (PIN_PC4) +#define PIN_HWSERIAL1_RX (PIN_PC5) +#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) +#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) // Nano Every USART (Serial2) // USART0 on mega4809 @@ -162,10 +162,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) #define HWSERIAL2_MUX (PORTMUX_USART0_DEFAULT_gc) #define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_WIRE_HWSERIAL2_TX (PIN_PA0) -#define PIN_WIRE_HWSERIAL2_RX (PIN_PA1) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PA4) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PA5) +#define PIN_HWSERIAL2_TX (PIN_PA0) +#define PIN_HWSERIAL2_RX (PIN_PA1) +#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PA4) +#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PA5) // Nano Every USART (Serial3) // USART2 on mega4809 @@ -177,10 +177,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) #define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) #define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL3_TX (PIN_PF4) -#define PIN_WIRE_HWSERIAL3_RX (PIN_PF5) -#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) -#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) +#define PIN_HWSERIAL3_TX (PIN_PF4) +#define PIN_HWSERIAL3_RX (PIN_PF5) +#define PIN_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) +#define PIN_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) // Analog pins #define PIN_A0 PIN_PD3 // AIN3 diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 96f8b3f..4df11a3 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -147,10 +147,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) #define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) #define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL0_TX (PIN_PB4) -#define PIN_WIRE_HWSERIAL0_RX (PIN_PB5) -#define PIN_WIRE_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) -#define PIN_WIRE_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) +#define PIN_HWSERIAL0_TX (PIN_PB4) +#define PIN_HWSERIAL0_RX (PIN_PB5) +#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) +#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) // Uno Wifi Rev2 USART (Serial1) // USART1 on mega4809 @@ -162,10 +162,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) #define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) #define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL1_TX (PIN_PC4) -#define PIN_WIRE_HWSERIAL1_RX (PIN_PC5) -#define PIN_WIRE_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) -#define PIN_WIRE_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) +#define PIN_HWSERIAL1_TX (PIN_PC4) +#define PIN_HWSERIAL1_RX (PIN_PC5) +#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) +#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) // Uno Wifi Rev2 USART for communicating with Wifi NINA (Serial2) // USART0 on mega4809 @@ -177,10 +177,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) #define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) #define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL2_TX (PIN_PA4) -#define PIN_WIRE_HWSERIAL2_RX (PIN_PA5) -#define PIN_WIRE_HWSERIAL2_TX_PINSWAP_1 (PIN_PA0) -#define PIN_WIRE_HWSERIAL2_RX_PINSWAP_1 (PIN_PA1) +#define PIN_HWSERIAL2_TX (PIN_PA4) +#define PIN_HWSERIAL2_RX (PIN_PA5) +#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PA0) +#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PA1) // Uno Wifi Rev2 USART (Serial3) // USART2 on mega4809 @@ -192,10 +192,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) #define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) #define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) -#define PIN_WIRE_HWSERIAL3_TX (PIN_PF4) -#define PIN_WIRE_HWSERIAL3_RX (PIN_PF5) -#define PIN_WIRE_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) -#define PIN_WIRE_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) +#define PIN_HWSERIAL3_TX (PIN_PF4) +#define PIN_HWSERIAL3_RX (PIN_PF5) +#define PIN_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) +#define PIN_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) // Analog pins #define PIN_A0 PIN_PD0 From 941063dc12b13e1e15e76560b49986257615bb89 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Sep 2020 20:14:17 +0200 Subject: [PATCH 174/351] Add macros for hardware serial XCK and XDIR pins Thanks to @SpenceKonde for the idea! --- .../variants/28pin-standard/pins_arduino.h | 14 +- .../variants/32pin-standard/pins_arduino.h | 13 +- .../variants/40pin-standard/pins_arduino.h | 149 ++++++++++-------- .../variants/48pin-standard/pins_arduino.h | 13 ++ megaavr/variants/nano-every/pins_arduino.h | 111 +++++++------ megaavr/variants/uno-wifi/pins_arduino.h | 111 +++++++------ 6 files changed, 237 insertions(+), 174 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 57042c8..f10f4ac 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -124,8 +124,12 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc #define PIN_HWSERIAL0_TX PIN_PA0 #define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_XCK PIN_PA2 +#define PIN_HWSERIAL0_XDIR PIN_PA3 #define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 #define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PA7 // USART1 // No pinswap available @@ -137,8 +141,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc #define PIN_HWSERIAL1_TX PIN_PC0 #define PIN_HWSERIAL1_RX PIN_PC1 -#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 -#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_XCK PIN_PC2 +#define PIN_HWSERIAL1_XDIR PIN_PC3 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_HWSERIAL1_TX +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_HWSERIAL1_RX // USART 2 // No pinswap by default @@ -150,8 +156,8 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc #define PIN_HWSERIAL2_TX PIN_PF0 #define PIN_HWSERIAL2_RX PIN_PF1 -#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF0 -#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF1 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_HWSERIAL2_TX +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_HWSERIAL2_RX // Analog pins #define PIN_A0 PIN_PD0 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index ddb5532..5bda929 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -127,8 +127,12 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc #define PIN_HWSERIAL0_TX PIN_PA0 #define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_XCK PIN_PA2 +#define PIN_HWSERIAL0_XDIR PIN_PA3 #define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 #define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PA7 // USART1 // No pinswap available @@ -140,8 +144,10 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc #define PIN_HWSERIAL1_TX PIN_PC0 #define PIN_HWSERIAL1_RX PIN_PC1 -#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 -#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_XCK PIN_PC2 +#define PIN_HWSERIAL1_XDIR PIN_PC3 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_HWSERIAL1_TX +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_HWSERIAL1_RX // USART 2 // No pinswap enabled by default @@ -153,8 +159,11 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc #define PIN_HWSERIAL2_TX PIN_PF0 #define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_XCK PIN_PF2 +#define PIN_HWSERIAL2_XDIR PIN_PF3 #define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 #define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PF6 // Analog pins #define PIN_A0 PIN_PD0 diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index d5890b2..dbe0a0d 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -59,14 +59,14 @@ #define PIN_PF6 32 #define PINS_COUNT 33 -#define NUM_DIGITAL_PINS (PINS_COUNT) +#define NUM_DIGITAL_PINS PINS_COUNT #define NUM_ANALOG_INPUTS 16 #define NUM_RESERVED_PINS 0 #define NUM_INTERNALLY_USED_PINS 0 #define NUM_I2C_PINS 2 #define NUM_SPI_PINS 3 -#define NUM_TOTAL_FREE_PINS (PINS_COUNT) -#define NUM_TOTAL_PINS (PINS_COUNT) +#define NUM_TOTAL_FREE_PINS PINS_COUNT +#define NUM_TOTAL_PINS PINS_COUNT #define ANALOG_INPUT_OFFSET 14 #define LED_BUILTIN PIN_PA7 #define EXTERNAL_NUM_INTERRUPTS 47 @@ -104,21 +104,21 @@ // No pinswap enabled by default // Pinswap 2 not available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_DEFAULT_gc) -#define SPI_MUX_PINSWAP_1 (PORTMUX_SPI0_ALT1_gc) -#define SPI_MUX_PINSWAP_2 (PORTMUX_SPI0_ALT2_gc) -#define PIN_SPI_MISO (PIN_PA5) -#define PIN_SPI_SCK (PIN_PA6) -#define PIN_SPI_MOSI (PIN_PA4) -#define PIN_SPI_SS (PIN_PA7) -#define PIN_SPI_MISO_PINSWAP_1 (PIN_PC1) -#define PIN_SPI_SCK_PINSWAP_1 (PIN_PC2) -#define PIN_SPI_MOSI_PINSWAP_1 (PIN_PC0) -#define PIN_SPI_SS_PINSWAP_1 (PIN_PC3) -#define PIN_SPI_MISO_PINSWAP_2 (PIN_PE1) -#define PIN_SPI_SCK_PINSWAP_2 (PIN_PE2) -#define PIN_SPI_MOSI_PINSWAP_2 (PIN_PE0) -#define PIN_SPI_SS_PINSWAP_2 (PIN_PE3) +#define SPI_MUX PORTMUX_SPI0_DEFAULT_gc +#define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_ALT1_gc +#define SPI_MUX_PINSWAP_2 PORTMUX_SPI0_ALT2_gc +#define PIN_SPI_MISO PIN_PA5 +#define PIN_SPI_SCK PIN_PA6 +#define PIN_SPI_MOSI PIN_PA4 +#define PIN_SPI_SS PIN_PA7 +#define PIN_SPI_MISO_PINSWAP_1 PIN_PC1 +#define PIN_SPI_SCK_PINSWAP_1 PIN_PC2 +#define PIN_SPI_MOSI_PINSWAP_1 PIN_PC0 +#define PIN_SPI_SS_PINSWAP_1 PIN_PC3 +#define PIN_SPI_MISO_PINSWAP_2 PIN_PE1 +#define PIN_SPI_SCK_PINSWAP_2 PIN_PE2 +#define PIN_SPI_MOSI_PINSWAP_2 PIN_PE0 +#define PIN_SPI_SS_PINSWAP_2 PIN_PE3 static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; @@ -126,71 +126,80 @@ static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define TWI_MUX_PINSWAP (PORTMUX_TWI0_ALT2_gc) -#define PIN_WIRE_SDA (PIN_PA2) -#define PIN_WIRE_SCL (PIN_PA3) -#define PIN_WIRE_SDA_PINSWAP_1 (PIN_PC2) -#define PIN_WIRE_SCL_PINSWAP_1 (PIN_PC3) +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define TWI_MUX_PINSWAP PORTMUX_TWI0_ALT2_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 +#define PIN_WIRE_SDA_PINSWAP_1 PIN_PC2 +#define PIN_WIRE_SCL_PINSWAP_1 PIN_PC3 static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; // USART 0 // No pinswap by default -#define HWSERIAL0 (&USART0) -#define HWSERIAL0_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART0_DEFAULT_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_HWSERIAL0_TX (PIN_PA0) -#define PIN_HWSERIAL0_RX (PIN_PA1) -#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PA4) -#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PA5) +#define HWSERIAL0 &USART0 +#define HWSERIAL0_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_HWSERIAL0_TX PIN_PA0 +#define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_XCK PIN_PA2 +#define PIN_HWSERIAL0_XDIR PIN_PA3 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PA7 // USART1 // No pinswap by default -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_DEFAULT_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_ALT1_gc) -#define PIN_HWSERIAL1_TX (PIN_PC0) -#define PIN_HWSERIAL1_RX (PIN_PC1) -#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC4) -#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC5) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_ALT1_gc +#define PIN_HWSERIAL1_TX PIN_PC0 +#define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_XCK PIN_PC2 +#define PIN_HWSERIAL1_XDIR PIN_PC3 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC4 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC5 // USART 2 // No pinswap by default -#define HWSERIAL2 (&USART2) -#define HWSERIAL2_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART2_DEFAULT_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART2_ALT1_gc) -#define PIN_HWSERIAL2_TX (PIN_PF0) -#define PIN_HWSERIAL2_RX (PIN_PF1) -#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PF4) -#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PF5) +#define HWSERIAL2 &USART2 +#define HWSERIAL2_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART2_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc +#define PIN_HWSERIAL2_TX PIN_PF0 +#define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_XCK PIN_PF2 +#define PIN_HWSERIAL2_XDIR PIN_PF3 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PF6 // Analog pins -#define PIN_A0 (PIN_PD0) -#define PIN_A1 (PIN_PD1) -#define PIN_A2 (PIN_PD2) -#define PIN_A3 (PIN_PD3) -#define PIN_A4 (PIN_PD4) -#define PIN_A5 (PIN_PD5) -#define PIN_A6 (PIN_PD6) -#define PIN_A7 (PIN_PD7) -#define PIN_A8 (PIN_PE0) -#define PIN_A9 (PIN_PE1) -#define PIN_A10 (PIN_PE2) -#define PIN_A11 (PIN_PE3) -#define PIN_A12 (PIN_PF2) -#define PIN_A13 (PIN_PF3) -#define PIN_A14 (PIN_PF4) -#define PIN_A15 (PIN_PF5) +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PD4 +#define PIN_A5 PIN_PD5 +#define PIN_A6 PIN_PD6 +#define PIN_A7 PIN_PD7 +#define PIN_A8 PIN_PE0 +#define PIN_A9 PIN_PE1 +#define PIN_A10 PIN_PE2 +#define PIN_A11 PIN_PE3 +#define PIN_A12 PIN_PF2 +#define PIN_A13 PIN_PF3 +#define PIN_A14 PIN_PF4 +#define PIN_A15 PIN_PF5 static const uint8_t A0 = PIN_A0; static const uint8_t A1 = PIN_A1; static const uint8_t A2 = PIN_A2; diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 09ca362..963f462 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -156,8 +156,12 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc #define PIN_HWSERIAL0_TX PIN_PA0 #define PIN_HWSERIAL0_RX PIN_PA1 +#define PIN_HWSERIAL0_XCK PIN_PA2 +#define PIN_HWSERIAL0_XDIR PIN_PA3 #define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PA4 #define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PA7 // USART1 // No pinswap by default @@ -169,8 +173,12 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_ALT1_gc #define PIN_HWSERIAL1_TX PIN_PC0 #define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_XCK PIN_PC2 +#define PIN_HWSERIAL1_XDIR PIN_PC3 #define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC4 #define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC5 +#define PIN_HWSERIAL1_XCK_PINSWAP_1 PIN_PC6 +#define PIN_HWSERIAL1_XDIR_PINSWAP_1 PIN_PC7 // USART 2 // No pinswap by default @@ -182,8 +190,11 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc #define PIN_HWSERIAL2_TX PIN_PF0 #define PIN_HWSERIAL2_RX PIN_PF1 +#define PIN_HWSERIAL2_XCK PIN_PF2 +#define PIN_HWSERIAL2_XDIR PIN_PF3 #define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PF4 #define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PF6 // USART 3 // No pinswap by default @@ -195,6 +206,8 @@ static const uint8_t SCL = PIN_WIRE_SCL; #define HWSERIAL3_MUX_PINSWAP_1 PORTMUX_USART3_ALT1_gc #define PIN_HWSERIAL3_TX PIN_PB0 #define PIN_HWSERIAL3_RX PIN_PB1 +#define PIN_HWSERIAL3_XCK PIN_PB2 +#define PIN_HWSERIAL3_XDIR PIN_PB3 #define PIN_HWSERIAL3_TX_PINSWAP_1 PIN_PB4 #define PIN_HWSERIAL3_RX_PINSWAP_1 PIN_PB5 diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index a54e3a8..c384bf5 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -80,7 +80,7 @@ #define NUM_INTERNALLY_USED_PINS 0 #define NUM_I2C_PINS 2 // (SDA / SCL) #define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_FREE_PINS NUM_DIGITAL_PINS #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) #define ANALOG_INPUT_OFFSET 14 #define LED_BUILTIN 13 @@ -104,11 +104,11 @@ // SPI 0 // Pinswap enabled by default and no alternative available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_ALT2_gc) -#define PIN_SPI_MISO (PIN_PE1) -#define PIN_SPI_SCK (PIN_PE2) -#define PIN_SPI_MOSI (PIN_PE0) -#define PIN_SPI_SS (PIN_PE3) +#define SPI_MUX PORTMUX_SPI0_ALT2_gc +#define PIN_SPI_MISO PIN_PE1 +#define PIN_SPI_SCK PIN_PE2 +#define PIN_SPI_MOSI PIN_PE0 +#define PIN_SPI_SS PIN_PE3 static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; @@ -116,9 +116,9 @@ static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default, and no alternative available -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define PIN_WIRE_SDA (PIN_PA2) -#define PIN_WIRE_SCL (PIN_PA3) +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; @@ -126,61 +126,74 @@ static const uint8_t SCL = PIN_WIRE_SCL; // USART3 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL0 in Serial library -#define HWSERIAL0 (&USART3) -#define HWSERIAL0_DRE_VECTOR (USART3_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART3_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_HWSERIAL0_TX (PIN_PB4) -#define PIN_HWSERIAL0_RX (PIN_PB5) -#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) -#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) +#define HWSERIAL0 &USART3 +#define HWSERIAL0_DRE_VECTOR USART3_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART3_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART3_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART3_ALT1_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART3_DEFAULT_gc +#define PIN_HWSERIAL0_TX PIN_PB4 +#define PIN_HWSERIAL0_RX PIN_PB5 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PB0 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PB1 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PB2 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PB3 // Nano every USART (Serial1) // USART1 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL1 in Serial library -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_HWSERIAL1_TX (PIN_PC4) -#define PIN_HWSERIAL1_RX (PIN_PC5) -#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) -#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_ALT1_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc +#define PIN_HWSERIAL1_TX PIN_PC4 +#define PIN_HWSERIAL1_RX PIN_PC5 +#define PIN_HWSERIAL1_XCK PIN_PC6 +#define PIN_HWSERIAL1_XDIR PIN_PC7 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_XCK_PINSWAP_1 PIN_PC2 +#define PIN_HWSERIAL1_XDIR_PINSWAP_1 PIN_PC3 // Nano Every USART (Serial2) // USART0 on mega4809 // Maps to default pins by default // Mapped to HWSERIAL2 in Serial library -#define HWSERIAL2 (&USART0) -#define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART0_DEFAULT_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_ALT1_gc) -#define PIN_HWSERIAL2_TX (PIN_PA0) -#define PIN_HWSERIAL2_RX (PIN_PA1) -#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PA4) -#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PA5) +#define HWSERIAL2 &USART0 +#define HWSERIAL2_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_HWSERIAL2_TX PIN_PA0 +#define PIN_HWSERIAL2_RX PIN_PA1 +#define PIN_HWSERIAL2_XCK PIN_PA2 +#define PIN_HWSERIAL2_XDIR PIN_PA3 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL2_XDIR_PINSWAP_1 PIN_PA7 // Nano Every USART (Serial3) // USART2 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL3 in Serial library -#define HWSERIAL3 (&USART2) -#define HWSERIAL3_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL3_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) -#define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) -#define PIN_HWSERIAL3_TX (PIN_PF4) -#define PIN_HWSERIAL3_RX (PIN_PF5) -#define PIN_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) -#define PIN_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) +#define HWSERIAL3 &USART2 +#define HWSERIAL3_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL3_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL3_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL3_MUX PORTMUX_USART2_ALT1_gc +#define HWSERIAL3_MUX_PINSWAP_1 PORTMUX_USART2_DEFAULT_gc +#define PIN_HWSERIAL3_TX PIN_PF4 +#define PIN_HWSERIAL3_RX PIN_PF5 +#define PIN_HWSERIAL3_XCK PIN_PF6 +#define PIN_HWSERIAL3_TX_PINSWAP_1 PIN_PF0 +#define PIN_HWSERIAL3_RX_PINSWAP_1 PIN_PF1 +#define PIN_HWSERIAL3_XCK_PINSWAP_1 PIN_PF2 +#define PIN_HWSERIAL3_XDIR_PINSWAP_1 PIN_PF3 // Analog pins #define PIN_A0 PIN_PD3 // AIN3 diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 4df11a3..d5daeef 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -81,7 +81,7 @@ #define NUM_INTERNALLY_USED_PINS 10 // (2 x Chip select + 2 x UART + 4 x IO + LED_BUILTIN + 1 unused pin) #define NUM_I2C_PINS 2 // (SDA / SCL) #define NUM_SPI_PINS 3 // (MISO / MOSI / SCK) -#define NUM_TOTAL_FREE_PINS (NUM_DIGITAL_PINS) +#define NUM_TOTAL_FREE_PINS NUM_DIGITAL_PINS #define NUM_TOTAL_PINS (NUM_DIGITAL_PINS + NUM_RESERVED_PINS + NUM_INTERNALLY_USED_PINS + NUM_I2C_PINS + NUM_SPI_PINS) #define ANALOG_INPUT_OFFSET 14 #define LED_BUILTIN PIN_PD6 @@ -119,11 +119,11 @@ // SPI 0 // Pinswap enabled by default and no alternative available #define SPI_INTERFACES_COUNT 1 -#define SPI_MUX (PORTMUX_SPI0_ALT1_gc) -#define PIN_SPI_MISO (PIN_PC1) -#define PIN_SPI_SCK (PIN_PC2) -#define PIN_SPI_MOSI (PIN_PC0) -#define PIN_SPI_SS (PIN_PB1) +#define SPI_MUX PORTMUX_SPI0_ALT1_gc +#define PIN_SPI_MISO PIN_PC1 +#define PIN_SPI_SCK PIN_PC2 +#define PIN_SPI_MOSI PIN_PC0 +#define PIN_SPI_SS PIN_PB1 static const uint8_t SS = PIN_SPI_SS; static const uint8_t MOSI = PIN_SPI_MOSI; static const uint8_t MISO = PIN_SPI_MISO; @@ -131,9 +131,9 @@ static const uint8_t SCK = PIN_SPI_SCK; // TWI 0 // No pinswap enabled by default, and no alternative available -#define TWI_MUX (PORTMUX_TWI0_DEFAULT_gc) -#define PIN_WIRE_SDA (PIN_PA2) -#define PIN_WIRE_SCL (PIN_PA3) +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 static const uint8_t SDA = PIN_WIRE_SDA; static const uint8_t SCL = PIN_WIRE_SCL; @@ -141,61 +141,74 @@ static const uint8_t SCL = PIN_WIRE_SCL; // USART3 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL0 in Serial library -#define HWSERIAL0 (&USART3) -#define HWSERIAL0_DRE_VECTOR (USART3_DRE_vect) -#define HWSERIAL0_DRE_VECTOR_NUM (USART3_DRE_vect_num) -#define HWSERIAL0_RXC_VECTOR (USART3_RXC_vect) -#define HWSERIAL0_MUX (PORTMUX_USART3_ALT1_gc) -#define HWSERIAL0_MUX_PINSWAP_1 (PORTMUX_USART3_DEFAULT_gc) -#define PIN_HWSERIAL0_TX (PIN_PB4) -#define PIN_HWSERIAL0_RX (PIN_PB5) -#define PIN_HWSERIAL0_TX_PINSWAP_1 (PIN_PB0) -#define PIN_HWSERIAL0_RX_PINSWAP_1 (PIN_PB1) +#define HWSERIAL0 &USART3 +#define HWSERIAL0_DRE_VECTOR USART3_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART3_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART3_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART3_ALT1_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART3_DEFAULT_gc +#define PIN_HWSERIAL0_TX PIN_PB4 +#define PIN_HWSERIAL0_RX PIN_PB5 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PB0 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PB1 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PB2 +#define PIN_HWSERIAL0_XDIR_PINSWAP_1 PIN_PB3 // Uno Wifi Rev2 USART (Serial1) // USART1 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL1 in Serial library -#define HWSERIAL1 (&USART1) -#define HWSERIAL1_DRE_VECTOR (USART1_DRE_vect) -#define HWSERIAL1_DRE_VECTOR_NUM (USART1_DRE_vect_num) -#define HWSERIAL1_RXC_VECTOR (USART1_RXC_vect) -#define HWSERIAL1_MUX (PORTMUX_USART1_ALT1_gc) -#define HWSERIAL1_MUX_PINSWAP_1 (PORTMUX_USART1_DEFAULT_gc) -#define PIN_HWSERIAL1_TX (PIN_PC4) -#define PIN_HWSERIAL1_RX (PIN_PC5) -#define PIN_HWSERIAL1_TX_PINSWAP_1 (PIN_PC0) -#define PIN_HWSERIAL1_RX_PINSWAP_1 (PIN_PC1) +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_ALT1_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc +#define PIN_HWSERIAL1_TX PIN_PC4 +#define PIN_HWSERIAL1_RX PIN_PC5 +#define PIN_HWSERIAL1_XCK PIN_PC6 +#define PIN_HWSERIAL1_XDIR PIN_PC7 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_PC0 +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_PC1 +#define PIN_HWSERIAL1_XCK_PINSWAP_1 PIN_PC2 +#define PIN_HWSERIAL1_XDIR_PINSWAP_1 PIN_PC3 // Uno Wifi Rev2 USART for communicating with Wifi NINA (Serial2) // USART0 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL2 in Serial library -#define HWSERIAL2 (&USART0) -#define HWSERIAL2_DRE_VECTOR (USART0_DRE_vect) -#define HWSERIAL2_DRE_VECTOR_NUM (USART0_DRE_vect_num) -#define HWSERIAL2_RXC_VECTOR (USART0_RXC_vect) -#define HWSERIAL2_MUX (PORTMUX_USART0_ALT1_gc) -#define HWSERIAL2_MUX_PINSWAP_1 (PORTMUX_USART0_DEFAULT_gc) -#define PIN_HWSERIAL2_TX (PIN_PA4) -#define PIN_HWSERIAL2_RX (PIN_PA5) -#define PIN_HWSERIAL2_TX_PINSWAP_1 (PIN_PA0) -#define PIN_HWSERIAL2_RX_PINSWAP_1 (PIN_PA1) +#define HWSERIAL2 &USART0 +#define HWSERIAL2_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART0_ALT1_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART0_DEFAULT_gc +#define PIN_HWSERIAL2_TX PIN_PA4 +#define PIN_HWSERIAL2_RX PIN_PA5 +#define PIN_HWSERIAL2_XCK PIN_PA6 +#define PIN_HWSERIAL2_XDIR PIN_PA7 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PA0 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PA1 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PA2 +#define PIN_HWSERIAL2_XDIR_PINSWAP_1 PIN_PA3 // Uno Wifi Rev2 USART (Serial3) // USART2 on mega4809 // Maps to alternative pins by default // Mapped to HWSERIAL3 in Serial library -#define HWSERIAL3 (&USART2) -#define HWSERIAL3_DRE_VECTOR (USART2_DRE_vect) -#define HWSERIAL3_DRE_VECTOR_NUM (USART2_DRE_vect_num) -#define HWSERIAL3_RXC_VECTOR (USART2_RXC_vect) -#define HWSERIAL3_MUX (PORTMUX_USART2_ALT1_gc) -#define HWSERIAL3_MUX_PINSWAP_1 (PORTMUX_USART2_DEFAULT_gc) -#define PIN_HWSERIAL3_TX (PIN_PF4) -#define PIN_HWSERIAL3_RX (PIN_PF5) -#define PIN_HWSERIAL3_TX_PINSWAP_1 (PIN_PF0) -#define PIN_HWSERIAL3_RX_PINSWAP_1 (PIN_PF1) +#define HWSERIAL3 &USART2 +#define HWSERIAL3_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL3_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL3_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL3_MUX PORTMUX_USART2_ALT1_gc +#define HWSERIAL3_MUX_PINSWAP_1 PORTMUX_USART2_DEFAULT_gc +#define PIN_HWSERIAL3_TX PIN_PF4 +#define PIN_HWSERIAL3_RX PIN_PF5 +#define PIN_HWSERIAL3_XCK PIN_PF6 +#define PIN_HWSERIAL3_TX_PINSWAP_1 PIN_PF0 +#define PIN_HWSERIAL3_RX_PINSWAP_1 PIN_PF1 +#define PIN_HWSERIAL3_XCK_PINSWAP_1 PIN_PF2 +#define PIN_HWSERIAL3_XDIR_PINSWAP_1 PIN_PF3 // Analog pins #define PIN_A0 PIN_PD0 From 769519eceb56eaa18b61d64ef1a0ae4ab7c25c80 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 27 Sep 2020 20:14:30 +0200 Subject: [PATCH 175/351] fix do_spm() vector in optiboot #89 related --- .../Optiboot_mega0_UART0_ALT_115200_A7.hex | 5 +- .../Optiboot_mega0_UART0_DEF_115200_A7.hex | 5 +- .../Optiboot_mega0_UART1_ALT_115200_A7.hex | 5 +- .../Optiboot_mega0_UART1_DEF_115200_A7.hex | 5 +- .../Optiboot_mega0_UART2_ALT_115200_A7.hex | 5 +- .../Optiboot_mega0_UART2_DEF_115200_A7.hex | 5 +- .../Optiboot_mega0_UART3_ALT_115200_A7.hex | 5 +- .../Optiboot_mega0_UART3_DEF_115200_A7.hex | 5 +- megaavr/bootloaders/optiboot/optiboot_x.c | 255 ++++++++---------- 9 files changed, 142 insertions(+), 153 deletions(-) diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex index cf32e3b..519918a 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex @@ -24,7 +24,8 @@ :1001700092FD01C0A89508959091010190FDFCCFDA :1001800098ED94BF809300010895EADF803219F062 :1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF88ED84BF6093000192 -:0A01B000809102108370E1F70895BA +:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 +:1001B00060930010809102108370E1F70895FC01B4 +:0401C00040830895DB :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex index 0dac87b..8237a5b 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex @@ -24,7 +24,8 @@ :1001700001C0A89508959091010190FDFCCF98EDE4 :1001800094BF809300010895EADF803219F081E086 :10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF88ED84BF60930001809192 -:0801B00002108370E1F70895CD +:1001A000E9F7CF91F1CF683048F48DE984BF6093CF +:1001B0000010809102108370E1F70895FC014083E4 +:0201C0000895A0 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex index a3af427..120e3d2 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex @@ -24,7 +24,8 @@ :1001700092FD01C0A89508959091010190FDFCCFDA :1001800098ED94BF809300010895EADF803219F062 :1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF88ED84BF6093000192 -:0A01B000809102108370E1F70895BA +:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 +:1001B00060930010809102108370E1F70895FC01B4 +:0401C00040830895DB :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex index 689e36f..c42f3aa 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex @@ -24,7 +24,8 @@ :1001700001C0A89508959091010190FDFCCF98EDE4 :1001800094BF809300010895EADF803219F081E086 :10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF88ED84BF60930001809192 -:0801B00002108370E1F70895CD +:1001A000E9F7CF91F1CF683048F48DE984BF6093CF +:1001B0000010809102108370E1F70895FC014083E4 +:0201C0000895A0 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex index ed9b4d0..67b0c0a 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex @@ -24,7 +24,8 @@ :1001700092FD01C0A89508959091010190FDFCCFDA :1001800098ED94BF809300010895EADF803219F062 :1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF88ED84BF6093000192 -:0A01B000809102108370E1F70895BA +:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 +:1001B00060930010809102108370E1F70895FC01B4 +:0401C00040830895DB :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex index f829c9b..4b6d606 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex @@ -24,7 +24,8 @@ :1001700001C0A89508959091010190FDFCCF98EDE4 :1001800094BF809300010895EADF803219F081E086 :10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF88ED84BF60930001809192 -:0801B00002108370E1F70895CD +:1001A000E9F7CF91F1CF683048F48DE984BF6093CF +:1001B0000010809102108370E1F70895FC014083E4 +:0201C0000895A0 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex index ec6e572..3969d98 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex @@ -24,7 +24,8 @@ :1001700092FD01C0A89508959091010190FDFCCFDA :1001800098ED94BF809300010895EADF803219F062 :1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF88ED84BF6093000192 -:0A01B000809102108370E1F70895BA +:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 +:1001B00060930010809102108370E1F70895FC01B4 +:0401C00040830895DB :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex index 8348a47..4441661 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex @@ -24,7 +24,8 @@ :1001700001C0A89508959091010190FDFCCF98EDE4 :1001800094BF809300010895EADF803219F081E086 :10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF88ED84BF60930001809192 -:0801B00002108370E1F70895CD +:1001A000E9F7CF91F1CF683048F48DE984BF6093CF +:1001B0000010809102108370E1F70895FC014083E4 +:0201C0000895A0 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/optiboot_x.c b/megaavr/bootloaders/optiboot/optiboot_x.c index e916fc9..f5be99f 100755 --- a/megaavr/bootloaders/optiboot/optiboot_x.c +++ b/megaavr/bootloaders/optiboot/optiboot_x.c @@ -1,118 +1,97 @@ -/**********************************************************/ -/* Optiboot bootloader for Arduino */ -/* */ -/* http://optiboot.googlecode.com */ -/* */ -/* Arduino-maintained version : See README.TXT */ -/* http://code.google.com/p/arduino/ */ -/* It is the intent that changes not relevant to the */ -/* Arduino production envionment get moved from the */ -/* optiboot project to the arduino project in "lumps." */ -/* */ -/* Heavily optimised bootloader that is faster and */ -/* smaller than the Arduino standard bootloader */ -/* */ -/* Enhancements: */ -/* Fits in 512 bytes, saving 1.5K of code space */ -/* Higher baud rate speeds up programming */ -/* Written almost entirely in C */ -/* Customisable timeout with accurate timeconstant */ -/* */ -/* What you lose: */ -/* Implements a skeleton STK500 protocol which is */ -/* missing several features including EEPROM */ -/* programming and non-page-aligned writes */ -/* High baud rate breaks compatibility with standard */ -/* Arduino flash settings */ -/* */ -/* Copyright 2013-2019 by Bill Westfield. */ -/* Copyright 2010 by Peter Knight. */ -/* */ -/* 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 2 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, write */ -/* to the Free Software Foundation, Inc., */ -/* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ -/* */ -/* Licence can be viewed at */ -/* http://www.fsf.org/licenses/gpl.txt */ -/* */ -/**********************************************************/ - - -/**********************************************************/ -/* */ -/* Optional defines: */ -/* */ -/**********************************************************/ -/* */ -/* BIGBOOT: */ -/* Build a 1k bootloader, not 512 bytes. This turns on */ -/* extra functionality. */ -/* */ -/* BAUD_RATE: */ -/* Set bootloader baud rate. */ -/* */ -/* LED_START_FLASHES: */ -/* Number of LED flashes on bootup. */ -/* */ -/* LED_DATA_FLASH: */ -/* Flash LED when transferring data. For boards without */ -/* TX or RX LEDs, or for people who like blinky lights. */ -/* */ -/* TIMEOUT_MS: */ -/* Bootloader timeout period, in milliseconds. */ -/* 500,1000,2000,4000,8000 supported. */ -/* */ -/* UART: */ -/* UART number (0..n) for devices with more than */ -/* one hardware uart (644P, 1284P, etc) */ -/* */ -/**********************************************************/ - -/**********************************************************/ -/* Version Numbers! */ -/* */ -/* Arduino Optiboot now includes this Version number in */ -/* the source and object code. */ -/* */ -/* Version 3 was released as zip from the optiboot */ -/* repository and was distributed with Arduino 0022. */ -/* Version 4 starts with the arduino repository commit */ -/* that brought the arduino repository up-to-date with */ -/* the optiboot source tree changes since v3. */ -/* : */ -/* Version 9 splits off the Mega0/Xtiny support. */ -/* This is very different from normal AVR because of */ -/* changed peripherals and unified address space. */ -/* */ -/* It would be good if versions implemented outside the */ -/* official repository used an out-of-seqeunce version */ -/* number (like 104.6 if based on based on 4.5) to */ -/* prevent collisions. The CUSTOM_VERSION=n option */ -/* adds n to the high version to facilitate this. */ -/* */ -/**********************************************************/ - -/**********************************************************/ -/* Edit History: */ -/* */ -/* Aug 2019 */ -/* 9.0 Refactored for Mega0/Xtiny from optiboot.c */ -/* : */ -/* 4.1 WestfW: put version number in binary. */ -/**********************************************************/ +/************************************************************/ +/* Optiboot bootloader for Mega0, Tiny0, Tiny1 */ +/* */ +/* https://github.com/optiboot/optiboot */ +/* */ +/* Heavily optimised bootloader that is fast and small */ +/* (512 bytes, 115200bps */ +/* */ +/* Written almost entirely in C */ +/* Customisable timeout with accurate timeconstant */ +/* */ +/* */ +/* Copyright 2013-2020 by Bill Westfield. */ +/* Copyright 2010 by Peter Knight. */ +/* */ +/* 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 2 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, write */ +/* to the Free Software Foundation, Inc., */ +/* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +/* */ +/* Licence can be viewed at */ +/* https://github.com/Optiboot/optiboot/blob/master/LICENSE */ +/* */ +/************************************************************/ + + +/************************************************************/ +/* */ +/* Optional defines: */ +/* */ +/************************************************************/ +/* */ +/* BIGBOOT: */ +/* Build a 1k bootloader, not 512 bytes. This turns on */ +/* extra functionality. */ +/* */ +/* BAUD_RATE: */ +/* Set bootloader baud rate. */ +/* */ +/* LED_START_FLASHES: */ +/* Number of LED flashes on bootup. */ +/* */ +/* LED_DATA_FLASH: */ +/* Flash LED when transferring data. For boards without */ +/* TX or RX LEDs, or for people who like blinky lights. */ +/* */ +/* TIMEOUT_MS: */ +/* Bootloader timeout period, in milliseconds. */ +/* 500,1000,2000,4000,8000 supported. */ +/* */ +/* UARTTX: */ +/* UART TX pin (B0, etc) for devices with more than */ +/* one hardware uart, or alternative pins */ +/* */ +/************************************************************/ + +/************************************************************/ +/* Version Numbers! */ +/* */ +/* Optiboot now includes a Version number in the source */ +/* and object code, and returns this value via STK500 */ +/* */ +/* The iniital Mega0/Xtiny support is version 9. */ +/* This is very different from normal AVR because of */ +/* changed peripherals and unified address space. */ +/* */ +/* It would be good if versions implemented outside the */ +/* official repository used an out-of-seqeunce version */ +/* number (like 104.6 if based on based on 4.5) to */ +/* prevent collisions. The CUSTOM_VERSION=n option */ +/* adds n to the high version to facilitate this. */ +/* */ +/************************************************************/ + +/************************************************************/ +/* Edit History: */ +/* */ +/* Aug 2019 */ +/* 9.0 Refactored for Mega0/Xtiny from optiboot.c */ +/* : */ +/* 4.1 WestfW: put version number in binary. */ +/************************************************************/ #define OPTIBOOT_MAJVER 9 #define OPTIBOOT_MINVER 0 @@ -130,7 +109,7 @@ unsigned const int __attribute__((section(".version"))) __attribute__((used)) optiboot_version = 256*(OPTIBOOT_MAJVER + OPTIBOOT_CUSTOMVER) + OPTIBOOT_MINVER; - + #include #include @@ -225,7 +204,7 @@ typedef union { # warning F_CPU is ignored for this chip (run from internal osc.) #endif #ifdef SINGLESPEED -# warning SINGLESPEED ignored for this chip. +# warning SINGLESPEED ignored for this chip. (Fractional BRG) #endif #ifdef UART # warning UART is ignored for this chip (use UARTTX=PortPin instead) @@ -311,7 +290,7 @@ void pre_main (void) { // so entry to this function will always be here, indepedent // of compilation, features, etc __asm__ __volatile__ ( - " rjmp 1f\n" + " rjmp 1f\n" #ifndef APP_NOSPM " rjmp do_nvmctrl\n" #else @@ -540,7 +519,8 @@ int main (void) { /* Get device signature bytes */ else if(ch == STK_READ_SIGN) { - // READ SIGN - return what Avrdude wants to hear + // READ SIGN - return actual device signature from SIGROW + // This enables the same binary to be ued on multiple chips. verifySpace(); putch(SIGROW_DEVICEID0); putch(SIGROW_DEVICEID1); @@ -625,32 +605,33 @@ void watchdogConfig (uint8_t x) { #ifndef APP_NOSPM /* - * Separate function for doing spm stuff - * It's needed for application to do SPM, as SPM instruction works only - * from bootloader. + * Separate function for doing nvmctrl stuff. + * It's needed for application to do manipulate flash, since only the + * bootloader can write or erase flash, or write to the flash alias areas. + * Note that this is significantly different in the details than the + * do_spm() function provided on older AVRs. Same "vector", though. * * How it works: - * - do SPM - * - wait for SPM to complete - * - if chip have RWW/NRWW sections it does additionaly: - * - if command is WRITE or ERASE, AND data=0 then reenable RWW section + * - if the "command" is legal, write it to NVMCTRL.CTRLA + * - if the command is not legal, store data to *address + * - wait for NVM to complete + * + * For example, to write a flash page: * - * In short: - * If you play erase-fill-write, just set data to 0 in ERASE and WRITE - * If you are brave, you have your code just below bootloader in NRWW section - * you could do fill-erase-write sequence with data!=0 in ERASE and - * data=0 in WRITE */ -static void do_nvmctrl(uint16_t address, uint8_t command, uint16_t data) __attribute__ ((used)); -static void do_nvmctrl (uint16_t address, uint8_t command, uint16_t data) { - _PROTECTED_WRITE(WDT.CTRLA, command); - while (NVMCTRL.STATUS & (NVMCTRL_FBUSY_bm|NVMCTRL_EEBUSY_bm)) - ; // wait for flash and EEPROM not busy, just in case. +static void do_nvmctrl(uint16_t address, uint8_t command, uint8_t data) __attribute__ ((used)); +static void do_nvmctrl (uint16_t address, uint8_t command, uint8_t data) { + if (command <= NVMCTRL_CMD_gm) { + _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, command); + while (NVMCTRL.STATUS & (NVMCTRL_FBUSY_bm|NVMCTRL_EEBUSY_bm)) + ; // wait for flash and EEPROM not busy, just in case. + } else { + *(uint8_t *)address = data; + } } #endif - #ifdef BIGBOOT /* * Optiboot is designed to fit in 512 bytes, with a minimum feature set. From 6c49c39cd3aeb1c6c6c5c0654c988bf1ebdfae9a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 14 Oct 2020 11:35:49 +0200 Subject: [PATCH 176/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index be13b07..52fe33d 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.4 +version=1.0.5 # AVR compile variables # --------------------- From 3f636b662dd4bd5c8d478e73ab493012ac9b5435 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 14 Oct 2020 23:12:40 +0200 Subject: [PATCH 177/351] Remove tabs and CRLF line endings --- megaavr/cores/coreX-corefiles/UART.h | 8 +- megaavr/cores/coreX-corefiles/api/Common.h | 4 +- .../EEPROM/examples/eeprom_crc/eeprom_crc.ino | 10 +- .../SoftwareSerial/src/SoftwareSerial.cpp | 918 +++++++++--------- .../SoftwareSerial/src/SoftwareSerial.h | 246 ++--- 5 files changed, 593 insertions(+), 593 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/UART.h b/megaavr/cores/coreX-corefiles/UART.h index a1147d6..896a8db 100644 --- a/megaavr/cores/coreX-corefiles/UART.h +++ b/megaavr/cores/coreX-corefiles/UART.h @@ -128,9 +128,9 @@ class UartClass : public HardwareSerial volatile USART_t * const _hwserial_module; struct UartPinSet { - uint8_t const rx_pin; - uint8_t const tx_pin; - uint8_t const mux; + uint8_t const rx_pin; + uint8_t const tx_pin; + uint8_t const mux; } _hw_set[SERIAL_PIN_SETS]; uint8_t _pin_set; @@ -176,7 +176,7 @@ class UartClass : public HardwareSerial // Interrupt handlers - Not intended to be called externally inline void _rx_complete_irq(void); void _tx_data_empty_irq(void); - + private: void _poll_tx_data_empty(void); }; diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 25cdca9..c74c901 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -99,11 +99,11 @@ void pinMode(pin_size_t pinNumber, uint8_t pinMode); void digitalWrite(pin_size_t pinNumber, uint8_t status); void _dwfast(pin_size_t pinNumber, uint8_t status); #define digitalWriteFast(pin, val) \ - (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _dwfast(pin, val) : digitalWrite(pin, val)) + (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _dwfast(pin, val) : digitalWrite(pin, val)) uint8_t digitalRead(pin_size_t pinNumber); uint8_t _drfast(pin_size_t pinNumber); #define digitalReadFast(pin) \ - (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _drfast(pin) : digitalRead(pin)) + (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _drfast(pin) : digitalRead(pin)) int analogRead(pin_size_t pinNumber); uint8_t analogReadResolution(uint8_t res); void analogReference(uint8_t mode); diff --git a/megaavr/libraries/EEPROM/examples/eeprom_crc/eeprom_crc.ino b/megaavr/libraries/EEPROM/examples/eeprom_crc/eeprom_crc.ino index f8694da..ec30bbd 100644 --- a/megaavr/libraries/EEPROM/examples/eeprom_crc/eeprom_crc.ino +++ b/megaavr/libraries/EEPROM/examples/eeprom_crc/eeprom_crc.ino @@ -1,10 +1,10 @@ /*** - Written by Christopher Andrews. - CRC algorithm generated by pycrc, MIT licence ( https://github.com/tpircher/pycrc ). + Written by Christopher Andrews. + CRC algorithm generated by pycrc, MIT licence ( https://github.com/tpircher/pycrc ). - A CRC is a simple way of checking whether data has changed or become corrupted. - This example calculates a CRC value directly on the EEPROM values. - The purpose of this example is to highlight how the EEPROM object can be used just like an array. + A CRC is a simple way of checking whether data has changed or become corrupted. + This example calculates a CRC value directly on the EEPROM values. + The purpose of this example is to highlight how the EEPROM object can be used just like an array. ***/ #include diff --git a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp index b90e4c9..6c101a1 100644 --- a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp +++ b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp @@ -1,459 +1,459 @@ -/* -SoftwareSerial.cpp (formerly NewSoftSerial.cpp) - -Multi-instance software serial library for Arduino/Wiring --- Interrupt-driven receive and other improvements by ladyada - (http://ladyada.net) --- Tuning, circular buffer, derivation from class Print/Stream, - multi-instance support, porting to 8MHz processors, - various optimizations, PROGMEM delay tables, inverse logic and - direct port writing by Mikal Hart (http://www.arduiniana.org) --- Pin change interrupt macros by Paul Stoffregen (http://www.pjrc.com) --- 20MHz processor support by Garrett Mace (http://www.macetech.com) --- ATmega1280/2560 support by Brett Hagman (http://www.roguerobotics.com/) - -This library is free software; you can redistribute it and/or -modify it under the terms of the GNU Lesser General Public -License as published by the Free Software Foundation; either -version 2.1 of the License, or (at your option) any later version. - -This library 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 -Lesser General Public License for more details. - -You should have received a copy of the GNU Lesser General Public -License along with this library; if not, write to the Free Software -Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -The latest version of this library can always be found at -http://arduiniana.org. -*/ - -// When set, _DEBUG co-opts pins 11 and 13 for debugging with an -// oscilloscope or logic analyzer. Beware: it also slightly modifies -// the bit times, so don't rely on it too much at high baud rates -#define _DEBUG 0 -#define _DEBUG_PIN1 11 -#define _DEBUG_PIN2 13 -// -// Includes -// -#include -#include -#include -#include -#include - -// -// Statics -// -SoftwareSerial *SoftwareSerial::active_object = 0; -uint8_t SoftwareSerial::_receive_buffer[_SS_MAX_RX_BUFF]; -volatile uint8_t SoftwareSerial::_receive_buffer_tail = 0; -volatile uint8_t SoftwareSerial::_receive_buffer_head = 0; - -// -// Debugging -// -// This function generates a brief pulse -// for debugging or measuring on an oscilloscope. -#if _DEBUG -inline void DebugPulse(uint8_t pin, uint8_t count) -{ - volatile uint8_t *pport = portOutputRegister(digitalPinToPort(pin)); - - uint8_t val = *pport; - while (count--) - { - *pport = val | digitalPinToBitMask(pin); - *pport = val; - } -} -#else -inline void DebugPulse(uint8_t, uint8_t) {} -#endif - -// -// Private methods -// - -/* static */ -inline void SoftwareSerial::tunedDelay(uint16_t delay) { - _delay_loop_2(delay); -} - -// This function sets the current object as the "listening" -// one and returns true if it replaces another -bool SoftwareSerial::listen() -{ - if (!_rx_delay_stopbit) - return false; - - if (active_object != this) - { - if (active_object) - active_object->stopListening(); - - _buffer_overflow = false; - _receive_buffer_head = _receive_buffer_tail = 0; - active_object = this; - - setRxIntMsk(true); - return true; - } - - return false; -} - -// Stop listening. Returns true if we were actually listening. -bool SoftwareSerial::stopListening() -{ - if (active_object == this) - { - setRxIntMsk(false); - active_object = NULL; - return true; - } - return false; -} - -// -// The receive routine called by the interrupt handler -// -void SoftwareSerial::recv() -{ - -#if GCC_VERSION < 40302 -// Work-around for avr-gcc 4.3.0 OSX version bug -// Preserve the registers that the compiler misses -// (courtesy of Arduino forum user *etracer*) - asm volatile( - "push r18 \n\t" - "push r19 \n\t" - "push r20 \n\t" - "push r21 \n\t" - "push r22 \n\t" - "push r23 \n\t" - "push r26 \n\t" - "push r27 \n\t" - ::); -#endif - - uint8_t d = 0; - - // If RX line is high, then we don't see any start bit - // so interrupt is probably not for us - if (_inverse_logic ? rx_pin_read() : !rx_pin_read()) - { - // Disable further interrupts during reception, this prevents - // triggering another interrupt directly after we return, which can - // cause problems at higher baudrates. - setRxIntMsk(false); - - // Wait approximately 1/2 of a bit width to "center" the sample - tunedDelay(_rx_delay_centering); - DebugPulse(_DEBUG_PIN2, 1); - - // Read each of the 8 bits - for (uint8_t i=8; i > 0; --i) - { - tunedDelay(_rx_delay_intrabit); - d >>= 1; - DebugPulse(_DEBUG_PIN2, 1); - if (rx_pin_read()) - d |= 0x80; - } - - if (_inverse_logic) - d = ~d; - - // if buffer full, set the overflow flag and return - uint8_t next = (_receive_buffer_tail + 1) % _SS_MAX_RX_BUFF; - if (next != _receive_buffer_head) - { - // save new data in buffer: tail points to where byte goes - _receive_buffer[_receive_buffer_tail] = d; // save new byte - _receive_buffer_tail = next; - } - else - { - DebugPulse(_DEBUG_PIN1, 1); - _buffer_overflow = true; - } - - // skip the stop bit - tunedDelay(_rx_delay_stopbit); - DebugPulse(_DEBUG_PIN1, 1); - - // Re-enable interrupts when we're sure to be inside the stop bit - setRxIntMsk(true); - - } - -#if GCC_VERSION < 40302 -// Work-around for avr-gcc 4.3.0 OSX version bug -// Restore the registers that the compiler misses - asm volatile( - "pop r27 \n\t" - "pop r26 \n\t" - "pop r23 \n\t" - "pop r22 \n\t" - "pop r21 \n\t" - "pop r20 \n\t" - "pop r19 \n\t" - "pop r18 \n\t" - ::); -#endif -} - -uint8_t SoftwareSerial::rx_pin_read() -{ - return *_receivePortRegister & _receiveBitMask; -} - -// -// Interrupt handling -// - -/* static */ -inline void SoftwareSerial::handle_interrupt() -{ - if (active_object) - { - active_object->recv(); - } -} - -// -// Constructor -// -SoftwareSerial::SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic /* = false */) : - _rx_delay_centering(0), - _rx_delay_intrabit(0), - _rx_delay_stopbit(0), - _tx_delay(0), - _buffer_overflow(false), - _inverse_logic(inverse_logic) -{ - setTX(transmitPin); - setRX(receivePin); -} - -// -// Destructor -// -SoftwareSerial::~SoftwareSerial() -{ - end(); -} - -void SoftwareSerial::setTX(uint8_t tx) -{ - // First write, then set output. If we do this the other way around, - // the pin would be output low for a short while before switching to - // output high. Now, it is input with pullup for a short while, which - // is fine. With inverse logic, either order is fine. - digitalWrite(tx, _inverse_logic ? LOW : HIGH); - pinMode(tx, OUTPUT); - _transmitBitMask = digitalPinToBitMask(tx); - uint8_t port = digitalPinToPort(tx); - _transmitPortRegister = portOutputRegister(port); -} - -void SoftwareSerial::setRX(uint8_t rx) -{ - pinMode(rx, INPUT); - if (!_inverse_logic) - digitalWrite(rx, HIGH); // pullup for normal logic! - _receivePin = rx; - _receiveBitMask = digitalPinToBitMask(rx); - uint8_t port = digitalPinToPort(rx); - _receivePortRegister = portInputRegister(port); -} - -uint16_t SoftwareSerial::subtract_cap(uint16_t num, uint16_t sub) { - if (num > sub) - return num - sub; - else - return 1; -} - -// -// Public methods -// - -void SoftwareSerial::begin(long speed) -{ - _rx_delay_centering = _rx_delay_intrabit = _rx_delay_stopbit = _tx_delay = 0; - - // Precalculate the various delays, in number of 4-cycle delays - uint16_t bit_delay = (F_CPU / speed) / 4; - - // 12 (gcc 4.8.2) or 13 (gcc 4.3.2) cycles from start bit to first bit, - // 15 (gcc 4.8.2) or 16 (gcc 4.3.2) cycles between bits, - // 12 (gcc 4.8.2) or 14 (gcc 4.3.2) cycles from last bit to stop bit - // These are all close enough to just use 15 cycles, since the inter-bit - // timings are the most critical (deviations stack 8 times) - _tx_delay = subtract_cap(bit_delay, 15 / 4); - - // Only setup rx when we have a valid PCINT for this pin - if (1) { - #if GCC_VERSION > 40800 - // Timings counted from gcc 4.8.2 output. This works up to 115200 on - // 16Mhz and 57600 on 8Mhz. - // - // When the start bit occurs, there are 3 or 4 cycles before the - // interrupt flag is set, 4 cycles before the PC is set to the right - // interrupt vector address and the old PC is pushed on the stack, - // and then 75 cycles of instructions (including the RJMP in the - // ISR vector table) until the first delay. After the delay, there - // are 17 more cycles until the pin value is read (excluding the - // delay in the loop). - // We want to have a total delay of 1.5 bit time. Inside the loop, - // we already wait for 1 bit time - 23 cycles, so here we wait for - // 0.5 bit time - (71 + 18 - 22) cycles. - _rx_delay_centering = subtract_cap(bit_delay / 2, (4 + 4 + 75 + 17 - 23) / 4); - - // There are 23 cycles in each loop iteration (excluding the delay) - _rx_delay_intrabit = subtract_cap(bit_delay, 23 / 4); - - // There are 37 cycles from the last bit read to the start of - // stopbit delay and 11 cycles from the delay until the interrupt - // mask is enabled again (which _must_ happen during the stopbit). - // This delay aims at 3/4 of a bit time, meaning the end of the - // delay will be at 1/4th of the stopbit. This allows some extra - // time for ISR cleanup, which makes 115200 baud at 16Mhz work more - // reliably - _rx_delay_stopbit = subtract_cap(bit_delay * 3 / 4, (37 + 11) / 4); - #else // Timings counted from gcc 4.3.2 output - // Note that this code is a _lot_ slower, mostly due to bad register - // allocation choices of gcc. This works up to 57600 on 16Mhz and - // 38400 on 8Mhz. - _rx_delay_centering = subtract_cap(bit_delay / 2, (4 + 4 + 97 + 29 - 11) / 4); - _rx_delay_intrabit = subtract_cap(bit_delay, 11 / 4); - _rx_delay_stopbit = subtract_cap(bit_delay * 3 / 4, (44 + 17) / 4); - #endif - - attachInterrupt(_receivePin, SoftwareSerial::handle_interrupt, CHANGE); - - tunedDelay(_tx_delay); // if we were low this establishes the end - } - -#if _DEBUG - pinMode(_DEBUG_PIN1, OUTPUT); - pinMode(_DEBUG_PIN2, OUTPUT); -#endif - - listen(); -} - -void SoftwareSerial::setRxIntMsk(bool enable) -{ - if (enable) - *_pcint_maskreg |= _pcint_maskvalue; - else - *_pcint_maskreg &= ~_pcint_maskvalue; -} - -void SoftwareSerial::end() -{ - stopListening(); -} - - -// Read data from buffer -int SoftwareSerial::read() -{ - if (!isListening()) - return -1; - - // Empty buffer? - if (_receive_buffer_head == _receive_buffer_tail) - return -1; - - // Read from "head" - uint8_t d = _receive_buffer[_receive_buffer_head]; // grab next byte - _receive_buffer_head = (_receive_buffer_head + 1) % _SS_MAX_RX_BUFF; - return d; -} - -int SoftwareSerial::available() -{ - if (!isListening()) - return 0; - - return (_receive_buffer_tail + _SS_MAX_RX_BUFF - _receive_buffer_head) % _SS_MAX_RX_BUFF; -} - -size_t SoftwareSerial::write(uint8_t b) -{ - if (_tx_delay == 0) { - setWriteError(); - return 0; - } - - // By declaring these as local variables, the compiler will put them - // in registers _before_ disabling interrupts and entering the - // critical timing sections below, which makes it a lot easier to - // verify the cycle timings - volatile uint8_t *reg = _transmitPortRegister; - uint8_t reg_mask = _transmitBitMask; - uint8_t inv_mask = ~_transmitBitMask; - uint8_t oldSREG = SREG; - bool inv = _inverse_logic; - uint16_t delay = _tx_delay; - - if (inv) - b = ~b; - - cli(); // turn off interrupts for a clean txmit - - // Write the start bit - if (inv) - *reg |= reg_mask; - else - *reg &= inv_mask; - - tunedDelay(delay); - - // Write each of the 8 bits - for (uint8_t i = 8; i > 0; --i) - { - if (b & 1) // choose bit - *reg |= reg_mask; // send 1 - else - *reg &= inv_mask; // send 0 - - tunedDelay(delay); - b >>= 1; - } - - // restore pin to natural state - if (inv) - *reg &= inv_mask; - else - *reg |= reg_mask; - - SREG = oldSREG; // turn interrupts back on - tunedDelay(_tx_delay); - - return 1; -} - -void SoftwareSerial::flush() -{ - // There is no tx buffering, simply return -} - -int SoftwareSerial::peek() -{ - if (!isListening()) - return -1; - - // Empty buffer? - if (_receive_buffer_head == _receive_buffer_tail) - return -1; - - // Read from "head" - return _receive_buffer[_receive_buffer_head]; -} +/* +SoftwareSerial.cpp (formerly NewSoftSerial.cpp) - +Multi-instance software serial library for Arduino/Wiring +-- Interrupt-driven receive and other improvements by ladyada + (http://ladyada.net) +-- Tuning, circular buffer, derivation from class Print/Stream, + multi-instance support, porting to 8MHz processors, + various optimizations, PROGMEM delay tables, inverse logic and + direct port writing by Mikal Hart (http://www.arduiniana.org) +-- Pin change interrupt macros by Paul Stoffregen (http://www.pjrc.com) +-- 20MHz processor support by Garrett Mace (http://www.macetech.com) +-- ATmega1280/2560 support by Brett Hagman (http://www.roguerobotics.com/) + +This library is free software; you can redistribute it and/or +modify it under the terms of the GNU Lesser General Public +License as published by the Free Software Foundation; either +version 2.1 of the License, or (at your option) any later version. + +This library 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 +Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public +License along with this library; if not, write to the Free Software +Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +The latest version of this library can always be found at +http://arduiniana.org. +*/ + +// When set, _DEBUG co-opts pins 11 and 13 for debugging with an +// oscilloscope or logic analyzer. Beware: it also slightly modifies +// the bit times, so don't rely on it too much at high baud rates +#define _DEBUG 0 +#define _DEBUG_PIN1 11 +#define _DEBUG_PIN2 13 +// +// Includes +// +#include +#include +#include +#include +#include + +// +// Statics +// +SoftwareSerial *SoftwareSerial::active_object = 0; +uint8_t SoftwareSerial::_receive_buffer[_SS_MAX_RX_BUFF]; +volatile uint8_t SoftwareSerial::_receive_buffer_tail = 0; +volatile uint8_t SoftwareSerial::_receive_buffer_head = 0; + +// +// Debugging +// +// This function generates a brief pulse +// for debugging or measuring on an oscilloscope. +#if _DEBUG +inline void DebugPulse(uint8_t pin, uint8_t count) +{ + volatile uint8_t *pport = portOutputRegister(digitalPinToPort(pin)); + + uint8_t val = *pport; + while (count--) + { + *pport = val | digitalPinToBitMask(pin); + *pport = val; + } +} +#else +inline void DebugPulse(uint8_t, uint8_t) {} +#endif + +// +// Private methods +// + +/* static */ +inline void SoftwareSerial::tunedDelay(uint16_t delay) { + _delay_loop_2(delay); +} + +// This function sets the current object as the "listening" +// one and returns true if it replaces another +bool SoftwareSerial::listen() +{ + if (!_rx_delay_stopbit) + return false; + + if (active_object != this) + { + if (active_object) + active_object->stopListening(); + + _buffer_overflow = false; + _receive_buffer_head = _receive_buffer_tail = 0; + active_object = this; + + setRxIntMsk(true); + return true; + } + + return false; +} + +// Stop listening. Returns true if we were actually listening. +bool SoftwareSerial::stopListening() +{ + if (active_object == this) + { + setRxIntMsk(false); + active_object = NULL; + return true; + } + return false; +} + +// +// The receive routine called by the interrupt handler +// +void SoftwareSerial::recv() +{ + +#if GCC_VERSION < 40302 +// Work-around for avr-gcc 4.3.0 OSX version bug +// Preserve the registers that the compiler misses +// (courtesy of Arduino forum user *etracer*) + asm volatile( + "push r18 \n\t" + "push r19 \n\t" + "push r20 \n\t" + "push r21 \n\t" + "push r22 \n\t" + "push r23 \n\t" + "push r26 \n\t" + "push r27 \n\t" + ::); +#endif + + uint8_t d = 0; + + // If RX line is high, then we don't see any start bit + // so interrupt is probably not for us + if (_inverse_logic ? rx_pin_read() : !rx_pin_read()) + { + // Disable further interrupts during reception, this prevents + // triggering another interrupt directly after we return, which can + // cause problems at higher baudrates. + setRxIntMsk(false); + + // Wait approximately 1/2 of a bit width to "center" the sample + tunedDelay(_rx_delay_centering); + DebugPulse(_DEBUG_PIN2, 1); + + // Read each of the 8 bits + for (uint8_t i=8; i > 0; --i) + { + tunedDelay(_rx_delay_intrabit); + d >>= 1; + DebugPulse(_DEBUG_PIN2, 1); + if (rx_pin_read()) + d |= 0x80; + } + + if (_inverse_logic) + d = ~d; + + // if buffer full, set the overflow flag and return + uint8_t next = (_receive_buffer_tail + 1) % _SS_MAX_RX_BUFF; + if (next != _receive_buffer_head) + { + // save new data in buffer: tail points to where byte goes + _receive_buffer[_receive_buffer_tail] = d; // save new byte + _receive_buffer_tail = next; + } + else + { + DebugPulse(_DEBUG_PIN1, 1); + _buffer_overflow = true; + } + + // skip the stop bit + tunedDelay(_rx_delay_stopbit); + DebugPulse(_DEBUG_PIN1, 1); + + // Re-enable interrupts when we're sure to be inside the stop bit + setRxIntMsk(true); + + } + +#if GCC_VERSION < 40302 +// Work-around for avr-gcc 4.3.0 OSX version bug +// Restore the registers that the compiler misses + asm volatile( + "pop r27 \n\t" + "pop r26 \n\t" + "pop r23 \n\t" + "pop r22 \n\t" + "pop r21 \n\t" + "pop r20 \n\t" + "pop r19 \n\t" + "pop r18 \n\t" + ::); +#endif +} + +uint8_t SoftwareSerial::rx_pin_read() +{ + return *_receivePortRegister & _receiveBitMask; +} + +// +// Interrupt handling +// + +/* static */ +inline void SoftwareSerial::handle_interrupt() +{ + if (active_object) + { + active_object->recv(); + } +} + +// +// Constructor +// +SoftwareSerial::SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic /* = false */) : + _rx_delay_centering(0), + _rx_delay_intrabit(0), + _rx_delay_stopbit(0), + _tx_delay(0), + _buffer_overflow(false), + _inverse_logic(inverse_logic) +{ + setTX(transmitPin); + setRX(receivePin); +} + +// +// Destructor +// +SoftwareSerial::~SoftwareSerial() +{ + end(); +} + +void SoftwareSerial::setTX(uint8_t tx) +{ + // First write, then set output. If we do this the other way around, + // the pin would be output low for a short while before switching to + // output high. Now, it is input with pullup for a short while, which + // is fine. With inverse logic, either order is fine. + digitalWrite(tx, _inverse_logic ? LOW : HIGH); + pinMode(tx, OUTPUT); + _transmitBitMask = digitalPinToBitMask(tx); + uint8_t port = digitalPinToPort(tx); + _transmitPortRegister = portOutputRegister(port); +} + +void SoftwareSerial::setRX(uint8_t rx) +{ + pinMode(rx, INPUT); + if (!_inverse_logic) + digitalWrite(rx, HIGH); // pullup for normal logic! + _receivePin = rx; + _receiveBitMask = digitalPinToBitMask(rx); + uint8_t port = digitalPinToPort(rx); + _receivePortRegister = portInputRegister(port); +} + +uint16_t SoftwareSerial::subtract_cap(uint16_t num, uint16_t sub) { + if (num > sub) + return num - sub; + else + return 1; +} + +// +// Public methods +// + +void SoftwareSerial::begin(long speed) +{ + _rx_delay_centering = _rx_delay_intrabit = _rx_delay_stopbit = _tx_delay = 0; + + // Precalculate the various delays, in number of 4-cycle delays + uint16_t bit_delay = (F_CPU / speed) / 4; + + // 12 (gcc 4.8.2) or 13 (gcc 4.3.2) cycles from start bit to first bit, + // 15 (gcc 4.8.2) or 16 (gcc 4.3.2) cycles between bits, + // 12 (gcc 4.8.2) or 14 (gcc 4.3.2) cycles from last bit to stop bit + // These are all close enough to just use 15 cycles, since the inter-bit + // timings are the most critical (deviations stack 8 times) + _tx_delay = subtract_cap(bit_delay, 15 / 4); + + // Only setup rx when we have a valid PCINT for this pin + if (1) { + #if GCC_VERSION > 40800 + // Timings counted from gcc 4.8.2 output. This works up to 115200 on + // 16Mhz and 57600 on 8Mhz. + // + // When the start bit occurs, there are 3 or 4 cycles before the + // interrupt flag is set, 4 cycles before the PC is set to the right + // interrupt vector address and the old PC is pushed on the stack, + // and then 75 cycles of instructions (including the RJMP in the + // ISR vector table) until the first delay. After the delay, there + // are 17 more cycles until the pin value is read (excluding the + // delay in the loop). + // We want to have a total delay of 1.5 bit time. Inside the loop, + // we already wait for 1 bit time - 23 cycles, so here we wait for + // 0.5 bit time - (71 + 18 - 22) cycles. + _rx_delay_centering = subtract_cap(bit_delay / 2, (4 + 4 + 75 + 17 - 23) / 4); + + // There are 23 cycles in each loop iteration (excluding the delay) + _rx_delay_intrabit = subtract_cap(bit_delay, 23 / 4); + + // There are 37 cycles from the last bit read to the start of + // stopbit delay and 11 cycles from the delay until the interrupt + // mask is enabled again (which _must_ happen during the stopbit). + // This delay aims at 3/4 of a bit time, meaning the end of the + // delay will be at 1/4th of the stopbit. This allows some extra + // time for ISR cleanup, which makes 115200 baud at 16Mhz work more + // reliably + _rx_delay_stopbit = subtract_cap(bit_delay * 3 / 4, (37 + 11) / 4); + #else // Timings counted from gcc 4.3.2 output + // Note that this code is a _lot_ slower, mostly due to bad register + // allocation choices of gcc. This works up to 57600 on 16Mhz and + // 38400 on 8Mhz. + _rx_delay_centering = subtract_cap(bit_delay / 2, (4 + 4 + 97 + 29 - 11) / 4); + _rx_delay_intrabit = subtract_cap(bit_delay, 11 / 4); + _rx_delay_stopbit = subtract_cap(bit_delay * 3 / 4, (44 + 17) / 4); + #endif + + attachInterrupt(_receivePin, SoftwareSerial::handle_interrupt, CHANGE); + + tunedDelay(_tx_delay); // if we were low this establishes the end + } + +#if _DEBUG + pinMode(_DEBUG_PIN1, OUTPUT); + pinMode(_DEBUG_PIN2, OUTPUT); +#endif + + listen(); +} + +void SoftwareSerial::setRxIntMsk(bool enable) +{ + if (enable) + *_pcint_maskreg |= _pcint_maskvalue; + else + *_pcint_maskreg &= ~_pcint_maskvalue; +} + +void SoftwareSerial::end() +{ + stopListening(); +} + + +// Read data from buffer +int SoftwareSerial::read() +{ + if (!isListening()) + return -1; + + // Empty buffer? + if (_receive_buffer_head == _receive_buffer_tail) + return -1; + + // Read from "head" + uint8_t d = _receive_buffer[_receive_buffer_head]; // grab next byte + _receive_buffer_head = (_receive_buffer_head + 1) % _SS_MAX_RX_BUFF; + return d; +} + +int SoftwareSerial::available() +{ + if (!isListening()) + return 0; + + return (_receive_buffer_tail + _SS_MAX_RX_BUFF - _receive_buffer_head) % _SS_MAX_RX_BUFF; +} + +size_t SoftwareSerial::write(uint8_t b) +{ + if (_tx_delay == 0) { + setWriteError(); + return 0; + } + + // By declaring these as local variables, the compiler will put them + // in registers _before_ disabling interrupts and entering the + // critical timing sections below, which makes it a lot easier to + // verify the cycle timings + volatile uint8_t *reg = _transmitPortRegister; + uint8_t reg_mask = _transmitBitMask; + uint8_t inv_mask = ~_transmitBitMask; + uint8_t oldSREG = SREG; + bool inv = _inverse_logic; + uint16_t delay = _tx_delay; + + if (inv) + b = ~b; + + cli(); // turn off interrupts for a clean txmit + + // Write the start bit + if (inv) + *reg |= reg_mask; + else + *reg &= inv_mask; + + tunedDelay(delay); + + // Write each of the 8 bits + for (uint8_t i = 8; i > 0; --i) + { + if (b & 1) // choose bit + *reg |= reg_mask; // send 1 + else + *reg &= inv_mask; // send 0 + + tunedDelay(delay); + b >>= 1; + } + + // restore pin to natural state + if (inv) + *reg &= inv_mask; + else + *reg |= reg_mask; + + SREG = oldSREG; // turn interrupts back on + tunedDelay(_tx_delay); + + return 1; +} + +void SoftwareSerial::flush() +{ + // There is no tx buffering, simply return +} + +int SoftwareSerial::peek() +{ + if (!isListening()) + return -1; + + // Empty buffer? + if (_receive_buffer_head == _receive_buffer_tail) + return -1; + + // Read from "head" + return _receive_buffer[_receive_buffer_head]; +} diff --git a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h index edcf760..ca4fd75 100644 --- a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h +++ b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.h @@ -1,123 +1,123 @@ -/* -SoftwareSerial.h (formerly NewSoftSerial.h) - -Multi-instance software serial library for Arduino/Wiring --- Interrupt-driven receive and other improvements by ladyada - (http://ladyada.net) --- Tuning, circular buffer, derivation from class Print/Stream, - multi-instance support, porting to 8MHz processors, - various optimizations, PROGMEM delay tables, inverse logic and - direct port writing by Mikal Hart (http://www.arduiniana.org) --- Pin change interrupt macros by Paul Stoffregen (http://www.pjrc.com) --- 20MHz processor support by Garrett Mace (http://www.macetech.com) --- ATmega1280/2560 support by Brett Hagman (http://www.roguerobotics.com/) - -This library is free software; you can redistribute it and/or -modify it under the terms of the GNU Lesser General Public -License as published by the Free Software Foundation; either -version 2.1 of the License, or (at your option) any later version. - -This library 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 -Lesser General Public License for more details. - -You should have received a copy of the GNU Lesser General Public -License along with this library; if not, write to the Free Software -Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -The latest version of this library can always be found at -http://arduiniana.org. -*/ - -#ifndef SoftwareSerial_h -#define SoftwareSerial_h - -#include -#include - -/****************************************************************************** -* Definitions -******************************************************************************/ - -#ifndef _SS_MAX_RX_BUFF -#define _SS_MAX_RX_BUFF 64 // RX buffer size -#endif - -#ifndef GCC_VERSION -#define GCC_VERSION (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) -#endif - -class SoftwareSerial : public Stream -{ -private: - // per object data - uint8_t _receivePin; - uint8_t _receiveBitMask; - volatile uint8_t *_receivePortRegister; - uint8_t _transmitBitMask; - volatile uint8_t *_transmitPortRegister; - volatile uint8_t *_pcint_maskreg; - uint8_t _pcint_maskvalue; - - // Expressed as 4-cycle delays (must never be 0!) - uint16_t _rx_delay_centering; - uint16_t _rx_delay_intrabit; - uint16_t _rx_delay_stopbit; - uint16_t _tx_delay; - - uint16_t _buffer_overflow:1; - uint16_t _inverse_logic:1; - - // static data - static uint8_t _receive_buffer[_SS_MAX_RX_BUFF]; - static volatile uint8_t _receive_buffer_tail; - static volatile uint8_t _receive_buffer_head; - static SoftwareSerial *active_object; - - // private methods - inline void recv() __attribute__((__always_inline__)); - uint8_t rx_pin_read(); - void setTX(uint8_t transmitPin); - void setRX(uint8_t receivePin); - inline void setRxIntMsk(bool enable) __attribute__((__always_inline__)); - - // Return num - sub, or 1 if the result would be < 1 - static uint16_t subtract_cap(uint16_t num, uint16_t sub); - - // private static method for timing - static inline void tunedDelay(uint16_t delay); - -public: - // public methods - SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic = false); - ~SoftwareSerial(); - void begin(long speed); - bool listen(); - void end(); - bool isListening() { return this == active_object; } - bool stopListening(); - bool overflow() { bool ret = _buffer_overflow; if (ret) _buffer_overflow = false; return ret; } - int peek(); - - virtual size_t write(uint8_t byte); - virtual int read(); - virtual int available(); - virtual void flush(); - explicit operator bool() { return true; } - - using Print::write; - - // public only for easy access by interrupt handlers - static inline void handle_interrupt() __attribute__((__always_inline__)); -}; - -// Arduino 0012 workaround -#undef int -#undef char -#undef long -#undef byte -#undef float -#undef abs -#undef round - -#endif +/* +SoftwareSerial.h (formerly NewSoftSerial.h) - +Multi-instance software serial library for Arduino/Wiring +-- Interrupt-driven receive and other improvements by ladyada + (http://ladyada.net) +-- Tuning, circular buffer, derivation from class Print/Stream, + multi-instance support, porting to 8MHz processors, + various optimizations, PROGMEM delay tables, inverse logic and + direct port writing by Mikal Hart (http://www.arduiniana.org) +-- Pin change interrupt macros by Paul Stoffregen (http://www.pjrc.com) +-- 20MHz processor support by Garrett Mace (http://www.macetech.com) +-- ATmega1280/2560 support by Brett Hagman (http://www.roguerobotics.com/) + +This library is free software; you can redistribute it and/or +modify it under the terms of the GNU Lesser General Public +License as published by the Free Software Foundation; either +version 2.1 of the License, or (at your option) any later version. + +This library 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 +Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public +License along with this library; if not, write to the Free Software +Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +The latest version of this library can always be found at +http://arduiniana.org. +*/ + +#ifndef SoftwareSerial_h +#define SoftwareSerial_h + +#include +#include + +/****************************************************************************** +* Definitions +******************************************************************************/ + +#ifndef _SS_MAX_RX_BUFF +#define _SS_MAX_RX_BUFF 64 // RX buffer size +#endif + +#ifndef GCC_VERSION +#define GCC_VERSION (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) +#endif + +class SoftwareSerial : public Stream +{ +private: + // per object data + uint8_t _receivePin; + uint8_t _receiveBitMask; + volatile uint8_t *_receivePortRegister; + uint8_t _transmitBitMask; + volatile uint8_t *_transmitPortRegister; + volatile uint8_t *_pcint_maskreg; + uint8_t _pcint_maskvalue; + + // Expressed as 4-cycle delays (must never be 0!) + uint16_t _rx_delay_centering; + uint16_t _rx_delay_intrabit; + uint16_t _rx_delay_stopbit; + uint16_t _tx_delay; + + uint16_t _buffer_overflow:1; + uint16_t _inverse_logic:1; + + // static data + static uint8_t _receive_buffer[_SS_MAX_RX_BUFF]; + static volatile uint8_t _receive_buffer_tail; + static volatile uint8_t _receive_buffer_head; + static SoftwareSerial *active_object; + + // private methods + inline void recv() __attribute__((__always_inline__)); + uint8_t rx_pin_read(); + void setTX(uint8_t transmitPin); + void setRX(uint8_t receivePin); + inline void setRxIntMsk(bool enable) __attribute__((__always_inline__)); + + // Return num - sub, or 1 if the result would be < 1 + static uint16_t subtract_cap(uint16_t num, uint16_t sub); + + // private static method for timing + static inline void tunedDelay(uint16_t delay); + +public: + // public methods + SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic = false); + ~SoftwareSerial(); + void begin(long speed); + bool listen(); + void end(); + bool isListening() { return this == active_object; } + bool stopListening(); + bool overflow() { bool ret = _buffer_overflow; if (ret) _buffer_overflow = false; return ret; } + int peek(); + + virtual size_t write(uint8_t byte); + virtual int read(); + virtual int available(); + virtual void flush(); + explicit operator bool() { return true; } + + using Print::write; + + // public only for easy access by interrupt handlers + static inline void handle_interrupt() __attribute__((__always_inline__)); +}; + +// Arduino 0012 workaround +#undef int +#undef char +#undef long +#undef byte +#undef float +#undef abs +#undef round + +#endif From b787d9ec1ed42b6094c07282eefb5f056b1e0c27 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 14:43:46 +0200 Subject: [PATCH 178/351] Add Travis CI Compiles only for48kB and 32kB parts at the moment. 16 and 8kB part will be added soon --- .travis.yml | 168 ++ .../travis-ci/arduino-ci-script/.travis.yml | 188 ++ megaavr/travis-ci/arduino-ci-script/LICENSE | 21 + megaavr/travis-ci/arduino-ci-script/README.md | 266 ++ .../arduino-ci-script/arduino-ci-script.sh | 2500 +++++++++++++++++ .../etc/astyle-configurations/1.conf | 33 + .../etc/astyle-configurations/2.conf | 46 + .../etc/astyle-configurations/3.conf | 125 + .../arduino-ci-script/etc/autoformat.sh | 1 + .../etc/codespell-ignore-words-list.txt | 4 + 10 files changed, 3352 insertions(+) create mode 100644 .travis.yml create mode 100644 megaavr/travis-ci/arduino-ci-script/.travis.yml create mode 100755 megaavr/travis-ci/arduino-ci-script/LICENSE create mode 100755 megaavr/travis-ci/arduino-ci-script/README.md create mode 100755 megaavr/travis-ci/arduino-ci-script/arduino-ci-script.sh create mode 100755 megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/1.conf create mode 100755 megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/2.conf create mode 100755 megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/3.conf create mode 100755 megaavr/travis-ci/arduino-ci-script/etc/autoformat.sh create mode 100755 megaavr/travis-ci/arduino-ci-script/etc/codespell-ignore-words-list.txt diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000..b03d5a6 --- /dev/null +++ b/.travis.yml @@ -0,0 +1,168 @@ +# This file is used to configure the Travis CI tests for MegaCoreX + +# Although sudo is no longer required by arduino-ci-script since the 1.0.0 release, for some reason setting "sudo: false" causes the Travis CI build time to significantly increase so this setting is left as "sudo: required" +sudo: required + + +env: + global: + # The Arduino IDE will be installed at APPLICATION_FOLDER/arduino + - APPLICATION_FOLDER="${HOME}/arduino-ide" + - SKETCHBOOK_FOLDER="${HOME}/Arduino" + + # Use Arduino IDE version that supports the new AVRs + - IDE_VERSION_LIST_FULL='"1.8.12" "newest"' + + + matrix: + # Compile every example sketch for every library included with MegaCoreX for every MCU, every board option, every installed IDE version + # Each line in the matrix will be run as a separate job in the Travis CI build + + ## ATmega4809 + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=40pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=40pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=40pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=uno_wifi, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=nano_every, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega4808 + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega3209 + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3209:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega3208 + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + +before_install: + # Check for tabs (excluding subtrees and keywords.txt files) + - find . -path './.git' -prune -or -path './megaavr/bootloaders/optiboot' -prune -or -path './megaavr/avrdude.conf' -prune -or -path './avr/travis-ci/arduino-ci-script' -prune -or \( -not -name 'keywords.txt' -and -type f \) -exec grep --with-filename --line-number --binary-files=without-match --regexp=$'\t' '{}' \; -exec echo 'Tab found.' \; -exec false '{}' + + + # Check for non-Unix line endings (excluding subtrees) + - find . -path './.git' -prune -or -path './megaavr/bootloaders/optiboot' -prune -or -path './megaavr/avrdude.conf' -prune -or -path './avr/travis-ci/arduino-ci-script' -prune -or -type f -exec grep --files-with-matches --binary-files=without-match --regexp=$'\r$' '{}' \; -exec echo 'Non-Unix EOL detected.' \; -exec false '{}' + + + # Install the script used to simplify use of Travis CI for testing Arduino projects + - source "${TRAVIS_BUILD_DIR}/megaavr/travis-ci/arduino-ci-script/arduino-ci-script.sh" + + # These functions can be used to get verbose output for debugging the script + # set_script_verbosity can be set to values from 0 - 2 (verbosity off - maximum verbosity) + #- set_script_verbosity 1 + # Setting set_verbose_output_during_compilation to true is the same as File > Preferences > Show verbose output during > compilation (check) in the Arduino IDE + #- set_verbose_output_during_compilation "true" + + - set_application_folder "$APPLICATION_FOLDER" + - set_sketchbook_folder "$SKETCHBOOK_FOLDER" + + # Check for board definition errors that don't affect compilation + - set_board_testing "true" + + # Check for library issues that don't affect compilation + - set_library_testing "true" + + # Install a version of Arduino IDE with an outdated bundled arduino:megaavr platform to force installation of latest arduino:avr + - install_ide "$IDE_VERSION_LIST" + # Install Arduino AVR Boards to get the AVR toolchain + - install_package "arduino:megaavr" + # Install MegaCoreX from the repository + - install_package + + # Install all IDE version required by the job + - install_ide "$IDE_VERSIONS" + + +script: + # Verify every sketch in SKETCH_PATH using the environment variables set in the matrix + - build_sketch "$SKETCH_PATH" "$BOARD_ID" "$ALLOW_FAILURE" "all" + + +after_script: + # Determine user name and repository name from TRAVIS_REPO_SLUG so the configuration will automatically adjust to forks + - USER_NAME="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 1)" + - REPOSITORY_NAME="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 2)" + # Commit a report of the job results to a folder named with the build number in the MegaCoreX branch of the CI-reports repository + - publish_report_to_repository "$REPORT_GITHUB_TOKEN" "https://github.com/${USER_NAME}/CI-reports.git" "$REPOSITORY_NAME" "build_$(printf "%05d\n" "${TRAVIS_BUILD_NUMBER}")" "false" + + # Print a tab separated report of all sketch verification results to the log + - display_report + + +notifications: + email: + on_success: never + on_failure: always diff --git a/megaavr/travis-ci/arduino-ci-script/.travis.yml b/megaavr/travis-ci/arduino-ci-script/.travis.yml new file mode 100644 index 0000000..8ecd7e5 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/.travis.yml @@ -0,0 +1,188 @@ +# This file is used to test the script with Travis CI + +# Although sudo is no longer required by arduino-ci-script since the 1.0.0 release, for some reason setting "sudo: false" causes the Travis CI build time to significantly increase so this setting is left as "sudo: required" +sudo: required + + +env: + global: + # The Arduino IDE will be installed at APPLICATION_FOLDER/arduino + - APPLICATION_FOLDER="${HOME}/arduino-ide" + - SKETCHBOOK_FOLDER="${HOME}/arduino-sketchbook" + + matrix: + # Test install_ide with no argument (using full version list). This would cause the Travis CI build to take much longer so I have it disabled + # - INSTALL_IDE_START_VERSION="" + # Test install_ide using full version list + - INSTALL_IDE_START_VERSION="all" VERBOSITY_LEVEL=0 VERBOSE_COMPILATION="false" + # Test install_ide using custom version list. Test the use of the special version names "oldest" and "newest" in a version list. Test use of "hourly" version name. + - INSTALL_IDE_START_VERSION='("oldest" "1.8.1" "1.8.2" "newest" "hourly")' VERBOSITY_LEVEL=1 VERBOSE_COMPILATION="true" + # Allowed to fail + # Test install_ide using single version + # test the failure behavior of install_package when a Boards Manager installation is attempted using an IDE version that doesn't support it. + - INSTALL_IDE_START_VERSION="1.6.3" VERBOSITY_LEVEL=2 VERBOSE_COMPILATION="false" + # Test install_ide using version range. Test the use of the special version names "oldest" and "newest" in a version range. + - INSTALL_IDE_START_VERSION="oldest" INSTALL_IDE_END_VERSION="newest" VERBOSITY_LEVEL=0 VERBOSE_COMPILATION="false" + + +matrix: + allow_failures: + # The expected behavior is failure because 1.6.3 doesn't support boards manager installation. + - env: INSTALL_IDE_START_VERSION="1.6.3" VERBOSITY_LEVEL=2 VERBOSE_COMPILATION="false" + + +addons: + apt: + sources: + - debian-sid + packages: + - shellcheck + + +before_install: + # Check for issues in the script + - bash -c 'shopt -s globstar; shellcheck arduino-ci-script.sh' + + # Check for trailing whitespace in all files in the repository + - "if grep --line-number --recursive --exclude-dir=.git '[[:blank:]]$' .; then echo 'Trailing whitespace found.'; false; fi" + # Check for tabs in all files in the repository + - "if grep --line-number --recursive --exclude-dir=.git $'\t' .; then echo 'Tab found.'; false; fi" + # Check if all files in the repository end in a newline (https://stackoverflow.com/a/25686825) + - find . -path ./.git -prune -o -type f -print0 | xargs -0 -L1 bash -c 'if test "$(tail --bytes=1 "$0")"; then echo "No new line at end of $0"; false; fi' + + - source "${TRAVIS_BUILD_DIR}/arduino-ci-script.sh" + + - set_script_verbosity "$VERBOSITY_LEVEL" + + - set_application_folder "$APPLICATION_FOLDER" + - set_sketchbook_folder "$SKETCHBOOK_FOLDER" + + # Check for board definition errors that don't affect compilation + - set_board_testing "true" + + # Check for library issues that don't affect compilation + - set_library_testing "true" + + - install_ide "$INSTALL_IDE_START_VERSION" "$INSTALL_IDE_END_VERSION" + + # Install hardware packages + # Test package install from this repository (can't do this because the repository isn't a hardware package) + # - install_package + # Test manual package install from compressed file download + - install_package "https://github.com/SpenceKonde/ATTinyCore/archive/master.zip" + # Test manual package install from Git repository clone + - install_package "https://github.com/MCUdude/MightyCore.git" + # Test manual package install from Git repository clone + - install_package "https://github.com/JChristensen/mighty-1284p.git" "v1.6.3" + + # Test library installation from repository (can't do this because there is no library in this repository) + # - install_library + # Test library install from .zip file. A non-GitHub library download must be used because GitHub appends -{branch name} or -{release version} to the .zip downloads and having a library folder installed whos name contains "-" causes arduino 1.5.6 or older to hang. + - install_library "https://bitbucket.org/teckel12/arduino-new-ping/downloads/NewPing_v1.8.zip" + # Test library install from .zip file with rename. If the rename doesn't work then any job verifying with Arduino IDE 1.5.6 or older will hang because GitHub changes the folder name to MPU9250-master, which is not a valid folder name on those IDE versions. + - install_library "https://github.com/brianc118/MPU9250/archive/master.zip" "MPU9250" + # Test library install from .zip file/folder that has a dot in the name + - install_library "https://github.com/arduino-libraries/CapacitiveSensor/archive/0.5.1.zip" + # Test library install from git repo + - install_library "https://github.com/sfrwmaker/WirelessOregonV2.git" + # Test library install from git repo with branch + - install_library "https://github.com/sde1000/NanodeUNIO.git" "master" + # Test library install from git repo with rename + - install_library "https://github.com/mikaelpatel/Arduino-Shell.git" "" "ArduinoShell" + # Test library install from git repo with branch and rename + - install_library "https://github.com/Avamander/max7456.git" "master" "max_7456" + # Test set_verbose_output_during_compilation. + - set_verbose_output_during_compilation "$VERBOSE_COMPILATION" + + # Boards Manager and Library Manager tests are done as late as possible to allow job 3 to do more thorough testing of script verbosity level 2 before the job fails + + # Test Boards Manager package install without URL. Test error handling of attempting to do a Boards Manager installation when the newest installed IDE version doesn't support it (should print a helpful error message and fail instead of hanging). + - install_package "arduino:sam" + # Test Boards Manager package install with URL + - install_package "MiniCore:avr" "https://mcudude.github.io/MiniCore/package_MCUdude_MiniCore_index.json" + + # Test library install from Library Manager + - install_library "Pushetta:1.0.1" + + +script: + # Verify sketches: + # build_sketch arguments: sketch name, fqbn, IDE version, allow failure + # IDE version: Use "all" for IDE version argument to verify sketch with all versions of the Arduino IDE, use "newest" for IDE version argument to verify sketch with the newest version of the Arduino IDE + + # Installed package tests: + # Test board from hardware package installed via Boards Manager without URL + # Test build_sketch with "newest" special version name + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "arduino:sam:arduino_due_x_dbg" "false" "newest" + # Test board from hardware package installed with Boards Manager URL + # Test build_sketch with specific IDE version + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "MiniCore:avr:328:variant=modelP,BOD=2v7,LTO=Os,clock=16MHz_external" "false" "1.8.1" + # Test board from hardware package manually installed from compressed file download + # Test build_sketch with an IDE version list + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "ATTinyCore-master:avr:attinyx5:LTO=disable,TimerClockSource=default,chip=85,clock=8internal,bod=disable" "false" '("1.8.1" "1.8.2")' + # Test board from hardware package manually installed by cloning Git repository + # Test build_sketch with an IDE version range + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "MightyCore:avr:1284:pinout=standard,variant=modelP,BOD=2v7,LTO=Os,clock=16MHz_external" "false" "1.8.1" "1.8.2" + # Test board from hardware package manually installed by cloning Git repository with non-default branch + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "mighty-1284p:avr:avr_developers" "false" "newest" + + # Installed library tests: + # Test build_sketch without absolute path + # Test library installed from .zip with rename + - cd "${SKETCHBOOK_FOLDER}/libraries/MPU9250/examples/MPU9250/" + - build_sketch "MPU9250.ino" "arduino:avr:uno" "false" "newest" + # Test library installed from .zip with dot in the folder name + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/CapacitiveSensor-0.5.1/examples/CapacitiveSensorSketch/CapacitiveSensorSketch.pde" "arduino:avr:uno" "false" "newest" + # Test library installed from .zip + # Test build_sketch with "all" IDE version name + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/NewPing/examples/NewPingExample/NewPingExample.pde" "arduino:avr:uno" "false" "all" + # Test library installed from .git + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/WirelessOregonV2/examples/OregonReceiver/OregonReceiver.ino" "arduino:avr:uno" "false" "newest" + # Test library installed from .git with branch + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/NanodeUNIO/examples/NanodeUNIO_test/NanodeUNIO_test.pde" "arduino:avr:uno" "false" "newest" + # Test library installed from .git with rename + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/ArduinoShell/examples/ShellBlink/ShellBlink.ino" "arduino:avr:uno" "false" "newest" + # Test library installed from .git with branch and rename + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/max_7456/examples/HelloWorld/HelloWorld.ino" "arduino:avr:uno" "false" "newest" + # Test library installed from Library Manager + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/Pushetta/examples/simple_notification/simple_notification.ino" "arduino:avr:uno" "false" "newest" + + # build_sketch with version argument tests + # Test build_sketch with no IDE version argument (should use all installed IDE versions) + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "arduino:avr:uno" "false" + # Test build_sketch with "oldest" IDE version name + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "arduino:avr:uno" "false" "oldest" + # Test build_sketch allowed to fail (this will fail because WirelessOregonV2 is AVR specific) + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/WirelessOregonV2/examples/OregonReceiver/OregonReceiver.ino" "arduino:sam:arduino_due_x_dbg" "true" "newest" + + # build_sketch with folder argument tests: + # Test build_sketch with folder argument with specific IDE version + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" "1.8.1" + # Test build_sketch with folder argument with "oldest" IDE version name + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" "oldest" + # Test build_sketch with folder argument with "newest" IDE version name + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" "newest" + # Test build_sketch with folder argument with "all" IDE version name + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" "all" + # Test build_sketch with folder argument with no IDE version specified (should use all installed IDE versions) + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" + # Test build_sketch with folder argument with an IDE version list + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" '("1.8.1" "1.8.2")' + # Test build_sketch with folder argument with an IDE version range + - build_sketch "${APPLICATION_FOLDER}/arduino/examples/01.Basics" "arduino:avr:uno" "false" "1.8.1" "1.8.2" + # Test build_sketch with folder argument required to fail (this will fail because WirelessOregonV2 is AVR specific) + - build_sketch "${SKETCHBOOK_FOLDER}/libraries/WirelessOregonV2/examples" "arduino:sam:arduino_due_x_dbg" "require" "newest" + + - publish_report_to_gist "$REPORT_GITHUB_TOKEN" "$REPORT_GIST_URL" "true" + + - USER_NAME="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 1)" + - REPOSITORY_NAME="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 2)" + - publish_report_to_repository "$REPORT_GITHUB_TOKEN" "https://github.com/${USER_NAME}/CI-reports.git" "$REPOSITORY_NAME" "build_$(printf "%05d\n" "${TRAVIS_BUILD_NUMBER}")" "true" + + - display_report + + +notifications: + email: + on_success: always + on_failure: always diff --git a/megaavr/travis-ci/arduino-ci-script/LICENSE b/megaavr/travis-ci/arduino-ci-script/LICENSE new file mode 100755 index 0000000..56c77ec --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2020 per1234, Vitalii Tereshchuk + +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. diff --git a/megaavr/travis-ci/arduino-ci-script/README.md b/megaavr/travis-ci/arduino-ci-script/README.md new file mode 100755 index 0000000..09eb6db --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/README.md @@ -0,0 +1,266 @@ +arduino-ci-script +========== + +Bash script for continuous integration of [Arduino](http://www.arduino.cc/) projects. This is currently targeted for use with [Travis CI](http://travis-ci.org/) but it could be easily adapted to other purposes. + +[![Build Status](https://travis-ci.org/per1234/arduino-ci-script.svg?branch=master)](https://travis-ci.org/per1234/arduino-ci-script) + + +### Table of contents +- [Installation](#installation) +- [Usage](#usage) +- [Publishing job reports](#publishing-job-reports) +- [Troubleshooting](#troubleshooting) +- [Contributing](#contributing) + + +### Installation +The script can be used in multiple ways: + +#### Clone the latest release +Include the latest release of the script in your project by adding the following lines to your build configuration file: +```yaml + # Clone the script repository + - git clone --depth 1 https://github.com/per1234/arduino-ci-script.git "${HOME}/scripts" + - cd "${HOME}/scripts" + # Get new tags from the remote + - git fetch --tags + # Checkout the latest tag + - git checkout $(git describe --tags `git rev-list --tags --max-count=1`) + - source "${HOME}/scripts/arduino-ci-script.sh" +``` + +#### Local copy +If you're passing a token to the script's publish report functions then best security practices would be to use a static copy of the script so you can be sure of the commands the token is used with: +- Download the latest version of the script from https://github.com/per1234/arduino-ci-script/releases by clicking one of the **Source code** links. +- Unzip the downloaded file. +- Copy arduino-ci-script.sh to a convenient location. +- Include the script in your project by adding the following line to your build configuration file: +```yaml + - source arduino-ci-script.sh +``` +Be sure to check for new releases of the script so that you can benefit from the ongoing development work. You can receive notifications of releases by [watching the repository](https://github.com/per1234/arduino-ci-script/subscription). + + +### Usage +See https://github.com/per1234/WatchdogLog/blob/master/.travis.yml for an example of the script in use. + +Please configure your continuous integration system to make the minimum number of downloads and sketch verifications necessary to effectively test your code. This will prevent wasting Arduino and Travis CI's bandwidth and keep the build durations short. + +##### `set_script_verbosity SCRIPT_VERBOSITY_LEVEL` +Control the level of verbosity of the script's output in the Travis CI log. Verbose output can be helpful for debugging but in normal usage it makes the log hard to read and may cause the log to exceed Travis CI's maximum log size of 4 MB, which causes the job to be terminated. The default verbosity level is `0`. +- Parameter: **SCRIPT_VERBOSITY_LEVEL** - `0`, `1` or `2` (least to most verbosity). + +##### `set_application_folder APPLICATION_FOLDER` +- Parameter: **APPLICATION_FOLDER** - The folder to install the Arduino IDE (and Artistic Style if you use `check_code_formatting`) to. This should be set to `/usr/local/share` or a subfolder of that location. The folder will be created if it doesn't already exist. The Arduino IDE will be installed in the `arduino` subfolder. + +##### `set_sketchbook_folder SKETCHBOOK_FOLDER` +- Parameter: **SKETCHBOOK_FOLDER** - The folder to be set as the Arduino IDE's sketchbook folder. The folder will be created if it doesn't already exist. Libraries installed via `install_library` will be installed to the `libraries` subfolder. Non-Boards Manager hardware packages installed via `install_package` will be installed to the `hardware` subfolder. This setting is only supported by Arduino IDE 1.5.6 and newer. + +##### `set_board_testing BOARD_TESTING` +Turn on/off checking for problems with the board definition that generate a warning message during sketch verification but don't ordinarily cause it to fail, such as missing bootloader file. If this is turned on and a problem is detected the `build_sketch` command will return a non-zero exit status. This feature is off by default. +- Parameter: **BOARD_TESTING** - `true`/`false` + +##### `set_library_testing LIBRARY_TESTING` +Turn on/off checking for problems with libraries that generate a warning message during sketch verification but don't ordinarily cause it to fail, such as missing or invalid items in the library.properties file. If this is turned on and a problem is detected the `build_sketch` command will return a non-zero exit status. This feature is off by default. +- Parameter: **LIBRARY_TESTING** - `true`/`false` + +##### Special version names: + - `all`: Refers to all versions of the Arduino IDE (including the hourly build). In the context of `install_ide` this means all IDE versions compatible with the script (those that support the command line interface, 1.5.2 and newer). In the context of all other functions this means all IDE versions that were installed via `install_ide`. + - `oldest`: The oldest release version of the Arduino IDE. In the context of `install_ide` this is the oldest of the IDE versions compatible with the script (1.5.2, the first version to have a command line interface). In the context of build_sketch this means the oldest IDE version that was installed via `install_ide`. + - `newest`: In the context of `install_ide` this means the newest IDE release version. In the context of all other functions this means the newest IDE release version that was installed via `install_ide`. 'newest' will only match to the hourly build if that is the only version available. + - `hourly`: The hourly build of the Arduino IDE. Note that this IDE version is intended for beta testing only. + +##### `install_ide [IDEversionList]` +Install a list of Arduino IDE version(s). +- Parameter(optional): **IDEversionList** - A list of the versions of the Arduino IDE you want installed, in order from oldest to newest. e.g., `'("1.6.5-r5" "1.6.9" "1.8.2")'`. If no arguments are supplied all IDE versions will be installed. The script allows you to install all IDE versions with a command line interface (1.5.2 and newer) for the sake of being complete but I don't see a good reason for testing with the 1.5.x versions of the Arduino IDE. Please only install the IDE versions you actually need for your test to avoid wasting Arduino's bandwidth. This will also result in a shorter build duration. Installation of the IDE will be skipped if it's found to already be installed in the folder specified via the `set_application_folder` function so `install_ide` can also be used simply to inform the script which IDE versions are available. + +##### `install_ide startIDEversion [endIDEversion]` +Install a range of version(s) of the Arduino IDE. +- Parameter: **startIDEversion** - The oldest version of the Arduino IDE to install. +- Parameter(optional): **endIDEversion** - The newest version of the Arduino IDE to install. If this argument is omitted then only startIDEversion will be installed. + +##### `install_package` +"Manually" install the hardware package from the current repository. Packages are installed to `$SKETCHBOOK_FOLDER/hardware`. Assumes the hardware package is located in the root of the download or repository and has the correct folder structure. + +##### `install_package packageURL` +"Manually" install a hardware package downloaded as a compressed file. Packages are installed to `$SKETCHBOOK_FOLDER/hardware`. Assumes the hardware package is located in the root of the file and has the correct folder structure. +- Parameter: **packageURL** - The URL of the hardware package download. The scheme component of the URL (e.g., `http://`, `https://`) is required. + +##### `install_package packageURL [branchName]` +"Manually" install a hardware package by cloning from a Git repository. Packages are installed to `$SKETCHBOOK_FOLDER/hardware`. Assumes the hardware package is located in the root of the repository and has the correct folder structure. +- Parameter: **packageURL** - The URL of the Git repository. The scheme component of the URL (e.g., `http://`, `https://`) is required. The URL must end in `.git`. +- Parameter(optional): **branchName** - Branch of the repository to install. If this argument is not specified or is left blank the default branch will be used. + +##### `install_package packageID [packageURL]` +Install a hardware package using the Arduino IDE (Boards Manager). Only the **Arduino AVR Boards** package is included with the Arduino IDE installation. Packages are installed to `$HOME/.arduino15/packages`. You must call `install_ide` before this function. This feature is only available with Arduino IDE 1.6.4 and newer. +- Parameter: **packageID** - `package name:platform architecture[:version]`. If `version` is omitted the most recent version will be installed. e.g., `arduino:samd` will install the most recent version of **Arduino SAMD Boards**. +- Parameter(optional): **packageURL** - The URL of the Boards Manager JSON file for 3rd party hardware packages. This can be omitted for hardware packages that are included in the official Arduino JSON file (e.g., Arduino SAM Boards, Arduino SAMD Boards, Intel Curie Boards). + +##### `install_library` +Install the library from the current repository. Assumes the library is in the root of the repository. The library is installed to the `libraries` subfolder of the sketchbook folder. + +##### `install_library libraryName` +Install a library that is listed in the Arduino Library Manager index. The library is installed to the `libraries` subfolder of the sketchbook folder. You must call `install_ide` before this function. This feature is only available with Arduino IDE 1.6.4 and newer installed. +- Parameter: **libraryName** - The name of the library to install. You can specify a version separated from the name by a colon, e.g., "LiquidCrystal I2C:1.1.2". If no version is specified the most recent version will be installed. You can also specify comma-separated lists of library names. + +##### `install_library libraryURL [newFolderName]` +Download a library in a compressed file from a URL. The library is installed to the `libraries` subfolder of the sketchbook folder. +- Parameter: **libraryURL** - The URL of the library download or library name in the Arduino Library Manager. The scheme component of the URL (e.g., `http://`, `https://`) is required. The download file can be in any compressed file format. Assumes the library is located in the root of the file. +- Parameter(optional): **newFolderName** - Folder name to rename the installed library folder to. This can be useful if the default folder name of the downloaded file is problematic. The Arduino IDE gives include file preference when the filename matches the library folder name. GitHub's "Download ZIP" file is given the folder name `{repository name}-{branch name}`. Library folder names that contain `-` or `.` are not compatible with Arduino IDE 1.5.6 and older, arduino will hang if it's started with a library using an invalid folder name installed. + +##### `install_library libraryURL [branchName [newFolderName]]` +Install a library by cloning a Git repository. The library is installed to the `libraries` subfolder of the sketchbook folder. Assumes the library is located in the root of the repository. +- Parameter: **libraryURL** - The URL of the library download or library name in the Arduino Library Manager. The scheme component of the URL (e.g., `http://`, `https://`) is required. The URL must end in `.git`. +- Parameter(optional): **branchName** - Branch of the repository to install. If this argument is not specified or is left blank the default branch will be used. +- Parameter(optional): **newFolderName** - Folder name to rename the installed library folder to. This can be useful if the default folder name of the downloaded file is problematic. The Arduino IDE gives include file preference when the filename matches the library folder name. Library folder names that contain `-` or `.` are not compatible with Arduino IDE 1.5.6 and older, arduino will hang if it's started with a library using an invalid folder name installed. If the `newFolderName` argument is specified the `branchName` argument must also be specified. If you don't want to specify a branch then use `""` for the `branchName` argument. + +##### `set_verbose_output_during_compilation verboseOutputDuringCompilation` +Turn on/off `arduino` verbose output during compilation (same as the IDE's **File > Preferences > Show verbose output during: > compilation**). This will show all the commands `arduino` runs during the process rather than just the compiler output. This is usually not very useful output and only clutters up the log. This feature is off by default. +- Parameter: **verboseOutputDuringCompilation** - `true`/`false` + +##### `check_sketch_structure searchPath` +Check sketches to ensure they have the correct structure. +- Parameter: **searchPath** - Path containing sketches. The path will be searched recursively and all sketches found under it will be checked. + +##### `check_library_structure basePath [depth]` +Check libraries to ensure they have the correct structure. This will also run `check_sketch_structure` on all sketches bundled with the library. +- Parameter: **basePath** - Path containing a library. +- Parameter(optional): **depth** - Folder depth relative to `basePath` where the libraries are located. A depth of 0 will check the library located at `basePath`. The default value is 0. + +##### `check_library_properties searchPath [maximumSearchDepth]` +Check [library.properties](https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format) library metadata files for errors. +- Parameter: **searchPath** - Path containing library.properties. +- Parameter(optional): **maximumSearchDepth** - The recursive search depth. A depth of 0 will only search `searchPath` and no subfolders. The default value is 0. + +##### `check_keywords_txt searchPath [maximumSearchDepth]` +Check [keywords.txt](https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#keywords) files for errors. +- Parameter: **searchPath** - Path containing keywords.txt files. +- Parameter(optional): **maximumSearchDepth** - The recursive search depth. A depth of 0 will only search `searchPath` and no subfolders. The default value is 0. + +##### `check_library_manager_compliance libraryPath` +Make some additional checks for compliance with the requirements for adding a library to the [Library Manager index](https://github.com/arduino/Arduino/wiki/Library-Manager-FAQ). This function should be used in combination with `check_library_structure` and `check_library_properties` to ensure full compliance with the requirements. +- Parameter: **libraryPath** - Path of the library to check. + +##### `check_code_formatting strictness excludedPathList targetPath` +Check code formatting for compliance with the Arduino code style. The [Artistic Style](http://astyle.sourceforge.net) formatter tool is used for this check. If it's not already installed, it will be installed to the `astyle` subfolder of the folder specified to `set_application_folder`. Note that in the Travis CI job logs, the `check_code_formatting` output is "folded" to make it easier to browse. You can click the triangle in the left margin of the command to unfold the output. +- Parameter: **strictness** - Determines how strict to be about code formatting compliance: 1 (least strict) - 3 (most strict). Each strictness level is based on the previous one, but with additional requirements. + - `1`: The Arduino IDE's auto format configuration. + - `2`: The configuration Arduino uses to format their example sketches. + - `3`: A custom configuration based on a study of the prevailing styles used in official Arduino code. +- Parameter: **excludedPathList** - A comma-separated list of paths to exclude from the check. +- Parameter: **targetPath** - The path to run the check on. All code files will be checked recursively. + +##### `build_sketch sketchPath boardID allowFail IDEversion` +##### `build_sketch sketchPath boardID allowFail [IDEversionList]` +##### `build_sketch sketchPath boardID allowFail startIDEversion endIDEversion` +Verify/compile sketch(es). `build_sketch` will echo the `arduino` exit status to the log, which is documented at https://github.com/arduino/Arduino/blob/master/build/shared/manpage.adoc#exit-status. Note that in the Travis CI job logs, the compilation output is "folded" to make it easier to browse. You can click the triangles in the left margin to unfold. +- Parameter: **sketchPath** - Path to a sketch or folder containing sketches. If a folder is specified it will be recursively searched and all sketches will be verified. +- Parameter: **boardID** - `package:arch:board[:parameters]` ID of the board to be compiled for. e.g., `arduino:avr:uno`. Board-specific parameters are only supported by Arduino IDE 1.5.5 and newer. +- Parameter: **allowFail** - `true`, `require`, or `false`. Allow the verification to fail without causing the CI build to fail. `require` will cause the build to fail if the sketch verification doesn't fail. +- Parameter: **IDEversion** - A single version of the Arduino IDE to use to verify the sketch. +- Parameter(optional): **IDEversionList** - A list of versions of the Arduino IDE to use to verify the sketch. e.g., `'("1.6.5-r5" "1.6.9" "1.8.2")'`. If no version list is provided all installed IDE versions will be used. +- Parameter: **startIDEversion** - The start (inclusive) of a range of versions of the Arduino IDE to use to verify the sketch. +- Parameter: **endIDEversion** - The end (inclusive) of a range of versions of the Arduino IDE to use to verify the sketch. + +##### `display_report` +Echo a tab separated report of all verification results to the log. The report is located in the `${HOME}/arduino-ci-script_report` folder and will be named according to the build number and job number. Note that Travis CI runs each build of the job in a separate virtual machine so if you have multiple jobs you will have multiple reports. The only way I have found to generate a single report for all tests is to run them as a single job. This means not setting multiple matrix environment variables in .travis.yml's `env` array. See: https://docs.travis-ci.com/user/environment-variables. The report consists of one line per verification: +- Build timestamp - Timestamp of the sketch verification in UTC. +- Build - The Travis CI build number. +- Job - Travis CI job number. +- Job URL - The URL of the Travis CI job log. +- Build Trigger - The cause of this Travis CI build. Possible values are `push`, `pull_request`, `api`, `cron`. +- Allow Job Failure - Whether the Travis CI configuration was set to allow the failure of this job without failing the build. See: https://docs.travis-ci.com/user/customizing-the-build/#Rows-that-are-Allowed-to-Fail. +- PR# - Pull request number (if build was triggered by a pull request). +- Branch - The branch of the repository that was built. +- Commit - Commit hash of the build. +- Commit range - The range of commits that were included in the push or pull request. +- Commit Message - First line of the commit message. +- Sketch filename +- Board ID +- IDE version +- Program Storage (bytes) - Program storage usage of the compiled sketch. +- Dynamic Memory (bytes) - Dynamic memory usage by global variables in the compiled sketch (not available for some boards). +- \# Warnings - Number of warnings reported by the compiler during the sketch compilation. +- Allow Failure - Whether the sketch verification was allowed to fail (set by the `allowFail` argument of `build_sketch`). +- Exit Status - Exit status returned by arduino after the sketch verification. +- \# Board Issues - The number of board issues detected. +- Board Issue - Short description of the last board issue detected. +- \# Library Issues - The number of library issues detected. Library issues are things that cause warnings in the sketch verification output that come from the IDE, rather than the compiler. +- Library Issue - Short description of the last library issue detected. + +##### `publish_report_to_repository REPORT_GITHUB_TOKEN repositoryURL reportBranch reportFolder doLinkComment` +Add the report to a repository. See the [instructions for publishing job reports](publishing-job-reports) for details. +- Parameter: **REPORT_GITHUB_TOKEN** - The hidden or encrypted environment variable containing the GitHub personal access token. +- Parameter: **repositoryURL** - The .git URL of the repository to publish the report to. This URL can be found by clicking the "Clone or download" button on the home page of the repository. The repository must already exist. +- Parameter: **reportBranch** - The branch to publish the report to. The branch must already exist. +- Parameter: **reportFolder** - The folder to publish the report to. The folder will be created if it doesn't exist. +- Parameter: **doLinkComment** - `true` or `false` Whether to comment on the GitHub thread of the commit that triggered the build with a link to the report. + +##### `publish_report_to_gist REPORT_GITHUB_TOKEN REPORT_GIST_URL doLinkComment` +Add the report to the report gist. See the [instructions for publishing job reports](publishing-job-reports) for details. +- Parameter: **REPORT_GITHUB_TOKEN** - The hidden or encrypted environment variable containing the GitHub personal access token. +- Parameter: **REPORT_GIST_URL** - The URL of the report gist. +- Parameter: **doLinkComment** - `true` or `false` Whether to comment on the GitHub thread of the commit that triggered the build with a link to the report. + + +### Publishing job reports +The script offers the option of publishing the job result reports to a repository or GitHub [gist](https://gist.github.com/) by using the `publish_report_to_repository` or `publish_report_to_gist` functions. This makes it easier to view the reports or to import them into a spreadsheet program. You also have the option of having the link to the reports automatically added in a comment to the commit that triggered the build. This requires some configuration, which is described in the instructions below. + +NOTE: For security reasons, reports for builds of pull requests from a fork of the repository can not be published. If the owner of that fork wants to publish reports they can create a GitHub token (and gist if using `publish_report_to_gist`) and configure the Travis CI settings for their fork of the repository following these instructions. + +#### Creating a GitHub personal access token +This is required for either publishing option. +1. Sign in to your GitHub account. +2. Click your avatar at the top right corner of GitHub > **Settings** > **Developer settings** > **Personal access tokens** > **Generate new token**. +3. Check the appropriate permissions for the token: + 1. If using `publish_report_to_gist` check **gist**. + 2. If using `publish_report_to_repository` or setting the `doLinkComment` argument of `publish_report_to_gist` check **public_repo** (for public repositories only) or **repo** (for private and public repositories). +5. Click the **Generate token** button. +6. When the generated token is displayed click the clipboard icon next to it to copy the token. +7. Open the settings page for your repository on the Travis CI website. +8. In the **Environment Variables** section enter `REPORT_GITHUB_TOKEN` in the **Name** field and the token in the **Value** field. Make sure the **Display value in build log** switch is in the off position. +9. Click the **Add** button. + +An alternative to using a Travis CI hidden environment variable as described above is to define the GitHub personal access token as an encrypted environment variable: https://docs.travis-ci.com/user/environment-variables/#Encrypting-environment-variables. + +#### Creating a gist +This is required for use of the `publish_report_to_gist` function. +1. Open https://gist.github.com/ +2. Sign in to your GitHub account. +3. Type an appropriate name in the **Filename including extension...** field. Gists sort files alphabetically so the filename should be something that will sort before the report filenames, which start at travis_ci_job_report_00001.001.tsv. +4. Add some text to the file contents box. +5. Click **Create secret gist** if you don't want the gist to be discoverable (it can still be read by anyone who knows the URL), or **Create public gist** to make it discoverable. +6. Copy the URL of the gist. +7. Open the settings page for your repository on the Travis CI website. +8. In the **Environment Variables** section enter `REPORT_GIST_URL` in the **Name** field and the URL of the gist in the **Value** field. You can turn the **Display value in build log** switch to the on position. The gist URL is not secret and this will provide more information in the log. +9. Click the **Add** button. + + +### Troubleshooting +##### Script hangs after an arduino command +The Arduino IDE will usually try to start the GUI whenever there is an error in the command. Since the Travis CI build environment does not support this it will just hang for ten minutes until Travis CI automatically cancels the job. This means you get no useful information on the cause of the problem. + +##### Verbose output +Verbose output results in a harder to read log so you should leave it off or minimized when possible but it can be useful for troubleshooting. Note that turning on verbose output for a large build may cause the log to exceed 4 MB, which causes Travis CI to terminate the job. +- Verbose script output - See [`set_script_verbosity` documentation](set_script_verbosity-script_verbosity_level) in the Usage section. +- Verbose output during compilation - See [`set_verbose_output_during_compilation` documentation](set_verbose_output_during_compilation-verboseoutputduringcompilation) in the Usage section. +- Verbose output for Travis CI - Add one or both of the following lines to your `.travis.yml` file to get more details of the Travis CI build process. + - Print shell input lines as they are read: + - `- set -o verbose` + - Print a trace of simple commands, for commands, case commands, select commands, and arithmetic for commands and their arguments or associated word lists after they are expanded and before they are executed. The value of the PS4 variable is expanded and the resultant value is printed before the command and its expanded arguments. + - `- set -o xtrace` + +##### Problematic IDE versions +Some older versions of the Arduino IDE have bugs or limitations that may cause problems if used with this script: +- 1.5.1 and older - The command line interface was added in 1.5.2, thus no version older than that can be used. +- 1.5.4 and older - Do not support board-specific parameters, set by custom **Tools** menu items. +- 1.5.5 and older - Do not support setting preferences (`--pref`), thus `set_sketchbook_folder` can not be used if no newer IDE version has been installed. +- 1.5.5-r2 and older - Don't recognize libraries that have a library.properties` file that doesn't define a `core-dependencies` property. The file include is successful but compilation of sketches that use the library functions will fail. +- 1.5.6 and older - `-` or `.` are not allowed in sketch or library folder names. If any are present the Arduino IDE will hang indefinitely when it's executed. +- 1.6.2 - Moves its hardware packages to the .arduino15 folder, causing all other IDE versions to use those cores, some of which are not compatible. For this reason 1.6.2 is not installed when a version range containing, but not starting or ending in, 1.6.2 is passed to `install_ide`. 1.6.2 is installed if it is explicitly specified in a version list. +- 1.6.3 and older - Do not support installing boards (`--install-boards`), thus `install_package` can't be used if no newer IDE version has been installed. + + +### Contributing +Pull requests or issue reports are welcome! Please see the [contribution rules](https://github.com/per1234/arduino-ci-script/blob/master/.github/CONTRIBUTING.md) for instructions. diff --git a/megaavr/travis-ci/arduino-ci-script/arduino-ci-script.sh b/megaavr/travis-ci/arduino-ci-script/arduino-ci-script.sh new file mode 100755 index 0000000..d96e545 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/arduino-ci-script.sh @@ -0,0 +1,2500 @@ +#!/bin/bash +# This script is used to automate continuous integration tasks for Arduino projects +# https://github.com/per1234/arduino-ci-script + +# Based on https://github.com/adafruit/travis-ci-arduino/blob/eeaeaf8fa253465d18785c2bb589e14ea9893f9f/install.sh#L11 +# It seems that arrays can't been seen in other functions. So instead I'm setting $IDE_VERSIONS to a string that is the command to create the array +readonly ARDUINO_CI_SCRIPT_IDE_VERSION_LIST_ARRAY_DECLARATION="declare -a -r IDEversionListArray=" + +readonly ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER="${HOME}/temporary/arduino-ci-script" +readonly ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER="arduino" +readonly ARDUINO_CI_SCRIPT_VERIFICATION_OUTPUT_FILENAME="${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/verification_output.txt" +readonly ARDUINO_CI_SCRIPT_REPORT_FILENAME="travis_ci_job_report_$(printf '%05d\n' "${TRAVIS_BUILD_NUMBER}").$(printf '%03d\n' "$(echo "$TRAVIS_JOB_NUMBER" | cut -d'.' -f 2)").tsv" +readonly ARDUINO_CI_SCRIPT_REPORT_FOLDER="${HOME}/arduino-ci-script_report" +readonly ARDUINO_CI_SCRIPT_REPORT_FILE_PATH="${ARDUINO_CI_SCRIPT_REPORT_FOLDER}/${ARDUINO_CI_SCRIPT_REPORT_FILENAME}" +# The arduino manpage(https://github.com/arduino/Arduino/blob/master/build/shared/manpage.adoc#exit-status) documents a range of exit statuses. These exit statuses indicate success, invalid arduino command, or compilation failed due to legitimate code errors. arduino sometimes returns other exit statuses that may indicate problems that may go away after a retry. +readonly ARDUINO_CI_SCRIPT_HIGHEST_ACCEPTABLE_ARDUINO_EXIT_STATUS=4 +readonly ARDUINO_CI_SCRIPT_SKETCH_VERIFY_RETRIES=3 +readonly ARDUINO_CI_SCRIPT_REPORT_PUSH_RETRIES=10 + +readonly ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS=0 +readonly ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS=1 + +# Arduino IDE 1.8.2 and newer generates a ton of garbage output (appears to be something related to jmdns) that must be filtered for the log to be readable and to avoid exceeding the maximum log length +readonly ARDUINO_CI_SCRIPT_ARDUINO_OUTPUT_FILTER_REGEX='(^\[SocketListener\(travis-job-*|^ *[0-9][0-9]*: [0-9a-g][0-9a-g]*|^dns\[query,[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*:[0-9][0-9]*, length=[0-9][0-9]*, id=|^dns\[response,[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*:[0-9][0-9]*, length=[0-9][0-9]*, id=|^questions:$|\[DNSQuestion@|type: TYPE_IGNORE|^\.\]$|^\.\]\]$|^.\.\]$|^.\.\]\]$)' + +# Default value +ARDUINO_CI_SCRIPT_TOTAL_SKETCH_BUILD_FAILURE_COUNT=0 + +# Set the arduino command name according to OS (on Windows arduino_debug should be used) +if [[ "$OSTYPE" == "cygwin" ]] || [[ "$OSTYPE" == "msys" ]]; then + ARDUINO_CI_SCRIPT_ARDUINO_COMMAND="arduino_debug" +else + ARDUINO_CI_SCRIPT_ARDUINO_COMMAND="arduino" +fi + +# Create the folder if it doesn't exist +function create_folder() { + local -r folderName="$1" + if ! [[ -d "$folderName" ]]; then + # shellcheck disable=SC2086 + mkdir --parents $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "$folderName" + fi +} + +function set_script_verbosity() { + ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL="$1" + + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" == "true" ]]; then + ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL=1 + fi + + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -eq 1 ]]; then + ARDUINO_CI_SCRIPT_VERBOSITY_OPTION="--verbose" + ARDUINO_CI_SCRIPT_QUIET_OPTION="" + # Show stderr only + ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT="1>/dev/null" + elif [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -eq 2 ]]; then + ARDUINO_CI_SCRIPT_VERBOSITY_OPTION="--verbose" + ARDUINO_CI_SCRIPT_QUIET_OPTION="" + # Show stdout and stderr + ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT="" + else + ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL=0 + ARDUINO_CI_SCRIPT_VERBOSITY_OPTION="" + # cabextract only takes the short option name so this is more universally useful than --quiet + ARDUINO_CI_SCRIPT_QUIET_OPTION="-q" + # Don't show stderr or stdout + ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT="&>/dev/null" + fi + +} + +# Deprecated, use set_script_verbosity +function set_verbose_script_output() { + set_script_verbosity 1 +} + +# Deprecated, use set_script_verbosity +function set_more_verbose_script_output() { + set_script_verbosity 2 +} + +# Turn on verbosity based on the preferences set by set_script_verbosity +function enable_verbosity() { + # Store previous verbosity settings so they can be set back to their original values at the end of the function + shopt -q -o verbose + ARDUINO_CI_SCRIPT_PREVIOUS_VERBOSE_SETTING="$?" + + shopt -q -o xtrace + ARDUINO_CI_SCRIPT_PREVIOUS_XTRACE_SETTING="$?" + + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -gt 0 ]]; then + # "Print shell input lines as they are read." + # https://www.gnu.org/software/bash/manual/html_node/The-Set-Builtin.html + set -o verbose + fi + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -gt 1 ]]; then + # "Print a trace of simple commands, for commands, case commands, select commands, and arithmetic for commands and their arguments or associated word lists after they are expanded and before they are executed. The value of the PS4 variable is expanded and the resultant value is printed before the command and its expanded arguments." + # https://www.gnu.org/software/bash/manual/html_node/The-Set-Builtin.html + set -o xtrace + fi +} + +# Return verbosity settings to their previous values +function disable_verbosity() { + if [[ "$ARDUINO_CI_SCRIPT_PREVIOUS_VERBOSE_SETTING" == "0" ]]; then + set -o verbose + else + set +o verbose + fi + + if [[ "$ARDUINO_CI_SCRIPT_PREVIOUS_XTRACE_SETTING" == "0" ]]; then + set -o xtrace + else + set +o xtrace + fi +} + +# Verbosity and, in some cases, errexit must be disabled before an early return from a public function, this allows it to be done in a single line instead of two +function return_handler() { + local -r exitStatus="$1" + + # If exit status is success and errexit is enabled then it must be disabled before exiting the script because errexit must be disabled by default and only enabled in the functions that specifically require it. + # If exit status is not success then errexit should not be disabled, otherwise Travis CI won't fail the build even though the exit status was failure. + if [[ "$exitStatus" == "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]] && shopt -q -o errexit; then + set +o errexit + fi + + disable_verbosity + + return "$exitStatus" +} + +function set_application_folder() { + enable_verbosity + + ARDUINO_CI_SCRIPT_APPLICATION_FOLDER="$1" + + disable_verbosity +} + +function set_sketchbook_folder() { + enable_verbosity + + ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER="$1" + + # Create the sketchbook folder if it doesn't already exist + create_folder "$ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER" + + # Set sketchbook location preference if the IDE is already installed + if [[ "$INSTALLED_IDE_VERSION_LIST_ARRAY" != "" ]]; then + set_ide_preference "sketchbook.path=$ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER" + fi + + disable_verbosity +} + +# Deprecated +function set_parameters() { + set_application_folder "$1" + set_sketchbook_folder "$2" +} + +# Check for errors with the board definition that don't affect sketch verification +function set_board_testing() { + enable_verbosity + + ARDUINO_CI_SCRIPT_TEST_BOARD="$1" + + disable_verbosity +} + +# Check for errors with libraries that don't affect sketch verification +function set_library_testing() { + enable_verbosity + + ARDUINO_CI_SCRIPT_TEST_LIBRARY="$1" + + disable_verbosity +} + +# Install all specified versions of the Arduino IDE +function install_ide() { + enable_verbosity + + local -r startIDEversion="$1" + local -r endIDEversion="$2" + + # https://docs.travis-ci.com/user/customizing-the-build/#Implementing-Complex-Build-Steps + # set -o errexit will cause the script to exit as soon as any command returns a non-zero exit status. Without this the success of the function call is determined by the exit status of the last command in the function + set -o errexit + + if [[ "$ARDUINO_CI_SCRIPT_APPLICATION_FOLDER" == "" ]]; then + echo "ERROR: Application folder was not set. Please use the set_application_folder function to define the location of the application folder." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + # Generate an array declaration string containing a list all available Arduino IDE versions which support CLI + # Save the current folder + local -r previousFolder="$PWD" + cd "$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" + # Create empty local repo for the purpose of getting a list of tags in the arduino/Arduino repository + git init --quiet Arduino + cd Arduino + git remote add origin https://github.com/arduino/Arduino.git + if [[ "$startIDEversion" != "1.6.2" ]] && [[ "$startIDEversion" != "1.6.2" ]]; then + # See "Arduino IDE version blocklist" documentation below + local -r IDEversion162regex=--regex='refs/tags/1\.6\.2' + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -gt 0 ]]; then + echo "NOTE: Due to not playing nicely with other versions, Arduino IDE 1.6.2 will not be installed unless explicitly specified in the version arguments." + fi + fi + + # Arduino IDE tag blocklist: + # <1.5.2: no CLI (https://github.com/arduino/Arduino/blob/master/build/shared/manpage.adoc#history) + # 1.5.4-r2: Not available for download + # 1.5.5-r2: Not available for download + # 1.5.7-macosx-java7: Not available for download + # 1.5.8-macosx-java7: Not available for download + # 1.6.2: has the nasty behavior of moving the included hardware cores to the .arduino15 folder, causing those versions to be used for all builds after Arduino IDE 1.6.2 is used. For that reason, 1.6.2 will only be installed if explicitly specified in the install_ide version arguments + # 1.6.5-r2: Not available for download + # 1.6.5-r3: Not available for download + # 1.6.5-r2: Not available for download + # 1.6.5-r3: Not available for download + # 1.8.11-ms-store-1: Not available for download + # 1.8.13-ms-store-1: Not available for download + local -r ARDUINO_CI_SCRIPT_FULL_IDE_VERSION_LIST_ARRAY="${ARDUINO_CI_SCRIPT_IDE_VERSION_LIST_ARRAY_DECLARATION}'(\"$(git ls-remote --quiet --tags --refs | grep --invert-match --regexp='refs/tags/1\.0' --regexp='refs/tags/1\.5$' --regexp='refs/tags/1\.5\.1$' --regexp='refs/tags/1\.5\.4-r2$' --regexp='refs/tags/1\.5\.5-r2$' --regexp='refs/tags/1\.5\.7-macosx-java7$' --regexp='refs/tags/1\.5\.8-macosx-java7$' ${IDEversion162regex} --regexp='refs/tags/1\.6\.5-r2$' --regexp='refs/tags/1\.6\.5-r3$' --regexp='refs/tags/.*-ms-store.*$' | grep --regexp='refs/tags/[0-9]\+\.[0-9]\+\.[0-9]\+\(\(-.*$\)\|$\)' | cut --delimiter='/' --fields=3 | sort --version-sort | sed ':a;N;$!ba;s/\n/\" \"/g')\")'" + cd .. + # Remove the temporary repo + rm Arduino --recursive --force + # Go back to the previous folder location + cd "$previousFolder" + + # Determine list of IDE versions to install + generate_ide_version_list_array "$ARDUINO_CI_SCRIPT_FULL_IDE_VERSION_LIST_ARRAY" "$startIDEversion" "$endIDEversion" + INSTALLED_IDE_VERSION_LIST_ARRAY="$ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY" + + # Set "$NEWEST_INSTALLED_IDE_VERSION" + determine_ide_version_extremes "$INSTALLED_IDE_VERSION_LIST_ARRAY" + NEWEST_INSTALLED_IDE_VERSION="$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" + + create_folder "$ARDUINO_CI_SCRIPT_APPLICATION_FOLDER" + + # This runs the command contained in the $INSTALLED_IDE_VERSION_LIST_ARRAY string, thus declaring the array locally as $IDEversionListArray. This must be done in any function that uses the array + # Dummy declaration to fix the "referenced but not assigned" warning. + local IDEversionListArray + eval "$INSTALLED_IDE_VERSION_LIST_ARRAY" + + # Determine whether any of the IDE versions to be installed require the creation of a virtual framebuffer (https://github.com/arduino/Arduino/blob/54264124b72eec40aaa22e327c16760f5e806c2a/build/shared/manpage.adoc#bugs) + # This is necessary in Arduino IDE 1.6.13 and older (https://github.com/arduino/Arduino/pull/5578) when running on a headless system + if [ -e /usr/bin/Xvfb ]; then + local -r virtualFramebufferRequiredRegex='^1\.[56]\.' + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + if [[ "$IDEversion" =~ $virtualFramebufferRequiredRegex ]]; then + # based on https://learn.adafruit.com/continuous-integration-arduino-and-you/testing-your-project + /sbin/start-stop-daemon --start $ARDUINO_CI_SCRIPT_QUIET_OPTION $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION --pidfile /tmp/custom_xvfb_1.pid --make-pidfile --background --exec /usr/bin/Xvfb -- :1 -ac -screen 0 1280x1024x16 + sleep 3 + export DISPLAY=:1.0 + break + fi + done + fi + + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + local IDEinstallFolder="$ARDUINO_CI_SCRIPT_APPLICATION_FOLDER/arduino-${IDEversion}" + + # Don't unnecessarily install the IDE + if ! [[ -d "$IDEinstallFolder" ]]; then + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -eq 0 ]]; then + # If the download/installation process is going slowly when installing a lot of IDE versions this function may cause the build to fail due to exceeding Travis CI's 10 minutes without log output timeout so it's necessary to periodically print something. + echo "Installing: $IDEversion" + fi + + # Determine download file extension + local tgzExtensionVersionsRegex="^1\.5\.[0-9]$" + if [[ "$IDEversion" =~ $tgzExtensionVersionsRegex ]]; then + # The download file extension prior to 1.6.0 is .tgz + local downloadFileExtension="tgz" + else + local downloadFileExtension="tar.xz" + fi + + if [[ "$IDEversion" == "hourly" ]]; then + # Deal with the inaccurate name given to the hourly build download + local downloadVersion="nightly" + else + local downloadVersion="$IDEversion" + fi + + wget --no-verbose $ARDUINO_CI_SCRIPT_QUIET_OPTION --directory-prefix="${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/" "http://downloads.arduino.cc/arduino-${downloadVersion}-linux64.${downloadFileExtension}" + tar --extract --directory="$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" --file="${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/arduino-${downloadVersion}-linux64.${downloadFileExtension}" + rm $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/arduino-${downloadVersion}-linux64.${downloadFileExtension}" + mv $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/arduino-${downloadVersion}" "$IDEinstallFolder" + fi + done + + set_ide_preference "compiler.warning_level=all" + + # If a sketchbook location has been defined then set the location in the Arduino IDE preferences + if [[ -d "$ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER" ]]; then + set_ide_preference "sketchbook.path=$ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER" + fi + + # Return errexit to the default state + set +o errexit + + disable_verbosity +} + +# Generate an array of Arduino IDE versions as a subset of the list provided in the base array defined by the start and end versions +# This function allows the same code to be shared by install_ide and build_sketch. The generated array is "returned" as a global named "$ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY" +function generate_ide_version_list_array() { + local -r baseIDEversionArray="$1" + local startIDEversion="$2" + local endIDEversion="$3" + + # Convert "oldest" or "newest" to actual version numbers + determine_ide_version_extremes "$baseIDEversionArray" + if [[ "$startIDEversion" == "oldest" ]]; then + startIDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION" + elif [[ "$startIDEversion" == "newest" ]]; then + startIDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" + fi + + if [[ "$endIDEversion" == "oldest" ]]; then + endIDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION" + elif [[ "$endIDEversion" == "newest" ]]; then + endIDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" + fi + + if [[ "$startIDEversion" == "" || "$startIDEversion" == "all" ]]; then + # Use the full base array + ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY="$baseIDEversionArray" + + else + local rawIDElist + local -r IDEversionListRegex='\(' + if [[ "$startIDEversion" =~ $IDEversionListRegex ]]; then + # IDE versions list was supplied + # Convert it to a temporary array + local -r suppliedIDEversionListArray="${ARDUINO_CI_SCRIPT_IDE_VERSION_LIST_ARRAY_DECLARATION}${startIDEversion}" + eval "$suppliedIDEversionListArray" + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + # Convert any use of "oldest" or "newest" special version names to the actual version number + if [[ "$IDEversion" == "oldest" ]]; then + IDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION" + elif [[ "$IDEversion" == "newest" ]]; then + IDEversion="$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" + fi + # Add the version to the array + rawIDElist="${rawIDElist} "'"'"$IDEversion"'"' + done + + elif [[ "$endIDEversion" == "" ]]; then + # Only a single version was specified + rawIDElist="$rawIDElist"'"'"$startIDEversion"'"' + + else + # A version range was specified + eval "$baseIDEversionArray" + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + if [[ "$IDEversion" == "$startIDEversion" ]]; then + # Start of the list reached, set a flag + local -r listIsStarted="true" + fi + + if [[ "$listIsStarted" == "true" ]]; then + # Add the version to the list + rawIDElist="${rawIDElist} "'"'"$IDEversion"'"' + fi + + if [[ "$IDEversion" == "$endIDEversion" ]]; then + # End of the list was reached, exit the loop + break + fi + done + fi + + # Turn the raw IDE version list into an array + declare -a -r rawIDElistArray="(${rawIDElist})" + + # Remove duplicates from list https://stackoverflow.com/a/13648438 + # shellcheck disable=SC2207 + readonly local uniqueIDElistArray=($(echo "${rawIDElistArray[@]}" | tr ' ' '\n' | sort --unique --version-sort | tr '\n' ' ')) + + # Generate ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY + ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY="$ARDUINO_CI_SCRIPT_IDE_VERSION_LIST_ARRAY_DECLARATION"'(' + for uniqueIDElistArrayIndex in "${!uniqueIDElistArray[@]}"; do + ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY="${ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY} "'"'"${uniqueIDElistArray[$uniqueIDElistArrayIndex]}"'"' + done + ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY="$ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY"')' + fi +} + +# Determine the oldest and newest (non-hourly unless hourly is the only version on the list) IDE version in the provided array +# The determined versions are "returned" by setting the global variables "$ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION" and "$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" +function determine_ide_version_extremes() { + local -r baseIDEversionArray="$1" + + # Reset the variables from any value they were assigned the last time the function was ran + ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION="" + ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION="" + + # Determine the oldest and newest (non-hourly) IDE version in the base array + eval "$baseIDEversionArray" + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + if [[ "$ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION" == "" ]]; then + ARDUINO_CI_SCRIPT_DETERMINED_OLDEST_IDE_VERSION="$IDEversion" + fi + if [[ "$ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION" == "" || "$IDEversion" != "hourly" ]]; then + ARDUINO_CI_SCRIPT_DETERMINED_NEWEST_IDE_VERSION="$IDEversion" + fi + done +} + +function set_ide_preference() { + local -r preferenceString="$1" + + # --pref option is only supported by Arduino IDE 1.5.6 and newer + local -r unsupportedPrefOptionVersionsRegex="^1\.5\.[0-5]$" + if ! [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedPrefOptionVersionsRegex ]]; then + install_ide_version "$NEWEST_INSTALLED_IDE_VERSION" + + # --save-prefs was added in Arduino IDE 1.5.8 + local -r unsupportedSavePrefsOptionVersionsRegex="^1\.5\.[6-7]$" + if ! [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedSavePrefsOptionVersionsRegex ]]; then + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --pref "$preferenceString" --save-prefs "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + else + # Arduino IDE 1.5.6 - 1.5.7 load the GUI if you only set preferences without doing a verify. So I am doing an unnecessary verification just to set the preferences in those versions. Definitely a hack but I prefer to keep the preferences setting code all here instead of cluttering build_sketch and this will pretty much never be used. + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --pref "$preferenceString" --verify "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/arduino/examples/01.Basics/BareMinimum/BareMinimum.ino" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + fi + fi +} + +function install_ide_version() { + local -r IDEversion="$1" + + # Create a symbolic link so that the Arduino IDE can always be referenced by the user from the same path no matter which version is being used. + if [[ "$OSTYPE" == "cygwin" ]] || [[ "$OSTYPE" == "msys" ]]; then + # git-bash's ln just does a copy instead of making a symlink, which takes forever and fails when the target folder exists (despite --force), which takes forever. + # Therefore, use the native Windows command mklink to create a directory junction instead. + # Using a directory junction instead of symlink because supposedly a symlink requires admin privileges. + + # Windows doesn't seem to provide any way to overwrite directory junctions + if [[ -d "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}" ]]; then + rm --recursive --force "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER:?}" + fi + # https://stackoverflow.com/a/25394801 + cmd <<<"mklink /J \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}\\${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}\" \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER//\//\\}\\arduino-${IDEversion}\"" >/dev/null + else + ln --symbolic --force --no-dereference $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/arduino-${IDEversion}" "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}" + fi +} + +# Install hardware packages +function install_package() { + enable_verbosity + + set -o errexit + + local -r URLregex="://" + if [[ "$1" =~ $URLregex ]]; then + # First argument is a URL, do a manual hardware package installation + # Note: Assumes the package is in the root of the download and has the correct folder structure (e.g. architecture folder added in Arduino IDE 1.5+) + + local -r packageURL="$1" + + # Create the hardware folder if it doesn't exist + create_folder "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware" + + if [[ "$packageURL" =~ \.git$ ]]; then + # Clone the repository + local -r branchName="$2" + + local -r previousFolder="$PWD" + cd "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware" + + if [[ "$branchName" == "" ]]; then + git clone --quiet "$packageURL" + else + git clone --quiet --branch "$branchName" "$packageURL" + fi + cd "$previousFolder" + else + local -r previousFolder="$PWD" + cd "$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" + + # Delete everything from the temporary folder + find ./ -mindepth 1 -delete + + # Download the package + wget --no-verbose $ARDUINO_CI_SCRIPT_QUIET_OPTION "$packageURL" + + # Uncompress the package + extract ./*.* + + # Delete all files from the temporary folder + find ./ -maxdepth 1 -type f -delete + + # Install the package + mv $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION ./* "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware/" + cd "$previousFolder" + fi + + elif [[ "$1" == "" ]]; then + # Install hardware package from this repository + # https://docs.travis-ci.com/user/environment-variables#Global-Variables + local packageName + packageName="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 2)" + mkdir --parents $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware/$packageName" + local -r previousFolder="$PWD" + cd "$TRAVIS_BUILD_DIR" + cp --recursive $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION ./* "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware/${packageName}" + # * doesn't copy .travis.yml but that file will be present in the user's installation so it should be there for the tests too + cp $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${TRAVIS_BUILD_DIR}/.travis.yml" "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/hardware/${packageName}" + cd "$previousFolder" + + else + # Install package via Boards Manager + + local -r packageID="$1" + local -r packageURL="$2" + + # Check if Arduino IDE is installed + if [[ "$INSTALLED_IDE_VERSION_LIST_ARRAY" == "" ]]; then + echo "ERROR: Installing a hardware package via Boards Manager requires the Arduino IDE to be installed. Please call install_ide before this command." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + # Check if the newest installed IDE version supports --install-boards + local -r unsupportedInstallBoardsOptionVersionsRange1regex="^1\.5\.[0-9]$" + local -r unsupportedInstallBoardsOptionVersionsRange2regex="^1\.6\.[0-3]$" + if [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedInstallBoardsOptionVersionsRange1regex ]] || [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedInstallBoardsOptionVersionsRange2regex ]]; then + echo "ERROR: --install-boards option is not supported by the newest version of the Arduino IDE you have installed. You must have Arduino IDE 1.6.4 or newer installed to use this function." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + else + # Temporarily install the latest IDE version to use for the package installation + install_ide_version "$NEWEST_INSTALLED_IDE_VERSION" + + # If defined add the boards manager URL to preferences + if [[ "$packageURL" != "" ]]; then + # Get the current Additional Boards Manager URLs preference value so it won't be overwritten when the new URL is added + local priorBoardsmanagerAdditionalURLs + local getPrefExitStatus + # arduino --get-pref returns 4 when the preference does not exist, which is an acceptable circumstance. So it's necessary to unset errexit + set +o errexit + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -eq 0 ]]; then + priorBoardsmanagerAdditionalURLs=$( + "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}" --get-pref boardsmanager.additional.urls 2>/dev/null | tail --lines=1 + exit "${PIPESTATUS[0]}" + ) + getPrefExitStatus="$?" + elif [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -eq 1 ]]; then + priorBoardsmanagerAdditionalURLs=$( + "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}" --get-pref boardsmanager.additional.urls | tail --lines=1 + exit "${PIPESTATUS[0]}" + ) + getPrefExitStatus="$?" + else + priorBoardsmanagerAdditionalURLs=$( + "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}" --get-pref boardsmanager.additional.urls | tee /dev/tty | tail --lines=1 + exit "${PIPESTATUS[0]}" + ) + getPrefExitStatus="$?" + fi + set -o errexit + + if [[ "$getPrefExitStatus" == "4" ]]; then + # No boardsmanager.additional.urls preference was set. This causes priorBoardsmanagerAdditionalURLs to have a garbage value with Arduino IDE 1.8.10 and newer. + priorBoardsmanagerAdditionalURLs="" + fi + + local -r blankregex="^[ ]*$" + if [[ "$priorBoardsmanagerAdditionalURLs" =~ $blankregex ]]; then + # There is no previous Additional Boards Manager URLs preference value + local boardsmanagerAdditionalURLs="$packageURL" + else + # There is a previous Additional Boards Manager URLs preference value so append the new one to the end of it + local boardsmanagerAdditionalURLs="${priorBoardsmanagerAdditionalURLs},${packageURL}" + fi + + # grep returns 1 when a line matches the regular expression so it's necessary to unset errexit + set +o errexit + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --pref boardsmanager.additional.urls="$boardsmanagerAdditionalURLs" --save-prefs "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" | tr --complement --delete '[:print:]\n\t' | tr --squeeze-repeats '\n' | grep --extended-regexp --invert-match "$ARDUINO_CI_SCRIPT_ARDUINO_OUTPUT_FILTER_REGEX" + local -r arduinoPreferenceSettingExitStatus="${PIPESTATUS[0]}" + set -o errexit + # this is required because otherwise the exit status of arduino is ignored + if [[ "$arduinoPreferenceSettingExitStatus" != "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]]; then + return_handler "$arduinoPreferenceSettingExitStatus" + fi + fi + + # Install the package + # grep returns 1 when a line matches the regular expression so it's necessary to unset errexit + set +o errexit + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --install-boards "$packageID" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" | tr --complement --delete '[:print:]\n\t' | tr --squeeze-repeats '\n' | grep --extended-regexp --invert-match "$ARDUINO_CI_SCRIPT_ARDUINO_OUTPUT_FILTER_REGEX" + local -r arduinoInstallPackageExitStatus="${PIPESTATUS[0]}" + set -o errexit + # this is required because otherwise the exit status of arduino is ignored + if [[ "$arduinoInstallPackageExitStatus" != "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]]; then + return_handler "$arduinoPreferenceSettingExitStatus" + fi + + fi + fi + + set +o errexit + + disable_verbosity +} + +function install_library() { + enable_verbosity + + set -o errexit + + local -r libraryIdentifier="$1" + + # Create the libraries folder if it doesn't already exist + create_folder "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries" + + local -r URLregex="://" + if [[ "$libraryIdentifier" =~ $URLregex ]]; then + # The argument is a URL + # Note: this assumes the library is in the root of the file + if [[ "$libraryIdentifier" =~ \.git$ ]]; then + # Clone the repository + local -r branchName="$2" + local -r newFolderName="$3" + + local -r previousFolder="$PWD" + cd "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries" + + if [[ "$branchName" == "" && "$newFolderName" == "" ]]; then + git clone --quiet "$libraryIdentifier" + elif [[ "$branchName" == "" ]]; then + git clone --quiet "$libraryIdentifier" "$newFolderName" + elif [[ "$newFolderName" == "" ]]; then + git clone --quiet --branch "$branchName" "$libraryIdentifier" + else + git clone --quiet --branch "$branchName" "$libraryIdentifier" "$newFolderName" + fi + cd "$previousFolder" + else + # Assume it's a compressed file + local -r newFolderName="$2" + # Download the file to the temporary folder + local -r previousFolder="$PWD" + cd "$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" + + # Delete everything from the temporary folder + find ./ -mindepth 1 -delete + + wget --no-verbose $ARDUINO_CI_SCRIPT_QUIET_OPTION "$libraryIdentifier" + + extract ./*.* + + # Delete all files from the temporary folder + find ./ -maxdepth 1 -type f -delete + + # Install the library + mv $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION ./* "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries/${newFolderName}" + cd "$previousFolder" + fi + + elif [[ "$libraryIdentifier" == "" ]]; then + # Install library from the repository + # https://docs.travis-ci.com/user/environment-variables#Global-Variables + local libraryName + libraryName="$(echo "$TRAVIS_REPO_SLUG" | cut -d'/' -f 2)" + mkdir --parents $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries/$libraryName" + local -r previousFolder="$PWD" + cd "$TRAVIS_BUILD_DIR" + cp --recursive $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION ./* "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries/${libraryName}" + # * doesn't copy .travis.yml but that file will be present in the user's installation so it should be there for the tests too + cp $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${TRAVIS_BUILD_DIR}/.travis.yml" "${ARDUINO_CI_SCRIPT_SKETCHBOOK_FOLDER}/libraries/${libraryName}" + cd "$previousFolder" + + else + # Install a library that is part of the Library Manager index + + # Check if Arduino IDE is installed + if [[ "$INSTALLED_IDE_VERSION_LIST_ARRAY" == "" ]]; then + echo "ERROR: Installing a library via Library Manager requires the Arduino IDE to be installed. Please call install_ide before this command." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + # Check if the newest installed IDE version supports --install-library + local -r unsupportedInstallLibraryOptionVersionsRange1regex="^1\.5\.[0-9]$" + local -r unsupportedInstallLibraryOptionVersionsRange2regex="^1\.6\.[0-3]$" + if [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedInstallLibraryOptionVersionsRange1regex ]] || [[ "$NEWEST_INSTALLED_IDE_VERSION" =~ $unsupportedInstallLibraryOptionVersionsRange2regex ]]; then + echo "ERROR: --install-library option is not supported by the newest version of the Arduino IDE you have installed. You must have Arduino IDE 1.6.4 or newer installed to use this function." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + else + local -r libraryName="$1" + + # Temporarily install the latest IDE version to use for the library installation + install_ide_version "$NEWEST_INSTALLED_IDE_VERSION" + + # Install the library + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --install-library "$libraryName" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + + fi + fi + + set +o errexit + + disable_verbosity +} + +# Extract common file formats +# https://github.com/xvoland/Extract +function extract() { + if [ -z "$1" ]; then + # display usage if no parameters given + echo "Usage: extract ." + echo " extract [path/file_name_2.ext] [path/file_name_3.ext]" + return "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + else + local filename + for filename in "$@"; do + if [ -f "$filename" ]; then + case "${filename%,}" in + *.tar.bz2 | *.tar.gz | *.tar.xz | *.tbz2 | *.tgz | *.txz | *.tar) + tar --extract --file="$filename" + ;; + *.lzma) + unlzma $ARDUINO_CI_SCRIPT_QUIET_OPTION ./"$filename" + ;; + *.bz2) + bunzip2 $ARDUINO_CI_SCRIPT_QUIET_OPTION ./"$filename" + ;; + *.rar) + eval unrar x -ad ./"$filename" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + ;; + *.gz) + gunzip ./"$filename" + ;; + *.zip) + unzip -qq ./"$filename" + ;; + *.z) + eval uncompress ./"$filename" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + ;; + *.7z | *.arj | *.cab | *.chm | *.deb | *.dmg | *.iso | *.lzh | *.msi | *.rpm | *.udf | *.wim | *.xar) + 7z x ./"$filename" + ;; + *.xz) + unxz $ARDUINO_CI_SCRIPT_QUIET_OPTION ./"$filename" + ;; + *.exe) + cabextract $ARDUINO_CI_SCRIPT_QUIET_OPTION ./"$filename" + ;; + *) + echo "extract: '$filename' - unknown archive method" + return "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + ;; + esac + else + echo "extract: '$filename' - file does not exist" + return "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + done + fi +} + +function set_verbose_output_during_compilation() { + enable_verbosity + + local -r verboseOutputDuringCompilation="$1" + if [[ "$verboseOutputDuringCompilation" == "true" ]]; then + ARDUINO_CI_SCRIPT_DETERMINED_VERBOSE_BUILD="--verbose" + else + ARDUINO_CI_SCRIPT_DETERMINED_VERBOSE_BUILD="" + fi + + disable_verbosity +} + +# Verify the sketch +function build_sketch() { + enable_verbosity + + local -r sketchPath="$1" + local -r boardID="$2" + local -r allowFail="$3" + local -r startIDEversion="$4" + local -r endIDEversion="$5" + + # Set default value for buildSketchExitStatus + local buildSketchExitStatus="$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" + + generate_ide_version_list_array "$INSTALLED_IDE_VERSION_LIST_ARRAY" "$startIDEversion" "$endIDEversion" + + if [[ "$ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY" == "$ARDUINO_CI_SCRIPT_IDE_VERSION_LIST_ARRAY_DECLARATION"'()' ]]; then + echo "ERROR: The IDE version(s) specified are not installed" + buildSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + else + eval "$ARDUINO_CI_SCRIPT_GENERATED_IDE_VERSION_LIST_ARRAY" + local IDEversion + for IDEversion in "${IDEversionListArray[@]}"; do + # Install the IDE + # This must be done before searching for sketches in case the path specified is in the Arduino IDE installation folder + install_ide_version "$IDEversion" + + # The package_index files installed by some versions of the IDE (1.6.5, 1.6.5) can cause compilation to fail for other versions (1.6.5-r4, 1.6.5-r5). Attempting to install a dummy package ensures that the correct version of those files will be installed before the sketch verification. + # Check if the newest installed IDE version supports --install-boards + local unsupportedInstallBoardsOptionVersionsRange1regex="^1\.5\.[0-9]$" + local unsupportedInstallBoardsOptionVersionsRange2regex="^1\.6\.[0-3]$" + if ! [[ "$IDEversion" =~ $unsupportedInstallBoardsOptionVersionsRange1regex ]] && ! [[ "$IDEversion" =~ $unsupportedInstallBoardsOptionVersionsRange2regex ]]; then + # shellcheck disable=SC2086 + eval \"${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}\" --install-boards arduino:dummy "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + if [[ "$ARDUINO_CI_SCRIPT_VERBOSITY_LEVEL" -gt 1 ]]; then + # The warning is printed to stdout + echo "NOTE: The warning above \"Selected board is not available\" is caused intentionally and does not indicate a problem." + fi + fi + + if [[ "$sketchPath" =~ \.ino$ ]] || [[ "$sketchPath" =~ \.pde$ ]]; then + # A sketch was specified + if ! [[ -f "$sketchPath" ]]; then + echo "ERROR: Specified sketch: $sketchPath doesn't exist" + buildSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + elif ! build_this_sketch "$sketchPath" "$boardID" "$IDEversion" "$allowFail"; then + # build_this_sketch returned a non-zero exit status + buildSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + else + # Search for all sketches in the path and put them in an array + local sketchFound="false" + # https://github.com/koalaman/shellcheck/wiki/SC2207 + declare -a sketches + mapfile -t sketches < <(find "$sketchPath" -name "*.pde" -o -name "*.ino") + local sketchName + for sketchName in "${sketches[@]}"; do + # Only verify the sketch that matches the name of the sketch folder, otherwise it will cause redundant verifications for sketches that have multiple .ino files + local sketchFolder + sketchFolder="$(echo "$sketchName" | rev | cut -d'/' -f 2 | rev)" + local sketchNameWithoutPathWithExtension + sketchNameWithoutPathWithExtension="$(echo "$sketchName" | rev | cut -d'/' -f 1 | rev)" + local sketchNameWithoutPathWithoutExtension + sketchNameWithoutPathWithoutExtension="${sketchNameWithoutPathWithExtension%.*}" + if [[ "$sketchFolder" == "$sketchNameWithoutPathWithoutExtension" ]]; then + sketchFound="true" + if ! build_this_sketch "$sketchName" "$boardID" "$IDEversion" "$allowFail"; then + # build_this_sketch returned a non-zero exit status + buildSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + fi + done + + if [[ "$sketchFound" == "false" ]]; then + echo "ERROR: No valid sketches were found in the specified path" + buildSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + fi + done + fi + + disable_verbosity + + return $buildSketchExitStatus +} + +function build_this_sketch() { + # Fold this section of output in the Travis CI build log to make it easier to read + echo -e "travis_fold:start:build_sketch" + + local -r sketchName="$1" + local -r boardID="$2" + local -r IDEversion="$3" + local -r allowFail="$4" + + # Produce a useful label for the fold in the Travis log for this function call + echo "build_sketch $sketchName $boardID $allowFail $IDEversion" + + # Arduino IDE 1.8.0 and 1.8.1 fail to verify a sketch if the absolute path to it is not specified + # http://stackoverflow.com/a/3915420/7059512 + local absoluteSketchName + absoluteSketchName="$( + cd "$(dirname "$1")" + pwd + )/$(basename "$1")" + + # Define a dummy value for arduinoExitStatus so that the while loop will run at least once + local arduinoExitStatus=255 + # Retry the verification if arduino returns an exit status that indicates there may have been a temporary error not caused by a bug in the sketch or the arduino command + while [[ $arduinoExitStatus -gt $ARDUINO_CI_SCRIPT_HIGHEST_ACCEPTABLE_ARDUINO_EXIT_STATUS && $verifyCount -le $ARDUINO_CI_SCRIPT_SKETCH_VERIFY_RETRIES ]]; do + # Verify the sketch + # shellcheck disable=SC2086 + "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/${ARDUINO_CI_SCRIPT_ARDUINO_COMMAND}" $ARDUINO_CI_SCRIPT_DETERMINED_VERBOSE_BUILD --verify "$absoluteSketchName" --board "$boardID" 2>&1 | tr --complement --delete '[:print:]\n\t' | tr --squeeze-repeats '\n' | grep --extended-regexp --invert-match "$ARDUINO_CI_SCRIPT_ARDUINO_OUTPUT_FILTER_REGEX" | tee "$ARDUINO_CI_SCRIPT_VERIFICATION_OUTPUT_FILENAME" + local arduinoExitStatus="${PIPESTATUS[0]}" + local verifyCount=$((verifyCount + 1)) + done + + if [[ "$arduinoExitStatus" != "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]]; then + # Sketch verification failed + local buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + else + # Sketch verification succeeded + local buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" + + # Parse through the output from the sketch verification to count warnings and determine the compile size + local warningCount=0 + local boardIssueCount=0 + local libraryIssueCount=0 + while read -r outputFileLine; do + # Determine program storage memory usage + local programStorageRegex="Sketch uses ([0-9,]+) *" + if [[ "$outputFileLine" =~ $programStorageRegex ]] >/dev/null; then + local -r programStorageWithComma=${BASH_REMATCH[1]} + fi + + # Determine dynamic memory usage + local dynamicMemoryRegex="Global variables use ([0-9,]+) *" + if [[ "$outputFileLine" =~ $dynamicMemoryRegex ]] >/dev/null; then + local -r dynamicMemoryWithComma=${BASH_REMATCH[1]} + fi + + # Increment warning count + local warningRegex="warning: " + if [[ "$outputFileLine" =~ $warningRegex ]] >/dev/null; then + warningCount=$((warningCount + 1)) + fi + + # Check for board issues + local bootloaderMissingRegex="Bootloader file specified but missing: " + if [[ "$outputFileLine" =~ $bootloaderMissingRegex ]] >/dev/null; then + local boardIssue="missing bootloader" + boardIssueCount=$((boardIssueCount + 1)) + fi + + local boardsDotTxtMissingRegex="Could not find boards.txt" + if [[ "$outputFileLine" =~ $boardsDotTxtMissingRegex ]] >/dev/null; then + local boardIssue="Could not find boards.txt" + boardIssueCount=$((boardIssueCount + 1)) + fi + + local buildDotBoardNotDefinedRegex="doesn't define a 'build.board' preference" + if [[ "$outputFileLine" =~ $buildDotBoardNotDefinedRegex ]] >/dev/null; then + local boardIssue="doesn't define a 'build.board' preference" + boardIssueCount=$((boardIssueCount + 1)) + fi + + # Check for library issues + # This is the generic "invalid library" warning that doesn't specify the reason + local invalidLibrarRegex1="Invalid library found in" + local invalidLibrarRegex2="from library$" + if [[ "$outputFileLine" =~ $invalidLibrarRegex1 ]] && ! [[ "$outputFileLine" =~ $invalidLibrarRegex2 ]] >/dev/null; then + local libraryIssue="Invalid library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingNameRegex="Invalid library found in .* Missing 'name' from library" + if [[ "$outputFileLine" =~ $missingNameRegex ]] >/dev/null; then + local libraryIssue="Missing 'name' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingVersionRegex="Invalid library found in .* Missing 'version' from library" + if [[ "$outputFileLine" =~ $missingVersionRegex ]] >/dev/null; then + local libraryIssue="Missing 'version' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingAuthorRegex="Invalid library found in .* Missing 'author' from library" + if [[ "$outputFileLine" =~ $missingAuthorRegex ]] >/dev/null; then + local libraryIssue="Missing 'author' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingMaintainerRegex="Invalid library found in .* Missing 'maintainer' from library" + if [[ "$outputFileLine" =~ $missingMaintainerRegex ]] >/dev/null; then + local libraryIssue="Missing 'maintainer' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingSentenceRegex="Invalid library found in .* Missing 'sentence' from library" + if [[ "$outputFileLine" =~ $missingSentenceRegex ]] >/dev/null; then + local libraryIssue="Missing 'sentence' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingParagraphRegex="Invalid library found in .* Missing 'paragraph' from library" + if [[ "$outputFileLine" =~ $missingParagraphRegex ]] >/dev/null; then + local libraryIssue="Missing 'paragraph' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local missingURLregex="Invalid library found in .* Missing 'url' from library" + if [[ "$outputFileLine" =~ $missingURLregex ]] >/dev/null; then + local libraryIssue="Missing 'url' from library" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local invalidVersionRegex="Invalid version found:" + if [[ "$outputFileLine" =~ $invalidVersionRegex ]] >/dev/null; then + local libraryIssue="Invalid version found:" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local invalidCategoryRegex="is not valid. Setting to 'Uncategorized'" + if [[ "$outputFileLine" =~ $invalidCategoryRegex ]] >/dev/null; then + local libraryIssue="Invalid category" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + local spuriousFolderRegex="WARNING: Spurious" + if [[ "$outputFileLine" =~ $spuriousFolderRegex ]] >/dev/null; then + local libraryIssue="Spurious folder" + libraryIssueCount=$((libraryIssueCount + 1)) + fi + + done <"$ARDUINO_CI_SCRIPT_VERIFICATION_OUTPUT_FILENAME" + + rm $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "$ARDUINO_CI_SCRIPT_VERIFICATION_OUTPUT_FILENAME" + + # Remove the stupid comma from the memory values if present + local -r programStorage=${programStorageWithComma//,/} + local -r dynamicMemory=${dynamicMemoryWithComma//,/} + + if [[ "$boardIssue" != "" && "$ARDUINO_CI_SCRIPT_TEST_BOARD" == "true" ]]; then + # There was a board issue and board testing is enabled so fail the build + local buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + if [[ "$libraryIssue" != "" && "$ARDUINO_CI_SCRIPT_TEST_LIBRARY" == "true" ]]; then + # There was a library issue and library testing is enabled so fail the build + local buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + fi + + # Add the build data to the report file + echo "$(date -u "+%Y-%m-%d %H:%M:%S")"$'\t'"$TRAVIS_BUILD_NUMBER"$'\t'"$TRAVIS_JOB_NUMBER"$'\t'"https://travis-ci.org/${TRAVIS_REPO_SLUG}/jobs/${TRAVIS_JOB_ID}"$'\t'"$TRAVIS_EVENT_TYPE"$'\t'"$TRAVIS_ALLOW_FAILURE"$'\t'"$TRAVIS_PULL_REQUEST"$'\t'"$TRAVIS_BRANCH"$'\t'"$TRAVIS_COMMIT"$'\t'"$TRAVIS_COMMIT_RANGE"$'\t'"${TRAVIS_COMMIT_MESSAGE%%$'\n'*}"$'\t'"$sketchName"$'\t'"$boardID"$'\t'"$IDEversion"$'\t'"$programStorage"$'\t'"$dynamicMemory"$'\t'"$warningCount"$'\t'"$allowFail"$'\t'"$arduinoExitStatus"$'\t'"$boardIssueCount"$'\t'"$boardIssue"$'\t'"$libraryIssueCount"$'\t'"$libraryIssue"$'\r' >>"$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" + + # Adjust the exit status according to the allowFail setting + if [[ "$buildThisSketchExitStatus" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" && ("$allowFail" == "true" || "$allowFail" == "require") ]]; then + buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" + elif [[ "$buildThisSketchExitStatus" == "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" && "$allowFail" == "require" ]]; then + buildThisSketchExitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + if [[ "$buildThisSketchExitStatus" != "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]]; then + ARDUINO_CI_SCRIPT_TOTAL_SKETCH_BUILD_FAILURE_COUNT=$((ARDUINO_CI_SCRIPT_TOTAL_SKETCH_BUILD_FAILURE_COUNT + 1)) + fi + ARDUINO_CI_SCRIPT_TOTAL_WARNING_COUNT=$((ARDUINO_CI_SCRIPT_TOTAL_WARNING_COUNT + warningCount + 0)) + ARDUINO_CI_SCRIPT_TOTAL_BOARD_ISSUE_COUNT=$((ARDUINO_CI_SCRIPT_TOTAL_BOARD_ISSUE_COUNT + boardIssueCount + 0)) + ARDUINO_CI_SCRIPT_TOTAL_LIBRARY_ISSUE_COUNT=$((ARDUINO_CI_SCRIPT_TOTAL_LIBRARY_ISSUE_COUNT + libraryIssueCount + 0)) + + # End the folded section of the Travis CI build log + echo -e "travis_fold:end:build_sketch" + # Add a useful message to the Travis CI build log + + echo "arduino Exit Status: ${arduinoExitStatus}, Allow Failure: ${allowFail}, # Warnings: ${warningCount}, # Board Issues: ${boardIssueCount}, # Library Issues: ${libraryIssueCount}" + + return $buildThisSketchExitStatus +} + +# Print the contents of the report file +function display_report() { + enable_verbosity + + if [ -e "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" ]; then + echo -e '\n\n\n**************Begin Report**************\n\n\n' + cat "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" + echo -e '\n\n' + echo "Total failed sketch builds: $ARDUINO_CI_SCRIPT_TOTAL_SKETCH_BUILD_FAILURE_COUNT" + echo "Total warnings: $ARDUINO_CI_SCRIPT_TOTAL_WARNING_COUNT" + echo "Total board issues: $ARDUINO_CI_SCRIPT_TOTAL_BOARD_ISSUE_COUNT" + echo "Total library issues: $ARDUINO_CI_SCRIPT_TOTAL_LIBRARY_ISSUE_COUNT" + echo -e '\n\n' + else + echo "No report file available for this job" + fi + + disable_verbosity +} + +# Add the report file to a Git repository +function publish_report_to_repository() { + enable_verbosity + + local -r token="$1" + local -r repositoryURL="$2" + local -r reportBranch="$3" + local -r reportFolder="$4" + local -r doLinkComment="$5" + + if [[ "$token" != "" ]] && [[ "$repositoryURL" != "" ]] && [[ "$reportBranch" != "" ]]; then + if [ -e "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" ]; then + # Location is a repository + if git clone --quiet --branch "$reportBranch" "$repositoryURL" "${HOME}/report-repository"; then + # Clone was successful + create_folder "${HOME}/report-repository/${reportFolder}" + cp $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" "${HOME}/report-repository/${reportFolder}" + local -r previousFolder="$PWD" + cd "${HOME}/report-repository" + git add $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "${HOME}/report-repository/${reportFolder}/${ARDUINO_CI_SCRIPT_REPORT_FILENAME}" + git config user.email "arduino-ci-script@nospam.me" + git config user.name "arduino-ci-script-bot" + # Only pushes the current branch to the corresponding remote branch that 'git pull' uses to update the current branch. + git config push.default simple + if [[ "$TRAVIS_TEST_RESULT" != "0" ]]; then + local -r jobSuccessMessage="FAILED" + else + local -r jobSuccessMessage="SUCCESSFUL" + fi + # Do a pull now in case another job has finished about the same time and pushed a report after the clone happened, which would otherwise cause the push to fail. This is the last chance to pull without having to deal with a merge or rebase. + git pull $ARDUINO_CI_SCRIPT_QUIET_OPTION + git commit $ARDUINO_CI_SCRIPT_QUIET_OPTION $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION --message="Add Travis CI job ${TRAVIS_JOB_NUMBER} report (${jobSuccessMessage})" --message="Total failed sketch builds: $ARDUINO_CI_SCRIPT_TOTAL_SKETCH_BUILD_FAILURE_COUNT" --message="Total warnings: $ARDUINO_CI_SCRIPT_TOTAL_WARNING_COUNT" --message="Total board issues: $ARDUINO_CI_SCRIPT_TOTAL_BOARD_ISSUE_COUNT" --message="Total library issues: $ARDUINO_CI_SCRIPT_TOTAL_LIBRARY_ISSUE_COUNT" --message="Job log: https://travis-ci.org/${TRAVIS_REPO_SLUG}/jobs/${TRAVIS_JOB_ID}" --message="Commit: https://github.com/${TRAVIS_REPO_SLUG}/commit/${TRAVIS_COMMIT}" --message="$TRAVIS_COMMIT_MESSAGE" --message="[skip ci]" + local gitPushExitStatus="1" + local pushCount=0 + while [[ "$gitPushExitStatus" != "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" && $pushCount -le $ARDUINO_CI_SCRIPT_REPORT_PUSH_RETRIES ]]; do + pushCount=$((pushCount + 1)) + # Do a pull now in case another job has finished about the same time and pushed a report since the last pull. This would require a merge or rebase. Rebase should be safe since the commits will be separate files. + git pull $ARDUINO_CI_SCRIPT_QUIET_OPTION --rebase + git push $ARDUINO_CI_SCRIPT_QUIET_OPTION $ARDUINO_CI_SCRIPT_VERBOSITY_OPTION "https://${token}@${repositoryURL#*//}" + gitPushExitStatus="$?" + done + cd "$previousFolder" + rm --recursive --force "${HOME}/report-repository" + if [[ "$gitPushExitStatus" == "$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" ]]; then + if [[ "$doLinkComment" == "true" ]]; then + # Only comment if it's job 1 + local -r firstJobRegex='\.1$' + if [[ "$TRAVIS_JOB_NUMBER" =~ $firstJobRegex ]]; then + local reportURL + reportURL="${repositoryURL%.*}/tree/${reportBranch}/${reportFolder}" + comment_report_link "$token" "$reportURL" + fi + fi + else + echo "ERROR: Failed to push to remote branch." + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + else + echo "ERROR: Failed to clone branch ${reportBranch} of repository URL ${repositoryURL}. Do they exist?" + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + else + echo "No report file available for this job" + fi + else + if [[ "$token" == "" ]]; then + echo "ERROR: GitHub token not specified. Failed to publish build report. See https://github.com/per1234/arduino-ci-script#publishing-job-reports for instructions." + fi + if [[ "$repositoryURL" == "" ]]; then + echo "ERROR: Repository URL not specified. Failed to publish build report." + fi + if [[ "$reportBranch" == "" ]]; then + echo "ERROR: Repository branch not specified. Failed to publish build report." + fi + return_handler "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + disable_verbosity +} + +# Add the report file to a gist +function publish_report_to_gist() { + enable_verbosity + + local -r token="$1" + local -r gistURL="$2" + local -r doLinkComment="$3" + + if [[ "$token" != "" ]] && [[ "$gistURL" != "" ]]; then + if [ -e "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" ]; then + # Get the gist ID from the gist URL + local gistID + gistID="$(echo "$gistURL" | rev | cut -d'/' -f 1 | rev)" + + # http://stackoverflow.com/a/33354920/7059512 + # Sanitize the report file content so it can be sent via a POST request without breaking the JSON + # Remove \r (from Windows end-of-lines), replace tabs by \t, replace " by \", replace EOL by \n + local reportContent + reportContent=$(sed -e 's/\r//' -e's/\t/\\t/g' -e 's/"/\\"/g' "$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" | awk '{ printf($0 "\\n") }') + + # Upload the report to the Gist. I have to use the here document to avoid the "Argument list too long" error from curl with long reports. Redirect output to dev/null because it dumps the whole gist to the log + eval curl --header "\"Authorization: token ${token}\"" --data @- "\"https://api.github.com/gists/${gistID}\"" "$ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" < Examples > INCOMPATIBLE." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_ARCHITECTURES_EMPTY_EXIT_STATUS) + else + # Check for invalid architectures + local validArchitecturesRegex='^((\*)|(ameba)|(arm)|(arc32)|(avr)|(efm32)|(esp32)|(esp8266)|(FP51)|(i586)|(i686)|(iot2000)|(mbed)|(megaavr)|(mraa)|(msp430)|(navspark)|(nRF5)|(nRF51822)|(nrf52)|(nRF52832)|(particle-photon)|(particle-electron)|(particle-core)|(pic)|(pic32)|(RFduino)|(sam)|(samd)|(samd_beta)|(Seeed_STM32F4)|(Simblee)|(solox)|(stm)|(STM32)|(stm32)|(STM32F1)|(STM32F2)|(STM32F3)|(STM32F4)|(stm32f4)|(STM32L1)|(STM32L4)|(teensy)|(win10)|(x86))$' + # Split string on , + IFS=',' + local validArchitectureFound=false + # Disable globbing, otherwise it fails when one of the architecture values is * + set -o noglob + # Check for * architecture. If this is found then the other architecture values don't matter + local wildcardArchitectureFound=false + for rawArchitecture in $architecturesValue; do + # The Arduino IDE ignores leading or trailing whitespace on architectures + # Strip leading whitespace + local architecture="${rawArchitecture#"${rawArchitecture%%[![:space:]]*}"}" + # Strip trailing whitespace + architecture="${architecture%"${architecture##*[![:space:]]}"}" + + if [[ "$architecture" == "*" ]]; then + wildcardArchitectureFound=true + validArchitectureFound=true + break + fi + done + if [[ "$wildcardArchitectureFound" == false ]]; then + for rawArchitecture in $architecturesValue; do + # The Arduino IDE ignores leading or trailing whitespace on architectures + # Strip leading whitespace + local architecture="${rawArchitecture#"${rawArchitecture%%[![:space:]]*}"}" + # Strip trailing whitespace + architecture="${architecture%"${architecture##*[![:space:]]}"}" + + if [[ "$architecture" =~ $validArchitecturesRegex ]]; then + validArchitectureFound=true + else + local aliasCheckPassed=true + # If an architecture alias is used then the correct architecture must also be present + check_architecture_alias "$architecture" '^((Avr)|(AVR)|([aA][tT][mM][eE][lL].?[aA][vV][rR]))$' "$architecturesValue" 'avr' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Sam)|(SAM))$' "$architecturesValue" 'sam' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Samd)|(SAMD)|(SamD)|((samD)|([aA][tT][mM][eE][lL].?[sS][aA][mM]))$' "$architecturesValue" 'samd' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Arc32)|(ARC32)|([aA][rR][cC].32)|([iI][nN][tT][eE][lL].?[aA][rR][cC]32))$' "$architecturesValue" 'arc32' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Esp8266)|(ESP8266)|([eE][sS][pP].8266)|(8266)|([eE][sS][pP])|([eE][sS][pP][rR][eE][sS][sS][iI][fF].?(8266)?))$' "$architecturesValue" 'esp8266' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Esp32)|(ESP32)|([eE][sS][pP].32)|(arduino-esp32)|([eE][sS][pP][rR][eE][sS][sS][iI][fF].?32))$' "$architecturesValue" 'esp32' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + check_architecture_alias "$architecture" '^((Teensy)|(TEENSY))$' "$architecturesValue" 'teensy' "$normalizedLibraryPropertiesPath" + if [[ "$?" == "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" ]]; then + aliasCheckPassed=false + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + + if [[ "$aliasCheckPassed" == true ]]; then + echo "WARNING: ${normalizedLibraryPropertiesPath}/library.properties: architectures field contains an unknown architecture: ${architecture}. Note: architecture values are case-sensitive." + fi + fi + done + fi + # Re-enable globbing + set +o noglob + # Set IFS back to default + unset IFS + + # At least one known architecture must be present + if [[ "$validArchitectureFound" == false ]]; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: architectures field (${architecturesValue}) doesn't contain any known architecture values." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_ARCHITECTURE_EXIT_STATUS) + fi + fi + fi + + # Check for invalid lines (anything other than property, comment, or blank line) + if grep --quiet --invert-match --extended-regexp --regexp='=' --regexp='^[[:space:]]*(#|$)' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Invalid line found. Installation of a library with invalid line will cause all compilations to fail. library.properties must only consist of property definitions, blank lines, and comments (#)." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INVALID_LINE_EXIT_STATUS) + fi + + # Check for incorrect includes field name case + if ! check_field_name_case "$libraryProperties" 'includes' "$normalizedLibraryPropertiesPath"; then + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INCLUDES_MISSPELLED_EXIT_STATUS) + fi + + # Check for misspelled includes field name + if grep --quiet --ignore-case --regexp='^[[:space:]]*include[[:space:]]*=' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Misspelled includes field name. It must be spelled exactly \"includes\". See https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_INCLUDES_MISSPELLED_EXIT_STATUS) + fi + + # Check for empty includes value + if grep --quiet --regexp='^[[:space:]]*includes[[:space:]]*=[[:space:]]*$' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Undefined includes field. Either define the field or remove it. See https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_EMPTY_INCLUDES_EXIT_STATUS) + fi + + # Check for incorrect dot_a_linkage field name case + if ! check_field_name_case "$libraryProperties" 'dot_a_linkage' "$normalizedLibraryPropertiesPath"; then + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_DOT_A_LINKAGE_MISSPELLED_EXIT_STATUS) + fi + + # Check for misspelled dot_a_linkage field name + if grep --quiet --ignore-case --extended-regexp --regexp='^[[:space:]]*((dot_a_linkages)|(dot-?a-?linkages?))[[:space:]]*=' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Misspelled dot_a_linkage field name. It must be spelled exactly \"dot_a_linkage\". See https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_DOT_A_LINKAGE_MISSPELLED_EXIT_STATUS) + fi + + # Check for incorrect precompiled field name case + if ! check_field_name_case "$libraryProperties" 'precompiled' "$normalizedLibraryPropertiesPath"; then + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_PRECOMPILED_MISSPELLED_EXIT_STATUS) + fi + + # Check for misspelled precompiled field name + if grep --quiet --ignore-case --extended-regexp --regexp='^[[:space:]]*((precompile)|(pre[-_]compiled?))[[:space:]]*=' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Misspelled precompiled field name. It must be spelled exactly \"precompiled\". See https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_PRECOMPILED_MISSPELLED_EXIT_STATUS) + fi + + # Check for incorrect ldflags field name case + if ! check_field_name_case "$libraryProperties" 'ldflags' "$normalizedLibraryPropertiesPath"; then + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_LDFLAGS_MISSPELLED_EXIT_STATUS) + fi + + # Check for misspelled ldflags field name + if grep --quiet --ignore-case --extended-regexp --regexp='^[[:space:]]*((ldflag)|(ld[-_]flags?))[[:space:]]*=' <<<"$libraryProperties"; then + echo "ERROR: ${normalizedLibraryPropertiesPath}/library.properties: Misspelled ldflags field name. It must be spelled exactly \"ldflags\". See https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_LDFLAGS_MISSPELLED_EXIT_STATUS) + fi + + done <<<"$(find "$normalizedLibraryPropertiesSearchPath" -maxdepth "$maximumSearchDepth" -type d | sort --dictionary-order)" + + return "$exitStatus" +} + +# https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#keywords +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=1 +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCONSEQUENTIAL_MULTIPLE_TABS_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_LINE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCONSEQUENTIAL_LEADING_SPACE_ON_KEYWORD_TOKENTYPE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_MULTIPLE_TABS_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_LEADING_SPACE_ON_KEYWORD_TOKENTYPE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_FOLDER_DOESNT_EXIST_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_MISSPELLED_FILENAME_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCORRECT_FILENAME_CASE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_FIELD_SEPARATOR_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_BOM_CORRUPTED_KEYWORD_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_KEYWORD_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_KEYWORD_TOKENTYPE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_LEADING_SPACE_ON_RSYNTAXTEXTAREA_TOKENTYPE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_RSYNTAXTEXTAREA_TOKENTYPE_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_REFERENCE_LINK_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +function check_keywords_txt() { + local -r keywordsTxtSearchPath="$1" + local maximumSearchDepth="$2" + if [[ "$maximumSearchDepth" == "" ]]; then + # Set default search depth + maximumSearchDepth=0 + fi + + local exitStatus=$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS + + # Replace backslashes with slashes + local -r keywordsTxtSearchPathWithSlashes="${keywordsTxtSearchPath//\\//}" + local -r keywordsTxtRegex='[kK][eE][yY][wW][oO][rR][dD][sS]\.[tT][xX][tT]$' + if [[ ! -d "$keywordsTxtSearchPathWithSlashes" && "$keywordsTxtSearchPathWithSlashes" =~ $keywordsTxtRegex ]]; then + # Path contains the filename but we only want the folder + local -r keywordsTxtSearchPathWithoutFile="${keywordsTxtSearchPathWithSlashes::-12}" + else + local -r keywordsTxtSearchPathWithoutFile="$keywordsTxtSearchPathWithSlashes" + fi + # Remove trailing slash + local -r normalizedKeywordsTxtSearchPath="${keywordsTxtSearchPathWithoutFile%/}" + + # Check whether folder exists + if [[ ! -d "$normalizedKeywordsTxtSearchPath" ]]; then + echo "ERROR: ${normalizedKeywordsTxtSearchPath}: Folder doesn't exist." + return $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_FOLDER_DOESNT_EXIST_EXIT_STATUS + fi + + while read -r normalizedKeywordsTxtPath; do + # Check for misspelled keywords.txt filename + if [[ "$(find "$normalizedKeywordsTxtPath" -type f -iname 'keyword.txt')" || "$(find "$normalizedKeywordsTxtPath" -type f -iregex '.*/keywords?\.text')" || "$(find "$normalizedKeywordsTxtPath" -type f -iregex '.*/keywords?\.txt\.txt')" ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}: Incorrectly spelled keywords.txt file. It must be spelled exactly \"keywords.txt\"." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_MISSPELLED_FILENAME_EXIT_STATUS) + fi + + # Check for incorrect filename case + local keywordsTxtFound=false + while read -r foundKeywordsTxtPath; do + # The while loop always runs once, even if no file was found + if [[ "$foundKeywordsTxtPath" == "" ]]; then + continue + fi + + if [[ "${foundKeywordsTxtPath: -12}" == 'keywords.txt' ]]; then + keywordsTxtFound=true + else + echo "ERROR: ${foundKeywordsTxtPath}: Incorrect filename case, which causes it to not be recognized on a filename case-sensitive OS such as Linux. It must be exactly \"keywords.txt\"." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCORRECT_FILENAME_CASE_EXIT_STATUS) + fi + done <<<"$(find "$normalizedKeywordsTxtPath" -maxdepth 1 -type f -iname 'keywords.txt' | sort --dictionary-order)" + + # Check whether the folder contains a keywords.txt file + if [[ "$keywordsTxtFound" == false ]]; then + # no point in doing any more checks on this folder + continue + fi + + # Read the keywords.txt file line by line + # Split into lines by CR + while IFS='' read -d $'\r' -r keywordsTxtCRline || [[ -n "$keywordsTxtCRline" ]]; do + # Split into lines by LN + while IFS='' read -r keywordsTxtLine || [[ -n "$keywordsTxtLine" ]]; do + # Skip blank lines and comments + local blankLineRegex='^[[:space:]]*$' + local commentRegex='^[[:space:]]*#' + if [[ "$keywordsTxtLine" =~ $blankLineRegex ]] || [[ "$keywordsTxtLine" =~ $commentRegex ]]; then + continue + fi + + # Skip BOM corrupted blank lines and comments + if grep --quiet $'\xEF\xBB\xBF' <<<"$keywordsTxtLine"; then + local BOMcorruptedCommentRegex='^.[[:space:]]*#' + local BOMcorruptedBlankLineRegex='^.[[:space:]]*$' + if [[ "$keywordsTxtLine" =~ $BOMcorruptedCommentRegex ]] || [[ "$keywordsTxtLine" =~ $BOMcorruptedBlankLineRegex ]]; then + echo "WARNING: ${normalizedKeywordsTxtPath}/keywords.txt: BOM found. In this case it does not cause an issue but it's recommended to use UTF-8 encoding for keywords.txt." + continue + fi + fi + + local spacesSeparatorRegex='^[[:space:]]*[^[:space:]]+ +[^[:space:]]+' + # Check for invalid separator + if [[ "$keywordsTxtLine" =~ $spacesSeparatorRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Space(s) used as a field separator. Fields must be separated by a single true tab." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_FIELD_SEPARATOR_EXIT_STATUS) + # The rest of the checks will be borked by messed up field separators so continue to the next line + continue + fi + + # Check for multiple tabs used as separator where this causes unintended results + local consequentialMultipleSeparatorRegex='^[[:space:]]*[^[:space:]]+[[:space:]]*'$'\t''+[[:space:]]*'$'\t''+[[:space:]]*((KEYWORD1)|(LITERAL1))' + if [[ "$keywordsTxtLine" =~ $consequentialMultipleSeparatorRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Multiple tabs used as field separator. It must be a single tab. This causes the default keyword highlighting (as used by KEYWORD2, KEYWORD3, LITERAL2) to be used rather than the intended highlighting." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_MULTIPLE_TABS_EXIT_STATUS) + # The rest of the checks will be borked by messed up field separators so continue to the next line + continue + fi + + # Check for multiple tabs used as separator where this causes no unintended results + local inconsequentialMultipleSeparatorRegex='^[[:space:]]*[^[:space:]]+[[:space:]]*'$'\t''+[[:space:]]*'$'\t''+[[:space:]]*((KEYWORD2)|(KEYWORD3)|(LITERAL2))' + if [[ "$keywordsTxtLine" =~ $inconsequentialMultipleSeparatorRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Multiple tabs used as field separator. It must be a single tab. This causes the default keyword highlighting (as used by KEYWORD2, KEYWORD3, LITERAL2). In this case that doesn't cause the keywords to be colored other than intended but it's recommended to fully comply with the Arduino library specification." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCONSEQUENTIAL_MULTIPLE_TABS_EXIT_STATUS) + # The rest of the checks will be borked by messed up field separators so continue to the next line + continue + fi + + # Check for invalid line + local invalidLineRegex='^[[:space:]]*[^[:space:]]+[[:space:]]*$' + if [[ "$keywordsTxtLine" =~ $invalidLineRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Invalid line. If this was intended as a comment, it should use the correct # syntax." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_LINE_EXIT_STATUS) + # The rest of the checks are pointless so continue to the next line of keywords.txt + continue + fi + + # Get the field values + # Use a unique, non-whitespace field separator character + fieldSeparator=$'\a' + IFS=$fieldSeparator + # Strip leading whitespace. This is ignored by the Arduino IDE (even tabs) + local keywordsTxtLineFrontStripped="${keywordsTxtLine#"${keywordsTxtLine%%[![:space:]]*}"}" + # Change tabs to the field separator character for line splitting + # shellcheck disable=SC2206 + local keywordsTxtLineSwappedTabs=(${keywordsTxtLineFrontStripped//$'\t'/$fieldSeparator}) + + # KEYWORD is the 1st field + local keywordRaw=${keywordsTxtLineSwappedTabs[0]} + # Strip trailing spaces + local keyword="${keywordRaw%"${keywordRaw##*[! ]}"}" + + # KEYWORD_TOKENTYPE is the 2nd field + local keywordTokentypeRaw=${keywordsTxtLineSwappedTabs[1]} + # The Arduino IDE strips trailing spaces from KEYWORD_TOKENTYPE + # Strip trailing spaces + local keywordTokentype="${keywordTokentypeRaw%"${keywordTokentypeRaw##*[! ]}"}" + + # REFERENCE_LINK is the 3rd field + local referenceLinkRaw=${keywordsTxtLineSwappedTabs[2]} + # The Arduino IDE strips leading and trailing whitespace from REFERENCE_LINK + # Strip leading spaces + local referenceLinkFrontStripped="${referenceLinkRaw#"${referenceLinkRaw%%[! ]*}"}" + # Strip trailing spaces + local referenceLink="${referenceLinkFrontStripped%"${referenceLinkFrontStripped##*[! ]}"}" + + # RSYNTAXTEXTAREA_TOKENTYPE is the 4th field + local rsyntaxtextareaTokentypeRaw=${keywordsTxtLineSwappedTabs[3]} + # The Arduino IDE strips trailing spaces from RSYNTAXTEXTAREA_TOKENTYPE + # Strip trailing spaces + local rsyntaxtextareaTokentype="${rsyntaxtextareaTokentypeRaw%"${rsyntaxtextareaTokentypeRaw##*[! ]}"}" + + # Reset IFS to default + unset IFS + + allowedKeywordCharactersRegex='^[a-zA-Z0-9_]+$' + # Check for corruption of KEYWORD field caused by UTF-8 BOM file encoding + if grep --quiet $'\xEF\xBB\xBF' <<<"$keyword"; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: UTF-8 BOM file encoding has corrupted the first keyword definition. Please change the file encoding to standard UTF-8." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_BOM_CORRUPTED_KEYWORD_EXIT_STATUS) + elif ! [[ "$keyword" =~ $allowedKeywordCharactersRegex ]]; then + # Check for invalid characters in KEYWORD + # The Arduino IDE does recognize keywords that start with a number, even though these are not valid identifiers. + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Keyword: $keyword contains invalid character(s), which causes it to not be recognized by the Arduino IDE. Keywords may only contain the characters a-z, A-Z, 0-9, and _." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_KEYWORD_EXIT_STATUS) + fi + + # Check for invalid KEYWORD_TOKENTYPE + local validKeywordTokentypeRegex='^((KEYWORD1)|(KEYWORD2)|(KEYWORD3)|(LITERAL1)|(LITERAL2))$' + local validRsyntaxtextareaTokentypeRegex='^((RESERVED_WORD)|(RESERVED_WORD_2)|(DATA_TYPE)|(PREPROCESSOR)|(LITERAL_BOOLEAN))$' + if ! [[ "$keywordTokentype" =~ $validKeywordTokentypeRegex ]]; then + # Check if it's invalid only because of leading space + local keywordTokentypeWithoutLeadingSpace="${keywordTokentype#"${keywordTokentype%%[![:space:]]*}"}" + if [[ "$keywordTokentypeWithoutLeadingSpace" =~ $validKeywordTokentypeRegex ]]; then + # Check if the issue doesn't cause any change from the intended highlighting + local inconsequentialTokentypeRegex='((KEYWORD2)|(KEYWORD3)|(LITERAL2))' + if [[ "$keywordTokentypeWithoutLeadingSpace" =~ $inconsequentialTokentypeRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Leading space on the KEYWORD_TOKENTYPE field causes it to not be recognized, so the default keyword highlighting is used. In this case that doesn't cause the keywords to be colored other than intended but it's recommended to fully comply with the Arduino library specification." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INCONSEQUENTIAL_LEADING_SPACE_ON_KEYWORD_TOKENTYPE_EXIT_STATUS) + else + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Leading space on the KEYWORD_TOKENTYPE field causes it to not be recognized, so the default keyword highlighting is used." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_LEADING_SPACE_ON_KEYWORD_TOKENTYPE_EXIT_STATUS) + fi + elif ! [[ "$keywordTokentypeWithoutLeadingSpace" == "" && "$rsyntaxtextareaTokentype" =~ $validRsyntaxtextareaTokentypeRegex ]]; then + # It's reasonable to leave KEYWORD_TOKENTYPE blank if RSYNTAXTEXTAREA_TOKENTYPE is defined and valid. This will not be compatible with 1.6.4 and older but that's really no big deal. + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Invalid KEYWORD_TOKENTYPE: $keywordTokentype causes the default keyword highlighting to be used. See: https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#keyword_tokentype" + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_KEYWORD_TOKENTYPE_EXIT_STATUS) + fi + fi + + # Check for invalid REFERENCE_LINK + if [[ "$referenceLink" != "" ]]; then + # The Arduino IDE must be installed to check if the reference page exists + if [[ "$NEWEST_INSTALLED_IDE_VERSION" == "" ]]; then + echo "WARNING: Arduino IDE is not installed so unable to check for invalid reference links. Please call install_ide before running check_keywords_txt." + else + install_ide_version "$NEWEST_INSTALLED_IDE_VERSION" + if [[ ! $(find "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/${ARDUINO_CI_SCRIPT_IDE_INSTALLATION_FOLDER}/reference/www.arduino.cc/en/Reference/" -type f -name "${referenceLink}.html") ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: REFERENCE_LINK value: $referenceLink is not a valid Arduino Language Reference page. See: https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#reference_link" + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_REFERENCE_LINK_EXIT_STATUS) + fi + fi + fi + + # Check for invalid RSYNTAXTEXTAREA_TOKENTYPE + if [[ "$rsyntaxtextareaTokentype" != "" ]]; then + if ! [[ "$rsyntaxtextareaTokentype" =~ $validRsyntaxtextareaTokentypeRegex ]]; then + # Check if it's invalid only because of leading space + local rsyntaxtextareaTokentypeWithoutLeadingSpace="${rsyntaxtextareaTokentype#"${rsyntaxtextareaTokentype%%[![:space:]]*}"}" + if [[ "$rsyntaxtextareaTokentypeWithoutLeadingSpace" =~ $validRsyntaxtextareaTokentypeRegex ]]; then + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Leading space on the RSYNTAXTEXTAREA_TOKENTYPE field causes it to not be recognized, so the default keyword highlighting is used." + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_LEADING_SPACE_ON_RSYNTAXTEXTAREA_TOKENTYPE_EXIT_STATUS) + else + echo "ERROR: ${normalizedKeywordsTxtPath}/keywords.txt: Invalid RSYNTAXTEXTAREA_TOKENTYPE: $rsyntaxtextareaTokentype causes the default keyword highlighting to be used. See: https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#rsyntaxtextarea_tokentype" + echo -e "\t$keywordsTxtLine" + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_KEYWORDS_TXT_INVALID_RSYNTAXTEXTAREA_TOKENTYPE_EXIT_STATUS) + fi + fi + fi + done <<<"$keywordsTxtCRline" + done <"${normalizedKeywordsTxtPath}/keywords.txt" + + done <<<"$(find "$normalizedKeywordsTxtSearchPath" -maxdepth "$maximumSearchDepth" -type d | sort --dictionary-order)" + + return "$exitStatus" +} + +# https://github.com/arduino/Arduino/wiki/Library-Manager-FAQ#how-is-the-library-list-generated +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=1 +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_FOLDER_DOESNT_EXIST_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_EXE_FOUND_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_DOT_DEVELOPMENT_FOUND_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_SYMLINK_FOUND_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_CHECK_FOLDER_NAME_OFFSET=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_HAS_INVALID_FIRST_CHARACTER_EXIT_STATUS=$((ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_CHECK_FOLDER_NAME_OFFSET + ARDUINO_CI_SCRIPT_CHECK_FOLDER_NAME_INVALID_FIRST_CHARACTER_EXIT_STATUS)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_HAS_INVALID_CHARACTER_EXIT_STATUS=$((ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_CHECK_FOLDER_NAME_OFFSET + ARDUINO_CI_SCRIPT_CHECK_FOLDER_NAME_INVALID_CHARACTER_EXIT_STATUS)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_TOO_LONG_EXIT_STATUS=$((ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_CHECK_FOLDER_NAME_OFFSET + ARDUINO_CI_SCRIPT_CHECK_FOLDER_NAME_TOO_LONG_EXIT_STATUS)) +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_TOO_LONG_EXIT_STATUS + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_BLANK_URL_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER=$((ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER + 1)) +readonly ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_IS_RESERVED_EXIT_STATUS=$ARDUINO_CI_SCRIPT_EXIT_STATUS_COUNTER +function check_library_manager_compliance() { + local -r libraryPath="$1" + # Replace backslashes with slashes + local -r libraryPathWithSlashes="${libraryPath//\\//}" + # Remove trailing slash + local -r normalizedLibraryPath="${libraryPathWithSlashes%/}" + + local exitStatus=$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS + + # Check whether folder exists + if [[ ! -d "$normalizedLibraryPath" ]]; then + echo "ERROR: ${libraryPath}: Folder doesn't exist." + return $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_FOLDER_DOESNT_EXIST_EXIT_STATUS + fi + + # Check for .exe files + local -r exePath=$(find "$normalizedLibraryPath" -type f -name '*.exe') + if [[ "$exePath" != "" ]]; then + echo "ERROR: ${exePath}: .exe file found." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_EXE_FOUND_EXIT_STATUS) + fi + + # Check for .development file + local -r dotDevelopmentPath=$(find "$normalizedLibraryPath" -maxdepth 1 -type f -name '.development') + if [[ "$dotDevelopmentPath" != "" ]]; then + echo "ERROR: ${dotDevelopmentPath}: .development file found." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_DOT_DEVELOPMENT_FOUND_EXIT_STATUS) + fi + + # Check for symlink + local -r symlinkPath=$(find "$normalizedLibraryPath" -type l) + if [[ "$symlinkPath" != "" ]]; then + echo "ERROR: ${symlinkPath}: Symlink found." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_SYMLINK_FOUND_EXIT_STATUS) + fi + + # Check for problems with library.properties + if [[ -f "$normalizedLibraryPath/library.properties" ]]; then + # Get rid of the CRs + local libraryProperties + libraryProperties=$(tr "\r" "\n" <"$normalizedLibraryPath/library.properties") + local nameValue + nameValue="$(get_library_properties_field_value "$libraryProperties" 'name')" + + # Check if the library.properties name value meets the requirements of the Library Manager indexer + check_library_properties_name "$nameValue" + local -r checkLibraryPropertiesNameExitStatus=$? + if [[ $checkLibraryPropertiesNameExitStatus -ne $ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS ]]; then + if [[ "$checkLibraryPropertiesNameExitStatus" == "$ARDUINO_CI_SCRIPT_CHECK_LIBRARY_PROPERTIES_NAME_RESERVED_NAME_EXIT_STATUS" ]]; then + echo "ERROR: ${normalizedLibraryPath}/library.properties: name value: $nameValue starts with \"arduino\". These names are reserved for official Arduino libraries." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_NAME_IS_RESERVED_EXIT_STATUS) + else + echo "ERROR: ${normalizedLibraryPath}/library.properties: name value: $nameValue does not meet the requirements of the Arduino Library Manager indexer. See: https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification#libraryproperties-file-format" + exitStatus=$(set_exit_status "$exitStatus" $((ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_CHECK_FOLDER_NAME_OFFSET + checkLibraryPropertiesNameExitStatus))) + fi + fi + + local urlValue + urlValue="$(get_library_properties_field_value "$libraryProperties" 'url')" + if [[ "$urlValue" == "" ]]; then + echo "ERROR: ${normalizedLibraryPath}/library.properties: Blank url value: You must define a URL." + exitStatus=$(set_exit_status "$exitStatus" $ARDUINO_CI_SCRIPT_CHECK_LIBRARY_MANAGER_COMPLIANCE_BLANK_URL_EXIT_STATUS) + fi + fi + + return "$exitStatus" +} + +function check_code_formatting() { + local -r strictness="$1" + local -r excludedPathList="$2" + local -r targetPath="$3" + + local -r astyleConfigurationFolder="etc/astyle-configurations" + local -r astyleConfigurationExtension=".conf" + + # Fold the output in the Travis CI log + echo -e -n 'travis_fold:start:check_code_formatting\r' + + if [[ $strictness -lt 1 ]] || [[ $strictness -gt 3 ]]; then + echo "ERROR: Invalid strictness parameter value. Valid values are 1 (least strict) - 3 (most strict)" + return "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + if ! [[ -d "$targetPath" ]]; then + echo "ERROR: targetPath doesn't exist" + return "$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + + local scriptFolder + # https://stackoverflow.com/a/246128 + local scriptSource="${BASH_SOURCE[0]}" + while [ -h "$scriptSource" ]; do # Resolve $scriptSource until the file is no longer a symlink + scriptFolder="$(cd -P "$(dirname "$scriptSource")" >/dev/null 2>&1 && pwd)" + scriptSource="$(readlink "$scriptSource")" + [[ $scriptSource != /* ]] && scriptSource="$scriptFolder/$scriptSource" # If $scriptSource was a relative symlink, we need to resolve it relative to the path where the symlink file was located + done + scriptFolder="$(cd -P "$(dirname "$scriptSource")" >/dev/null 2>&1 && pwd)" + + # Assemble the find options for the excluded paths from the list + for excludedPath in ${excludedPathList//,/ }; do + excludeOptions="$excludeOptions -path $excludedPath -prune -or" + done + + local astylePath + astylePath=$(command -v astyle) + if [[ ! -e "$astylePath" ]]; then + # Install astyle + # Save the current folder + local -r previousFolder="$PWD" + mkdir --parents "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/astyle" + wget --no-verbose $ARDUINO_CI_SCRIPT_QUIET_OPTION --output-document="${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/astyle.tar.gz" "https://iweb.dl.sourceforge.net/project/astyle/astyle/astyle%203.1/astyle_3.1_linux.tar.gz" + tar --extract --file="${ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER}/astyle.tar.gz" --directory="${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}" + cd "${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/astyle/build/gcc" + eval "make $ARDUINO_CI_SCRIPT_VERBOSITY_REDIRECT" + astylePath="${ARDUINO_CI_SCRIPT_APPLICATION_FOLDER}/astyle/build/gcc/bin/astyle" + # Return to the previous folder + cd "$previousFolder" + fi + + # Set default exit status + exitStatus="$ARDUINO_CI_SCRIPT_SUCCESS_EXIT_STATUS" + + while read -r filename; do + # Check if it's a file (find matches on pruned folders) + if [[ -f "$filename" ]]; then + if ! diff --strip-trailing-cr "$filename" <("${astylePath}" --options="${scriptFolder}/${astyleConfigurationFolder}/${strictness}${astyleConfigurationExtension}" --dry-run <"$filename"); then + echo "ERROR: Non-compliant code formatting in $filename" + # Make the function fail + exitStatus="$ARDUINO_CI_SCRIPT_FAILURE_EXIT_STATUS" + fi + fi + done <<<"$(eval "find $targetPath -regextype posix-extended $excludeOptions \( -iregex '.*\.((ino)|(h)|(hpp)|(hh)|(hxx)|(h\+\+)|(cpp)|(cc)|(cxx)|(c\+\+)|(cp)|(c)|(ipp)|(ii)|(ixx)|(inl)|(tpp)|(txx)|(tpl))$' -and -type f \)")" + + echo -e -n 'travis_fold:end:check_code_formatting\r' + return "$exitStatus" +} + +# Set default verbosity (must be called after the function definitions +set_script_verbosity 0 + +# Create the temporary folder +rm "$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" --recursive --force +create_folder "$ARDUINO_CI_SCRIPT_TEMPORARY_FOLDER" + +# Create the report folder +create_folder "$ARDUINO_CI_SCRIPT_REPORT_FOLDER" + +# Add column names to report +echo "Build Timestamp (UTC)"$'\t'"Build"$'\t'"Job"$'\t'"Job URL"$'\t'"Build Trigger"$'\t'"Allow Job Failure"$'\t'"PR#"$'\t'"Branch"$'\t'"Commit"$'\t'"Commit Range"$'\t'"Commit Message"$'\t'"Sketch Filename"$'\t'"Board ID"$'\t'"IDE Version"$'\t'"Program Storage (bytes)"$'\t'"Dynamic Memory (bytes)"$'\t'"# Warnings"$'\t'"Allow Failure"$'\t'"Exit Status"$'\t'"# Board Issues"$'\t'"Board Issue"$'\t'"# Library Issues"$'\t'"Library Issue"$'\r' >"$ARDUINO_CI_SCRIPT_REPORT_FILE_PATH" diff --git a/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/1.conf b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/1.conf new file mode 100755 index 0000000..fe9cf30 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/1.conf @@ -0,0 +1,33 @@ +# source: https://raw.githubusercontent.com/arduino/Arduino/1.8.9/build/shared/lib/formatter.conf + +# This configuration file contains a selection of the available options provided by the formatting tool "Artistic Style" +# http://astyle.sourceforge.net/astyle.html +# +# If you wish to change them, don't edit this file. +# Instead, copy it in the same folder of file "preferences.txt" and modify the copy. This way, you won't lose your custom formatter settings when upgrading the IDE +# If you don't know where file preferences.txt is stored, open the IDE, File -> Preferences and you'll find a link + +mode=c + +# 2 spaces indentation +indent=spaces=2 + +# also indent macros +indent-preprocessor + +# indent classes, switches (and cases), comments starting at column 1 +indent-classes +indent-switches +indent-cases +indent-col1-comments + +# put a space around operators +pad-oper + +# put a space after if/for/while +pad-header + +# if you like one-liners, keep them +keep-one-line-statements + +remove-comment-prefix diff --git a/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/2.conf b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/2.conf new file mode 100755 index 0000000..124f547 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/2.conf @@ -0,0 +1,46 @@ +# source: https://raw.githubusercontent.com/arduino/Arduino/1.8.9/build/shared/examples_formatter.conf + +# This configuration file contains a selection of the available options provided by the formatting tool "Artistic Style" +# http://astyle.sourceforge.net/astyle.html +# +# If you wish to change them, don't edit this file. +# Instead, copy it in the same folder of file "preferences.txt" and modify the copy. This way, you won't lose your custom formatter settings when upgrading the IDE +# If you don't know where file preferences.txt is stored, open the IDE, File -> Preferences and you'll find a link + +mode=c + +# 2 spaces indentation +indent=spaces=2 + +# also indent macros +indent-preprocessor + +# indent classes, switches (and cases), comments starting at column 1 +indent-classes +indent-switches +indent-cases +indent-col1-comments + +# put a space around operators +pad-oper + +# put a space after if/for/while +pad-header + +# if you like one-liners, keep them +keep-one-line-statements + +style=java +attach-namespaces +attach-classes +attach-inlines +attach-extern-c +indent-modifiers +indent-namespaces +indent-labels +indent-preproc-block +indent-preproc-define +indent-preproc-cond +unpad-paren +add-brackets +remove-comment-prefix diff --git a/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/3.conf b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/3.conf new file mode 100755 index 0000000..66613c2 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/etc/astyle-configurations/3.conf @@ -0,0 +1,125 @@ +# source: https://github.com/arduino/ArduinoCore-avr/issues/71#issuecomment-466763471 2019-06-09 + +# formatter.conf, examples_formatter.conf +mode=c + + +# examples_formatter.conf +# http://astyle.sourceforge.net/astyle.html#_style=java +# Considering changing this to the synonym "style=attach", which seems more descriptive +style=java + + +# examples_formatter.conf +attach-namespaces + +# examples_formatter.conf +attach-classes + +# examples_formatter.conf +attach-inlines + +# examples_formatter.conf +attach-extern-c + + +# formatter.conf, examples_formatter.conf +indent=spaces=2 + +# formatter.conf, examples_formatter.conf +indent-classes + +# formatter.conf, examples_formatter.conf +indent-switches + +# formatter.conf, examples_formatter.conf +indent-cases + +# formatter.conf, examples_formatter.conf +indent-col1-comments + +# examples_formatter.conf +indent-modifiers + +# examples_formatter.conf +indent-namespaces + +# examples_formatter.conf +indent-labels + +# examples_formatter.conf +indent-preproc-define + + +# formatter.conf, examples_formatter.conf +pad-header + +# formatter.conf, examples_formatter.conf +pad-oper + +# examples_formatter.conf +unpad-paren + + +# formatter.conf, examples_formatter.conf +remove-comment-prefix + +# formatter.conf, examples_formatter.conf +# http://astyle.sourceforge.net/astyle.html#_keep-one-line-statements +# "Don't break complex statements and multiple statements residing on a single line." +# I don't like one line complex statements, but I guess since it's in formatter.conf it must stay. +keep-one-line-statements + + + +# Options from examples_formatter.conf that I think should be removed: + +# http://astyle.sourceforge.net/astyle.html#_indent-preproc-block +# "Indent preprocessor blocks at brace level zero and immediately within a namespace. There are restrictions on what will be indented. Blocks within methods, classes, arrays, etc., will not be indented. Blocks containing braces or multi-line define statements will not be indented. Without this option the preprocessor block is not indented." +# This does indent for #ifdef, but not for #ifndef, so it's quite inconsistent +# Indentation of preprocessor directives as done by this option is not very common in Arduino AVR Boards core, and where it is used, it's typically done inconsistently throughout the file +indent-preproc-block + +# http://astyle.sourceforge.net/astyle.html#_indent-preproc-cond +# "Indent preprocessor conditional statements to the same level as the source code." +# Indentation of preprocessor directives as done by this option is very rare in Arduino AVR Boards core +indent-preproc-cond + + + +# Options I have not implemented from formatter.conf or examples_formatter.conf: + +# examples_formatter.conf +# Not a valid option in the latest version of AStyle. I think the correct option name is "add-braces", which I do use in my configuration +# add-brackets + +# formatter.conf, examples_formatter.conf +# Not a valid option in the latest version of AStyle. +# indent-preprocessor + + + +# Options I have added: + +# http://astyle.sourceforge.net/astyle.html#_add-braces +# "I believe this is the correct option name to use instead the "add-brackets" option used in examples_formatter.conf. "add-brackets" is not a valid option in the latest version of AStyle" +add-braces + +# http://astyle.sourceforge.net/astyle.html#_convert-tabs +# "Converts tabs into spaces in the non-indentation part of the line." +# AStyle is already configured to use spaces for indentation by indent=spaces=2. The Arduino IDE uses spaces instead of tabs by default. +convert-tabs + +# http://astyle.sourceforge.net/astyle.html#_attach-return-type +# "Attach the return type to the function name in function definitions." +attach-return-type + +# http://astyle.sourceforge.net/astyle.html#_attach-return-type +# "Attach the return type to the function name in function declarations." +attach-return-type-decl + +# http://astyle.sourceforge.net/astyle.html#_align-pointer +# "Attach a pointer or reference operator (*, &, or ^) to either the variable type (left) or variable name (right), or place it between the type and name (middle)." +# In Arduino AVR Boards core, name alignment of pointers is somewhat more common, though all possible styles are used +# I don't care which style is chosen (type, middle, name), but I do think one should be chosen and used. +align-pointer=name diff --git a/megaavr/travis-ci/arduino-ci-script/etc/autoformat.sh b/megaavr/travis-ci/arduino-ci-script/etc/autoformat.sh new file mode 100755 index 0000000..0ef37d9 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/etc/autoformat.sh @@ -0,0 +1 @@ +shfmt -i 2 -w ../arduino-ci-script.sh diff --git a/megaavr/travis-ci/arduino-ci-script/etc/codespell-ignore-words-list.txt b/megaavr/travis-ci/arduino-ci-script/etc/codespell-ignore-words-list.txt new file mode 100755 index 0000000..c74fb04 --- /dev/null +++ b/megaavr/travis-ci/arduino-ci-script/etc/codespell-ignore-words-list.txt @@ -0,0 +1,4 @@ +ba +propert +te +exampels From 28e33cb79af52206cefedc69e1bb4909cecae3d7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 14:45:36 +0200 Subject: [PATCH 179/351] Add Travis CI badge --- README.md | 36 +++++++++++++++++++----------------- 1 file changed, 19 insertions(+), 17 deletions(-) diff --git a/README.md b/README.md index 67a85ac..185dd92 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,6 @@ # MegaCoreX +[![Build Status](https://travis-ci.org/MCUdude/MegaCoreX.svg?branch=master)](https://travis-ci.org/MCUdude/MegaCoreX) + An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. Its largest variant, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis. Compared to older AVR families they also have more advanced and accurate internal oscillators which can provide base frequencies of 16 and 20 MHz. These can again be divided down internally to reduce the processor speed and power consumption. This means in most applications an external clock isn't necessary anymore. You can read more about clocks and clock frequencies in the [Supported clock frequencies](#supported-clock-frequencies) section. @@ -50,9 +52,9 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB | **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | | **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | - 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library -* TQFP32/QFN32 package -** SSOP28 package + 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library +* TQFP32/QFN32 package +** SSOP28 package *** DIP40 package @@ -84,7 +86,7 @@ MegaCoreX lets you choose what clock frequency you want to run your microcontrol | 8 MHz | External clock | | | 1 MHz | External clock | | -Note that unlike other AVRs **none of these chips can drive an external crystal or resonator**. If you need an external oscillator it has to be one with a driven clock output. +Note that unlike other AVRs **none of these chips can drive an external crystal or resonator**. If you need an external oscillator it has to be one with a driven clock output. The microcontroller will freeze if the external clock suddenly drops out. If not present on boot, it will automatically choose the 16 MHz internal oscillator instead. Another thing to watch out for is the lowest possible baudrates when running at 16 or 20 MHz. At 16 MHz the lowest baud rate is 1200 baud. When running at 20 MHz the lowest is 2400 baud. This is caused by the way the internal baud rate generator works. If you need lower baud rates you'll either have to reduce the main clock speed or use the software serial library instead. @@ -123,7 +125,7 @@ Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. ## Pin macros Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that map "Arduino pins" to the port and port number. -Note that all my Arduino cores have these macros if you prefer to use these rather than the default Arduino pin number. +Note that all my Arduino cores have these macros if you prefer to use these rather than the default Arduino pin number. ```c++ // Use PIN_PA0 macro to refer to pin PA0 (Arduino pin 0) @@ -144,7 +146,7 @@ This core provides several different Arduino pin mappings based on your current - **Nano Every**: This pinout is 100% compatible with the Arduino Nano Every. If you have code that's written for the Nano Every it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. This pinout is only available when ATmega4809 is selected. Please have a look at the pins_arduino.h files for detailed info.

-Click to enlarge: +Click to enlarge: | **MegaCoreX ATmega809/1609/3209/4809 pinout** | **MegaCoreX ATmega808/1608/3208/4808 pinout** | |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| @@ -155,9 +157,9 @@ Please have a look at the pins_arduino.h files for detailed info.

Here's some hardware specific features that differ from the older AVR families. ### Interrupt pins -Unlike older AVRs the megaAVR-0 microcontrollers have fully featured interrupts on every pin. -Supported states are *RISING*, *FALLING*, *CHANGE*, *HIGH* and *LOW*. This means there's no need to use the `digitalPinToInterrupt` macro. Simply call attachInterrupt like this: - +Unlike older AVRs the megaAVR-0 microcontrollers have fully featured interrupts on every pin. +Supported states are *RISING*, *FALLING*, *CHANGE*, *HIGH* and *LOW*. This means there's no need to use the `digitalPinToInterrupt` macro. Simply call attachInterrupt like this: + ```c attachInterrupt(myPin, myInterruptFunction, RISING); ``` @@ -180,8 +182,8 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. ### Analog read resolution -The default analog read resolution for these chips is 10 bit, which gives you values between 0 - 1023. If you need less resolution you can turn it down to 8 bits instead, which gives you values between 0 - 255. -Simply call `analogReadResolution` like this: +The default analog read resolution for these chips is 10 bit, which gives you values between 0 - 1023. If you need less resolution you can turn it down to 8 bits instead, which gives you values between 0 - 255. +Simply call `analogReadResolution` like this: ```c analogReadResolution(8); // Set resolution to 8 bits ``` @@ -190,7 +192,7 @@ analogReadResolution(8); // Set resolution to 8 bits The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performance. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from each other, connected together or generate an interrupt to the CPU. I've made a [light weight, high-level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integration with the CCL hardware. ### Analog Comparator (AC) -The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. +The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. ### Alternative pins @@ -296,29 +298,29 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he ### Arduino Uno WiFi Rev2 [The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. -Click to enlarge: +Click to enlarge: ### Arduino Nano Every [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. -Click to enlarge: +Click to enlarge: ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. -Click to enlarge: +Click to enlarge: ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. -Click to enlarge: +Click to enlarge: ### ATmega4809 Xplained Pro [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. -Click to enlarge: +Click to enlarge: From 9233e92a332e5deeb5bff3ebfc4793cb4e94998e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 14:47:46 +0200 Subject: [PATCH 180/351] Fix issue where unsupported IDE versions where installed --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index b03d5a6..2591684 100644 --- a/.travis.yml +++ b/.travis.yml @@ -136,7 +136,7 @@ before_install: - set_library_testing "true" # Install a version of Arduino IDE with an outdated bundled arduino:megaavr platform to force installation of latest arduino:avr - - install_ide "$IDE_VERSION_LIST" + - install_ide "1.8.13" # Install Arduino AVR Boards to get the AVR toolchain - install_package "arduino:megaavr" # Install MegaCoreX from the repository From ed6c9f65ec0a8fe96d1ec12a2c86a6e7b78406da Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 14:56:24 +0200 Subject: [PATCH 181/351] Fix issue where 'newest' couldn't be installed hardcoded IDE 1.8.12 and 1.8.13 for now. Maybe @per1234 can help out with this later? --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 2591684..2b73186 100644 --- a/.travis.yml +++ b/.travis.yml @@ -11,7 +11,7 @@ env: - SKETCHBOOK_FOLDER="${HOME}/Arduino" # Use Arduino IDE version that supports the new AVRs - - IDE_VERSION_LIST_FULL='"1.8.12" "newest"' + - IDE_VERSION_LIST_FULL='"1.8.12" "1.8.13"' matrix: From ff3fcd73c2c6662b02ca94e3c07f5267ef8e4b24 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 15:19:08 +0200 Subject: [PATCH 182/351] Remove _div Makes the CI FWBN logic a little simpler --- megaavr/boards.txt | 560 ++++++++++++++++++++++----------------------- 1 file changed, 280 insertions(+), 280 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index c4bd61a..a6edd2c 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -87,41 +87,41 @@ menu.bootloader=Bootloader 4809.menu.clock.internal_20MHz.build.oscillator= 4809.menu.clock.internal_20MHz.build.f_cpu=20000000L -4809.menu.clock.internal_10MHz_div=Internal 10 MHz -4809.menu.clock.internal_10MHz_div.upload.speed=115200 -4809.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -4809.menu.clock.internal_10MHz_div.build.oscillator= -4809.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -4809.menu.clock.internal_8MHz_div=Internal 8 MHz -4809.menu.clock.internal_8MHz_div.upload.speed=115200 -4809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.internal_8MHz_div.build.oscillator= -4809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -4809.menu.clock.internal_5MHz_div=Internal 5 MHz -4809.menu.clock.internal_5MHz_div.upload.speed=115200 -4809.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -4809.menu.clock.internal_5MHz_div.build.oscillator= -4809.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -4809.menu.clock.internal_4MHz_div=Internal 4 MHz -4809.menu.clock.internal_4MHz_div.upload.speed=115200 -4809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.internal_4MHz_div.build.oscillator= -4809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -4809.menu.clock.internal_2MHz_div=Internal 2 MHz -4809.menu.clock.internal_2MHz_div.upload.speed=115200 -4809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.internal_2MHz_div.build.oscillator= -4809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -4809.menu.clock.internal_1MHz_div=Internal 1 MHz -4809.menu.clock.internal_1MHz_div.upload.speed=115200 -4809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -4809.menu.clock.internal_1MHz_div.build.oscillator= -4809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +4809.menu.clock.internal_10MHz=Internal 10 MHz +4809.menu.clock.internal_10MHz.upload.speed=115200 +4809.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_10MHz.build.oscillator= +4809.menu.clock.internal_10MHz.build.f_cpu=10000000L + +4809.menu.clock.internal_8MHz=Internal 8 MHz +4809.menu.clock.internal_8MHz.upload.speed=115200 +4809.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_8MHz.build.oscillator= +4809.menu.clock.internal_8MHz.build.f_cpu=8000000L + +4809.menu.clock.internal_5MHz=Internal 5 MHz +4809.menu.clock.internal_5MHz.upload.speed=115200 +4809.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +4809.menu.clock.internal_5MHz.build.oscillator= +4809.menu.clock.internal_5MHz.build.f_cpu=5000000L + +4809.menu.clock.internal_4MHz=Internal 4 MHz +4809.menu.clock.internal_4MHz.upload.speed=115200 +4809.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_4MHz.build.oscillator= +4809.menu.clock.internal_4MHz.build.f_cpu=4000000L + +4809.menu.clock.internal_2MHz=Internal 2 MHz +4809.menu.clock.internal_2MHz.upload.speed=115200 +4809.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_2MHz.build.oscillator= +4809.menu.clock.internal_2MHz.build.f_cpu=2000000L + +4809.menu.clock.internal_1MHz.=Internal 1 MHz +4809.menu.clock.internal_1MHz.upload.speed=115200 +4809.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +4809.menu.clock.internal_1MHz.build.oscillator= +4809.menu.clock.internal_1MHz.build.f_cpu=1000000L 4809.menu.clock.external_20MHz=External 20 MHz 4809.menu.clock.external_20MHz.upload.speed=115200 @@ -324,41 +324,41 @@ menu.bootloader=Bootloader 4808.menu.clock.internal_20MHz.build.oscillator= 4808.menu.clock.internal_20MHz.build.f_cpu=20000000L -4808.menu.clock.internal_10MHz_div=Internal 10 MHz -4808.menu.clock.internal_10MHz_div.upload.speed=115200 -4808.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -4808.menu.clock.internal_10MHz_div.build.oscillator= -4808.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -4808.menu.clock.internal_8MHz_div=Internal 8 MHz -4808.menu.clock.internal_8MHz_div.upload.speed=115200 -4808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.internal_8MHz_div.build.oscillator= -4808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -4808.menu.clock.internal_5MHz_div=Internal 5 MHz -4808.menu.clock.internal_5MHz_div.upload.speed=115200 -4808.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -4808.menu.clock.internal_5MHz_div.build.oscillator= -4808.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -4808.menu.clock.internal_4MHz_div=Internal 4 MHz -4808.menu.clock.internal_4MHz_div.upload.speed=115200 -4808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.internal_4MHz_div.build.oscillator= -4808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -4808.menu.clock.internal_2MHz_div=Internal 2 MHz -4808.menu.clock.internal_2MHz_div.upload.speed=115200 -4808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.internal_2MHz_div.build.oscillator= -4808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -4808.menu.clock.internal_1MHz_div=Internal 1 MHz -4808.menu.clock.internal_1MHz_div.upload.speed=115200 -4808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -4808.menu.clock.internal_1MHz_div.build.oscillator= -4808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +4808.menu.clock.internal_10MHz=Internal 10 MHz +4808.menu.clock.internal_10MHz.upload.speed=115200 +4808.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_10MHz.build.oscillator= +4808.menu.clock.internal_10MHz.build.f_cpu=10000000L + +4808.menu.clock.internal_8MHz=Internal 8 MHz +4808.menu.clock.internal_8MHz.upload.speed=115200 +4808.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_8MHz.build.oscillator= +4808.menu.clock.internal_8MHz.build.f_cpu=8000000L + +4808.menu.clock.internal_5MHz=Internal 5 MHz +4808.menu.clock.internal_5MHz.upload.speed=115200 +4808.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +4808.menu.clock.internal_5MHz.build.oscillator= +4808.menu.clock.internal_5MHz.build.f_cpu=5000000L + +4808.menu.clock.internal_4MHz=Internal 4 MHz +4808.menu.clock.internal_4MHz.upload.speed=115200 +4808.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_4MHz.build.oscillator= +4808.menu.clock.internal_4MHz.build.f_cpu=4000000L + +4808.menu.clock.internal_2MHz=Internal 2 MHz +4808.menu.clock.internal_2MHz.upload.speed=115200 +4808.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_2MHz.build.oscillator= +4808.menu.clock.internal_2MHz.build.f_cpu=2000000L + +4808.menu.clock.internal_1MHz=Internal 1 MHz +4808.menu.clock.internal_1MHz.upload.speed=115200 +4808.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +4808.menu.clock.internal_1MHz.build.oscillator= +4808.menu.clock.internal_1MHz.build.f_cpu=1000000L 4808.menu.clock.external_16MHz=External 16 MHz 4808.menu.clock.external_16MHz.upload.speed=115200 @@ -536,41 +536,41 @@ menu.bootloader=Bootloader 3209.menu.clock.internal_20MHz.build.oscillator= 3209.menu.clock.internal_20MHz.build.f_cpu=20000000L -3209.menu.clock.internal_10MHz_div=Internal 10 MHz -3209.menu.clock.internal_10MHz_div.upload.speed=115200 -3209.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -3209.menu.clock.internal_10MHz_div.build.oscillator= -3209.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -3209.menu.clock.internal_8MHz_div=Internal 8 MHz -3209.menu.clock.internal_8MHz_div.upload.speed=115200 -3209.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.internal_8MHz_div.build.oscillator= -3209.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -3209.menu.clock.internal_5MHz_div=Internal 5 MHz -3209.menu.clock.internal_5MHz_div.upload.speed=115200 -3209.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -3209.menu.clock.internal_5MHz_div.build.oscillator= -3209.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -3209.menu.clock.internal_4MHz_div=Internal 4 MHz -3209.menu.clock.internal_4MHz_div.upload.speed=115200 -3209.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.internal_4MHz_div.build.oscillator= -3209.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -3209.menu.clock.internal_2MHz_div=Internal 2 MHz -3209.menu.clock.internal_2MHz_div.upload.speed=115200 -3209.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.internal_2MHz_div.build.oscillator= -3209.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -3209.menu.clock.internal_1MHz_div=Internal 1 MHz -3209.menu.clock.internal_1MHz_div.upload.speed=115200 -3209.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -3209.menu.clock.internal_1MHz_div.build.oscillator= -3209.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +3209.menu.clock.internal_10MHz=Internal 10 MHz +3209.menu.clock.internal_10MHz.upload.speed=115200 +3209.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_10MHz.build.oscillator= +3209.menu.clock.internal_10MHz.build.f_cpu=10000000L + +3209.menu.clock.internal_8MHz=Internal 8 MHz +3209.menu.clock.internal_8MHz.upload.speed=115200 +3209.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_8MHz.build.oscillator= +3209.menu.clock.internal_8MHz.build.f_cpu=8000000L + +3209.menu.clock.internal_5MHz=Internal 5 MHz +3209.menu.clock.internal_5MHz.upload.speed=115200 +3209.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +3209.menu.clock.internal_5MHz.build.oscillator= +3209.menu.clock.internal_5MHz.build.f_cpu=5000000L + +3209.menu.clock.internal_4MHz=Internal 4 MHz +3209.menu.clock.internal_4MHz.upload.speed=115200 +3209.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_4MHz.build.oscillator= +3209.menu.clock.internal_4MHz.build.f_cpu=4000000L + +3209.menu.clock.internal_2MHz=Internal 2 MHz +3209.menu.clock.internal_2MHz.upload.speed=115200 +3209.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_2MHz.build.oscillator= +3209.menu.clock.internal_2MHz.build.f_cpu=2000000L + +3209.menu.clock.internal_1MHz=Internal 1 MHz +3209.menu.clock.internal_1MHz.upload.speed=115200 +3209.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +3209.menu.clock.internal_1MHz.build.oscillator= +3209.menu.clock.internal_1MHz.build.f_cpu=1000000L 3209.menu.clock.external_16MHz=External 16 MHz 3209.menu.clock.external_16MHz.upload.speed=115200 @@ -767,41 +767,41 @@ menu.bootloader=Bootloader 3208.menu.clock.internal_20MHz.build.oscillator= 3208.menu.clock.internal_20MHz.build.f_cpu=20000000L -3208.menu.clock.internal_10MHz_div=Internal 10 MHz -3208.menu.clock.internal_10MHz_div.upload.speed=115200 -3208.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -3208.menu.clock.internal_10MHz_div.build.oscillator= -3208.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -3208.menu.clock.internal_8MHz_div=Internal 8 MHz -3208.menu.clock.internal_8MHz_div.upload.speed=115200 -3208.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.internal_8MHz_div.build.oscillator= -3208.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -3208.menu.clock.internal_5MHz_div=Internal 5 MHz -3208.menu.clock.internal_5MHz_div.upload.speed=115200 -3208.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -3208.menu.clock.internal_5MHz_div.build.oscillator= -3208.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -3208.menu.clock.internal_4MHz_div=Internal 4 MHz -3208.menu.clock.internal_4MHz_div.upload.speed=115200 -3208.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.internal_4MHz_div.build.oscillator= -3208.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -3208.menu.clock.internal_2MHz_div=Internal 2 MHz -3208.menu.clock.internal_2MHz_div.upload.speed=115200 -3208.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.internal_2MHz_div.build.oscillator= -3208.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -3208.menu.clock.internal_1MHz_div=Internal 1 MHz -3208.menu.clock.internal_1MHz_div.upload.speed=115200 -3208.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -3208.menu.clock.internal_1MHz_div.build.oscillator= -3208.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +3208.menu.clock.internal_10MHz=Internal 10 MHz +3208.menu.clock.internal_10MHz.upload.speed=115200 +3208.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_10MHz.build.oscillator= +3208.menu.clock.internal_10MHz.build.f_cpu=10000000L + +3208.menu.clock.internal_8MHz=Internal 8 MHz +3208.menu.clock.internal_8MHz.upload.speed=115200 +3208.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_8MHz.build.oscillator= +3208.menu.clock.internal_8MHz.build.f_cpu=8000000L + +3208.menu.clock.internal_5MHz=Internal 5 MHz +3208.menu.clock.internal_5MHz.upload.speed=115200 +3208.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +3208.menu.clock.internal_5MHz.build.oscillator= +3208.menu.clock.internal_5MHz.build.f_cpu=5000000L + +3208.menu.clock.internal_4MHz=Internal 4 MHz +3208.menu.clock.internal_4MHz.upload.speed=115200 +3208.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_4MHz.build.oscillator= +3208.menu.clock.internal_4MHz.build.f_cpu=4000000L + +3208.menu.clock.internal_2MHz=Internal 2 MHz +3208.menu.clock.internal_2MHz.upload.speed=115200 +3208.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_2MHz.build.oscillator= +3208.menu.clock.internal_2MHz.build.f_cpu=2000000L + +3208.menu.clock.internal_1MHz=Internal 1 MHz +3208.menu.clock.internal_1MHz.upload.speed=115200 +3208.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +3208.menu.clock.internal_1MHz.build.oscillator= +3208.menu.clock.internal_1MHz.build.f_cpu=1000000L 3208.menu.clock.external_16MHz=External 16 MHz 3208.menu.clock.external_16MHz.upload.speed=115200 @@ -978,41 +978,41 @@ menu.bootloader=Bootloader 1609.menu.clock.internal_20MHz.build.oscillator= 1609.menu.clock.internal_20MHz.build.f_cpu=20000000L -1609.menu.clock.internal_10MHz_div=Internal 10 MHz -1609.menu.clock.internal_10MHz_div.upload.speed=115200 -1609.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -1609.menu.clock.internal_10MHz_div.build.oscillator= -1609.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -1609.menu.clock.internal_8MHz_div=Internal 8 MHz -1609.menu.clock.internal_8MHz_div.upload.speed=115200 -1609.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.internal_8MHz_div.build.oscillator= -1609.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -1609.menu.clock.internal_5MHz_div=Internal 5 MHz -1609.menu.clock.internal_5MHz_div.upload.speed=115200 -1609.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -1609.menu.clock.internal_5MHz_div.build.oscillator= -1609.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -1609.menu.clock.internal_4MHz_div=Internal 4 MHz -1609.menu.clock.internal_4MHz_div.upload.speed=115200 -1609.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.internal_4MHz_div.build.oscillator= -1609.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -1609.menu.clock.internal_2MHz_div=Internal 2 MHz -1609.menu.clock.internal_2MHz_div.upload.speed=115200 -1609.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.internal_2MHz_div.build.oscillator= -1609.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -1609.menu.clock.internal_1MHz_div=Internal 1 MHz -1609.menu.clock.internal_1MHz_div.upload.speed=115200 -1609.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -1609.menu.clock.internal_1MHz_div.build.oscillator= -1609.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +1609.menu.clock.internal_10MHz=Internal 10 MHz +1609.menu.clock.internal_10MHz.upload.speed=115200 +1609.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_10MHz.build.oscillator= +1609.menu.clock.internal_10MHz.build.f_cpu=10000000L + +1609.menu.clock.internal_8MHz=Internal 8 MHz +1609.menu.clock.internal_8MHz.upload.speed=115200 +1609.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_8MHz.build.oscillator= +1609.menu.clock.internal_8MHz.build.f_cpu=8000000L + +1609.menu.clock.internal_5MHz=Internal 5 MHz +1609.menu.clock.internal_5MHz.upload.speed=115200 +1609.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +1609.menu.clock.internal_5MHz.build.oscillator= +1609.menu.clock.internal_5MHz.build.f_cpu=5000000L + +1609.menu.clock.internal_4MHz=Internal 4 MHz +1609.menu.clock.internal_4MHz.upload.speed=115200 +1609.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_4MHz.build.oscillator= +1609.menu.clock.internal_4MHz.build.f_cpu=4000000L + +1609.menu.clock.internal_2MHz=Internal 2 MHz +1609.menu.clock.internal_2MHz.upload.speed=115200 +1609.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_2MHz.build.oscillator= +1609.menu.clock.internal_2MHz.build.f_cpu=2000000L + +1609.menu.clock.internal_1MHz=Internal 1 MHz +1609.menu.clock.internal_1MHz.upload.speed=115200 +1609.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +1609.menu.clock.internal_1MHz.build.oscillator= +1609.menu.clock.internal_1MHz.build.f_cpu=1000000L 1609.menu.clock.external_16MHz=External 16 MHz 1609.menu.clock.external_16MHz.upload.speed=115200 @@ -1209,41 +1209,41 @@ menu.bootloader=Bootloader 1608.menu.clock.internal_20MHz.build.oscillator= 1608.menu.clock.internal_20MHz.build.f_cpu=20000000L -1608.menu.clock.internal_10MHz_div=Internal 10 MHz -1608.menu.clock.internal_10MHz_div.upload.speed=115200 -1608.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -1608.menu.clock.internal_10MHz_div.build.oscillator= -1608.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -1608.menu.clock.internal_8MHz_div=Internal 8 MHz -1608.menu.clock.internal_8MHz_div.upload.speed=115200 -1608.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.internal_8MHz_div.build.oscillator= -1608.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -1608.menu.clock.internal_5MHz_div=Internal 5 MHz -1608.menu.clock.internal_5MHz_div.upload.speed=115200 -1608.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -1608.menu.clock.internal_5MHz_div.build.oscillator= -1608.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -1608.menu.clock.internal_4MHz_div=Internal 4 MHz -1608.menu.clock.internal_4MHz_div.upload.speed=115200 -1608.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.internal_4MHz_div.build.oscillator= -1608.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -1608.menu.clock.internal_2MHz_div=Internal 2 MHz -1608.menu.clock.internal_2MHz_div.upload.speed=115200 -1608.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.internal_2MHz_div.build.oscillator= -1608.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -1608.menu.clock.internal_1MHz_div=Internal 1 MHz -1608.menu.clock.internal_1MHz_div.upload.speed=115200 -1608.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -1608.menu.clock.internal_1MHz_div.build.oscillator= -1608.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +1608.menu.clock.internal_10MHz=Internal 10 MHz +1608.menu.clock.internal_10MHz.upload.speed=115200 +1608.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_10MHz.build.oscillator= +1608.menu.clock.internal_10MHz.build.f_cpu=10000000L + +1608.menu.clock.internal_8MHz=Internal 8 MHz +1608.menu.clock.internal_8MHz.upload.speed=115200 +1608.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_8MHz.build.oscillator= +1608.menu.clock.internal_8MHz.build.f_cpu=8000000L + +1608.menu.clock.internal_5MHz=Internal 5 MHz +1608.menu.clock.internal_5MHz.upload.speed=115200 +1608.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +1608.menu.clock.internal_5MHz.build.oscillator= +1608.menu.clock.internal_5MHz.build.f_cpu=5000000L + +1608.menu.clock.internal_4MHz=Internal 4 MHz +1608.menu.clock.internal_4MHz.upload.speed=115200 +1608.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_4MHz.build.oscillator= +1608.menu.clock.internal_4MHz.build.f_cpu=4000000L + +1608.menu.clock.internal_2MHz=Internal 2 MHz +1608.menu.clock.internal_2MHz.upload.speed=115200 +1608.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_2MHz.build.oscillator= +1608.menu.clock.internal_2MHz.build.f_cpu=2000000L + +1608.menu.clock.internal_1MHz=Internal 1 MHz +1608.menu.clock.internal_1MHz.upload.speed=115200 +1608.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +1608.menu.clock.internal_1MHz.build.oscillator= +1608.menu.clock.internal_1MHz.build.f_cpu=1000000L 1608.menu.clock.external_16MHz=External 16 MHz 1608.menu.clock.external_16MHz.upload.speed=115200 @@ -1420,41 +1420,41 @@ menu.bootloader=Bootloader 809.menu.clock.internal_20MHz.build.oscillator= 809.menu.clock.internal_20MHz.build.f_cpu=20000000L -809.menu.clock.internal_10MHz_div=Internal 10 MHz -809.menu.clock.internal_10MHz_div.upload.speed=115200 -809.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -809.menu.clock.internal_10MHz_div.build.oscillator= -809.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -809.menu.clock.internal_8MHz_div=Internal 8 MHz -809.menu.clock.internal_8MHz_div.upload.speed=115200 -809.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.internal_8MHz_div.build.oscillator= -809.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -809.menu.clock.internal_5MHz_div=Internal 5 MHz -809.menu.clock.internal_5MHz_div.upload.speed=115200 -809.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -809.menu.clock.internal_5MHz_div.build.oscillator= -809.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -809.menu.clock.internal_4MHz_div=Internal 4 MHz -809.menu.clock.internal_4MHz_div.upload.speed=115200 -809.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.internal_4MHz_div.build.oscillator= -809.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -809.menu.clock.internal_2MHz_div=Internal 2 MHz -809.menu.clock.internal_2MHz_div.upload.speed=115200 -809.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.internal_2MHz_div.build.oscillator= -809.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -809.menu.clock.internal_1MHz_div=Internal 1 MHz -809.menu.clock.internal_1MHz_div.upload.speed=115200 -809.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -809.menu.clock.internal_1MHz_div.build.oscillator= -809.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +809.menu.clock.internal_10MHz=Internal 10 MHz +809.menu.clock.internal_10MHz.upload.speed=115200 +809.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +809.menu.clock.internal_10MHz.build.oscillator= +809.menu.clock.internal_10MHz.build.f_cpu=10000000L + +809.menu.clock.internal_8MHz=Internal 8 MHz +809.menu.clock.internal_8MHz.upload.speed=115200 +809.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_8MHz.build.oscillator= +809.menu.clock.internal_8MHz.build.f_cpu=8000000L + +809.menu.clock.internal_5MHz=Internal 5 MHz +809.menu.clock.internal_5MHz.upload.speed=115200 +809.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +809.menu.clock.internal_5MHz.build.oscillator= +809.menu.clock.internal_5MHz.build.f_cpu=5000000L + +809.menu.clock.internal_4MHz=Internal 4 MHz +809.menu.clock.internal_4MHz.upload.speed=115200 +809.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_4MHz.build.oscillator= +809.menu.clock.internal_4MHz.build.f_cpu=4000000L + +809.menu.clock.internal_2MHz=Internal 2 MHz +809.menu.clock.internal_2MHz.upload.speed=115200 +809.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_2MHz.build.oscillator= +809.menu.clock.internal_2MHz.build.f_cpu=2000000L + +809.menu.clock.internal_1MHz=Internal 1 MHz +809.menu.clock.internal_1MHz.upload.speed=115200 +809.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +809.menu.clock.internal_1MHz.build.oscillator= +809.menu.clock.internal_1MHz.build.f_cpu=1000000L 809.menu.clock.external_16MHz=External 16 MHz 809.menu.clock.external_16MHz.upload.speed=115200 @@ -1651,41 +1651,41 @@ menu.bootloader=Bootloader 808.menu.clock.internal_20MHz.build.oscillator= 808.menu.clock.internal_20MHz.build.f_cpu=20000000L -808.menu.clock.internal_10MHz_div=Internal 10 MHz -808.menu.clock.internal_10MHz_div.upload.speed=115200 -808.menu.clock.internal_10MHz_div.bootloader.OSCCFG=0x02 -808.menu.clock.internal_10MHz_div.build.oscillator= -808.menu.clock.internal_10MHz_div.build.f_cpu=10000000L - -808.menu.clock.internal_8MHz_div=Internal 8 MHz -808.menu.clock.internal_8MHz_div.upload.speed=115200 -808.menu.clock.internal_8MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.internal_8MHz_div.build.oscillator= -808.menu.clock.internal_8MHz_div.build.f_cpu=8000000L - -808.menu.clock.internal_5MHz_div=Internal 5 MHz -808.menu.clock.internal_5MHz_div.upload.speed=115200 -808.menu.clock.internal_5MHz_div.bootloader.OSCCFG=0x02 -808.menu.clock.internal_5MHz_div.build.oscillator= -808.menu.clock.internal_5MHz_div.build.f_cpu=5000000L - -808.menu.clock.internal_4MHz_div=Internal 4 MHz -808.menu.clock.internal_4MHz_div.upload.speed=115200 -808.menu.clock.internal_4MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.internal_4MHz_div.build.oscillator= -808.menu.clock.internal_4MHz_div.build.f_cpu=4000000L - -808.menu.clock.internal_2MHz_div=Internal 2 MHz -808.menu.clock.internal_2MHz_div.upload.speed=115200 -808.menu.clock.internal_2MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.internal_2MHz_div.build.oscillator= -808.menu.clock.internal_2MHz_div.build.f_cpu=2000000L - -808.menu.clock.internal_1MHz_div=Internal 1 MHz -808.menu.clock.internal_1MHz_div.upload.speed=115200 -808.menu.clock.internal_1MHz_div.bootloader.OSCCFG=0x01 -808.menu.clock.internal_1MHz_div.build.oscillator= -808.menu.clock.internal_1MHz_div.build.f_cpu=1000000L +808.menu.clock.internal_10MHz=Internal 10 MHz +808.menu.clock.internal_10MHz.upload.speed=115200 +808.menu.clock.internal_10MHz.bootloader.OSCCFG=0x02 +808.menu.clock.internal_10MHz.build.oscillator= +808.menu.clock.internal_10MHz.build.f_cpu=10000000L + +808.menu.clock.internal_8MHz=Internal 8 MHz +808.menu.clock.internal_8MHz.upload.speed=115200 +808.menu.clock.internal_8MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_8MHz.build.oscillator= +808.menu.clock.internal_8MHz.build.f_cpu=8000000L + +808.menu.clock.internal_5MHz=Internal 5 MHz +808.menu.clock.internal_5MHz.upload.speed=115200 +808.menu.clock.internal_5MHz.bootloader.OSCCFG=0x02 +808.menu.clock.internal_5MHz.build.oscillator= +808.menu.clock.internal_5MHz.build.f_cpu=5000000L + +808.menu.clock.internal_4MHz=Internal 4 MHz +808.menu.clock.internal_4MHz.upload.speed=115200 +808.menu.clock.internal_4MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_4MHz.build.oscillator= +808.menu.clock.internal_4MHz.build.f_cpu=4000000L + +808.menu.clock.internal_2MHz=Internal 2 MHz +808.menu.clock.internal_2MHz.upload.speed=115200 +808.menu.clock.internal_2MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_2MHz.build.oscillator= +808.menu.clock.internal_2MHz.build.f_cpu=2000000L + +808.menu.clock.internal_1MHz=Internal 1 MHz +808.menu.clock.internal_1MHz.upload.speed=115200 +808.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 +808.menu.clock.internal_1MHz.build.oscillator= +808.menu.clock.internal_1MHz.build.f_cpu=1000000L 808.menu.clock.external_16MHz=External 16 MHz 808.menu.clock.external_16MHz.upload.speed=115200 From 3698469d585e8cbba93aa15f06cb6829f26059b8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 15:50:03 +0200 Subject: [PATCH 183/351] Fix compilation issues Typo in boards.txt, and Serial3 is only available on 40-pin targets --- megaavr/boards.txt | 2 +- .../Comparator/examples/Interrupt/Interrupt.ino | 10 +++++----- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/megaavr/boards.txt b/megaavr/boards.txt index a6edd2c..da611d0 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -117,7 +117,7 @@ menu.bootloader=Bootloader 4809.menu.clock.internal_2MHz.build.oscillator= 4809.menu.clock.internal_2MHz.build.f_cpu=2000000L -4809.menu.clock.internal_1MHz.=Internal 1 MHz +4809.menu.clock.internal_1MHz=Internal 1 MHz 4809.menu.clock.internal_1MHz.upload.speed=115200 4809.menu.clock.internal_1MHz.bootloader.OSCCFG=0x01 4809.menu.clock.internal_1MHz.build.oscillator= diff --git a/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino index 4a5e529..ca8c890 100644 --- a/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino @@ -25,19 +25,19 @@ void setup() { // Configure serial port - Serial3.begin(9600); - + Serial2.begin(9600); + // Configure relevant comparator parameters Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) Comparator.input_n = in_n::dacref; // Connect the negative pin to the DACREF voltage Comparator.reference = ref::vref_2v5; // Set the DACREF voltage to 2.5V - Comparator.dacref = 255; // Gives us 2.5V -> (255 / 256) * 2.5V = 2.5V + Comparator.dacref = 255; // Gives us 2.5V -> (255 / 256) * 2.5V = 2.5V Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis Comparator.output = out::disable; // Use interrupt trigger instead of output pin // Initialize comparator Comparator.init(); - + // Set interrupt (supports RISING, FALLING and CHANGE) Comparator.attachInterrupt(interruptFunction, RISING); @@ -53,5 +53,5 @@ void loop() // This function runs when an interrupt occurs void interruptFunction() { - Serial3.println("Output of analog comparator went high!"); + Serial2.println("Output of analog comparator went high!"); } From 0ce06f28754da6d1aa208772f021acdb9644b094 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 Oct 2020 17:20:31 +0200 Subject: [PATCH 184/351] Fix incorrect servo timer for Nano Every and Uno Wifi --- megaavr/libraries/Servo/src/megaavr/ServoTimers.h | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/megaavr/libraries/Servo/src/megaavr/ServoTimers.h b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h index 3a64217..6762ed8 100644 --- a/megaavr/libraries/Servo/src/megaavr/ServoTimers.h +++ b/megaavr/libraries/Servo/src/megaavr/ServoTimers.h @@ -25,7 +25,9 @@ #define __SERVO_TIMERS_H__ #if !defined(SERVO_USE_TIMERB0) || !defined(SERVO_USE_TIMERB1) || !defined(SERVO_USE_TIMERB2) || !defined(SERVO_USE_TIMERB3) - #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) \ + || defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) \ + || defined(NANO_EVERY_PINOUT) || defined(UNO_WIFI_REV2_PINOUT) #define SERVO_USE_TIMERB1 #elif defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) #define SERVO_USE_TIMERB3 From dfd026057871de658b854e9f28c6672cb74ff786 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 16 Oct 2020 21:58:40 +0200 Subject: [PATCH 185/351] Add ATmega1609,1608,809,808 CI targets --- .travis.yml | 77 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 77 insertions(+) diff --git a/.travis.yml b/.travis.yml index 2b73186..22d13fb 100644 --- a/.travis.yml +++ b/.travis.yml @@ -110,6 +110,83 @@ env: # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:3208:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + ## ATmega1609 + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1609:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega1608 + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:1608:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega809 + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + ## ATmega808 + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + before_install: # Check for tabs (excluding subtrees and keywords.txt files) - find . -path './.git' -prune -or -path './megaavr/bootloaders/optiboot' -prune -or -path './megaavr/avrdude.conf' -prune -or -path './avr/travis-ci/arduino-ci-script' -prune -or \( -not -name 'keywords.txt' -and -type f \) -exec grep --with-filename --line-number --binary-files=without-match --regexp=$'\t' '{}' \; -exec echo 'Tab found.' \; -exec false '{}' + From be6981622723d18b338504ba99ef3fb6dd2e77bf Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 18 Oct 2020 20:30:28 +0200 Subject: [PATCH 186/351] Update Wire library A little formatting, and added another overloaded onReceive function --- megaavr/libraries/Wire/src/Wire.cpp | 27 ++++++++------ megaavr/libraries/Wire/src/Wire.h | 55 +++++++++++++++-------------- 2 files changed, 44 insertions(+), 38 deletions(-) diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index be88af6..7d10f19 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -163,9 +163,9 @@ void TwoWire::end(void) TWI_Disable(); } -void TwoWire::setClock(uint32_t clock) +void TwoWire::setClock(uint32_t frequency) { - TWI_MasterSetBaud(clock); + TWI_MasterSetBaud(frequency); } uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity, bool sendStop) @@ -184,19 +184,24 @@ uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity, bool sendStop) return bytes_read; } +uint8_t TwoWire::requestFrom(int address, int quantity, int sendStop) +{ + return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); +} + uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity) { return requestFrom(address, quantity, true); } -uint8_t TwoWire::requestFrom(int address, int quantity) +uint8_t TwoWire::requestFrom(uint8_t address, uint8_t quantity) { - return requestFrom((uint8_t)address, (size_t)quantity, true); + return requestFrom(address, (size_t)quantity, true); } -uint8_t TwoWire::requestFrom(int address, int quantity, int sendStop) +uint8_t TwoWire::requestFrom(int address, int quantity) { - return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); + return requestFrom((uint8_t)address, (size_t)quantity, true); } void TwoWire::beginTransmission(uint8_t address) @@ -289,7 +294,7 @@ size_t TwoWire::write(const uint8_t *data, size_t quantity) // must be called in: // slave rx event callback // or after requestFrom(address, numBytes) -int TwoWire::available(void) +int TwoWire::available() { return rxBufferLength - rxBufferIndex; } @@ -297,7 +302,7 @@ int TwoWire::available(void) // must be called in: // slave rx event callback // or after requestFrom(address, numBytes) -int TwoWire::read(void) +int TwoWire::read() { int value = -1; @@ -314,7 +319,7 @@ int TwoWire::read(void) // must be called in: // slave rx event callback // or after requestFrom(address, numBytes) -int TwoWire::peek(void) +int TwoWire::peek() { int value = -1; @@ -328,7 +333,7 @@ int TwoWire::peek(void) // can be used to get out of an error state in TWI module // e.g. when MDATA regsiter is written before MADDR -void TwoWire::flush(void) +void TwoWire::flush() { // /* Clear buffers */ // for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ @@ -371,7 +376,7 @@ void TwoWire::onReceiveService(int numBytes) } // behind the scenes function that is called when data is requested -uint8_t TwoWire::onRequestService(void) +uint8_t TwoWire::onRequestService() { // don't bother if user hasn't registered a callback if (!user_onRequest) diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index dc2f0c2..d320c61 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -49,9 +49,9 @@ class TwoWire : public Stream static uint8_t txBufferLength; static uint8_t transmitting; - static void (*user_onRequest)(void); + static void (*user_onRequest)(); static void (*user_onReceive)(int); - static uint8_t onRequestService(void); + static uint8_t onRequestService(); static void onReceiveService(int); public: @@ -59,35 +59,36 @@ class TwoWire : public Stream bool pins(uint8_t sda_pin, uint8_t scl_pin); bool swap(uint8_t state = 1); void begin(); - void begin(uint8_t); - void begin(int); - void begin(uint8_t, bool, uint8_t); - void begin(int, bool, uint8_t); - void begin(uint8_t, bool); - void begin(int, bool); + void begin(uint8_t address); + void begin(int address); + void begin(uint8_t address, bool receive_broadcast, uint8_t second_address); + void begin(int address, bool receive_broadcast, uint8_t second_address); + void begin(uint8_t address, bool receive_broadcast); + void begin(int address, bool receive_broadcast); void end(); - void setClock(uint32_t); - void beginTransmission(uint8_t); - void beginTransmission(int); - uint8_t endTransmission(void); - uint8_t endTransmission(bool); - uint8_t requestFrom(uint8_t, size_t); - uint8_t requestFrom(uint8_t, size_t, bool); - uint8_t requestFrom(int, int); - uint8_t requestFrom(int, int, int); - virtual size_t write(uint8_t); - virtual size_t write(const uint8_t *, size_t); - virtual int available(void); - virtual int read(void); - virtual int peek(void); - virtual void flush(void); + void setClock(uint32_t frequency); + void beginTransmission(uint8_t address); + void beginTransmission(int address); + uint8_t endTransmission(); + uint8_t endTransmission(bool sendStop); + uint8_t requestFrom(uint8_t address, size_t quantity, bool sendStop); + uint8_t requestFrom(int address, int quantity, int sendStop); + uint8_t requestFrom(uint8_t address, size_t quantity); + uint8_t requestFrom(uint8_t address, uint8_t quantity); + uint8_t requestFrom(int address, int quantity); + virtual size_t write(uint8_t data); + virtual size_t write(const uint8_t *data, size_t quantity); + virtual int available(); + virtual int read(); + virtual int peek(); + virtual void flush(); void onReceive(void (*)(int)); void onRequest(void (*)(void)); - inline size_t write(unsigned long n) { return write((uint8_t)n); } - inline size_t write(long n) { return write((uint8_t)n); } - inline size_t write(unsigned int n) { return write((uint8_t)n); } - inline size_t write(int n) { return write((uint8_t)n); } + inline size_t write(unsigned long data) { return write((uint8_t)data); } + inline size_t write(long data) { return write((uint8_t)data); } + inline size_t write(unsigned int data) { return write((uint8_t)data); } + inline size_t write(int data) { return write((uint8_t)data); } using Print::write; }; From 6c3a2e501c7494e1944a1400b07d16b09438308f Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 4 Nov 2020 09:29:27 +0100 Subject: [PATCH 187/351] Create PlatformIO.md --- PlatformIO.md | 267 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 267 insertions(+) create mode 100644 PlatformIO.md diff --git a/PlatformIO.md b/PlatformIO.md new file mode 100644 index 0000000..4bace19 --- /dev/null +++ b/PlatformIO.md @@ -0,0 +1,267 @@ +# PlatformIO + +[PlatformIO](https://platformio.org) is an open source ecosystem for embedded development. +It has a built-in library manager and is Arduino compatible. It supports most operating systems; Windows, MacOS, Linux 32 and 64-bit, ARM and X86. And best of all, MegaCoreX is supported! + +* [What is PlatformIO?](http://docs.platformio.org/en/latest/what-is-platformio.html) +* [PlatformIO IDE](https://platformio.org/platformio-ide) +* Getting started with [PlatformIO IDE](https://docs.platformio.org/en/latest/integration/ide/visualstudio.html) or [PlatformIO command line interface](https://docs.platformio.org/en/latest/core/index.html) +* [Advanced functionality](https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html) +* [Project Examples](https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html#examples) + + +## MegaCoreX + PlatformIO +MegaCoreX and PlatformIO goes great together. You can do serial uploads and upload using a dedicated UPDI programmer, but you can also let PlatformIO calulate the fuses and load the correct bootloader file, just like Arduino IDE does! + +PlatformIO uses the information provided in platformio.ini to calculate what fuse bits and what bootloader file to load. +Simply provide enough information and run the following commands: + +```ini +; Only set fuses +pio run -t fuses -e fuses_bootloader +; Set fuses and burn bootloader +pio run -t bootloader -e fuses_bootloader +; (where "fuses_bootloader" can be replace with a different environment to match your build configuration) +``` + +You can find a platformio.ini template you can use when creating a project for a MegaCoreX compatible device below. +The most common functionality is available in this template. As you can see, the templated is divided into multiple environments. + +* The default build environment are defined under *[platformio]*. +* All parameters that are common for all environments are defined under *[env]*. +* Use the *[env:Upload_UPDI]* or *[env:Upload_UART]* to upload to your target. +* Use *[env:fuses_bootloader]* to set the fuses or burn the bootloader. + +More information on what each line means can be found futher down on this page. + + +## platformio.ini template + +```ini +; PlatformIO template configuration file for MegaCoreX +; https://github.com/MCUdude/MegaCoreX/ +; +; Build options: build flags, source filter +; Hardware options: oscillator type, BOD, UART number, EEPROM retain +; Upload options: custom upload port, speed, and extra flags +; Library options: dependencies, extra library storages +; Advanced options: extra scripting +; +; Please visit documentation for the other options +; https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md +; https://docs.platformio.org/page/projectconf.html +; https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html + +[platformio] +; Default build target +default_envs = Upload_UPDI + +; Parameters used for all environments +[env] +platform = atmelmegaavr +framework = arduino + +; Chip in use +board = ATmega4809 +; Clock frequency in [Hz] +board_build.f_cpu = 16000000L +; Oscillator type (internal or external) +board_hardware.oscillator = internal +; Arduino pinout variant +board_build.variant = 48pin-standard + +; Unflag build flags +build_unflags = +; Extra build flags +build_flags = + +; Monitor port is auto detected. Override here +;monitor_port = +; Serial monitor baud rate +monitor_speed = 9600 + + +; Run the following command to upload with this environment +; pio run -e Upload_UPDI -t upload +[env:Upload_UPDI] +; Upload protocol for UPDI upload +upload_protocol = xplainedmini_updi +upload_flags = + + +; Run the following command to upload with this environment +; pio run -e Upload_UART -t upload +[env:Upload_UART] +; Upload protocol for serial uploads (using Optiboot) +upload_protocol = arduino +upload_flags = +upload_port = /dev/cu.usbserial* + + +; run the following command to set fuses +; pio run -e fuses_bootloader -t fuses +; run the following command to set fuses + burn bootloader +; pio run -e fuses_bootloader -t bootloader +[env:fuses_bootloader] +; Upload protocol for used to set fuses/bootloader +upload_protocol = ${env:Upload_UPDI.upload_protocol} +upload_flags = +; Hardware settings +board_hardware.bod = 2.7v +board_hardware.eesave = yes +board_hardware.uart = no_bootloader +board_hardware.rstpin = reset + +``` + + +### `board` +PlatformIO requires the `board` parameter to be present. +The table below shows what board name should be used for each target +| Board name | +|---------------| +| `ATmega4809` | +| `ATmega4808` | +| `ATmega3209` | +| `ATmega3208` | +| `ATmega1609` | +| `ATmega1608` | +| `ATmega809` | +| `ATmega808` | + + +### `board_build.f_cpu` +Specifies the clock frequency in [Hz]. +Used to determine what oscillator option to choose. A capital *L* has to be added to the end of the frequency number. +Below is a table with supported clocks for MegaCoreX. Defaults to 16 MHz internal if not specified. + +| Clock speed | Oscillator | board_build.f_cpu | +|-------------|------------|-----------------------| +| 20 MHz | Internal | `20000000L` | +| 16 MHz | Internal | `16000000L` (default) | +| 10 MHz | Internal | `10000000L` | +| 8 MHz | Internal | `8000000L` | +| 5 MHz | Internal | `5000000L` | +| 4 MHz | Internal | `4000000L` | +| 2 MHz | Internal | `2000000L` | +| 1 MHz | Internal | `1000000L` | +| 16 MHz | External | `16000000L` | +| 12 MHz | External | `12000000L` | +| 8 MHz | External | `8000000L` | +| 4 MHz | External | `4000000L` | +| 1 MHz | External | `1000000L` | + + +### `board_hardware.oscillator` +Spefices to use the internal or an external oscillator. + +| Oscillator option | +|----------------------| +| `internal` (default) | +| `external` | + + +### `board_hardware.uart` +Specifies the hardware UART port used for serial upload. Use `no_bootloader` if you’re using a dedicated UPDI programmer, i.e not using a bootloader for serial upload. + +| Upload serial port option | Description | +|---------------------------|------------------------------------------------| +| `no_bootloader` (default) | | +| `uart0` / `uart0_def` | Use UART0 default pins | +| `uart0_alt` | Use UART0 alternative pins | +| `uart1` / `uart1_def` | Use UART1 default pins | +| `uart1_alt` | Use UART1 alternative pins | +| `uart2` / `uart2_def` | Use UART2 default pins | +| `uart2_alt` | Use UART2 alternative pins | +| `uart3` / `uart3_def` | Use UART3 default pins (48-pin parts only) | +| `uart3_alt` | Use UART3 alternative pins (48-pin parts only) | + +### `board_hardware.bod` +Specifies the hardware brown-out detection. Use `disabled` to disable. + +| BOD | +|------------------| +| `4.3v` | +| `2.6v` (default) | +| `1.8v` | +| `disabled` | + + +### `board_hardware.eesave` +Specifies if the EEPROM memory should be retained when uploading using a programmer. Use `no` to disable. + +| EEPROM retain | +|-----------------| +| `yes` (default) | +| `no` | + + +### `board_hardware.rstpin` +Specifies what functionality the reset pin should have. Note that the option `reset` _will_ be selected regardless if you're using a bootloader. + +| Reset pin functionality | +|---------------------------| +| `reset` (default) | +| `gpio` | + + +### `board_build.variant` +Holds the current pinout in use. +See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. + +| Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | +|---------------------------|-----------------------------------|---------------------------|---------------------------| +| `48pin-default` (default) | `40pin-default` (must be defined) | `32pin-default` (default) | `28pin-default` (default) | +| `nano-every` | | | | +| `uno-wifi` | | | | + + +### `build_unflags` +This parameter is used to unflag flags automatically set by the PlatformIO build environment. + +**Example:** +`build_unflags =-flto -fpermissive` + + +### `build_flags` +This parameter is used to set compiler flags. This is useful if you want to for instance want to chage the serial RX or TX buffer. Here's a list of the current available core files flags: + +| Flag | Default size | Description | +|-----------------------------|--------------|-----------------------------------------------------------| +| -lprintf_flt | | Lets you print floats with printf (occupies ~1.5 kB) | +| -Wall -Wextra | | Show on all compiler warnings | +| -DSERIAL_RX_BUFFER_SIZE=128 | 64 bytes | Sets the serial RX buffer to 128 bytes | +| -DSERIAL_TX_BUFFER_SIZE=128 | 64 bytes | Sets the serial TX buffer to 128 bytes | +| -DTWI_BUFFER_SIZE=64 | 32 bytes | Sets the TWI (i2c) buffer to 64 bytes | +| -DTWI1_BUFFER_SIZE=64 | 32 bytes | Sets the TWI1 (i2c) buffer to 64 bytes (ATmega324PB only) | + +**Example:** +`build_flags = -DSERIAL_RX_BUFFER_SIZE=128 -DSERIAL_TX_BUFFER_SIZE=128` + + +### `upload_port` +Holds the serial port used for uploading. Only needed if you're uploading using a JTAG2UPDI programmer or with a USB to serial adapter using the Optiboot bootloader. PlatformIO automatically detects the serial port. However, if you want to override this you can uncomment `upload_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. + + +### `upload_protocol` +Used when using a programmer rather than using a USB to serial adapter. +Supports all Avrdude compatible UPDI programmers such as `jtag2updi`, `xplainedmini_updi` and `curiosity_updi`. + + +### `upload_flags` +Used to pass extra flags to Avrdude when uploading using a programmer. +Typical parameters are `-PUSB` and `-v`. +**Note that every flag has to be on its own line, and they have to be indented with two spaces:** +```ini +upload_flags = + -PUSB + -v +``` + + +### `monitor_port` +PlatformIO detects serial ports automatically. However, if you want to override this you can uncomment `monitor_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. + + +### `monitor_speed` +Sets the serial monitor baud rate. Defaults to 9600 if not defined. From ec4d6891a76d10b180310abade259b24e5a3fc32 Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 4 Nov 2020 09:31:16 +0100 Subject: [PATCH 188/351] Add PlatformIO to README --- README.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/README.md b/README.md index 185dd92..78ef71c 100644 --- a/README.md +++ b/README.md @@ -32,6 +32,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) + - [PlatformIO](#platformio) * [Minimal setup](#minimal-setup) * [Getting your hardware working](#getting-your-hardware-working) - [Arduino Uno WiFi Rev2](#arduino-uno-wifi-rev2) @@ -285,6 +286,11 @@ Available pin combinations for the *Nano Every* pinout are: Click on the "Download ZIP" button. Extract the ZIP file, and move the extracted folder to the location "**~/Documents/Arduino/hardware**". Create the "hardware" folder if it doesn't exist. Open Arduino IDE and a new category in the boards menu called "MightyCoreX" will show up. +#### PlatformIO +[PlatformIO](http://platformio.org) is an open source ecosystem for IoT development and supports MegaCoreX. + +**See [PlatformIO.md](https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md) for more information.** + ## Minimal setup Here are some simple schematics that show a minimal setup. The straight 6-pin header may in the future be used for serial uploads without having to use a UPDI programmer. As of today, we're still waiting for a stable version of Optiboot. From 7f0c1c42ac87fbcc8b9eb64573dd92e78f403b2c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 11 Nov 2020 22:03:57 +0100 Subject: [PATCH 189/351] Formatting --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 52fe33d..003c5ba 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -130,7 +130,7 @@ tools.avrdude_nanoevery.upload.params.verbose=-v tools.avrdude_nanoevery.upload.params.quiet=-q -q tools.avrdude_nanoevery.upload.verify= tools.avrdude_nanoevery.upload.params.noverify=-V -tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i" "-Ufuse0:w:{bootloader.WDTCFG}:m" "-Ufuse1:w:{bootloader.BODCFG}:m" "-Ufuse2:w:{bootloader.OSCCFG}:m" "-Ufuse4:w:{bootloader.TCD0CFG}:m" "-Ufuse5:w:{bootloader.SYSCFG0}:m" "-Ufuse6:w:{bootloader.SYSCFG1}:m" "-Ufuse7:w:{bootloader.APPEND}:m" "-Ufuse8:w:{bootloader.BOOTEND}:m" "-Ulock:w:{bootloader.LOCKBIT}:m" +tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q From 4631c4020ee8a8054d06fecfceba7791500cf1dd Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 16 Nov 2020 09:29:50 +0100 Subject: [PATCH 190/351] Add pyupdi section Yes, it is possible to upload using pyupdi as well! --- PlatformIO.md | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/PlatformIO.md b/PlatformIO.md index 4bace19..004b914 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -265,3 +265,32 @@ PlatformIO detects serial ports automatically. However, if you want to override ### `monitor_speed` Sets the serial monitor baud rate. Defaults to 9600 if not defined. + + +## pyupdi +[pyupdi](https://github.com/mraardvark/pyupdi) is a Python-based tool for programming tinyAVR and megaAVR devices with UPDI interface via a standard serial port. It can be installed directly in the PlatformIO virtual environment using the following command: + +``` +pip install https://github.com/mraardvark/pyupdi/archive/master.zip +``` + +Once pyupdi is installed it can be used as the uploader via a custom upload_command option: + +```ini +[env:pyupdi_upload] +platform = atmelmegaavr +framework = arduino +board = ATmega4809 +upload_speed = 115200 +upload_flags = + -d + mega4809 + -c + $UPLOAD_PORT + -b + $UPLOAD_SPEED +upload_command = pyupdi $UPLOAD_FLAGS -f $SOURCE +``` + +Note that the pyupdi target naming scheme is a little bit different, and therefore has to be manually specified under `upload_flags`. +The target `ATmega4809` is recognised as `mega4809` by pyupdi. From c2321a73e51144e0484bab78f351293d072218c7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 16 Nov 2020 11:28:50 +0100 Subject: [PATCH 191/351] Update Servo library It now behaves like the official Servo library. Closes #95 --- megaavr/libraries/Servo/library.properties | 6 +- megaavr/libraries/Servo/src/Servo.h | 73 +++---- megaavr/libraries/Servo/src/megaavr/Servo.cpp | 180 +++++++++--------- 3 files changed, 135 insertions(+), 124 deletions(-) diff --git a/megaavr/libraries/Servo/library.properties b/megaavr/libraries/Servo/library.properties index 6fd2324..f8d54ca 100644 --- a/megaavr/libraries/Servo/library.properties +++ b/megaavr/libraries/Servo/library.properties @@ -1,9 +1,9 @@ name=Servo -version=1.1.5 -author=MCUdude based on work by Michael Margolis, Arduino +version=1.2.0 +author=Spence Konde and MCUdude based on work by Michael Margolis, Arduino maintainer=MCUdude sentence=Allows megaAVR0 chips to control a variety of servo motors. -paragraph=This library can control a great number of servos.
It makes careful use of timers: the library can control 12 servos using only 1 timer.
On the Arduino Due you can control up to 60 servos.
+paragraph=This library can control a great number of servos.
It makes careful use of timers: the library can control 12 servos using only 1 timer.
category=Device Control url=http://www.arduino.cc/en/Reference/Servo architectures=megaavr diff --git a/megaavr/libraries/Servo/src/Servo.h b/megaavr/libraries/Servo/src/Servo.h index d3dc383..9f092f7 100644 --- a/megaavr/libraries/Servo/src/Servo.h +++ b/megaavr/libraries/Servo/src/Servo.h @@ -47,16 +47,15 @@ #ifndef Servo_h #define Servo_h - #include /* - * Defines for 16 bit timers used with Servo library - * - * If _useTimerX is defined then TimerX is a 16 bit timer on the current board - * timer16_Sequence_t enumerates the sequence that the timers should be allocated - * _Nbr_16timers indicates how many 16 bit timers are available. - */ + Defines for 16 bit timers used with Servo library + + If _useTimerX is defined then TimerX is a 16 bit timer on the current board + timer16_Sequence_t enumerates the sequence that the timers should be allocated + _Nbr_16timers indicates how many 16 bit timers are available. +*/ // Architecture specific include #if defined(ARDUINO_ARCH_MEGAAVR) @@ -65,47 +64,51 @@ #warning "Running at 1MHz results in unstable servo signal." #endif #else - #error "This library only supports boards with a megaAVR-0 processor." + #error "This is an architecture specific library for ARDUINO_ARCH_MEGAAVR, but this device is not of that architecture" #endif -#define Servo_VERSION 2 // software version of this library +#define Servo_VERSION 2 // software version of this library -#define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo -#define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo -#define DEFAULT_PULSE_WIDTH 1500 // default pulse width when servo is attached -#define REFRESH_INTERVAL 20000 // minumim time to refresh servos in microseconds +#define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo +#define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo +#define DEFAULT_PULSE_WIDTH 1500 // default pulse width when servo is attached +#define REFRESH_INTERVAL 20000UL // minumim time to refresh servos in microseconds -#define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer +#define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer #define MAX_SERVOS (_Nbr_16timers * SERVOS_PER_TIMER) -#define INVALID_SERVO 255 // flag indicating an invalid servo index +#define INVALID_SERVO 255 // flag indicating an invalid servo index typedef struct { - uint8_t nbr :6 ; // a pin number from 0 to 63 - uint8_t isActive :1 ; // true if this channel is enabled, pin not pulsed if false -} ServoPin_t ; + //uint8_t nbr; // a pin number from 0 to 63 + // the original implementation with bitslices and just isActive and nbr in a single byte saved 2 bytes of ram per servo, as a cost of a very small amount of flash. + // optimization it supports (losing digitalWrite() in the ISR) has surprisingly little impact - though I do think it has a more significant impact on time spent + // in the ISR, which you don't see most of the time... + uint8_t isActive; // true if this channel is enabled, pin not pulsed if false + uint8_t port; + uint8_t bitmask; +} ServoPin_t; typedef struct { ServoPin_t Pin; - volatile unsigned int ticks; + volatile uint16_t ticks; } servo_t; -class Servo -{ -public: - Servo(); - uint8_t attach(uint8_t pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure - uint8_t attach(uint8_t pin, int16_t min, int16_t max); // as above but also sets min and max values for writes. - void detach(); - void write(int16_t value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds - void writeMicroseconds(int16_t value); // Write pulse width in microseconds - int read(); // returns current pulse width as an angle between 0 and 180 degrees - int readMicroseconds(); // returns current pulse width in microseconds for this servo (was read_us() in first release) - bool attached(); // return true if this servo is attached, otherwise false -private: - uint8_t servoIndex; // index into the channel data for this servo - int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH - int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH +class Servo { + public: + Servo(); + uint8_t attach(uint8_t pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure + uint8_t attach(uint8_t pin, int16_t min, int16_t max); // as above but also sets min and max values for writes. + void detach(); + void write(uint16_t value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds + void writeMicroseconds(uint16_t value); // Write pulse width in microseconds + int16_t read(); // returns current pulse width as an angle between 0 and 180 degrees + uint16_t readMicroseconds(); // returns current pulse width in microseconds for this servo (was read_us() in first release) + bool attached(); // return true if this servo is attached, otherwise false + private: + uint8_t servoIndex; // index into the channel data for this servo + int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH + int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH }; #endif diff --git a/megaavr/libraries/Servo/src/megaavr/Servo.cpp b/megaavr/libraries/Servo/src/megaavr/Servo.cpp index 92d0ad7..32c9693 100644 --- a/megaavr/libraries/Servo/src/megaavr/Servo.cpp +++ b/megaavr/libraries/Servo/src/megaavr/Servo.cpp @@ -4,7 +4,7 @@ #include #if (F_CPU > 10000000L) - #define usToTicks(_us) ((( _us / 2) * clockCyclesPerMicrosecond())) // converts microseconds to tick + #define usToTicks(_us) ((( (_us) / 2) * clockCyclesPerMicrosecond())) // converts microseconds to tick #define ticksToUs(_ticks) (((unsigned) _ticks * 2) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds #define TRIM_DURATION 37 // compensation ticks to trim adjust for digitalWrite delays #else @@ -28,47 +28,55 @@ static volatile int8_t currentServoIndex[_Nbr_16timers]; // index for the servo #define SERVO_MIN() (MIN_PULSE_WIDTH - this->min * 4) // minimum value in uS for this servo #define SERVO_MAX() (MAX_PULSE_WIDTH - this->max * 4) // maximum value in uS for this servo -void ServoHandler(int timer) -{ - if (currentServoIndex[timer] < 0) { - // Write compare register - _timer->CCMP = 0; +void ServoHandler(int16_t timer) { + static uint32_t currentCycleTicks = 0; + if (currentServoIndex[timer] < 0) { + // we're at servo index -1... but before we go further - we need to see if we've waited through a refresh cycle... + if (currentCycleTicks < usToTicks(REFRESH_INTERVAL)) { + uint32_t tval=usToTicks(REFRESH_INTERVAL)-currentCycleTicks; + uint16_t tval16=(tval>65535)?65535:tval; + _timer->CCMP = tval16; + currentCycleTicks+=tval16; + // wait longer, and terminate the ISR without further action./* Clear flag */ + _timer->INTFLAGS = TCB_CAPT_bm; + return; } else { - if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { - digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, LOW); // pulse this channel low if activated - } + // current cycle is done, so reset the currentCycleTicks, and run the rest of things... + currentCycleTicks=0; } - - // Select the next servo controlled by this timer - currentServoIndex[timer]++; - - if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && currentServoIndex[timer] < SERVOS_PER_TIMER) { - if (SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { // check if activated - digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, HIGH); // it's an active channel so pulse it high - } - - // Get the counter value - uint16_t tcCounterValue = 0; //_timer->CCMP; - _timer->CCMP = (uint16_t) (tcCounterValue + SERVO(timer, currentServoIndex[timer]).ticks); + } else { + if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { + //digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, LOW); // pulse this channel low if activated + ((PORT_t *)&PORTA + SERVO(timer, currentServoIndex[timer]).Pin.port)->OUTCLR = SERVO(timer, currentServoIndex[timer]).Pin.bitmask; } - else { - // finished all channels so wait for the refresh period to expire before starting over - - // Get the counter value - uint16_t tcCounterValue = _timer->CCMP; + } - if (tcCounterValue + 4UL < usToTicks(REFRESH_INTERVAL)) { // allow a few ticks to ensure the next OCR1A not missed - _timer->CCMP = (uint16_t) usToTicks(REFRESH_INTERVAL); - } - else { - _timer->CCMP = (uint16_t) (tcCounterValue + 4UL); // at least REFRESH_INTERVAL has elapsed - } + // Select the next servo controlled by this timer + currentServoIndex[timer]++; - currentServoIndex[timer] = -1; // this will get incremented at the end of the refresh period to start again at the first channel + if (SERVO_INDEX(timer, currentServoIndex[timer]) < ServoCount && currentServoIndex[timer] < SERVOS_PER_TIMER) { + if (SERVO(timer, currentServoIndex[timer]).Pin.isActive == true) { // check if activated + //digitalWrite(SERVO(timer, currentServoIndex[timer]).Pin.nbr, HIGH); // it's an active channel so pulse it high + ((PORT_t *)&PORTA + SERVO(timer, currentServoIndex[timer]).Pin.port)->OUTSET = SERVO(timer, currentServoIndex[timer]).Pin.bitmask; } - /* Clear flag */ - _timer->INTFLAGS = TCB_CAPT_bm; + // Get the counter value + _timer->CCMP = SERVO(timer, currentServoIndex[timer]).ticks; + currentCycleTicks += SERVO(timer, currentServoIndex[timer]).ticks; + } else { + // finished all channels so wait for the refresh period to expire before starting over + if (currentCycleTicks + 100 < usToTicks(REFRESH_INTERVAL)) { // let's not bother if it's gonna take less than 100 ticks for the next + uint32_t tval = usToTicks(REFRESH_INTERVAL) - currentCycleTicks; + uint16_t tval16 = tval > 65535 ? 65535 : tval; + _timer->CCMP = tval16; + currentCycleTicks += tval16; + } else { // in this case it's less than 100 ticks for next interval, so we just set it to that... + currentCycleTicks = usToTicks(REFRESH_INTERVAL); + } + currentServoIndex[timer] = -1; // this will get incremented at the end of the refresh period to start again at the first channel + } + /* Clear flag */ + _timer->INTFLAGS = TCB_CAPT_bm; } #if defined(SERVO_USE_TIMERB0) @@ -84,8 +92,7 @@ ISR(TCB3_INT_vect) ServoHandler(0); } -static void initISR(__attribute__ ((unused)) timer16_Sequence_t timer) -{ +static void initISR() { //divide CLK_PER by 2 instead of using TCA0-prescaled at 16/20MHz #if (F_CPU > 10000000L) _timer->CTRLA = TCB_CLKSEL_CLKDIV2_gc; @@ -103,26 +110,24 @@ static void initISR(__attribute__ ((unused)) timer16_Sequence_t timer) _timer->CTRLA |= TCB_ENABLE_bm; } -static void finISR(__attribute__ ((unused)) timer16_Sequence_t timer) -{ +static void finISR() { // Disable interrupt _timer->INTCTRL = 0; } -static boolean isTimerActive(timer16_Sequence_t timer) -{ +static bool isTimerActive(timer16_Sequence_t timer) { // returns true if any servo is active on this timer - for(uint8_t channel=0; channel < SERVOS_PER_TIMER; channel++) { - if(SERVO(timer,channel).Pin.isActive == true) + for (uint8_t channel = 0; channel < SERVOS_PER_TIMER; channel++) { + if (SERVO(timer, channel).Pin.isActive == true) { return true; + } } return false; } /****************** end of static functions ******************************/ -Servo::Servo() -{ +Servo::Servo() { if (ServoCount < MAX_SERVOS) { this->servoIndex = ServoCount++; // assign a servo index to this instance servos[this->servoIndex].ticks = usToTicks(DEFAULT_PULSE_WIDTH); // store default values @@ -131,93 +136,96 @@ Servo::Servo() } } -uint8_t Servo::attach(uint8_t pin) -{ +uint8_t Servo::attach(uint8_t pin) { return this->attach(pin, MIN_PULSE_WIDTH, MAX_PULSE_WIDTH); } -uint8_t Servo::attach(uint8_t pin, int16_t min, int16_t max) -{ +uint8_t Servo::attach(uint8_t pin, int16_t min, int16_t max) { timer16_Sequence_t timer; if (this->servoIndex < MAX_SERVOS) { - pinMode(pin, OUTPUT); // set servo pin to output - servos[this->servoIndex].Pin.nbr = pin; + //pinMode(pin, OUTPUT); // set servo pin to output + //servos[this->servoIndex].Pin.nbr = pin; + uint8_t bitmask = digitalPinToBitMask(pin); + if (bitmask == NOT_A_PIN) + return NOT_A_PIN; + servos[this->servoIndex].Pin.bitmask = bitmask; + uint8_t prt = digitalPinToPort(pin); + servos[this->servoIndex].Pin.port = prt; + PORT_t *port=((PORT_t *)&PORTA + prt); + port->DIRSET=bitmask; // todo min/max check: abs(min - MIN_PULSE_WIDTH) /4 < 128 - this->min = (MIN_PULSE_WIDTH - min)/4; //resolution of min/max is 4 uS - this->max = (MAX_PULSE_WIDTH - max)/4; + this->min = (MIN_PULSE_WIDTH - min) / 4; //resolution of min/max is 4 uS + this->max = (MAX_PULSE_WIDTH - max) / 4; // initialize the timer if it has not already been initialized timer = SERVO_INDEX_TO_TIMER(servoIndex); if (isTimerActive(timer) == false) { - initISR(timer); + initISR(); } servos[this->servoIndex].Pin.isActive = true; // this must be set after the check for isTimerActive } return this->servoIndex; } -void Servo::detach() -{ +void Servo::detach() { timer16_Sequence_t timer; servos[this->servoIndex].Pin.isActive = false; timer = SERVO_INDEX_TO_TIMER(servoIndex); - if(isTimerActive(timer) == false) { - finISR(timer); + if (isTimerActive(timer) == false) { + finISR(); } } -void Servo::write(int16_t value) -{ +void Servo::write(uint16_t value) { // treat values less than 544 as angles in degrees (valid values in microseconds are handled as microseconds) - if (value < MIN_PULSE_WIDTH) - { - if (value < 0) - value = 0; - else if (value > 180) + if (value < MIN_PULSE_WIDTH) { + // ditch this, the argument is an unsigned int, so this is pointless... + //if (value < 0) { + // value = 0; + //} else + if (value > 180) { value = 180; + } value = map(value, 0, 180, SERVO_MIN(), SERVO_MAX()); } writeMicroseconds(value); } -void Servo::writeMicroseconds(int16_t value) -{ + +void Servo::writeMicroseconds(uint16_t value) { // calculate and store the values for the given channel - byte channel = this->servoIndex; - if( (channel < MAX_SERVOS) ) // ensure channel is valid - { - if (value < SERVO_MIN()) // ensure pulse width is valid + uint8_t channel = this->servoIndex; + if ((channel < MAX_SERVOS)) { // ensure channel is valid + if (value < (uint16_t) SERVO_MIN()) { // ensure pulse width is valid value = SERVO_MIN(); - else if (value > SERVO_MAX()) + } else if (value > (uint16_t) SERVO_MAX()) { value = SERVO_MAX(); + } + + value = usToTicks(value); // convert to ticks BEFORE compensating for interrupt overhead value = value - TRIM_DURATION; - value = usToTicks(value); // convert to ticks after compensating for interrupt overhead servos[channel].ticks = value; } } -int Servo::read() // return the value as degrees -{ - return map(readMicroseconds()+1, SERVO_MIN(), SERVO_MAX(), 0, 180); +int16_t Servo::read() { // return the value as degrees + return map(readMicroseconds() + 1, SERVO_MIN(), SERVO_MAX(), 0, 180); } -int Servo::readMicroseconds() -{ - unsigned int pulsewidth; - if (this->servoIndex != INVALID_SERVO) - pulsewidth = ticksToUs(servos[this->servoIndex].ticks) + TRIM_DURATION; - else +uint16_t Servo::readMicroseconds() { + uint16_t pulsewidth; + if (this->servoIndex != INVALID_SERVO) { + pulsewidth = ticksToUs(servos[this->servoIndex].ticks + TRIM_DURATION); + } else { pulsewidth = 0; - + } return pulsewidth; } -bool Servo::attached() -{ +bool Servo::attached() { return servos[this->servoIndex].Pin.isActive; } - #endif From 2b34004d185db90c5f115b0ae4c06fda10a1d831 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 23 Nov 2020 18:38:57 +0100 Subject: [PATCH 192/351] Make sure pin numbers are constant If using digitalReadFast or digitalWriteFast --- README.md | 4 ++-- megaavr/cores/coreX-corefiles/api/Common.h | 16 ++++++++++------ megaavr/cores/coreX-corefiles/wiring_digital.c | 10 ++++++++-- 3 files changed, 20 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 78ef71c..6885a4b 100644 --- a/README.md +++ b/README.md @@ -120,8 +120,8 @@ If you're using a serial port, simply use `Serial.printf("Milliseconds since sta ## Fast IO -For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compile down to a single instruction. -Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that in order to gain any speed improvements, the pin number has to be a constant. +For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compiles down to a single instruction. +Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that the pin number has to be known at compile time. ## Pin macros diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index c74c901..e0d9d6c 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -97,13 +97,9 @@ typedef uint8_t pin_size_t; void pinMode(pin_size_t pinNumber, uint8_t pinMode); void digitalWrite(pin_size_t pinNumber, uint8_t status); -void _dwfast(pin_size_t pinNumber, uint8_t status); -#define digitalWriteFast(pin, val) \ - (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _dwfast(pin, val) : digitalWrite(pin, val)) +void digitalWriteFast(pin_size_t pinNumber, uint8_t status); uint8_t digitalRead(pin_size_t pinNumber); -uint8_t _drfast(pin_size_t pinNumber); -#define digitalReadFast(pin) \ - (__builtin_constant_p(pin) ? /*&& __builtin_constant_p(val)*/ _drfast(pin) : digitalRead(pin)) +uint8_t digitalReadFast(pin_size_t pinNumber); int analogRead(pin_size_t pinNumber); uint8_t analogReadResolution(uint8_t res); void analogReference(uint8_t mode); @@ -126,6 +122,14 @@ void detachInterrupt(pin_size_t interruptNumber); void setup(void); void loop(void); +// Constant checks error handler +void badArg(const char*) __attribute__((error(""))); +inline __attribute__((always_inline)) void check_constant_pin(pin_size_t pin) +{ + if(!__builtin_constant_p(pin)) + badArg("Digital pin must be a constant"); +} + #ifdef __cplusplus } // extern "C" #endif diff --git a/megaavr/cores/coreX-corefiles/wiring_digital.c b/megaavr/cores/coreX-corefiles/wiring_digital.c index 6672885..3f07a6e 100644 --- a/megaavr/cores/coreX-corefiles/wiring_digital.c +++ b/megaavr/cores/coreX-corefiles/wiring_digital.c @@ -202,8 +202,11 @@ void digitalWrite(uint8_t pin, uint8_t val) } } -inline __attribute__((always_inline)) void _dwfast(uint8_t pin, uint8_t val) +inline __attribute__((always_inline)) void digitalWriteFast(uint8_t pin, uint8_t val) { + // Make sure pin is constant and know at compile time + check_constant_pin(pin); + // Mega-0, Tiny-1 style IOPORTs // Assumes VPORTs exist starting at 0 for each PORT structure uint8_t mask = 1 << digital_pin_to_bit_position[pin]; @@ -244,8 +247,11 @@ uint8_t digitalRead(uint8_t pin) return LOW; } -inline __attribute__((always_inline)) uint8_t _drfast(uint8_t pin) +inline __attribute__((always_inline)) uint8_t digitalReadFast(uint8_t pin) { + // Make sure pin is constant and know at compile time + check_constant_pin(pin); + // Mega-0, Tiny-1 style IOPORTs // Assumes VPORTs exist starting at 0 for each PORT structure uint8_t mask = 1 << digital_pin_to_bit_position[pin]; From 865d41388d3c8c7fa206c8955c66d6d356d63ac1 Mon Sep 17 00:00:00 2001 From: f1oat Date: Thu, 26 Nov 2020 20:40:29 +0100 Subject: [PATCH 193/351] Update EEPROM.h Avoid link error "multiple definition of nvm_write_byte(unsigned int, unsigned char)" when including EEPROM.h in multiple files of a project --- megaavr/libraries/EEPROM/src/EEPROM.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/EEPROM/src/EEPROM.h b/megaavr/libraries/EEPROM/src/EEPROM.h index d700217..7ac7b08 100644 --- a/megaavr/libraries/EEPROM/src/EEPROM.h +++ b/megaavr/libraries/EEPROM/src/EEPROM.h @@ -32,7 +32,7 @@ #define nvm_read_byte(idx) *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) -void nvm_write_byte(uint16_t idx, uint8_t dat) +static void nvm_write_byte(uint16_t idx, uint8_t dat) { *(uint8_t *)((idx & 0xFF) | ((idx & 0x100) ? USER_SIGNATURES_START : EEPROM_START)) = dat; uint8_t oldSREG = SREG; From 7971cdfb0787634777caf3d3831002a2c0f378b4 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 2 Dec 2020 19:26:37 +0100 Subject: [PATCH 194/351] Remove whitespace --- megaavr/cores/coreX-corefiles/Arduino.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 664aab8..80b4557 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -28,6 +28,7 @@ #undef F #define F(str) (str) +#define __FlashStringHelper char #ifdef __cplusplus extern "C"{ @@ -71,7 +72,7 @@ extern "C"{ #define _NOP() do { __asm__ volatile ("nop"); } while (0) #endif -/* Allows performing a correction on the CPU value using the signature row +/* Allows performing a correction on the CPU value using the signature row values indicating oscillator error provided from the device manufacturer */ #define PERFORM_SIGROW_CORRECTION_F_CPU 0 From b6d44b7158df220fdcc592a1f4a67d727cd431f0 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 2 Dec 2020 19:27:26 +0100 Subject: [PATCH 195/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 003c5ba..79e3746 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.5 +version=1.0.6 # AVR compile variables # --------------------- From 0acb67b4f1075c6b8bfbd180752024bffeee00c9 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Dec 2020 21:11:52 +0100 Subject: [PATCH 196/351] Clear LUTCTRLA before itializing it Closes #98 --- megaavr/libraries/Logic/src/Logic.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 428186b..39d8384 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -281,6 +281,7 @@ void Logic::init() } // Set logic output state and output filter + block.LUTCTRLA = 0x00; block.LUTCTRLA = (output ? CCL_OUTEN_bm : 0) | (edgedetect ? CCL_EDGEDET_EN_gc : 0 ) | (filter << CCL_FILTSEL_gp) From b2c918282e4572464a48dadc70f945a602881c06 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Dec 2020 21:58:41 +0100 Subject: [PATCH 197/351] Reformat LUTCTRLA clear --- megaavr/libraries/Logic/src/Logic.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 39d8384..9294426 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -248,6 +248,9 @@ void Logic::init() initInput(input1, block.PORT_IN, block.input1_bm); initInput(input2, block.PORT_IN, block.input2_bm); + // Clear LUTCTRLA in case the CCL block gets reinitialized + block.LUTCTRLA = 0x00; + // Set inputs modes block.LUTCTRLB = (input1 << CCL_INSEL1_gp) | (input0 << CCL_INSEL0_gp); block.LUTCTRLC = (input2 << CCL_INSEL2_gp); @@ -281,7 +284,6 @@ void Logic::init() } // Set logic output state and output filter - block.LUTCTRLA = 0x00; block.LUTCTRLA = (output ? CCL_OUTEN_bm : 0) | (edgedetect ? CCL_EDGEDET_EN_gc : 0 ) | (filter << CCL_FILTSEL_gp) From 2be078e89ee9fead67b95818e5228fb6e4be197e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Dec 2020 22:17:30 +0100 Subject: [PATCH 198/351] Add MPLAB SNAP and PICkit4 UPDI programmers ... and remove whitespaces --- megaavr/avrdude.conf | 144 +++++++++++++++++++++++----------------- megaavr/programmers.txt | 14 ++++ 2 files changed, 98 insertions(+), 60 deletions(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 14437b3..61c8b5c 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -36,7 +36,7 @@ # vfyled = ; # pin number # usbvid = ; # USB VID (Vendor ID) # usbpid = [, ...] # USB PID (Product ID) (1) -# usbdev = ; # USB interface or other device info +# usbdev = ; # USB interface or other device info # usbvendor = ; # USB Vendor Name # usbproduct = ; # USB Product Name # usbsn = ; # USB Serial Number @@ -148,9 +148,9 @@ # complain. # # Parts can also inherit parameters from previously defined parts -# using the following syntax. In this case specified integer and -# string values override parameter values from the parent part. New -# memory definitions are added to the definitions inherited from the +# using the following syntax. In this case specified integer and +# string values override parameter values from the parent part. New +# memory definitions are added to the definitions inherited from the # parent. # # part parent # quoted string @@ -159,7 +159,7 @@ # ; # # NOTES: -# * 'devicecode' is the device code used by the STK500 (see codes +# * 'devicecode' is the device code used by the STK500 (see codes # listed below) # * Not all memory types will implement all instructions. # * AVR Fuse bits and Lock bits are implemented as a type of memory. @@ -373,7 +373,7 @@ programmer # http://dangerousprototypes.com/docs/FT2232_breakout_board # http://www.ftdichip.com/Products/Modules/DLPModules.htm,DLP-2232*,DLP-USB1232H # http://flashrom.org/FT2232SPI_Programmer -# +# # The drivers will look for a specific device and use the first one found. # If you have mulitple devices, then look for unique information (like SN) # And fill that in here. @@ -415,7 +415,7 @@ programmer type = "avrftdi"; connection_type = usb; usbvid = 0x0403; -# Note: This PID is reserved for generic H devices and +# Note: This PID is reserved for generic H devices and # should be programmed into the EEPROM # usbpid = 0x8A48; usbpid = 0x6010; @@ -423,13 +423,13 @@ programmer usbvendor = ""; usbproduct = ""; usbsn = ""; -#ISP-signals +#ISP-signals reset = 3; sck = 0; mosi = 1; miso = 2; buff = ~4; -#LED SIGNALs +#LED SIGNALs errled = ~ 11; rdyled = ~ 14; pgmled = ~ 13; @@ -527,8 +527,8 @@ programmer # On the adapter you can read "O-Link". On the PCB is printed "OpenJTAG v3.1" -# You can find it as "OpenJTAG ARM JTAG USB" in the internet. -# (But there are also several projects called Open JTAG, eg. +# You can find it as "OpenJTAG ARM JTAG USB" in the internet. +# (But there are also several projects called Open JTAG, eg. # http://www.openjtag.org, which are completely different.) # http://www.100ask.net/shop/english.html (website seems to be outdated) # http://item.taobao.com/item.htm?id=1559277013 @@ -806,7 +806,7 @@ programmer # TTL-232R TXD 4 Orange -> ICPS RESET (pin 5) # TTL-232R RXD 5 Yellow -> ICPS SCK (pin 3) # TTL-232R RTS 6 Green -> ICPS MISO (pin 1) -# Except for VCC and GND, you can connect arbitual pairs as long as +# Except for VCC and GND, you can connect arbitual pairs as long as # the following table is adjusted. programmer id = "ttl232r"; @@ -927,7 +927,7 @@ programmer type = "butterfly"; connection_type = serial; ; - + # suggested in http://forum.mikrokopter.de/topic-post48317.html programmer id = "mkbutterfly"; @@ -1247,6 +1247,30 @@ programmer usbpid = 0x2144; ; +programmer + id = "pickit4_updi"; + desc = "MPLAB(R) PICkit 4 in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; + ; + + programmer + id = "snap_updi"; + desc = "MPLAB(R) SNAP in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x217F, 0x2180, 0x2181; + ; + + programmer + id = "pkobn_updi"; + desc = "PKOB nano (nEDBG) in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2175; + ; + programmer id = "pavr"; desc = "Jason Kyle's pAVR Serial Programmer"; @@ -1311,7 +1335,7 @@ programmer reset = 25; ; -# some ultra cheap programmers use bitbanging on the +# some ultra cheap programmers use bitbanging on the # serialport. # # PC - DB9 - Pins for RS232: @@ -1971,7 +1995,7 @@ part max_write_delay = 9000; readback_p1 = 0x00; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", + read = "1 0 1 0 0 0 0 0 x x x x x x x x", "x x a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = "1 1 0 0 0 0 0 0 x x x x x x x x", @@ -2084,7 +2108,7 @@ part max_write_delay = 20000; readback_p1 = 0x80; readback_p2 = 0x7f; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", + read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", @@ -2197,7 +2221,7 @@ part max_write_delay = 9000; readback_p1 = 0x80; readback_p2 = 0x7f; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", + read = "1 0 1 0 0 0 0 0 x x x x x x x x", "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = "1 1 0 0 0 0 0 0 x x x x x x x x", @@ -2311,7 +2335,7 @@ part max_write_delay = 20000; readback_p1 = 0x00; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", + read = "1 0 1 0 0 0 0 0 x x x x x x x x", "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = "1 1 0 0 0 0 0 0 x x x x x x x x", @@ -2438,7 +2462,7 @@ part max_write_delay = 20000; readback_p1 = 0x00; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0", + read = "1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0", "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = "1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0", @@ -2562,7 +2586,7 @@ part max_write_delay = 20000; readback_p1 = 0x00; readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x x", + read = " 1 0 1 0 0 0 0 0 x x x x x x x x", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = " 1 1 0 0 0 0 0 0 x x x x x x x x", @@ -2656,7 +2680,7 @@ part max_write_delay = 20000; readback_p1 = 0x00; readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x x", + read = " 1 0 1 0 0 0 0 0 x x x x x x x x", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = " 1 1 0 0 0 0 0 0 x x x x x x x x", @@ -2770,7 +2794,7 @@ part max_write_delay = 9000; readback_p1 = 0x80; readback_p2 = 0x7f; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", + read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", @@ -2883,7 +2907,7 @@ part max_write_delay = 20000; readback_p1 = 0x00; readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", + read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", @@ -3011,7 +3035,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; mode = 0x04; @@ -3163,7 +3187,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; mode = 0x04; @@ -3347,7 +3371,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; mode = 0x04; @@ -3528,7 +3552,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 0 x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -4103,7 +4127,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -4305,7 +4329,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -4513,7 +4537,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -4721,7 +4745,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -4915,7 +4939,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -5099,7 +5123,7 @@ part mode = 0x41; delay = 10; blocksize = 128; - readsize = 256; + readsize = 256; ; @@ -5459,7 +5483,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -6380,7 +6404,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; mode = 0x04; @@ -7661,7 +7685,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 0 x x x x x", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -7873,7 +7897,7 @@ part write = " 1 1 0 0 0 0 0 0", " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -8082,7 +8106,7 @@ part " 0 0 0 x x x x a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; - + write = " 1 1 0 0 0 0 0 0", " 0 0 0 x x x x a8", " a7 a6 a5 a4 a3 a2 a1 a0", @@ -8117,22 +8141,22 @@ part " 0 0 0 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; - + read_hi = " 0 0 1 0 1 0 0 0", " 0 0 0 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; - + loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; - + loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; - + writepage = " 0 1 0 0 1 1 0 0", " 0 0 0 a12 a11 a10 a9 a8", " a7 a6 x x x x x x", @@ -8144,57 +8168,57 @@ part readsize = 256; ; - + memory "lfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x o o o o o o o o"; - + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", "x x x x x x x x i i i i i i i i"; ; - + memory "hfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; - + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", "x x x x x x x x i i i i i i i i"; ; - + memory "efuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; - + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", "x x x x x x x x x x x x x i i i"; ; - + memory "lock" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x x x o o o o o o"; - + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; ; - + memory "calibration" size = 1; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; - + memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", @@ -8658,7 +8682,7 @@ part parent "m328" max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; - + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", "x x x x x x x x x x i i i i i i"; ; @@ -9318,7 +9342,7 @@ part parent "pwm3b" part parent "pwm316" id = "pwm216"; desc = "AT90PWM216"; - ; + ; #------------------------------------------------------------ # ATtiny25 @@ -9946,7 +9970,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -10136,7 +10160,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -10339,7 +10363,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -11637,7 +11661,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -11828,7 +11852,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -12032,7 +12056,7 @@ part write = " 1 1 0 0 0 0 0 0", " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index b242e5e..2305629 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -31,3 +31,17 @@ atmelice_updi.protocol=atmelice_updi atmelice_updi.program.protocol=jtagice3_updi atmelice_updi.program.tool=avrdude atmelice_updi.program.extra_params=-Pusb + +pickit4_updi.name=PICkit4 (UPDI) +pickit4_updi.communication=usb +pickit4_updi.protocol=pickit4_updi +pickit4_updi.program.protocol=jtagice3_updi +pickit4_updi.program.tool=avrdude +pickit4_updi.program.extra_params=-Pusb + +snap_updi.name=MPLAB SNAP (UPDI) +snap_updi.communication=usb +snap_updi.protocol=snap_updi +snap_updi.program.protocol=jtagice3_updi +snap_updi.program.tool=avrdude +snap_updi.program.extra_params=-Pusb From 458fe4ddbab26d143853cbe7f222547ee2d78da5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Dec 2020 14:06:59 +0100 Subject: [PATCH 199/351] Update pyupdi section pyupdi now supports "regular" target names such as atmega4809 --- PlatformIO.md | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/PlatformIO.md b/PlatformIO.md index 004b914..996a8b4 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -278,19 +278,15 @@ Once pyupdi is installed it can be used as the uploader via a custom upload_comm ```ini [env:pyupdi_upload] -platform = atmelmegaavr -framework = arduino -board = ATmega4809 +upload_protocol = custom upload_speed = 115200 +upload_port = /some/serial/port upload_flags = -d - mega4809 + ${env.board_build.mcu} -c $UPLOAD_PORT -b $UPLOAD_SPEED upload_command = pyupdi $UPLOAD_FLAGS -f $SOURCE ``` - -Note that the pyupdi target naming scheme is a little bit different, and therefore has to be manually specified under `upload_flags`. -The target `ATmega4809` is recognised as `mega4809` by pyupdi. From 7997a2722c4d0de9805a6891e1fec6323eae0843 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 17 Dec 2020 14:11:24 +0100 Subject: [PATCH 200/351] Use BOARD_MCU instead of env.board_build.mcu --- PlatformIO.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PlatformIO.md b/PlatformIO.md index 996a8b4..08e0b0e 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -283,7 +283,7 @@ upload_speed = 115200 upload_port = /some/serial/port upload_flags = -d - ${env.board_build.mcu} + $BOARD_MCU -c $UPLOAD_PORT -b From 843b9feb07796ca99b2875c2d8e5c2610c7b6085 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 19 Dec 2020 00:11:10 +0100 Subject: [PATCH 201/351] Fix incorrect analogReadResolution setting Closes #101 --- megaavr/cores/coreX-corefiles/wiring_analog.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index f5abd04..7a9ce57 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -84,11 +84,11 @@ uint8_t analogReadResolution(uint8_t res) { if (res==8) { - ADC0.CTRLA&=~ADC_RESSEL_bm; + ADC0.CTRLA |= ADC_RESSEL_bm; return 1; } // If argument wasn't 8, we'll be putting it to default value either way - ADC0.CTRLA |= ADC_RESSEL_bm; + ADC0.CTRLA &= ~ADC_RESSEL_bm; return (res == 10); // Only return true if the value passed was the valid option, 10. } From d1318aa38a849358f570d17e5c8ac6460c246550 Mon Sep 17 00:00:00 2001 From: "Spence Konde (aka Dr. Azzy)" Date: Thu, 24 Dec 2020 14:42:05 -0500 Subject: [PATCH 202/351] Correct description of feedback feedback input takes the "output" of the *even* LUT (which is taken as the output of the sequencer if that is used, otherwise the output of the LUT itself. Unclear if intended and the documentation is poorly written. Also - were you going to cut the tinyAVR and Dx-stuff from the readme for MegaCoreX? (do note that I've cut the mega/Dx-stuff from megaTinyCore readme, and am cutting tiny stuff from DxCore version. --- megaavr/libraries/Logic/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index 1ffe616..d137255 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -41,7 +41,7 @@ Accepted values for DA-series and megaAVR 0-series parts: in::masked; // Pin not in use in::unused; // Pin not in use in::disable; // Pin not in use -in::feedback; // Connect output of the logic block to this input +in::feedback; // Connect output of sequencer (if used) or even-numbered logic block (n or n-1) to this input in::link; // Connect output of logic block n+1 to this input in::event_0; // Connect input to event a in::event_a; // Connect input to event a From 4ded96f7043512167683567390d7c04de84b0a88 Mon Sep 17 00:00:00 2001 From: "Spence Konde (aka Dr. Azzy)" Date: Thu, 24 Dec 2020 16:26:56 -0500 Subject: [PATCH 203/351] Dear god, I just noticed that part... It *only* controls filter/sync, and sequential logic. without those, these logic blocks react as fast as the transistors can switch. Which can be..... surprisingly fast! --- megaavr/libraries/Logic/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index d137255..c872af7 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -166,7 +166,7 @@ Logic0.filter = filter::filter; // Enable filter on output of block 0 ### clocksource -Variable set the clock source for the LUT. The inputs are checked and output updated on the rising edge of this clock. Except on the Dx-series parts, only clk_per (peripheral clock, ie, the system clock) and in2 are available. If you don't know what this means, you want clk_per. If sequential logic is used, this is also used to clock that. +Variable to set the clock source for the logic block; this is used for the synchronizer and filter only (otherwise, the logic blocks are asynchronous). Except on the Dx-series parts, only clk_per (peripheral clock, ie, the system clock) and in2 are available. If you don't know what this means, you want clk_per. If sequential logic is used, it is clocked from the clock source used by the even-numbered logic block. Accepted values: ```c++ clocksource::clk_per; // Clock from the peripheral clock (ie, system clock) From b8c5a8c67eccf3d190bafa48ff73545eddb4f686 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 29 Dec 2020 10:58:41 +0100 Subject: [PATCH 204/351] Fix typo --- megaavr/libraries/Logic/src/Logic.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 9294426..30ea058 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -334,7 +334,7 @@ void Logic::detachInterrupt() { // Disable interrupt for a given block output #if defined(CCL_TRUTH4) - if(block_number > 4) + if(block.number > 4) CCL.INTCTRL1 &= ~(CCL_INTMODE1_gm << ((block.number & 3) * 2)); else CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); From 1d3991bc2ee2864cb40ca7173363a3562b35776d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 29 Dec 2020 19:18:42 +0100 Subject: [PATCH 205/351] Update Logic library Sync library version number and source files with the DxCore version and update README --- megaavr/libraries/Logic/README.md | 144 +++--- megaavr/libraries/Logic/library.properties | 8 +- megaavr/libraries/Logic/src/Logic.cpp | 512 ++++++++++++++------- megaavr/libraries/Logic/src/Logic.h | 167 +++++-- 4 files changed, 534 insertions(+), 297 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index c872af7..bd66c2f 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -1,19 +1,22 @@ # Logic -A library for interfacing with the CCL (Configurable Custom Logic) peripherals of the megaAVR-0 MCUs. -Developed by MCUdude for use with [MegaCoreX](https://github.com/MCUdude/MegaCoreX), adapted to megaAVR ATtiny parts by [Tadashi G. Takaoka](https://github.com/tgtakaoka), and to DA-series by [Spence Konde](https://github.com/SpenceKonde) -The megaAVR-0 has four independent internal logic blocks that can be individually customized. +A library for interfacing with the CCL (Configurable Custom Logic) peripherals of the megaAVR-0 MCUs. +Developed by MCUdude for use with [MegaCoreX](https://github.com/MCUdude/MegaCoreX), adapted to megaAVR ATtiny parts by [Tadashi G. Takaoka](https://github.com/tgtakaoka), and to Dx-series by [Spence Konde](https://github.com/SpenceKonde). +The library is compatible with all these parts, but this README only covers the megaAVR-0 functionality. +The megaAVR-0 has four independent internal logic blocks that can be individually customized. All of the megaTiny parts have 2 blocks of CCL available. The examples included assume the use of megaTinyCore in their defines to detect the applicable part. More useful information about CCL can be found in the [Microchip Application Note TB3218](http://ww1.microchip.com/downloads/en/AppNotes/TB3218-Getting-Started-with-CCL-90003218A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf), part in question. ## Logic -Class for interfacing with the built-in logic block. use the predefined objects `Logic0`, `Logic1`, `Logic2` and `Logic3`. -`Logic2` and `Logic3` are only available on the ATmega parts, `Logic4` and `Logic5` only on AVR-DA. -Each object contains register pointers for interfacing with the right registers. Some of these variables are available to the user. +Class for interfacing with the built-in logic block (sometimes referred to as `LUT`s - "LookUp Table"). +Use the predefined objects `Logic0`, `Logic1`, `Logic2` and `Logic3`. The logic blocks are paired, each pair sharing a single sequencer and `feedback` channel. +Additionally, each logic block is associated with a specific port, having it's input on pins 0 through 2, and it's output on pin 3 or 6. In order: `PORTA`, `PORTC`, `PORTD` and `PORTF`. + +These objects expose all configuration options as member variables as documented below, as well as member methods to set the applicable registers. ### enable -Variable for enabling or disabling a logic block. +Variable for enabling or disabling a logic block. Accepted values: ```c++ true; // Enable the current logic block @@ -31,12 +34,8 @@ Logic0.enable = true; // Enable logic block 0 ### input0..input2 Variable for setting what mode input 0..2 on a logic block should have. -Notes for all parts: -* The datasheets give different names for the event channels for ATtiny and ATmega parts, both are supported by library: event 0 and event a are the same, as are event 1 and event b. These can be generated using the event system, see the relevant datasheet and examples for more information. -* Timer WO channels correspond to the specified timer's PWM Output channels. They are true when the specified timer's value is higher than the compare register for that output channel. -* Type-B timers can only generate an output under circumstances where they could drive an output pin if CCMPEN in TCBn.CTRLA is set. +Accepted values for megaAVR 0-series parts: -Accepted values for DA-series and megaAVR 0-series parts: ``` c++ in::masked; // Pin not in use in::unused; // Pin not in use @@ -52,61 +51,25 @@ in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, s in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off in::ac; // Connect input to the output of the internal analog comparator (input 0,1,2 from AC0,1,2) -in::zcd; // Connect input to the output of the zero crossing detector (input 0,1,2 from ZCD0,1,2) - DA-series only in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 -in::tca1; // Connect input to TCA1. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 - DA-series only +in::tca; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO. -in::tcd; // Connect input to TCD0. Input 0 connects to WOA, input 1 to WOB and input2 to WOC - DA-series only ``` Notes specific to ATmega parts -* The 48-pin and 64-pin DA-series parts have 6 LUTs. No pins for CCL5 are available in the 48-pin package. -* On 28-pin versions of the ATmega 4808, 3208, 1608, and 808, IN1 and IN2 inputs for logic3 are not available. If all input pins for all logic blocks are needed, the event system workaround shown for the ATtiny parts in the examples can be used, though note that register names and values are different. Same principle applies to the DA-series devices with fewer pins. -* According to the datasheet for SPI as input source, inputs 0 and 1 connect to MOSI. Thus, on these parts, there is no input to the logic blocks for MISO. Note also that the order is different from the ATtiny parts. -* If input on the highest-number Logic block is set to link, it will use the output of Logic0 (unless it's an early production DA-series - see the errata) +* On 28-pin versions of the ATmega 4808, 3208, 1608, and 808, IN1 and IN2 inputs for logic3 are not available. If all input pins for all logic blocks are needed, the event system can be used. +* According to the datasheet for SPI as input source, inputs 0 and 1 connect to MOSI. Thus, on these parts, there is no input to the logic blocks for MISO. +* If input on the highest-number Logic block is set to link, it will use the output of Logic0 * If you need to link input to logic block other than the n+1 block, you can use the event system for that. -Accepted values for tinyAVR 0/1-series parts: - -``` c++ -in::masked; // Pin not in use -in::unused; // Pin not in use -in::disable; // Pin not in use -in::feedback; // Connect output of the logic block to this input -in::link; // Connect output of the other logic block to this input -in::event_0; // Connect input to event 0 -in::event_a; // Connect input to event 0 -in::event_1; // Connect input to event 1 -in::event_b; // Connect input to event 1 -in::pin; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, do not change pinMode -in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup on -in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off -in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off -in::ac0; // Connect input to AC0 OUT -in::tcb0; // Connect input to TCB0 WO -in::tca; // Connect input to TCA0 WO0~2 for input 0~2 -in::tca0; // Connect input to TCA0 WO0~2 for input 0~2 -in::tcd; // Connect input to TCD WOAn, WOB, WOA for input 0, 1, 2 -in::usart; // Connect input to U(S)ART0 XCK and TXD for input 0, 1 -in::spi; // Connect input to SPI0 SCK, MOSI, MISO for input 0, 1, 2 -in::ac1; // Connect input to AC1 OUT (input 0, 1 only) -in::tcb1; // Connect input to TCB1 WO (input 0, 1 only) -in::ac2; // Connect input to AC2 OUT (input 0, 1 only) -``` - -Notes specific to ATtiny: -* It is not clear what TCD0 WOAn is. I suspect it is true when TCD0 count is greater than TCD0.COMPSET0 and TCD0.CMPCLR0, ie, when WOA turns on and off, which can be individually controlled; the timer continues counting until reaching TCD0.CMPCLR1 when WOB turns off (TCD0 is a very strange timer). -* Not all inputs are available on all parts - only input sources corresponding to peripherals on that device are available. Not all options are avalable for input 2, as noted above. -* On CCL1 (logic1), IN0 I/O input is available only on the 20 and-24 pin parts, and IN1 and IN2 only on 24-pin parts. The event inputs can be used with pin events to take input from a diferent pins for up to two inputs. This is demonstrated in the five input example. -* CCL0's IN0 pin is on PA0, which is nominally the UPDI pin. It can only be used as input when that pin is set as GPIO. This limits the usefulness of CCL0 on the ATtiny parts; configuring UPDI as GPIO prevents further programming via UPDI except via HV programming. Configuring this option is only supported on megaTinyCore with Optiboot bootloader (from 1.1.6 on), and prevents further modification of the fuses or bootloader without HV programming, however, as noted above, input0 can be used via the event inputs to take input from another pin. This is demonstrated in the three input examples. ##### Usage ``` c++ -Logic0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 -Logic0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO -Logic0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO and enable pullup +Logic0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 +Logic0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO +Logic0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO, with pullup on ``` ##### Default state @@ -114,7 +77,7 @@ Logic0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPI ### output -Variable for changing the logic block output pin behavior. Note that the output of the logic block still can be used internally if the output pin is disabled. +Variable for changing the logic block output pin behavior. Note that the output of the logic block still can be used internally if the output pin is disabled. Accepted values: ```c++ out::disable; // Disable the output GPIO pin. Useful when triggering an interrupt instead. @@ -131,10 +94,10 @@ Logic0.output = out::disable; // Disable the output GPIO pin. ### output_swap -Variable for pin swapping the physical output pin to its alternative position. See the pinout diagrams in the main MegaCoreX README for detailed info. +Variable for pin swapping the physical output pin to its alternative position. See the pinout diagrams in the main MegaCoreX README for detailed info. Accepted values: ```c++ -out::no_swap; // Use default pin position, pin 2 on the port +out::no_swap; // Use default pin position, pin 3 on the port out::pin_swap; // Use alternative position, pin 6 on the port ``` @@ -148,11 +111,16 @@ Logic0.output_swap = out::no_swap; // No pin swap for output of block0 ### filter -Variable to connecting a filter or synchronizer to the logic block output. Useful when multiple logic blocks are connected internally to prevent logic race. +Variable to control whether the output passes through a synchronizer or filter. +Useful when multiple logic blocks are connected internally to prevent race conditions and glitches that could arise due to the asynchronous nature of CCL clocking. +Alternately, the delay itself may be desirable, or it can be combined with a configuration which would oscillate asynchronously to instead output a prescaled clock, which could, in turn, be used with "clock on event" to provide a type B timer with a prescaled clock. +Either filter or synchronizer is required for edge detector, below. Accepted values: ```c++ -filter::disable; // No filter used +filter::disable; // No filter used, asynchronous output. filter::synchronizer; // Connect synchronizer to output; delays output by 2 clock cycles. +filter::synch; // Syntactic sugar for synchronizer +filter::sync; // Syntactic sugar for synchronizer filter::filter; // Connect filter to output; delays output by 4 clock cycles, only passes output that is stable for >2 clock cycles. ``` @@ -166,17 +134,15 @@ Logic0.filter = filter::filter; // Enable filter on output of block 0 ### clocksource -Variable to set the clock source for the logic block; this is used for the synchronizer and filter only (otherwise, the logic blocks are asynchronous). Except on the Dx-series parts, only clk_per (peripheral clock, ie, the system clock) and in2 are available. If you don't know what this means, you want clk_per. If sequential logic is used, it is clocked from the clock source used by the even-numbered logic block. +Variable to set the clock source for the logic block; this is used for the synchronizer and filter only (otherwise, the logic blocks are asynchronous). +If sequential logic is used, it is clocked from the clock source used by the even-numbered logic block. Accepted values: ```c++ clocksource::clk_per; // Clock from the peripheral clock (ie, system clock) clocksource::in2; // Clock from the selected input2; it is treated as a 0 in the truth table. -clocksource::oschf; // Clock from the **unprescaled** internal HF oscillator. Same as clk_per if system clock not prescaled. -clocksource::osc32k; // Clock from the internal 32.768 kHz oscillator -clocksource::osc1l; // Clock from the internal 32.768 kHz oscillator prescaled by 32 ``` -#### Usage +##### Usage ```c++ Logic0.clocksource = clocksource::clk_per; ``` @@ -203,13 +169,14 @@ Logic0.edgedetect = edgedetect::enable; ### sequencer -Variable for connecting a sequencer to the logic block output. There is 1 sequencer per 2 CCLs; this option is ignored for the odd-numbered logic blocks. +Variable for connecting a "sequencer" to the logic block output - these are latches or flip-flops which remember a state. There is 1 sequencer per 2 CCLs, each controls one of the two inputs to a flip flop or latch; this option is ignored for the odd-numbered logic blocks. Flip-flops are clocked from the same clock source as the even logic block, latches are asynchronous. + Accepted values: ```c++ sequencer::disable; // No sequencer connected sequencer::d_flip_flop; // D flip flop sequencer connected sequencer::jk_flip_flop; // JK flip flop sequencer connected -sequencer::d_latch; // D latch sequencer connected +sequencer::d_latch; // Gated D latch sequencer connected - note that on most megaAVR parts, this doesn't work. See the Errata. sequencer::rs_latch; // RS latch sequencer connected ``` @@ -223,7 +190,7 @@ Logic0.sequencer = sequencer::disable; // Disable sequencer ### truth -Variable to hold the 8-bit truth table value. +Variable to hold the 8-bit truth table value. Accepted values between 0x00 and 0xFF. ##### Usage @@ -237,7 +204,7 @@ Logic0.truth = 0xF0; ## init() -Method for initializing a logic block. The logic block object to initialize is passed as an argument. +Method for initializing a logic block; the settings you have previously configured will be applied and pins configured as requested at this time only. ##### Usage ```c++ @@ -246,9 +213,8 @@ Logic1.init(); // Initialize block 1 ``` - ## start() -Method for starting the CCL hardware after all registers have been initialized using init(block_t). +Method for starting the CCL hardware after desired blocks have been initialized using `LogicN.init()`. ##### Usage ```c++ @@ -256,21 +222,47 @@ Logic::start(); // Start CCL hardware ``` - ## stop() -Method for stopping the CCL hardware. +Method for stopping the CCL hardware, for example to reconfigure the logic blocks. ##### Usage ```c++ Logic::stop(); // Stop CCL ``` +## Reconfiguring +There are TWO levels of "enable protection" on the CCL hardware. According to the Silicon Errata, only one of these is intended. +As always, it's anyone's guess when or if this issue will be corrected in a future silicon revision. +The intended enable-protection is that a given logic block cannot be reconfigured while enabled. +This is handled by `init()` - you can write your new setting to a logic block, call `LogicN.init()` and it will briefly disable the logic block, make the changes, and reenable it. +The unintended layer is that no logic block can be reconfigured without also disabling the whole CCL system. +Changes can be freely made to the `Logic` classes, however, only the `init()` method will apply those changes, and you must call `Logic::stop()` before calling them, and `Logic::start()` afterwards. + +##### Example +```c++ +// logic blocks 0, 1 configured, initialized, and in use +Logic1.truth=0x55; // new truth table +Logic1.input2=tca0; // and different input 2 +Logic3.enabled=true; // enable another LUT +Logic3.input0=in::link; // Use link from LUT0 +Logic3.input1=in::ac; // and the analog comparator +Logic3.input2=in::pin; // and the LUT3 IN2 pin +Logic3.truth=0x79; // truth table for LUT3 + +Logic3.attachInterrupt(RISING,interruptFunction); + +// Interrupt now attached - but - Logic3 not enabled, and logic1 is using old settings + +Logic::stop(); // have to turn off Logic0 too, even though I might not want to +Logic1.init(); // apply changes to logic block 1 +Logic3.init(); // apply settings to logic block 3 for the first time +Logic::start(); // reenable +``` ## attachInterrupt() -Method for enabling interrupts for a specific block. +Method for enabling interrupts for a specific block. Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. -This method ins't available on tinyAVR series, as these parts cannot generate an interrupt from the CCL blocks. ##### Usage ```c++ @@ -283,10 +275,8 @@ void blinkLED() ``` - ## detachInterrupt() Method for disabling interrupts for a specific block. -This method ins't available on tinyAVR series. ##### Usage ```c++ diff --git a/megaavr/libraries/Logic/library.properties b/megaavr/libraries/Logic/library.properties index e3bb320..c57d9d9 100644 --- a/megaavr/libraries/Logic/library.properties +++ b/megaavr/libraries/Logic/library.properties @@ -1,8 +1,8 @@ name=Logic -version=1.0.2 -author=MCUdude -maintainer=MCUdude -sentence=A library for interfacing with the customizable logic in megaAVR 0-series, tinyAVR 0/1-series, and Dx-series chips +version=1.1.1 +author=MCUdude and Spence Konde +maintainer=MCUdude and Spence Konde +sentence=A library for interfacing with the customizable logic in megaAVR 0-series, tinyAVR 0/1-series, and Dx-series chips. MegaCoreX version of documentation and examples. paragraph= category=Signal Input/Output url=https://github.com/MCUdude/MegaCoreX diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 30ea058..e6b50cf 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -2,39 +2,37 @@ // Array for storing ISR function pointers #if defined(CCL_CCL_vect) -#if defined(TRUTH5) -static volatile voidFuncPtr intFuncCCL[6]; -#else -static volatile voidFuncPtr intFuncCCL[4]; -#endif + #if defined(TRUTH5) + static volatile voidFuncPtr intFuncCCL[6]; + #else + static volatile voidFuncPtr intFuncCCL[4]; + #endif #endif -struct Logic::CCLBlock -{ +struct Logic::CCLBlock { const uint8_t number; const uint8_t input0_bm; const uint8_t input1_bm; const uint8_t input2_bm; const uint8_t output_bm; const uint8_t output_alt_bm; - PORT_t& PORT_IN; - PORT_t& PORT_OUT; - PORT_t& PORT_ALT_OUT; - volatile register8_t& SEQCTRL; - volatile register8_t& LUTCTRLA; - volatile register8_t& LUTCTRLB; - volatile register8_t& LUTCTRLC; - volatile register8_t& TRUTH; + PORT_t &PORT_IN; + PORT_t &PORT_OUT; + PORT_t &PORT_ALT_OUT; + volatile register8_t &SEQCTRL; + volatile register8_t &LUTCTRLA; + volatile register8_t &LUTCTRLB; + volatile register8_t &LUTCTRLC; + volatile register8_t &TRUTH; }; -static const struct Logic::CCLBlock blocks[] = -{ -#if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ - defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ - defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ - defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ - defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ - defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) +static const struct Logic::CCLBlock blocks[] = { + #if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ + defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ + defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ + defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ + defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ + defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) { 0, PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, @@ -47,13 +45,13 @@ static const struct Logic::CCLBlock blocks[] = PORTA, PORTA, PORTA, CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, }, -#endif -#if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ - defined(__AVR_ATtiny1606__) || \ - defined(__AVR_ATtiny416__) || defined(__AVR_ATtiny816__) || \ - defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) -#define PORTMUX_CCL PORTMUX.CTRLA -#define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + #endif + #if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ + defined(__AVR_ATtiny1606__) || \ + defined(__AVR_ATtiny416__) || defined(__AVR_ATtiny816__) || \ + defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) + #define PORTMUX_CCL PORTMUX.CTRLA + #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) { 0, PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, @@ -66,12 +64,12 @@ static const struct Logic::CCLBlock blocks[] = PORTC, PORTA, PORTC, CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, }, -#endif -#if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ - defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ - defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) -#define PORTMUX_CCL PORTMUX.CTRLA -#define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + #endif + #if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ + defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ + defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) + #define PORTMUX_CCL PORTMUX.CTRLA + #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) { 0, PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, @@ -84,14 +82,142 @@ static const struct Logic::CCLBlock blocks[] = PORTC, PORTA, PORTC, CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, }, -#endif -#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ - defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__)|| \ - defined(__AVR_AVR128DA32__)|| defined(__AVR_AVR128DA28__) || \ - defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ - defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) -#define PORTMUX_CCL PORTMUX.CCLROUTEA -#define PORTMUX_ALTOUT_bm (1 << block.number) + #endif + #if defined(__AVR_ATtiny424__) || defined(__AVR_ATtiny824__) || \ + defined(__AVR_ATtiny1624__) || defined(__AVR_ATtiny3224__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, 0, 0, PIN7_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTB, PORTB, PORTA, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + 0, 0, 0, 0, PIN5_bm, + PORTC, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny826__) || \ + defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTB, PORTB, PORTA, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, 0, PIN5_bm, + PORTC, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATtiny427__) || defined(__AVR_ATtiny827__) || \ + defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTB, PORTB, PORTB, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN4_bm, PIN5_bm, + PORTC, PORTC, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ + defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ + defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) + + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + 0, 0, 0, 0, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + 0, 0, 0, 0, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ + defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ + defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) || \ + defined(__AVR_AVR64EA32__) || defined(__AVR_AVR64EA28__) || \ + defined(__AVR_AVR32EA32__) || defined(__AVR_AVR32EA28__) || \ + defined(__AVR_AVR16EA32__) || defined(__AVR_AVR16EA28__) || \ + defined(__AVR_AVR8EA32__) || defined(__AVR_AVR8EA28__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) { 0, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, @@ -104,33 +230,83 @@ static const struct Logic::CCLBlock blocks[] = PORTC, PORTC, PORTC, CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, }, + #if defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) + // These have no PD0, because it was sacrificed for VDDIO2 + { + 2, + 0, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + #else { 2, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, PORTD, PORTD, PORTD, CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, }, - { // Note: 28-Pin version doesn't have input2 and output_alt + #endif + #if defined(__AVR_AVR128DA28__)|| defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA28__) || defined(__AVR_AVR64EA28__) || \ + defined(__AVR_AVR32EA28__) || defined(__AVR_AVR16EA28__) || \ + defined(__AVR_AVR8EA28__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD28__) || defined(__AVR_AVR16DD28__) + // only has PF0, PF1, and even if RESET set GPIO, is input only + { + 3, + PIN0_bm, PIN1_bm, 0, 0, 0, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #elif defined(__AVR_AVR128DA32__)|| defined(__AVR_AVR64DA32__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR64EA32__) || \ + defined(__AVR_AVR32EA32__) || defined(__AVR_AVR16EA32__) || \ + defined(__AVR_AVR8EA32__) || defined(__AVR_AVR64DD32__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR16DD32__) + // even if RESET set GPIO, is input only + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #else + // megaAVR 0-series with 32-pins + // Note that PF6 is Reset, which must be set as GPIO to use as alt output. + { 3, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, PORTF, PORTF, PORTF, CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, }, -#endif -#if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ - defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ - defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) -#define PORTMUX_CCL PORTMUX.CCLROUTEA -#define PORTMUX_ALTOUT_bm (1 << block.number) + #endif + #endif + #if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ + defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ + defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ + defined(__AVR_AVR16EA48__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) { 0, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, PORTA, PORTA, PORTA, CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, }, - { // Note: 40-Pin version doesn't have output_alt + { + // Note: 40-Pin version doesn't have output_alt, but the parts cannot + // be programmatically distinguished - it's a 48-pin die in 40-pin package 1, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, PORTC, PORTC, PORTC, @@ -148,10 +324,13 @@ static const struct Logic::CCLBlock blocks[] = PORTF, PORTF, PORTF, CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, }, -#endif -#if defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) + #endif + #if defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) { 4, PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, @@ -160,97 +339,126 @@ static const struct Logic::CCLBlock blocks[] = }, { 5, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTG, PORTG, PORTG, + #ifdef PORTG + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTG, PORTG, PORTG, + #else + 0,0,0,0,0, + PORTA,PORTA,PORTA, + #endif CCL.SEQCTRL2, CCL.LUT5CTRLA, CCL.LUT5CTRLB, CCL.LUT5CTRLC, CCL.TRUTH5, }, -#endif + #endif }; #if defined(CCL_TRUTH0) -Logic Logic0(0); + Logic Logic0(0); #endif #if defined(CCL_TRUTH1) -Logic Logic1(1); + Logic Logic1(1); #endif #if defined(CCL_TRUTH2) -Logic Logic2(2); + Logic Logic2(2); #endif #if defined(CCL_TRUTH3) -Logic Logic3(3); + Logic Logic3(3); #endif #if defined(CCL_TRUTH4) -Logic Logic4(4); + Logic Logic4(4); #endif #if defined(CCL_TRUTH5) -Logic Logic5(5); + Logic Logic5(5); #endif Logic::Logic(const uint8_t block_number) - : enable(false), - input0(in::masked), - input1(in::masked), - input2(in::masked), - output(out::disable), - output_swap(out::no_swap), - filter(filter::disable), - edgedetect(edgedetect::disable), - truth(0x00), - sequencer(sequencer::disable), - clocksource(clocksource::clk_per), - block(blocks[block_number]) -{ + : enable(false), + input0(in::masked), + input1(in::masked), + input2(in::masked), + output(out::disable), + output_swap(out::no_swap), + filter(filter::disable), + edgedetect(edgedetect::disable), + truth(0x00), + sequencer(sequencer::disable), + clocksource(clocksource::clk_per), + block(blocks[block_number]) { } // static -void Logic::start(bool state) -{ +void Logic::start(bool state) { CCL.CTRLA = (state ? CCL_ENABLE_bm : 0); } // static -void Logic::stop() -{ +void Logic::stop() { start(false); } -static volatile register8_t& PINCTRL(PORT_t& port, const uint8_t pin_bm) -{ - if(pin_bm == PIN0_bm) return port.PIN0CTRL; - if(pin_bm == PIN1_bm) return port.PIN1CTRL; - if(pin_bm == PIN2_bm) return port.PIN2CTRL; - if(pin_bm == PIN3_bm) return port.PIN3CTRL; - if(pin_bm == PIN4_bm) return port.PIN4CTRL; - if(pin_bm == PIN5_bm) return port.PIN5CTRL; - if(pin_bm == PIN6_bm) return port.PIN6CTRL; +static volatile register8_t &PINCTRL(PORT_t &port, const uint8_t pin_bm) { + if (pin_bm == PIN0_bm) { + return port.PIN0CTRL; + } + if (pin_bm == PIN1_bm) { + return port.PIN1CTRL; + } + if (pin_bm == PIN2_bm) { + return port.PIN2CTRL; + } + if (pin_bm == PIN3_bm) { + return port.PIN3CTRL; + } + if (pin_bm == PIN4_bm) { + return port.PIN4CTRL; + } + if (pin_bm == PIN5_bm) { + return port.PIN5CTRL; + } + if (pin_bm == PIN6_bm) { + return port.PIN6CTRL; + } return port.PIN7CTRL; } -void Logic::initInput(in::input_t& input, PORT_t& port, const uint8_t pin_bm) -{ - if((input & 0x30) && pin_bm) // Input pin is either set to input or input with pullup - { +void Logic::initInput(in::input_t &input, PORT_t &port, const uint8_t pin_bm) { + if ((input & 0x30) && pin_bm) { // Input pin is either set to input or input with pullup port.DIRCLR = pin_bm; - if(input == in::input) - PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; - else + if (input == in::input) { PINCTRL(port, pin_bm) &= ~PORT_PULLUPEN_bm; - + } else { + PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; + } input = in::input; } } void Logic::init() { + // Clear LUTCTRLA in case the CCL block gets reinitialized + block.LUTCTRLA = 0x00; + + // Configure input pins initInput(input0, block.PORT_IN, block.input0_bm); initInput(input1, block.PORT_IN, block.input1_bm); initInput(input2, block.PORT_IN, block.input2_bm); - - // Clear LUTCTRLA in case the CCL block gets reinitialized - block.LUTCTRLA = 0x00; - + + // Set output pin state and output pin swap + if (output == out::enable) { + if (output_swap == out::pin_swap && block.output_alt_bm) { + #if defined(PORTMUX_CCL) + PORTMUX_CCL |= PORTMUX_ALTOUT_bm; + #endif + block.PORT_OUT.DIRSET = block.output_alt_bm; + } else if (output_swap == out::no_swap && block.output_bm) { + #if defined(PORTMUX_CCL) + PORTMUX_CCL &= ~PORTMUX_ALTOUT_bm; + #endif + block.PORT_ALT_OUT.DIRSET = block.output_bm; + } + } + // Set inputs modes block.LUTCTRLB = (input1 << CCL_INSEL1_gp) | (input0 << CCL_INSEL0_gp); block.LUTCTRLC = (input2 << CCL_INSEL2_gp); @@ -259,44 +467,26 @@ void Logic::init() block.TRUTH = truth; // Set sequencer - if (!(block.number & 0x01)) - { + if (!(block.number & 0x01)) { block.SEQCTRL = sequencer; } - // Set output pin state and output pin swap - if(output == out::enable) - { - if(output_swap == out::pin_swap && block.output_alt_bm) - { -#if defined(PORTMUX_CCL) - PORTMUX_CCL |= PORTMUX_ALTOUT_bm; -#endif - block.PORT_OUT.DIRSET = block.output_alt_bm; - } - else if(output_swap == out::no_swap && block.output_bm) - { -#if defined(PORTMUX_CCL) - PORTMUX_CCL &= ~PORTMUX_ALTOUT_bm; -#endif - block.PORT_ALT_OUT.DIRSET = block.output_bm; - } - } - // Set logic output state and output filter block.LUTCTRLA = (output ? CCL_OUTEN_bm : 0) - | (edgedetect ? CCL_EDGEDET_EN_gc : 0 ) - | (filter << CCL_FILTSEL_gp) - | (clocksource << CCL_CLKSRC_gp) - | (enable ? CCL_ENABLE_bm : 0); + | (edgedetect ? CCL_EDGEDET_EN_gc : 0) + | (filter << CCL_FILTSEL_gp) + #ifdef CCL_CLKSRC_gp + | (clocksource << CCL_CLKSRC_gp) + #else + | (clocksource << CCL_CLKSRC_bm) + #endif + | (enable ? CCL_ENABLE_bm : 0); } #if defined(CCL_CCL_vect) -void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) -{ +void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) { CCL_INTMODE0_t intmode; - switch (mode) - { + switch (mode) { // Set RISING, FALLING or CHANGE interrupt trigger for a block output case RISING: intmode = CCL_INTMODE0_RISING_gc; @@ -311,88 +501,78 @@ void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) // Only RISING, FALLING and CHANGE is supported return; } -#if defined(CCL_TRUTH4) - if (block.number > 3) - { + #if defined(CCL_TRUTH4) + if (block.number > 3) { const int16_t intmode_bp = (block.number & 0x03) * 2; CCL.INTCTRL1 = (CCL.INTCTRL1 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); - } - else - { + } else { const int16_t intmode_bp = (block.number & 0x03) * 2; CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); } -#else + #else const int16_t intmode_bp = block.number * 2; CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); -#endif + #endif // Store function pointer intFuncCCL[block.number] = userFunc; } -void Logic::detachInterrupt() -{ +void Logic::detachInterrupt() { // Disable interrupt for a given block output -#if defined(CCL_TRUTH4) - if(block.number > 4) + #if defined(CCL_TRUTH4) + if (block.number > 4) { CCL.INTCTRL1 &= ~(CCL_INTMODE1_gm << ((block.number & 3) * 2)); - else + } else { CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); -#else + } + #else CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); -#endif + #endif } // CCL interrupt service routine // Use attachIntterupt to activate this. -ISR(CCL_CCL_vect) -{ +ISR(CCL_CCL_vect) { // Check for block 0 interrupt - if(CCL.INTFLAGS & CCL_INT0_bm) - { + if (CCL.INTFLAGS & CCL_INT0_bm) { // Run user function intFuncCCL[CCL_INT0_bp](); // Clear flag CCL.INTFLAGS |= CCL_INT0_bm; } // Check for block 1 interrupt - if(CCL.INTFLAGS & CCL_INT1_bm) - { + if (CCL.INTFLAGS & CCL_INT1_bm) { // Run user function intFuncCCL[CCL_INT1_bp](); // Clear flag CCL.INTFLAGS |= CCL_INT1_bm; } // Check for block 2 interrupt - if(CCL.INTFLAGS & CCL_INT2_bm) - { + if (CCL.INTFLAGS & CCL_INT2_bm) { // Run user function intFuncCCL[CCL_INT2_bp](); // Clear flag CCL.INTFLAGS |= CCL_INT2_bm; } // Check for block 3 interrupt - if(CCL.INTFLAGS & CCL_INT3_bm) - { + if (CCL.INTFLAGS & CCL_INT3_bm) { // Run user function intFuncCCL[CCL_INT3_bp](); // Clear flag CCL.INTFLAGS |= CCL_INT3_bm; } -#if defined(TRUTH4) + #if defined(TRUTH4) // Check for block 4 interrupt - if(CCL.INTFLAGS & CCL_INT4_bm) - { + if (CCL.INTFLAGS & CCL_INT4_bm) { // Run user function intFuncCCL[CCL_INT4_bp](); // Clear flag CCL.INTFLAGS |= CCL_INT4_bm; } -#endif -#if defined(TRUTH5) + #endif + #if defined(TRUTH5) // Check for block 5 interrupt - if(CCL.INTFLAGS & CCL_INT5_bm) - { + if (CCL.INTFLAGS & CCL_INT5_bm) { // Run user function intFuncCCL[CCL_INT5_bp](); // Clear flag diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index cadd322..48c8cc3 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -3,14 +3,18 @@ #include -namespace in -{ - enum input_t : uint8_t - { -#if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ - defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__)|| \ - defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ - defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) +namespace in { + enum input_t : uint8_t { + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ + defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ + defined(__AVR_ATtiny3227__) || defined(__AVR_ATtiny3226__) || \ + defined(__AVR_ATtiny3224__) || defined(__AVR_ATtiny1627__) || \ + defined(__AVR_ATtiny1626__) || defined(__AVR_ATtiny1624__) || \ + defined(__AVR_ATtiny827__) || defined(__AVR_ATtiny826__) || \ + defined(__AVR_ATtiny824__) || defined(__AVR_ATtiny427__) || \ + defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny424__) masked = 0x00, unused = 0x00, disable = 0x00, @@ -22,19 +26,27 @@ namespace in event_b = 0x04, pin = 0x05, ac = 0x06, + uart = 0x08, usart = 0x08, spi = 0x09, tca0 = 0x0A, + tca = 0x0A, tcb = 0x0C, input_pullup = 0x15, input = 0x25, input_no_pullup = 0x25, -#elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA32__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ - defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) + #elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA32__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB32__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) masked = 0x00, unused = 0x00, disable = 0x00, @@ -50,13 +62,21 @@ namespace in usart = 0x08, spi = 0x09, tca0 = 0x0A, + tca = 0x0A, tca1 = 0x0B, tcb = 0x0C, tcd = 0x0D, input_pullup = 0x15, input = 0x25, input_no_pullup = 0x25, -#else //megaAVR-0 and 1 ATtiny + #elif defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ + defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ + defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) + // educated guess - these have at least one of everything the rest of DA-series has, + // and these lists have been super consistent since v1.0 (tinyAVR 0/1-series) masked = 0x00, unused = 0x00, disable = 0x00, @@ -67,76 +87,124 @@ namespace in event_1 = 0x04, event_b = 0x04, pin = 0x05, + ac = 0x06, + zcd = 0x07, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tcb = 0x0C, + tcd = 0x0D, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + #elif defined(__AVR_AVR64EA28__) || defined(__AVR_AVR32EA28__) || \ + defined(__AVR_AVR16EA28__) || defined(__AVR_AVR8EA28__) || \ + defined(__AVR_AVR64EA32__) || defined(__AVR_AVR32EA32__) || \ + defined(__AVR_AVR16EA32__) || defined(__AVR_AVR8EA32__) || \ + defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ + defined(__AVR_AVR16EA48__) + // educated guess based on recent consistency and which peripherals they have + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tca1 = 0x0B, + tcb = 0x0C, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + + #else //tinyAVR 0/1-series + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, ac0 = 0x06, tcb0 = 0x07, + tcb = 0x07, tca = 0x08, + tca0 = 0x08, tcd0 = 0x09, usart = 0x0A, + usart0 = 0x0A, spi = 0x0B, + spi0 = 0x0B, ac1 = 0x0C, tcb1 = 0x0D, ac2 = 0x0E, input_pullup = 0x15, input = 0x25, input_no_pullup = 0x25, -#endif + #endif }; }; // Use out:: when working with logic outputs -namespace out -{ - enum output_t : uint8_t - { +namespace out { + enum output_t : uint8_t { disable = 0x00, enable = 0x01, }; - enum pinswap_t : uint8_t - { + enum pinswap_t : uint8_t { no_swap = 0x00, pin_swap = 0x01, }; }; // Use filter:: when working with logic output filter -namespace filter -{ - enum filter_t : uint8_t - { +namespace filter { + enum filter_t : uint8_t { disable = 0x00, synchronizer = 0x01, + synch = 0x01, + sync = 0x01, filter = 0x02, }; }; // Use clocksource:: when working with logic clock source -namespace clocksource -{ - enum clocksource_t : uint8_t - { +namespace clocksource { + enum clocksource_t : uint8_t { clk_per = 0x00, in2 = 0x01, + #ifdef CCL_CLKSEL_gm oschf = 0x04, osc32k = 0x05, osc1k = 0x06, + #endif }; }; // Use edgedetect:: when using edge detection with filter -namespace edgedetect -{ - enum edgedet_t : uint8_t - { +namespace edgedetect { + enum edgedet_t : uint8_t { disable = 0x00, enable = 0x01 }; }; // Use sequencer:: when working with LUT sequencer -namespace sequencer -{ - enum sequencer_t : uint8_t - { +namespace sequencer { + enum sequencer_t : uint8_t { disable = 0x00, d_flip_flop = 0x01, jk_flip_flop = 0x02, @@ -146,18 +214,17 @@ namespace sequencer }; }; -class Logic -{ +class Logic { public: static void start(bool state = true); static void stop(); Logic(const uint8_t block_number); void init(); -#if defined(CCL_CCL_vect) + #if defined(CCL_CCL_vect) void attachInterrupt(voidFuncPtr callback, uint8_t mode); void detachInterrupt(); -#endif + #endif bool enable; in::input_t input0; @@ -174,28 +241,28 @@ class Logic struct CCLBlock; private: - const struct CCLBlock& block; + const struct CCLBlock █ - void initInput(in::input_t& input, PORT_t& port, const uint8_t pin_bm); + void initInput(in::input_t &input, PORT_t &port, const uint8_t pin_bm); }; #if defined(CCL_TRUTH0) -extern Logic Logic0; + extern Logic Logic0; #endif #if defined(CCL_TRUTH1) -extern Logic Logic1; + extern Logic Logic1; #endif #if defined(CCL_TRUTH2) -extern Logic Logic2; + extern Logic Logic2; #endif #if defined(CCL_TRUTH3) -extern Logic Logic3; + extern Logic Logic3; #endif #if defined(CCL_TRUTH4) -extern Logic Logic4; + extern Logic Logic4; #endif #if defined(CCL_TRUTH5) -extern Logic Logic5; + extern Logic Logic5; #endif #endif From 8c28b640a54de767f706b65004d249abf7dbb978 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 16 Jan 2021 23:36:23 +0100 Subject: [PATCH 206/351] Add Event system library This is an initial commit. I still have to proof-read the README and add a few examples --- megaavr/libraries/Event/README.md | 175 +++++++ megaavr/libraries/Event/keywords.txt | 50 ++ megaavr/libraries/Event/library.properties | 9 + megaavr/libraries/Event/src/Event.cpp | 175 +++++++ megaavr/libraries/Event/src/Event.h | 555 +++++++++++++++++++++ 5 files changed, 964 insertions(+) create mode 100644 megaavr/libraries/Event/README.md create mode 100644 megaavr/libraries/Event/keywords.txt create mode 100644 megaavr/libraries/Event/library.properties create mode 100644 megaavr/libraries/Event/src/Event.cpp create mode 100644 megaavr/libraries/Event/src/Event.h diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md new file mode 100644 index 0000000..c136609 --- /dev/null +++ b/megaavr/libraries/Event/README.md @@ -0,0 +1,175 @@ +# Event +A library for interfacing with the built-in Event system on the megaAVR-0 series MCUs. +Developed by [MCUdude](https://github.com/MCUdude/). + +**From the datasheet:** +> The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. +It allows a change in one peripheral (the event generator) to trigger actions in other +peripherals (the event users) through event channels, without using the CPU. +It is designed to provide short and predictable response times between peripherals, +allowing for autonomous peripheral control and interaction, and also for synchronized +timing of actions in several peripheral modules. It is thus a powerful tool for reducing +the complexity, size, and execution time of the software. + +More information about the Event system and how it works can be found in the [Microchip Application Note AN2451](http://ww1.microchip.com/downloads/en/AppNotes/DS00002451B.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). + + +## Event +Class for interfacing with the built-in Event system. Each event generator channel has its +own object. Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, +`Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make +sure you use the right channel for the task. + +In short terms: +* `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels +* `genN::rtc_div512`, `genN::rtc_div256`, `genN::rtc_div128` and `genN::rtc_div64` are only available on even numbered channels +* PIN PA0..7 and PB0..7 can only be used as event generators on channel 0 and 1 +* PIN PC0..7 and PD0..7 can only be used as event generators on channel 2 and 3 +* PIN PE0..7 and PF0..7 can only be used as event generators on channel 4 and 5 + + +## get_channel_number() +Function to get the current channel number. Useful if the channel object has been passed to a function as reference. + +### Usage +``` c++ +uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channel_number will return 0 +``` + + +## get_user_channel() +Function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. +An event generator can have multiple event users, but an event user can only have one event generator. + +### Usage +```c++ +uint8_t connected_to = Event::get_user_channel(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to +``` + + +## set_generator() +Function to assign an event generator to a channel. Note that we use prefix genN (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. + +### Usage +```c++ +Event0.set_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 +Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 +``` + +### Generator table +Below is a table with all possible generators for each channel: + +| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | +|----------------------|---------------------|--------------------|---------------------|--------------------|---------------------|--------------------|---------------------|--------------------| +| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | +| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | +| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | +| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | +| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | +| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0` | `gen5::pin_pe0` | | | +| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1` | `gen5::pin_pe1` | | | +| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2` | `gen5::pin_pe2` | | | +| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3` | `gen5::pin_pe3` | | | +| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4` | `gen3::pin_pc4` | `gen4::pin_pe4` | `gen5::pin_pe4` | | | +| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5` | `gen3::pin_pc5` | `gen4::pin_pe5` | `gen5::pin_pe5` | | | +| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6` | `gen3::pin_pc6` | `gen4::pin_pe6` | `gen5::pin_pe6` | | | +| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7` | `gen3::pin_pc7` | `gen4::pin_pe7` | `gen5::pin_pe7` | | | +| `gen::usart3_xck` | `gen0::pin_pb0` | `gen1::pin_pb0` | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | +| `gen::spi0_sck` | `gen0::pin_pb1` | `gen1::pin_pb1` | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | +| `gen::tca0_ovf_lunf` | `gen0::pin_pb2` | `gen1::pin_pb2` | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2` | `gen5::pin_pf2` | | | +| `gen::tca0_hunf` | `gen0::pin_pb3` | `gen1::pin_pb3` | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3` | `gen5::pin_pf3` | | | +| `gen::tca0_cmp0` | `gen0::pin_pb4` | `gen1::pin_pb4` | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4` | `gen5::pin_pf4` | | | +| `gen::tca0_cmp1` | `gen0::pin_pb5` | `gen1::pin_pb5` | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5` | `gen5::pin_pf5` | | | +| `gen::tca0_cmp2` | `gen0::pin_pb6` | `gen1::pin_pb6` | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | +| `gen::tcb0_capt` | `gen0::pin_pb7` | `gen1::pin_pb7` | `gen2::pin_pd7` | `gen3::pin_pd7` | `gen4::pin_pf7` | `gen5::pin_pf7` | | | +| `gen::tcb1_capt` | | | | | | | | | +| `gen::tcb2_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | + + +## get_generator() +Function to get the generator used for a particular channel. + +### Usage +```c++ +uint8_t generator_used = Event0.get_generator(); +if(generator_used == gen::ccl0_out) { + Serial.println("We're using gen::ccl0_out as generator"); +} +``` + + +## set_user() +Function to connect an event user to an event generator. Note that a generator can have multiple users. + +### Usage +```c++ +Event0.set_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 +Event0.set_user(user::evoutc); // Set EVOUTC (pin PC2) as event user +Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user +``` + +### User table +Below is a table with all possible event users: + +| Event users | +|----------------------| +| `user::ccl0_event_a` | +| `user::ccl0_event_b` | +| `user::ccl1_event_a` | +| `user::ccl1_event_b` | +| `user::ccl2_event_a` | +| `user::ccl2_event_b` | +| `user::ccl3_event_a` | +| `user::ccl3_event_b` | +| `user::adc0_start` | +| `user::evouta` | +| `user::evoutb` | +| `user::evoutc` | +| `user::evoutd` | +| `user::evoute` | +| `user::evoutf` | +| `user::usart0_irda` | +| `user::usart1_irda` | +| `user::usart2_irda` | +| `user::usart3_irda` | +| `user::tca0` | +| `user::tcb0` | +| `user::tcb1` | +| `user::tcb2` | +| `user::tcb3` | + + +## clear_user() +Function to detach a user from a channel. Note that you don't need to know what channel to detach from, simply use `Event::clear_user()`. + +### Usage +```c++ +Event::clear_user(user::evouta); // Remove the user::evouta from whatever event channel it is connected to +``` + + +## soft_event() +Creates a single software event similar to what a hardware event does. Great if you have to force trigger something! + +### Usage +```c++ +Event0.soft_event(); // Create a single software event on Event0 +``` + +## start() +Starts an event generator channel. + +### Usage +```c++ +Event0.start(); // Starts the Event0 generator channel +``` + +## stop() +Stops an event generator channel. + +# Usage +```c++ +Event0.stop(); // Stops the Event0 generator channel +``` diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt new file mode 100644 index 0000000..cacc12b --- /dev/null +++ b/megaavr/libraries/Event/keywords.txt @@ -0,0 +1,50 @@ +####################################### +# Syntax Coloring Map For Wire +####################################### + +####################################### +# Datatypes (KEYWORD1) +####################################### + + +####################################### +# Methods and Functions (KEYWORD2) +####################################### +get_channel_number KEYWORD2 +get_user_channel KEYWORD2 +set_generator KEYWORD2 +get_generator KEYWORD2 +set_user KEYWORD2 +clear_user KEYWORD2 +soft_event KEYWORD2 +start KEYWORD2 +stop KEYWORD2 + +####################################### +# Instances (KEYWORD2) +####################################### + +Event KEYWORD2 +Event0 KEYWORD2 +Event1 KEYWORD2 +Event2 KEYWORD2 +Event3 KEYWORD2 +Event4 KEYWORD2 +Event5 KEYWORD2 +Event6 KEYWORD2 +Event7 KEYWORD2 + +####################################### +# Constants (LITERAL1) +####################################### + +gen LITERAL1 +gen0 LITERAL1 +gen1 LITERAL1 +gen2 LITERAL1 +gen3 LITERAL1 +gen4 LITERAL1 +gen5 LITERAL1 +gen6 LITERAL1 +gen7 LITERAL1 +user LITERAL1 diff --git a/megaavr/libraries/Event/library.properties b/megaavr/libraries/Event/library.properties new file mode 100644 index 0000000..228af79 --- /dev/null +++ b/megaavr/libraries/Event/library.properties @@ -0,0 +1,9 @@ +name=Event System +version=1.0.0 +author=MCUdude +maintainer=MCUdude +sentence=A library for interfacing with the built-in event system +paragraph= +category=Signal Input/Output +url=https://github.com/MCUdude/MegaCoreX +architectures=megaavr diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp new file mode 100644 index 0000000..9597206 --- /dev/null +++ b/megaavr/libraries/Event/src/Event.cpp @@ -0,0 +1,175 @@ +#include "Event.h" + +// Pre-defined objects +#if defined(EVSYS_CHANNEL0) + Event Event0(0, EVSYS_CHANNEL0); +#endif +#if defined(EVSYS_CHANNEL1) + Event Event1(1, EVSYS_CHANNEL1); +#endif +#if defined(EVSYS_CHANNEL2) + Event Event2(2, EVSYS_CHANNEL2); +#endif +#if defined(EVSYS_CHANNEL3) + Event Event3(3, EVSYS_CHANNEL3); +#endif +#if defined(EVSYS_CHANNEL4) + Event Event4(4, EVSYS_CHANNEL4); +#endif +#if defined(EVSYS_CHANNEL5) + Event Event5(5, EVSYS_CHANNEL5); +#endif +#if defined(EVSYS_CHANNEL6) + Event Event6(6, EVSYS_CHANNEL6); +#endif +#if defined(EVSYS_CHANNEL7) + Event Event7(7, EVSYS_CHANNEL7); +#endif +#if defined(EVSYS_CHANNEL8) + Event Event8(8, EVSYS_CHANNEL8); +#endif +#if defined(EVSYS_CHANNEL9) + Event Event9(9, EVSYS_CHANNEL9); +#endif + + +/** + * @brief Construct a new Event object + * + * @param channel_num Event channel number + * @param channel_addr Register address to channel generator + */ +Event::Event(uint8_t channel_num, volatile uint8_t &channel_addr) + : channel_number(channel_num), channel_address(channel_addr) +{ +} + + +/** + * @brief Returns the event channel number in use + * + * @return uint8_t Event channel number + */ +uint8_t Event::get_channel_number() +{ + return channel_number; +} + + +/** + * @brief Returns the Event channel number a particular user is connected to + * + * @param event_user The event user to check + * @return int8_t Event channel number. Returns -1 if not connected to any event channel + */ +int8_t Event::get_user_channel(user::user_t event_user) +{ + // Figure out what user register to read from to based on the passed parameter + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + + // Return what channel the user is connected to + return *user_register - 1; +} + + +/** + * @brief Sets a generator for a particular event channel + * + * @param event_generator Set generator. + * Use gen:: for functionality present on all event channels. + * Use genN:: for functionality present on channel N. + */ +void Event::set_generator(uint8_t event_generator) +{ + // Store event generator setting for use in start() and stop() + generator_type = event_generator; +} + + +/** + * @brief Returns the generator type a particular channel has + * + * @return uint8_t Generator type. Returns 0 if no generator is used + */ +uint8_t Event::get_generator() +{ + return generator_type; +} + + +/** + * @brief Sets a user for a particular event channel + * + * @param event_user The event user to connect to a particular channel + */ +void Event::set_user(user::user_t event_user) +{ + // Figure out what user register to write to based on the passed parameter + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + + // Connect user to the channel we're working with + *user_register = channel_number + 1; +} + + +/** + * @brief Clears/removed a user from a particular event channel if set + * + * @param event_user The event user to remove from a particular channel + */ +void Event::clear_user(user::user_t event_user) +{ + // Figure out what user register to write to based on the passed parameter + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + + // Disconnect from event generator + *user_register = 0x00; +} + + +/** + * @brief Creates a software event for a particular event channel + * + */ +void Event::soft_event() +{ + // Write to the bit that represent the channel in the strobe register + #if defined(MEGAAVR_0) + EVSYS_STROBE = (1 << channel_number); + #elif defined(AVR_DA) || defined(AVR_DB) + if(channel_number < 8) + EVSYS_SWEVENTA = (1 << channel_number); + else + EVSYS_SWEVENTB = (1 << (channel_number - 8)); + #endif +} + + +/** + * @brief Starts the event generator for a particular event channel + * + * @param state Optional parameter. Defaults to true + */ +void Event::start(bool state) +{ + if (state) + { + // Write event generator setting to EVSYS_CHANNELn register + channel_address = generator_type; + } + else + { + // Disable event generator + channel_address = gen::disable; + } +} + + +/** + * @brief Stops the event generator for a particular event channel + * + */ +void Event::stop() +{ + start(false); +} diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h new file mode 100644 index 0000000..e76f2a4 --- /dev/null +++ b/megaavr/libraries/Event/src/Event.h @@ -0,0 +1,555 @@ +#ifndef EVENT_H +#define EVENT_H + +#include + +// Helper macros to prevent us from having to check for every possible target +#if defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ +|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ +|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ +|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) + #define MEGAAVR_0 +#elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) \ +|| defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) \ +|| defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) \ +|| defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) \ +|| defined(__AVR_AVR32DA48__) || defined(__AVR_AVR32DA32__) \ +|| defined(__AVR_AVR32DA28__) + #define AVR_DA +#elif defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) \ +|| defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) \ +|| defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) \ +|| defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) \ +|| defined(__AVR_AVR32DB48__) || defined(__AVR_AVR32DB32__) \ +|| defined(__AVR_AVR32DB28__) + #define AVR_DB +#endif + + +// Features present on all generator channels +namespace gen +{ + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + updi_synch = 0x01, + rtc_ovf = 0x06, + rtc_cmp = 0x07, + ccl0_out = 0x10, + ccl1_out = 0x11, + ccl2_out = 0x12, + ccl3_out = 0x13, + ac0_out = 0x20, + adc0_ready = 0x24, + usart0_xck = 0x60, + usart1_xck = 0x61, + usart2_xck = 0x62, + usart3_xck = 0x63, + spi0_sck = 0x68, + tca0_ovf_lunf = 0x80, + tca0_hunf = 0x81, + tca0_cmp0 = 0x84, + tca0_cmp1 = 0x85, + tca0_cmp2 = 0x86, + tcb0_capt = 0xA0, + tcb1_capt = 0xA2, + tcb2_capt = 0xA4, + tcb3_capt = 0xA6, + #if defined(AVR_DA) || defined(AVR_DB) + ccl4_out = 0x14, + ccl5_out = 0x15, + ac1_out = 0x21, + ac2_out = 0x22, + zcd0_out = 0x30, + zcd1_out = 0x31, + zcd2_out = 0x32, + usart4_xck = 0x64, + usart5_xck = 0x65, + spi1_sck = 0x69, + tca1_ovf_lunf = 0x88, + tca1_hunf = 0x89, + tca1_cmp0 = 0x8C, + tca1_cmp1 = 0x8D, + tca1_cmp2 = 0x8E, + tcb0_ovf = 0xA1, + tcb1_ovf = 0xA3, + tcb2_ovf = 0xA5, + tcb3_ovf = 0xA7, + tcb4_capt = 0xA8, + tcb4_ovf = 0xA9, + tcd0_cmpbclr = 0xB0, + tcd0_cmpaset = 0xB1, + tcd0_cmpbset = 0xB2, + tcd0_progev = 0xB3, + #endif + #if defined(AVR_DB) + mvio_ok = 0x05, + opamp0_ready = 0x34, + opamp1_ready = 0x35, + opamp2_ready = 0x36, + #endif + }; +}; + +// Features unique to event generator channel 0 +#if defined(EVSYS_CHANNEL0) + namespace gen0 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, + }; + }; +#endif + +// Features unique to event generator channel 1 +#if defined(EVSYS_CHANNEL1) + namespace gen1 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, + }; + }; +#endif + +// Features unique to event generator channel 2 +#if defined(EVSYS_CHANNEL2) + namespace gen2 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, + pin_pd0 = 0x48, + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, + pin_pd4 = 0x4C, + pin_pd5 = 0x4F, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, + }; + }; +#endif + +// Features unique to event generator channel 3 +#if defined(EVSYS_CHANNEL3) + namespace gen3 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, + pin_pd0 = 0x48, + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, + pin_pd4 = 0x4C, + pin_pd5 = 0x4F, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, + }; + }; +#endif + +// Features unique to event generator channel 4 +#if defined(EVSYS_CHANNEL4) + namespace gen4 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, + pin_pf0 = 0x48, + pin_pf1 = 0x49, + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, + pin_pf6 = 0x4E, + }; + }; +#endif + +// Features unique to event generator channel 5 +#if defined(EVSYS_CHANNEL5) + namespace gen5 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, + pin_pf0 = 0x48, + pin_pf1 = 0x49, + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, + pin_pf6 = 0x4E, + }; + }; +#endif + +// Features unique to event generator channel 6 +#if defined(EVSYS_CHANNEL6) + namespace gen6 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + #if defined(AVR_DA) || defined(AVR_DB) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, + #endif + }; + }; +#endif + +// Features unique to event generator channel 7 +#if defined(EVSYS_CHANNEL7) + namespace gen7 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + #if defined(AVR_DA) || defined(AVR_DB) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, + #endif + }; + }; +#endif + +// Features unique to event generator channel 8 +#if defined(EVSYS_CHANNEL8) + namespace gen8 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + }; + }; +#endif + +// Features unique to event generator channel 9 +#if defined(EVSYS_CHANNEL9) + namespace gen9 + { + enum generator_t : uint8_t + { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + }; + }; +#endif + +// Generator users +namespace user +{ + enum user_t : uint8_t + { + #if defined(MEGAAVR_0) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta = 0x09, + evoutb = 0x0A, + evoutc = 0x0B, + evoutd = 0x0C, + evoute = 0x0D, + evoutf = 0x0E, + usart0_irda = 0x0F, + usart1_irda = 0x10, + usart2_irda = 0x11, + usart3_irda = 0x12, + tca0 = 0x13, + tcb0 = 0x14, + tcb1 = 0x15, + tcb2 = 0x16, + tcb3 = 0x17, + #endif + #if defined(AVR_DA) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, + adc0_start = 0x0C, + ptc_start = 0x0D, + evouta = 0x0E, + evoutb = 0x0F, + evoutc = 0x10, + evoutd = 0x11, + evoute = 0x12, + evoutf = 0x13, + evoutg = 0x14, + usart0_irda = 0x15, + usart1_irda = 0x16, + usart2_irda = 0x17, + usart3_irda = 0x18, + usart4_irda = 0x19, + usart5_irda = 0x1A, + tca0_cnta = 0x1B, + tca0_cntb = 0x1C, + tca1_cnta = 0x1D, + tca1_cntb = 0x1E, + tcb0_capt = 0x1F, + tcb0_cnt = 0x20, + tcb1_capt = 0x21, + tcb1_cnt = 0x22, + tcb2_capt = 0x23, + tcb2_cnt = 0x24, + tcb3_capt = 0x25, + tcb3_cnt = 0x26, + tcb4_capt = 0x27, + tcb4_cnt = 0x28, + tcd0_in_a = 0x29, + tcd0_in_b = 0x2A, + #endif + #if defined(AVR_DB) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, + adc0_start = 0x0C, + evouta = 0x0D, + evoutb = 0x0E, + evoutc = 0x0F, + evoutd = 0x10, + evoute = 0x11, + evoutf = 0x12, + evoutg = 0x13, + usart0_irda = 0x14, + usart1_irda = 0x15, + usart2_irda = 0x16, + usart3_irda = 0x17, + usart4_irda = 0x18, + usart5_irda = 0x19, + tca0_cnta = 0x1A, + tca0_cntb = 0x1B, + tca1_cnta = 0x1C, + tca1_cntb = 0x1D, + tcb0_capt = 0x1E, + tcb0_cnt = 0x1F, + tcb1_capt = 0x20, + tcb1_cnt = 0x21, + tcb2_capt = 0x22, + tcb2_cnt = 0x23, + tcb3_capt = 0x24, + tcb3_cnt = 0x25, + tcb4_capt = 0x26, + tcb4_cnt = 0x27, + tcd0_in_a = 0x28, + tcd0_in_b = 0x29, + opamp0_enable = 0x2A, + opamp0_disable = 0x2B, + opamp0_dump = 0x2C, + opamp0_drive = 0x2D, + opamp1_enable = 0x2E, + opamp1_disable = 0x2F, + opamp1_dump = 0x30, + opamp1_drive = 0x31, + opamp2_enable = 0x32, + opamp2_disable = 0x33, + opamp2_dump = 0x34, + opamp2_drive = 0x35, + #endif + }; +}; + +class Event +{ + public: + Event(uint8_t channel_num, volatile uint8_t &channel_addr); + uint8_t get_channel_number(); + static int8_t get_user_channel(user::user_t event_user); + void set_generator(uint8_t generator); + uint8_t get_generator(); + void set_user(user::user_t event_user); + void clear_user(user::user_t event_user); + void soft_event(); + void start(bool state = true); + void stop(); + + private: + const uint8_t channel_number; // Holds the event generator channel number + volatile uint8_t &channel_address; // Reference to the event channel address + uint8_t generator_type; // Generator type the event channel is using +}; + +#if defined(EVSYS_CHANNEL0) + extern Event Event0; +#endif +#if defined(EVSYS_CHANNEL1) + extern Event Event1; +#endif +#if defined(EVSYS_CHANNEL2) + extern Event Event2; +#endif +#if defined(EVSYS_CHANNEL3) + extern Event Event3; +#endif +#if defined(EVSYS_CHANNEL4) + extern Event Event4; +#endif +#if defined(EVSYS_CHANNEL5) + extern Event Event5; +#endif +#if defined(EVSYS_CHANNEL6) + extern Event Event6; +#endif +#if defined(EVSYS_CHANNEL7) + extern Event Event7; +#endif +#if defined(EVSYS_CHANNEL8) + extern Event Event8; +#endif +#if defined(EVSYS_CHANNEL9) + extern Event Event9; +#endif + +#endif // EVENT_H From 5f565611b4997ea017480f25f97fcc7d82946efd Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 12:04:38 +0100 Subject: [PATCH 207/351] Formatting --- megaavr/libraries/Event/README.md | 18 +++++------------- 1 file changed, 5 insertions(+), 13 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index c136609..ece1890 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -3,22 +3,14 @@ A library for interfacing with the built-in Event system on the megaAVR-0 series Developed by [MCUdude](https://github.com/MCUdude/). **From the datasheet:** -> The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. -It allows a change in one peripheral (the event generator) to trigger actions in other -peripherals (the event users) through event channels, without using the CPU. -It is designed to provide short and predictable response times between peripherals, -allowing for autonomous peripheral control and interaction, and also for synchronized -timing of actions in several peripheral modules. It is thus a powerful tool for reducing -the complexity, size, and execution time of the software. +> The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. More information about the Event system and how it works can be found in the [Microchip Application Note AN2451](http://ww1.microchip.com/downloads/en/AppNotes/DS00002451B.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). ## Event -Class for interfacing with the built-in Event system. Each event generator channel has its -own object. Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, -`Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make -sure you use the right channel for the task. +Class for interfacing with the built-in Event system. Each event generator channel has its own object. +Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make sure you use the right channel for the task. In short terms: * `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels @@ -38,7 +30,7 @@ uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channe ## get_user_channel() -Function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. +Function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also, note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. An event generator can have multiple event users, but an event user can only have one event generator. ### Usage @@ -48,7 +40,7 @@ uint8_t connected_to = Event::get_user_channel(user::ccl0_event_a); // Returns t ## set_generator() -Function to assign an event generator to a channel. Note that we use prefix genN (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. +Function to assign an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. ### Usage ```c++ From bf40b53f4c5c9846e54af0502e3f7b6fe57874ba Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 19:57:35 +0100 Subject: [PATCH 208/351] Add support for EVOUT pinswap By utilizing PORTMUX_EVSYSROUTEA --- megaavr/libraries/Event/README.md | 60 ++++----- megaavr/libraries/Event/src/Event.cpp | 30 ++++- megaavr/libraries/Event/src/Event.h | 167 ++++++++++++++------------ 3 files changed, 153 insertions(+), 104 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index ece1890..7e446ec 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -103,34 +103,38 @@ Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user ``` ### User table -Below is a table with all possible event users: - -| Event users | -|----------------------| -| `user::ccl0_event_a` | -| `user::ccl0_event_b` | -| `user::ccl1_event_a` | -| `user::ccl1_event_b` | -| `user::ccl2_event_a` | -| `user::ccl2_event_b` | -| `user::ccl3_event_a` | -| `user::ccl3_event_b` | -| `user::adc0_start` | -| `user::evouta` | -| `user::evoutb` | -| `user::evoutc` | -| `user::evoutd` | -| `user::evoute` | -| `user::evoutf` | -| `user::usart0_irda` | -| `user::usart1_irda` | -| `user::usart2_irda` | -| `user::usart3_irda` | -| `user::tca0` | -| `user::tcb0` | -| `user::tcb1` | -| `user::tcb2` | -| `user::tcb3` | +Below is a table with all possible event users. +Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` + +| Event users | +|--------------------------------------------------------------------------| +| `user::ccl0_event_a` | +| `user::ccl0_event_b` | +| `user::ccl1_event_a` | +| `user::ccl1_event_b` | +| `user::ccl2_event_a` | +| `user::ccl2_event_b` | +| `user::ccl3_event_a` | +| `user::ccl3_event_b` | +| `user::adc0_start` | +| `user::evouta_pin_pa2` | +| `user::evouta_pin_pa7`
**Pin swapped variant of `evouta_pin_pa2`** | +| `user::evoutb_pin_pa2` | +| `user::evoutc_pin_pa2` | +| `user::evoutc_pin_pa7`
**Pin swapped variant of `evoutc_pin_pc2`** | +| `user::evoutd_pin_pa2` | +| `user::evoutd_pin_pa7`
**Pin swapped variant of `evoutd_pin_pd2`** | +| `user::evoute_pin_pa2` | +| `user::evoutf_pin_pa2` | +| `user::usart0_irda` | +| `user::usart1_irda` | +| `user::usart2_irda` | +| `user::usart3_irda` | +| `user::tca0` | +| `user::tcb0` | +| `user::tcb1` | +| `user::tcb2` | +| `user::tcb3` | ## clear_user() diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 9597206..2b06a27 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -105,10 +105,23 @@ uint8_t Event::get_generator() void Event::set_user(user::user_t event_user) { // Figure out what user register to write to based on the passed parameter - volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + uint8_t event_user_mask = event_user & 0x7F; + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; // Connect user to the channel we're working with *user_register = channel_number + 1; + + // Set PORTMUX pin swap for EVOUT if selected as channel generator + if (event_user & 0x80) + { + #if defined(MEGAAVR_0) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); + #elif defined(AVR_DA) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0E)); + #elif defined(AVR_DB) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0D)); + #endif + } } @@ -120,10 +133,23 @@ void Event::set_user(user::user_t event_user) void Event::clear_user(user::user_t event_user) { // Figure out what user register to write to based on the passed parameter - volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + uint8_t event_user_mask = event_user & 0x7F; + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; // Disconnect from event generator *user_register = 0x00; + + // Clear PORTMUX pin swap for EVOUT if selected as channel generator + if (event_user & 0x80) + { + #if defined(MEGAAVR_0) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); + #elif defined(AVR_DA) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0E)); + #elif defined(AVR_DB) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0D)); + #endif + } } diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index e76f2a4..28af3ea 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -372,75 +372,86 @@ namespace user enum user_t : uint8_t { #if defined(MEGAAVR_0) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - adc0_start = 0x08, - evouta = 0x09, - evoutb = 0x0A, - evoutc = 0x0B, - evoutd = 0x0C, - evoute = 0x0D, - evoutf = 0x0E, - usart0_irda = 0x0F, - usart1_irda = 0x10, - usart2_irda = 0x11, - usart3_irda = 0x12, - tca0 = 0x13, - tcb0 = 0x14, - tcb1 = 0x15, - tcb2 = 0x16, - tcb3 = 0x17, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta_pin_pa2 = 0x09, + evoutb_pin_pb2 = 0x0A, + evoutc_pin_pc2 = 0x0B, + evoutd_pin_pd2 = 0x0C, + evoute_pin_pe2 = 0x0D, + evoutf_pin_pf2 = 0x0E, + usart0_irda = 0x0F, + usart1_irda = 0x10, + usart2_irda = 0x11, + usart3_irda = 0x12, + tca0 = 0x13, + tcb0 = 0x14, + tcb1 = 0x15, + tcb2 = 0x16, + tcb3 = 0x17, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x89, + evoutc_pin_pc7 = 0x8B, + evoutd_pin_pd7 = 0x8C, #endif #if defined(AVR_DA) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - ccl4_event_a = 0x08, - ccl4_event_b = 0x09, - ccl5_event_a = 0x0A, - ccl5_event_b = 0x0B, - adc0_start = 0x0C, - ptc_start = 0x0D, - evouta = 0x0E, - evoutb = 0x0F, - evoutc = 0x10, - evoutd = 0x11, - evoute = 0x12, - evoutf = 0x13, - evoutg = 0x14, - usart0_irda = 0x15, - usart1_irda = 0x16, - usart2_irda = 0x17, - usart3_irda = 0x18, - usart4_irda = 0x19, - usart5_irda = 0x1A, - tca0_cnta = 0x1B, - tca0_cntb = 0x1C, - tca1_cnta = 0x1D, - tca1_cntb = 0x1E, - tcb0_capt = 0x1F, - tcb0_cnt = 0x20, - tcb1_capt = 0x21, - tcb1_cnt = 0x22, - tcb2_capt = 0x23, - tcb2_cnt = 0x24, - tcb3_capt = 0x25, - tcb3_cnt = 0x26, - tcb4_capt = 0x27, - tcb4_cnt = 0x28, - tcd0_in_a = 0x29, - tcd0_in_b = 0x2A, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, + adc0_start = 0x0C, + ptc_start = 0x0D, + evouta_pin_pa2 = 0x0E, + evoutb_pin_pb2 = 0x0F, + evoutc_pin_pc2 = 0x10, + evoutd_pin_pd2 = 0x11, + evoute_pin_pe2 = 0x12, + evoutf_pin_pf2 = 0x13, + evoutg_pin_pg2 = 0x14, + usart0_irda = 0x15, + usart1_irda = 0x16, + usart2_irda = 0x17, + usart3_irda = 0x18, + usart4_irda = 0x19, + usart5_irda = 0x1A, + tca0_cnta = 0x1B, + tca0_cntb = 0x1C, + tca1_cnta = 0x1D, + tca1_cntb = 0x1E, + tcb0_capt = 0x1F, + tcb0_cnt = 0x20, + tcb1_capt = 0x21, + tcb1_cnt = 0x22, + tcb2_capt = 0x23, + tcb2_cnt = 0x24, + tcb3_capt = 0x25, + tcb3_cnt = 0x26, + tcb4_capt = 0x27, + tcb4_cnt = 0x28, + tcd0_in_a = 0x29, + tcd0_in_b = 0x2A, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8E, + evoutb_pin_pb7 = 0x8F, + evoutc_pin_pc7 = 0x90, + evoutd_pin_pd7 = 0x91, + evoute_pin_pe7 = 0x92, + evoutg_pin_pg7 = 0x94, #endif #if defined(AVR_DB) ccl0_event_a = 0x00, @@ -456,13 +467,13 @@ namespace user ccl5_event_a = 0x0A, ccl5_event_b = 0x0B, adc0_start = 0x0C, - evouta = 0x0D, - evoutb = 0x0E, - evoutc = 0x0F, - evoutd = 0x10, - evoute = 0x11, - evoutf = 0x12, - evoutg = 0x13, + evouta_pin_pa2 = 0x0D, + evoutb_pin_pb2 = 0x0E, + evoutc_pin_pc2 = 0x0F, + evoutd_pin_pd2 = 0x10, + evoute_pin_pe2 = 0x11, + evoutf_pin_pf2 = 0x12, + evoutg_pin_pg2 = 0x13, usart0_irda = 0x14, usart1_irda = 0x15, usart2_irda = 0x16, @@ -497,6 +508,14 @@ namespace user opamp2_disable = 0x33, opamp2_dump = 0x34, opamp2_drive = 0x35, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8D, + evoutb_pin_pb7 = 0x8E, + evoutc_pin_pc7 = 0x8F, + evoutd_pin_pd7 = 0x90, + evoute_pin_pe7 = 0x91, + evoutf_pin_pf7 = 0x92, + evoutg_pin_pg7 = 0x93, #endif }; }; From b3b61f20678d2303cc162fff65571339b8719e64 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 20:08:09 +0100 Subject: [PATCH 209/351] Fix typos --- megaavr/libraries/Event/README.md | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 7e446ec..fe5b46a 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -119,13 +119,13 @@ Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is | `user::adc0_start` | | `user::evouta_pin_pa2` | | `user::evouta_pin_pa7`
**Pin swapped variant of `evouta_pin_pa2`** | -| `user::evoutb_pin_pa2` | -| `user::evoutc_pin_pa2` | -| `user::evoutc_pin_pa7`
**Pin swapped variant of `evoutc_pin_pc2`** | -| `user::evoutd_pin_pa2` | -| `user::evoutd_pin_pa7`
**Pin swapped variant of `evoutd_pin_pd2`** | -| `user::evoute_pin_pa2` | -| `user::evoutf_pin_pa2` | +| `user::evoutb_pin_pb2` | +| `user::evoutc_pin_pc2` | +| `user::evoutc_pin_pc7`
**Pin swapped variant of `evoutc_pin_pc2`** | +| `user::evoutd_pin_pd2` | +| `user::evoutd_pin_pd7`
**Pin swapped variant of `evoutd_pin_pd2`** | +| `user::evoute_pin_pe2` | +| `user::evoutf_pin_pf2` | | `user::usart0_irda` | | `user::usart1_irda` | | `user::usart2_irda` | From 2a4c41903015b8c010ad89a6359aba98faa55001 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 21:18:39 +0100 Subject: [PATCH 210/351] Update README Add more information about software events --- megaavr/libraries/Event/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index fe5b46a..1a410d8 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -147,7 +147,7 @@ Event::clear_user(user::evouta); // Remove the user::evouta from whatever event ## soft_event() -Creates a single software event similar to what a hardware event does. Great if you have to force trigger something! +Creates a single software event similar to what a hardware event does. Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! ### Usage ```c++ From 49b5cc2f86e96ca451976211c03fc592fcea380f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 21:18:56 +0100 Subject: [PATCH 211/351] Add examples --- .../Read_event_settings.ino | 59 ++++++++++++++++++ .../Route_logic_pins/Route_logic_pins.ino | 61 +++++++++++++++++++ .../examples/Simple_event/Simple_event.ino | 36 +++++++++++ 3 files changed, 156 insertions(+) create mode 100644 megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino create mode 100644 megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino create mode 100644 megaavr/libraries/Event/examples/Simple_event/Simple_event.ino diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino new file mode 100644 index 0000000..6cf2ec9 --- /dev/null +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -0,0 +1,59 @@ +/***********************************************************************| +| megaAVR event system library | +| | +| Read_event_settings.ino | +| | +| A library for interfacing with the megaAVR event system. | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example, we demonstrate the possibilities of reading out what | +| event channel we're working with, what generator is used, and which | +| channel an event user has been connected to. | +| | +| See Microchip's application note AN2451 for more information. | +|***********************************************************************/ + +#include + +// Function to print information about the passed event +void print_event_info(Event& my_event) +{ + Serial2.printf("This is event channel no. %d\n", my_event.get_channel_number()); + Serial2.printf("This channel uses generator no. 0x%02x, which you can find in Event.h\n", my_event.get_generator()); +} + +void print_user_info(user::user_t my_user) +{ + // Event::get_user_channel() returns -1 if the user isn't connected to any event generator + Serial2.printf("User 0x%02x is connected to event channel no. %d\n\n", my_user, Event::get_user_channel(my_user)); +} + +void setup() +{ + Serial2.begin(9600); // Initialize hardware serial port + + Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator + Event5.set_generator(gen5::pin_pe1); // Set pin PE1 as event generator + + // For more information about EVOUT, see the PORTMUX section in the datasheet + Event4.set_user(user::evoute_pin_pe2); // Set EVOUTE as event user + Event5.set_user(user::evoutf_pin_pf2); // Set EVOUTF as event user + + // Start event channels + Event4.start(); + Event5.start(); +} + +void loop() +{ + // Print info about Event4 and its event user + print_event_info(Event4); + print_user_info(user::evoute_pin_pe2); + + // Print info about Event5 and its event user + print_event_info(Event5); + print_user_info(user::evoutf_pin_pf2); + + delay(5000); +} diff --git a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino new file mode 100644 index 0000000..fce8b84 --- /dev/null +++ b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino @@ -0,0 +1,61 @@ +/***********************************************************************| +| megaAVR event system library | +| | +| Route_logic_pins.ino | +| | +| A library for interfacing with the megaAVR event system. | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use the configurable logic peripherals on the | +| megaAVR to create a 3-input AND gate using logic block 0, but we | +| utilize the event system to route logic input 0 and 1 to pins PC0 and | +| PC1 instead of the default pins. | +| Here's how 0x80 turns out to be the correct value to create a 3-input | +| AND gate: | +| 3-input AND truth table: | +| If we look at the truth table |PA2|PC1|PC0| Y | | +| to the right, we can see that |---|---|---|---| | +| all binary values for Y can | 0 | 0 | 0 | 0 | | +| be represented as 10000000. | 0 | 0 | 1 | 0 | | +| If we convert this 8-bit | 0 | 1 | 0 | 0 | | +| binary number into hex, we | 0 | 1 | 1 | 0 | | +| get 0x80. | 1 | 0 | 0 | 0 | | +| | 1 | 0 | 1 | 0 | | +| In this example the output pin, | 1 | 1 | 0 | 0 | | +| PA3 will go high if all three | 1 | 1 | 1 | 1 | | +| inputs are high. | +| | +| See Microchip's application note AN2451 for more information. | +|***********************************************************************/ + +#include +#include + +void setup() +{ + // Initialize Event channel 2 and 3 + Event2.set_generator(gen2::pin_pc0); // Set pin PC0 as event generator + Event3.set_generator(gen3::pin_pc1); // Set pin PC1 as event generator + Event2.set_user(user::ccl0_event_a); // Set CCL0 (Logic0) event A as user + Event3.set_user(user::ccl0_event_b); // Set CCL0 (Logic0) event B as user + + // Initialize logic block 0 + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::event_a; // Connect input 0 to ccl0_event_a (PC0 through Event2) + Logic0.input1 = in::event_b; // Connect input 0 to ccl0_event_b (PC1 through Event3) + Logic0.input2 = in::input; // Set PA2 as input + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.truth = 0x80; // Set truth table + Logic0.init(); + + // Start event channels and the logic hardware + Event2.start(); + Event3.start(); + Logic::start(); +} + +void loop() +{ + +} diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino new file mode 100644 index 0000000..73603ee --- /dev/null +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -0,0 +1,36 @@ +/***********************************************************************| +| megaAVR event system library | +| | +| Simple_Event.ino | +| | +| A library for interfacing with the megaAVR event system. | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we use pin PE0 as an event generator, and pin PE2 and | +| PF2 as event users. In practive, pin PE2 and PF2 will follow | +| PE0's state. | +| | +| See Microchip's application note AN2451 for more information. | +|***********************************************************************/ + +#include + +void setup() +{ + // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object + // Note that we use gen4:: to refer to functionality unique to event channel 4 + Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator + + // For more information about EVOUT, see the PORTMUX section in the datasheet + Event4.set_user(user::evoute_pin_pe2); // Set EVOUTE as event user + Event4.set_user(user::evoutf_pin_pf2); // Set EVOUTF as event user + + // Start the event channel + Event4.start(); +} + +void loop() +{ + +} From ec43b446b181eacea5fd29e1d548bf7873cf1514 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Jan 2021 23:36:02 +0100 Subject: [PATCH 212/351] Re-implement old F macro implementation for compatibility reasons. Closes #105 --- megaavr/cores/coreX-corefiles/Arduino.h | 4 ---- 1 file changed, 4 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 80b4557..1ee6ad7 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -26,10 +26,6 @@ #include #include -#undef F -#define F(str) (str) -#define __FlashStringHelper char - #ifdef __cplusplus extern "C"{ #endif From a4605d92f91eae17b0e9b74d2c7dd9715cc3abc6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 18 Jan 2021 14:33:35 +0100 Subject: [PATCH 213/351] Fix typos --- megaavr/libraries/Event/README.md | 2 +- megaavr/libraries/Event/src/Event.h | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 1a410d8..d4f5677 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -165,7 +165,7 @@ Event0.start(); // Starts the Event0 generator channel ## stop() Stops an event generator channel. -# Usage +### Usage ```c++ Event0.stop(); // Stops the Event0 generator channel ``` diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 28af3ea..3f8747a 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -5,9 +5,9 @@ // Helper macros to prevent us from having to check for every possible target #if defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ -|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ -|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ -|| defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) +|| defined(__AVR_ATmega3209__) || defined(__AVR_ATmega3208__) \ +|| defined(__AVR_ATmega1609__) || defined(__AVR_ATmega1608__) \ +|| defined(__AVR_ATmega809__) || defined(__AVR_ATmega808__) #define MEGAAVR_0 #elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) \ || defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) \ From ae9a50ef70cb8c4de1593e80f92b5e0805a4d819 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 18 Jan 2021 23:16:40 +0100 Subject: [PATCH 214/351] Add info about the event system --- README.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 6885a4b..520b82a 100644 --- a/README.md +++ b/README.md @@ -28,6 +28,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB - [Analog read resolution](#analog-read-resolution) - [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) - [Analog Comparator (AC)](#analog-comparator-ac) + - [Event System (EVSYS)](#event-system-evsys) - [Alternative pins](#alternative-pins) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) @@ -194,7 +195,10 @@ The megaAVR-0 microcontrollers are equipped with four independent configurable l ### Analog Comparator (AC) The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. -Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. +Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. + +### Event System (EVSYS) +The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. Give the [Event library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Event) a try! Here you'll find documentation and useful library examples. ### Alternative pins The megaAVR-0 microcontrollers support alternative pin assignments for some of their built-in peripherals. From 5147ce39cb0e78ff2d309daea859815b722e0c83 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 15:11:09 +0100 Subject: [PATCH 215/351] Declare Event::clear_user() static #106 related --- megaavr/libraries/Event/src/Event.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 3f8747a..d999b8f 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -529,7 +529,7 @@ class Event void set_generator(uint8_t generator); uint8_t get_generator(); void set_user(user::user_t event_user); - void clear_user(user::user_t event_user); + static void clear_user(user::user_t event_user); void soft_event(); void start(bool state = true); void stop(); From 1a26e397cae3e78b98f66d72b8afaca6af9583ba Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 15:38:23 +0100 Subject: [PATCH 216/351] Update README ... to reflect features on the megaAVR-0 chips better --- megaavr/libraries/Event/README.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index d4f5677..893c67c 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -62,18 +62,18 @@ Below is a table with all possible generators for each channel: | `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1` | `gen5::pin_pe1` | | | | `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2` | `gen5::pin_pe2` | | | | `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3` | `gen5::pin_pe3` | | | -| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4` | `gen3::pin_pc4` | `gen4::pin_pe4` | `gen5::pin_pe4` | | | -| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5` | `gen3::pin_pc5` | `gen4::pin_pe5` | `gen5::pin_pe5` | | | -| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6` | `gen3::pin_pc6` | `gen4::pin_pe6` | `gen5::pin_pe6` | | | -| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7` | `gen3::pin_pc7` | `gen4::pin_pe7` | `gen5::pin_pe7` | | | +| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4` | `gen3::pin_pc4` | | | | | +| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5` | `gen3::pin_pc5` | | | | | +| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6` | `gen3::pin_pc6` | | | | | +| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7` | `gen3::pin_pc7` | | | | | | `gen::usart3_xck` | `gen0::pin_pb0` | `gen1::pin_pb0` | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | | `gen::spi0_sck` | `gen0::pin_pb1` | `gen1::pin_pb1` | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | | `gen::tca0_ovf_lunf` | `gen0::pin_pb2` | `gen1::pin_pb2` | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2` | `gen5::pin_pf2` | | | | `gen::tca0_hunf` | `gen0::pin_pb3` | `gen1::pin_pb3` | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3` | `gen5::pin_pf3` | | | | `gen::tca0_cmp0` | `gen0::pin_pb4` | `gen1::pin_pb4` | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4` | `gen5::pin_pf4` | | | | `gen::tca0_cmp1` | `gen0::pin_pb5` | `gen1::pin_pb5` | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5` | `gen5::pin_pf5` | | | -| `gen::tca0_cmp2` | `gen0::pin_pb6` | `gen1::pin_pb6` | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | -| `gen::tcb0_capt` | `gen0::pin_pb7` | `gen1::pin_pb7` | `gen2::pin_pd7` | `gen3::pin_pd7` | `gen4::pin_pf7` | `gen5::pin_pf7` | | | +| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | +| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | | `gen::tcb1_capt` | | | | | | | | | | `gen::tcb2_capt` | | | | | | | | | | `gen::tcb3_capt` | | | | | | | | | From 547aef01268e0812bbae2214e416248e7db2d8b8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 15:39:37 +0100 Subject: [PATCH 217/351] There are AVR-DA's and DB's that doesn't have 9 event channels --- megaavr/libraries/Event/src/Event.cpp | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 2b06a27..2eef462 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -160,13 +160,22 @@ void Event::clear_user(user::user_t event_user) void Event::soft_event() { // Write to the bit that represent the channel in the strobe register - #if defined(MEGAAVR_0) - EVSYS_STROBE = (1 << channel_number); - #elif defined(AVR_DA) || defined(AVR_DB) - if(channel_number < 8) - EVSYS_SWEVENTA = (1 << channel_number); - else - EVSYS_SWEVENTB = (1 << (channel_number - 8)); + #if defined(EVSYS_STROBE) + // megaAVR 0-series + EVSYS.STROBE = (1 << channel_number); + #elif defined(EVSYS_ASYNCCH0) + // TODO: tinyAVR 0/1-series + #else + // We expect there to be an EVSYS.SWEVENTA channel plus an + // EVSYS.SWEVENTB if it has more than 8 event channels. + #if defined(EVSYS_SWEVENTB) + if(channel_number < 8) + EVSYS.SWEVENTA = (1 << channel_number); + else + EVSYS.SWEVENTB = (1 << (channel_number - 8)); + #else + EVSYS.SWEVENTA = (1 << channel_number); + #endif #endif } From 1c652f6a4c267599a10b2bce8d294cf43795690c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 18:36:40 +0100 Subject: [PATCH 218/351] Don't enable options that aren't supported for a particular megaavr-0 target --- megaavr/libraries/Event/src/Event.cpp | 12 +- megaavr/libraries/Event/src/Event.h | 184 ++++++++++++++------------ 2 files changed, 102 insertions(+), 94 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 2eef462..4163099 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -114,11 +114,11 @@ void Event::set_user(user::user_t event_user) // Set PORTMUX pin swap for EVOUT if selected as channel generator if (event_user & 0x80) { - #if defined(MEGAAVR_0) + #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); - #elif defined(AVR_DA) + #elif defined(__AVR_DA__) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0E)); - #elif defined(AVR_DB) + #elif defined(__AVR_DB__) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0D)); #endif } @@ -142,11 +142,11 @@ void Event::clear_user(user::user_t event_user) // Clear PORTMUX pin swap for EVOUT if selected as channel generator if (event_user & 0x80) { - #if defined(MEGAAVR_0) + #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); - #elif defined(AVR_DA) + #elif defined(__AVR_DA__) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0E)); - #elif defined(AVR_DB) + #elif defined(__AVR_DB__) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0D)); #endif } diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index d999b8f..ef96932 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -3,28 +3,6 @@ #include -// Helper macros to prevent us from having to check for every possible target -#if defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) \ -|| defined(__AVR_ATmega3209__) || defined(__AVR_ATmega3208__) \ -|| defined(__AVR_ATmega1609__) || defined(__AVR_ATmega1608__) \ -|| defined(__AVR_ATmega809__) || defined(__AVR_ATmega808__) - #define MEGAAVR_0 -#elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) \ -|| defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) \ -|| defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) \ -|| defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) \ -|| defined(__AVR_AVR32DA48__) || defined(__AVR_AVR32DA32__) \ -|| defined(__AVR_AVR32DA28__) - #define AVR_DA -#elif defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) \ -|| defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) \ -|| defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) \ -|| defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) \ -|| defined(__AVR_AVR32DB48__) || defined(__AVR_AVR32DB32__) \ -|| defined(__AVR_AVR32DB28__) - #define AVR_DB -#endif - // Features present on all generator channels namespace gen @@ -56,7 +34,7 @@ namespace gen tcb1_capt = 0xA2, tcb2_capt = 0xA4, tcb3_capt = 0xA6, - #if defined(AVR_DA) || defined(AVR_DB) + #if defined(__AVR_DA__) || defined(__AVR_DB__) ccl4_out = 0x14, ccl5_out = 0x15, ac1_out = 0x21, @@ -83,7 +61,7 @@ namespace gen tcd0_cmpbset = 0xB2, tcd0_progev = 0xB3, #endif - #if defined(AVR_DB) + #if defined(__AVR_DB__) mvio_ok = 0x05, opamp0_ready = 0x34, opamp1_ready = 0x35, @@ -112,14 +90,18 @@ namespace gen pin_pa5 = 0x45, pin_pa6 = 0x46, pin_pa7 = 0x47, - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4F, - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, + #endif + #if defined(Dx_64_PINS) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, + #endif }; }; #endif @@ -144,14 +126,18 @@ namespace gen pin_pa5 = 0x45, pin_pa6 = 0x46, pin_pa7 = 0x47, - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4F, - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, + #endif + #if defined(Dx_64_PINS) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, + #endif }; }; #endif @@ -172,10 +158,12 @@ namespace gen pin_pc1 = 0x41, pin_pc2 = 0x42, pin_pc3 = 0x43, - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, + #endif pin_pd0 = 0x48, pin_pd1 = 0x49, pin_pd2 = 0x4A, @@ -204,10 +192,12 @@ namespace gen pin_pc1 = 0x41, pin_pc2 = 0x42, pin_pc3 = 0x43, - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, + #endif pin_pd0 = 0x48, pin_pd1 = 0x49, pin_pd2 = 0x4A, @@ -232,20 +222,26 @@ namespace gen rtc_div4096 = 0x09, rtc_div2048 = 0x0A, rtc_div1024 = 0x0B, - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, + #endif + #if defined(Dx_64_PINS) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, + #endif pin_pf0 = 0x48, pin_pf1 = 0x49, - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, + #if !defined(Dx_28_PINS) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, + #endif pin_pf6 = 0x4E, }; }; @@ -263,20 +259,26 @@ namespace gen rtc_div256 = 0x09, rtc_div128 = 0x0A, rtc_div64 = 0x0B, - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, + #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, + #endif + #if defined(Dx_64_PINS) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, + #endif pin_pf0 = 0x48, pin_pf1 = 0x49, - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, + #if !defined(Dx_28_PINS) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, + #endif pin_pf6 = 0x4E, }; }; @@ -294,7 +296,7 @@ namespace gen rtc_div4096 = 0x09, rtc_div2048 = 0x0A, rtc_div1024 = 0x0B, - #if defined(AVR_DA) || defined(AVR_DB) + #if defined(Dx_64_PINS) pin_pg0 = 0x40, pin_pg1 = 0x41, pin_pg2 = 0x42, @@ -320,15 +322,15 @@ namespace gen rtc_div256 = 0x09, rtc_div128 = 0x0A, rtc_div64 = 0x0B, - #if defined(AVR_DA) || defined(AVR_DB) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, + #if defined(Dx_64_PINS) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, #endif }; }; @@ -371,7 +373,7 @@ namespace user { enum user_t : uint8_t { - #if defined(MEGAAVR_0) + #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) ccl0_event_a = 0x00, ccl0_event_b = 0x01, ccl1_event_a = 0x02, @@ -382,10 +384,14 @@ namespace user ccl3_event_b = 0x07, adc0_start = 0x08, evouta_pin_pa2 = 0x09, - evoutb_pin_pb2 = 0x0A, + #if defined(__AVR_ATmegax09__) + evoutb_pin_pb2 = 0x0A, + #endif evoutc_pin_pc2 = 0x0B, evoutd_pin_pd2 = 0x0C, - evoute_pin_pe2 = 0x0D, + #if defined(__AVR_ATmegax09__) + evoute_pin_pe2 = 0x0D, + #endif evoutf_pin_pf2 = 0x0E, usart0_irda = 0x0F, usart1_irda = 0x10, @@ -398,10 +404,12 @@ namespace user tcb3 = 0x17, // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX evouta_pin_pa7 = 0x89, - evoutc_pin_pc7 = 0x8B, + #if defined(__AVR_ATmegax09__) + evoutc_pin_pc7 = 0x8B, + #endif evoutd_pin_pd7 = 0x8C, #endif - #if defined(AVR_DA) + #if defined(__AVR_DA__) ccl0_event_a = 0x00, ccl0_event_b = 0x01, ccl1_event_a = 0x02, @@ -453,7 +461,7 @@ namespace user evoute_pin_pe7 = 0x92, evoutg_pin_pg7 = 0x94, #endif - #if defined(AVR_DB) + #if defined(__AVR_DB__) ccl0_event_a = 0x00, ccl0_event_b = 0x01, ccl1_event_a = 0x02, From d98a40c23b439b53a2cfd44850b63564628469ce Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 20:46:29 +0100 Subject: [PATCH 219/351] Update generator and user tables To express which targets supports which options --- megaavr/libraries/Event/README.md | 116 +++++++++++++++--------------- 1 file changed, 58 insertions(+), 58 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 893c67c..7624b15 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -49,35 +49,35 @@ Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Ev ``` ### Generator table -Below is a table with all possible generators for each channel: - -| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | -|----------------------|---------------------|--------------------|---------------------|--------------------|---------------------|--------------------|---------------------|--------------------| -| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | -| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | -| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | -| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | -| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | -| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0` | `gen5::pin_pe0` | | | -| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1` | `gen5::pin_pe1` | | | -| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2` | `gen5::pin_pe2` | | | -| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3` | `gen5::pin_pe3` | | | -| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4` | `gen3::pin_pc4` | | | | | -| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5` | `gen3::pin_pc5` | | | | | -| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6` | `gen3::pin_pc6` | | | | | -| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7` | `gen3::pin_pc7` | | | | | -| `gen::usart3_xck` | `gen0::pin_pb0` | `gen1::pin_pb0` | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | -| `gen::spi0_sck` | `gen0::pin_pb1` | `gen1::pin_pb1` | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | -| `gen::tca0_ovf_lunf` | `gen0::pin_pb2` | `gen1::pin_pb2` | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2` | `gen5::pin_pf2` | | | -| `gen::tca0_hunf` | `gen0::pin_pb3` | `gen1::pin_pb3` | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3` | `gen5::pin_pf3` | | | -| `gen::tca0_cmp0` | `gen0::pin_pb4` | `gen1::pin_pb4` | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4` | `gen5::pin_pf4` | | | -| `gen::tca0_cmp1` | `gen0::pin_pb5` | `gen1::pin_pb5` | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5` | `gen5::pin_pf5` | | | -| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | -| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | -| `gen::tcb1_capt` | | | | | | | | | -| `gen::tcb2_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | +Below is a table with all possible generators for each channel. + +| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | +|----------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|---------------------|--------------------| +| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | +| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | +| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | +| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | +| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | +| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0`
(Only available on ATmegaX809) | `gen5::pin_pe0`
(Only available on ATmegaX809) | | | +| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1`
(Only available on ATmegaX809) | `gen5::pin_pe1`
(Only available on ATmegaX809) | | | +| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2`
(Only available on ATmegaX809) | `gen5::pin_pe2`
(Only available on ATmegaX809) | | | +| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3`
(Only available on ATmegaX809) | `gen5::pin_pe3`
(Only available on ATmegaX809) | | | +| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4`
(Only available on ATmegaX809) | `gen3::pin_pc4`
(Only available on ATmegaX809) | | | | | +| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5`
(Only available on ATmegaX809) | `gen3::pin_pc5`
(Only available on ATmegaX809) | | | | | +| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6`
(Only available on ATmegaX809) | `gen3::pin_pc6`
(Only available on ATmegaX809) | | | | | +| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7`
(Only available on ATmegaX809) | `gen3::pin_pc7`
(Only available on ATmegaX809) | | | | | +| `gen::usart3_xck` | `gen0::pin_pb0`
(Only available on ATmegaX809) | `gen1::pin_pb0`
(Only available on ATmegaX809) | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | +| `gen::spi0_sck` | `gen0::pin_pb1`
(Only available on ATmegaX809) | `gen1::pin_pb1`
(Only available on ATmegaX809) | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | +| `gen::tca0_ovf_lunf` | `gen0::pin_pb2`
(Only available on ATmegaX809) | `gen1::pin_pb2`
(Only available on ATmegaX809) | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2` | `gen5::pin_pf2` | | | +| `gen::tca0_hunf` | `gen0::pin_pb3`
(Only available on ATmegaX809) | `gen1::pin_pb3`
(Only available on ATmegaX809) | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3` | `gen5::pin_pf3` | | | +| `gen::tca0_cmp0` | `gen0::pin_pb4`
(Only available on ATmegaX809) | `gen1::pin_pb4`
(Only available on ATmegaX809) | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4` | `gen5::pin_pf4` | | | +| `gen::tca0_cmp1` | `gen0::pin_pb5`
(Only available on ATmegaX809) | `gen1::pin_pb5`
(Only available on ATmegaX809) | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5` | `gen5::pin_pf5` | | | +| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | +| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | +| `gen::tcb1_capt` | | | | | | | | | +| `gen::tcb2_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | ## get_generator() @@ -106,35 +106,35 @@ Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user Below is a table with all possible event users. Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` -| Event users | -|--------------------------------------------------------------------------| -| `user::ccl0_event_a` | -| `user::ccl0_event_b` | -| `user::ccl1_event_a` | -| `user::ccl1_event_b` | -| `user::ccl2_event_a` | -| `user::ccl2_event_b` | -| `user::ccl3_event_a` | -| `user::ccl3_event_b` | -| `user::adc0_start` | -| `user::evouta_pin_pa2` | -| `user::evouta_pin_pa7`
**Pin swapped variant of `evouta_pin_pa2`** | -| `user::evoutb_pin_pb2` | -| `user::evoutc_pin_pc2` | -| `user::evoutc_pin_pc7`
**Pin swapped variant of `evoutc_pin_pc2`** | -| `user::evoutd_pin_pd2` | -| `user::evoutd_pin_pd7`
**Pin swapped variant of `evoutd_pin_pd2`** | -| `user::evoute_pin_pe2` | -| `user::evoutf_pin_pf2` | -| `user::usart0_irda` | -| `user::usart1_irda` | -| `user::usart2_irda` | -| `user::usart3_irda` | -| `user::tca0` | -| `user::tcb0` | -| `user::tcb1` | -| `user::tcb2` | -| `user::tcb3` | +| Event users | +|-------------------------------------------------------------------------------------------------------------| +| `user::ccl0_event_a` | +| `user::ccl0_event_b` | +| `user::ccl1_event_a` | +| `user::ccl1_event_b` | +| `user::ccl2_event_a` | +| `user::ccl2_event_b` | +| `user::ccl3_event_a` | +| `user::ccl3_event_b` | +| `user::adc0_start` | +| `user::evouta_pin_pa2` | +| `user::evouta_pin_pa7`
(Pin swapped variant of `evouta_pin_pa2`) | +| `user::evoutb_pin_pb2`
(Only available on ATmegaX809) | +| `user::evoutc_pin_pc2` | +| `user::evoutc_pin_pc7`
(Pin swapped variant of `evoutc_pin_pc2`)
(Only available on ATmegaX809) | +| `user::evoutd_pin_pd2` | +| `user::evoutd_pin_pd7`
(Pin swapped variant of `evoutd_pin_pd2`) | +| `user::evoute_pin_pe2`
(Only available on ATmegaX809) | +| `user::evoutf_pin_pf2` | +| `user::usart0_irda` | +| `user::usart1_irda` | +| `user::usart2_irda` | +| `user::usart3_irda` | +| `user::tca0` | +| `user::tcb0` | +| `user::tcb1` | +| `user::tcb2` | +| `user::tcb3` | ## clear_user() From e29b7c5475feccfe9be4ff1bb2f06f2ca99dbce8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 21 Jan 2021 20:51:30 +0100 Subject: [PATCH 220/351] Format user table --- megaavr/libraries/Event/README.md | 116 +++++++++++++++--------------- 1 file changed, 58 insertions(+), 58 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 7624b15..ff86b67 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -15,9 +15,9 @@ Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Ev In short terms: * `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels * `genN::rtc_div512`, `genN::rtc_div256`, `genN::rtc_div128` and `genN::rtc_div64` are only available on even numbered channels -* PIN PA0..7 and PB0..7 can only be used as event generators on channel 0 and 1 +* PIN PA0..7 and PB0..5 can only be used as event generators on channel 0 and 1 * PIN PC0..7 and PD0..7 can only be used as event generators on channel 2 and 3 -* PIN PE0..7 and PF0..7 can only be used as event generators on channel 4 and 5 +* PIN PE0..3 and PF0..6 can only be used as event generators on channel 4 and 5 ## get_channel_number() @@ -51,33 +51,33 @@ Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Ev ### Generator table Below is a table with all possible generators for each channel. -| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | -|----------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|---------------------|--------------------| -| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | -| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | -| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | -| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | -| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | -| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0`
(Only available on ATmegaX809) | `gen5::pin_pe0`
(Only available on ATmegaX809) | | | -| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1`
(Only available on ATmegaX809) | `gen5::pin_pe1`
(Only available on ATmegaX809) | | | -| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2`
(Only available on ATmegaX809) | `gen5::pin_pe2`
(Only available on ATmegaX809) | | | -| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3`
(Only available on ATmegaX809) | `gen5::pin_pe3`
(Only available on ATmegaX809) | | | -| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4`
(Only available on ATmegaX809) | `gen3::pin_pc4`
(Only available on ATmegaX809) | | | | | -| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5`
(Only available on ATmegaX809) | `gen3::pin_pc5`
(Only available on ATmegaX809) | | | | | -| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6`
(Only available on ATmegaX809) | `gen3::pin_pc6`
(Only available on ATmegaX809) | | | | | -| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7`
(Only available on ATmegaX809) | `gen3::pin_pc7`
(Only available on ATmegaX809) | | | | | -| `gen::usart3_xck` | `gen0::pin_pb0`
(Only available on ATmegaX809) | `gen1::pin_pb0`
(Only available on ATmegaX809) | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | -| `gen::spi0_sck` | `gen0::pin_pb1`
(Only available on ATmegaX809) | `gen1::pin_pb1`
(Only available on ATmegaX809) | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | -| `gen::tca0_ovf_lunf` | `gen0::pin_pb2`
(Only available on ATmegaX809) | `gen1::pin_pb2`
(Only available on ATmegaX809) | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2` | `gen5::pin_pf2` | | | -| `gen::tca0_hunf` | `gen0::pin_pb3`
(Only available on ATmegaX809) | `gen1::pin_pb3`
(Only available on ATmegaX809) | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3` | `gen5::pin_pf3` | | | -| `gen::tca0_cmp0` | `gen0::pin_pb4`
(Only available on ATmegaX809) | `gen1::pin_pb4`
(Only available on ATmegaX809) | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4` | `gen5::pin_pf4` | | | -| `gen::tca0_cmp1` | `gen0::pin_pb5`
(Only available on ATmegaX809) | `gen1::pin_pb5`
(Only available on ATmegaX809) | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5` | `gen5::pin_pf5` | | | -| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | -| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | -| `gen::tcb1_capt` | | | | | | | | | -| `gen::tcb2_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | +| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | +|----------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|------------------------------------------------------|------------------------------------------------------|---------------------|--------------------| +| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | +| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | +| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | +| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | +| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | +| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0`
(Only available on ATmegaX809) | `gen5::pin_pe0`
(Only available on ATmegaX809) | | | +| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1`
(Only available on ATmegaX809) | `gen5::pin_pe1`
(Only available on ATmegaX809) | | | +| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2`
(Only available on ATmegaX809) | `gen5::pin_pe2`
(Only available on ATmegaX809) | | | +| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3`
(Only available on ATmegaX809) | `gen5::pin_pe3`
(Only available on ATmegaX809) | | | +| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4`
(Only available on ATmegaX809) | `gen3::pin_pc4`
(Only available on ATmegaX809) | | | | | +| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5`
(Only available on ATmegaX809) | `gen3::pin_pc5`
(Only available on ATmegaX809) | | | | | +| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6`
(Only available on ATmegaX809) | `gen3::pin_pc6`
(Only available on ATmegaX809) | | | | | +| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7`
(Only available on ATmegaX809) | `gen3::pin_pc7`
(Only available on ATmegaX809) | | | | | +| `gen::usart3_xck` | `gen0::pin_pb0`
(Only available on ATmegaX809) | `gen1::pin_pb0`
(Only available on ATmegaX809) | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | +| `gen::spi0_sck` | `gen0::pin_pb1`
(Only available on ATmegaX809) | `gen1::pin_pb1`
(Only available on ATmegaX809) | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | +| `gen::tca0_ovf_lunf` | `gen0::pin_pb2`
(Only available on ATmegaX809) | `gen1::pin_pb2`
(Only available on ATmegaX809) | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2`
(Not available on 28-pin parts) | `gen5::pin_pf2`
(Not available on 28-pin parts) | | | +| `gen::tca0_hunf` | `gen0::pin_pb3`
(Only available on ATmegaX809) | `gen1::pin_pb3`
(Only available on ATmegaX809) | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3`
(Not available on 28-pin parts) | `gen5::pin_pf3`
(Not available on 28-pin parts) | | | +| `gen::tca0_cmp0` | `gen0::pin_pb4`
(Only available on ATmegaX809) | `gen1::pin_pb4`
(Only available on ATmegaX809) | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4`
(Not available on 28-pin parts) | `gen5::pin_pf4`
(Not available on 28-pin parts) | | | +| `gen::tca0_cmp1` | `gen0::pin_pb5`
(Only available on ATmegaX809) | `gen1::pin_pb5`
(Only available on ATmegaX809) | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5`
(Not available on 28-pin parts) | `gen5::pin_pf5`
(Not available on 28-pin parts) | | | +| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | +| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | +| `gen::tcb1_capt` | | | | | | | | | +| `gen::tcb2_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | +| `gen::tcb3_capt` | | | | | | | | | ## get_generator() @@ -106,35 +106,35 @@ Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user Below is a table with all possible event users. Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` -| Event users | -|-------------------------------------------------------------------------------------------------------------| -| `user::ccl0_event_a` | -| `user::ccl0_event_b` | -| `user::ccl1_event_a` | -| `user::ccl1_event_b` | -| `user::ccl2_event_a` | -| `user::ccl2_event_b` | -| `user::ccl3_event_a` | -| `user::ccl3_event_b` | -| `user::adc0_start` | -| `user::evouta_pin_pa2` | -| `user::evouta_pin_pa7`
(Pin swapped variant of `evouta_pin_pa2`) | -| `user::evoutb_pin_pb2`
(Only available on ATmegaX809) | -| `user::evoutc_pin_pc2` | -| `user::evoutc_pin_pc7`
(Pin swapped variant of `evoutc_pin_pc2`)
(Only available on ATmegaX809) | -| `user::evoutd_pin_pd2` | -| `user::evoutd_pin_pd7`
(Pin swapped variant of `evoutd_pin_pd2`) | -| `user::evoute_pin_pe2`
(Only available on ATmegaX809) | -| `user::evoutf_pin_pf2` | -| `user::usart0_irda` | -| `user::usart1_irda` | -| `user::usart2_irda` | -| `user::usart3_irda` | -| `user::tca0` | -| `user::tcb0` | -| `user::tcb1` | -| `user::tcb2` | -| `user::tcb3` | +| Event users | Notes | +|------------------------|-----------------------------------------------------------------------| +| `user::ccl0_event_a` | | +| `user::ccl0_event_b` | | +| `user::ccl1_event_a` | | +| `user::ccl1_event_b` | | +| `user::ccl2_event_a` | | +| `user::ccl2_event_b` | | +| `user::ccl3_event_a` | | +| `user::ccl3_event_b` | | +| `user::adc0_start` | | +| `user::evouta_pin_pa2` | | +| `user::evouta_pin_pa7` | Pin swapped variant of `evouta_pin_pa2` | +| `user::evoutb_pin_pb2` | Only available on ATmegaX809 | +| `user::evoutc_pin_pc2` | | +| `user::evoutc_pin_pc7` | Pin swapped variant of `evoutc_pin_pc2`. Only available on ATmegaX809 | +| `user::evoutd_pin_pd2` | | +| `user::evoutd_pin_pd7` | Pin swapped variant of `evoutd_pin_pd2` | +| `user::evoute_pin_pe2` | Only available on ATmegaX809 | +| `user::evoutf_pin_pf2` | Not available on 28-pin parts | +| `user::usart0_irda` | | +| `user::usart1_irda` | | +| `user::usart2_irda` | | +| `user::usart3_irda` | | +| `user::tca0` | | +| `user::tcb0` | | +| `user::tcb1` | | +| `user::tcb2` | | +| `user::tcb3` | | ## clear_user() From 753a4e0e8b9923992a01b711ecb1a3018d1b12ab Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 22 Jan 2021 20:28:44 +0100 Subject: [PATCH 221/351] Disable AVR-DA/DB features that aren't available + formatting --- megaavr/libraries/Event/src/Event.h | 635 ++++++++++++++++------------ 1 file changed, 358 insertions(+), 277 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index ef96932..8c64299 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -23,7 +23,9 @@ namespace gen usart0_xck = 0x60, usart1_xck = 0x61, usart2_xck = 0x62, +#if defined(USART3) usart3_xck = 0x63, +#endif spi0_sck = 0x68, tca0_ovf_lunf = 0x80, tca0_hunf = 0x81, @@ -33,40 +35,58 @@ namespace gen tcb0_capt = 0xA0, tcb1_capt = 0xA2, tcb2_capt = 0xA4, +#if defined(TCB3) tcb3_capt = 0xA6, - #if defined(__AVR_DA__) || defined(__AVR_DB__) - ccl4_out = 0x14, - ccl5_out = 0x15, - ac1_out = 0x21, - ac2_out = 0x22, - zcd0_out = 0x30, - zcd1_out = 0x31, - zcd2_out = 0x32, - usart4_xck = 0x64, - usart5_xck = 0x65, - spi1_sck = 0x69, - tca1_ovf_lunf = 0x88, - tca1_hunf = 0x89, - tca1_cmp0 = 0x8C, - tca1_cmp1 = 0x8D, - tca1_cmp2 = 0x8E, - tcb0_ovf = 0xA1, - tcb1_ovf = 0xA3, - tcb2_ovf = 0xA5, - tcb3_ovf = 0xA7, - tcb4_capt = 0xA8, - tcb4_ovf = 0xA9, - tcd0_cmpbclr = 0xB0, - tcd0_cmpaset = 0xB1, - tcd0_cmpbset = 0xB2, - tcd0_progev = 0xB3, - #endif - #if defined(__AVR_DB__) - mvio_ok = 0x05, - opamp0_ready = 0x34, - opamp1_ready = 0x35, - opamp2_ready = 0x36, - #endif +#endif +#if defined(__AVR_DA__) || defined(__AVR_DB__) + ccl4_out = 0x14, + ccl5_out = 0x15, + ac1_out = 0x21, + ac2_out = 0x22, + zcd0_out = 0x30, + zcd1_out = 0x31, +#if defined(ZCD2) + zcd2_out = 0x32, +#endif +#if defined(USART4) + usart4_xck = 0x64, +#endif +#if defined(USART5) + usart5_xck = 0x65, +#endif + spi1_sck = 0x69, +#if defined(TCA1) + tca1_ovf_lunf = 0x88, + tca1_hunf = 0x89, + tca1_cmp0 = 0x8C, + tca1_cmp1 = 0x8D, + tca1_cmp2 = 0x8E, +#endif +#if defined(TCB4) + tcb4_capt = 0xA8, +#endif + tcb0_ovf = 0xA1, + tcb1_ovf = 0xA3, + tcb2_ovf = 0xA5, +#if defined(TCB3) + tcb3_ovf = 0xA7, +#endif +#if defined(TCB4) + tcb4_ovf = 0xA9, +#endif + tcd0_cmpbclr = 0xB0, + tcd0_cmpaset = 0xB1, + tcd0_cmpbset = 0xB2, + tcd0_progev = 0xB3, +#endif // defined(__AVR_DA__) || defined(__AVR_DB__) +#if defined(__AVR_DB__) + mvio_ok = 0x05, + opamp0_ready = 0x34, + opamp1_ready = 0x35, +#if defined (OPAMP2) + opamp2_ready = 0x36, +#endif +#endif // defined(__AVR_DB__) }; }; @@ -90,18 +110,18 @@ namespace gen pin_pa5 = 0x45, pin_pa6 = 0x46, pin_pa7 = 0x47, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4F, - #endif - #if defined(Dx_64_PINS) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, +#endif +#if defined(Dx_64_PINS) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, +#endif }; }; #endif @@ -126,18 +146,18 @@ namespace gen pin_pa5 = 0x45, pin_pa6 = 0x46, pin_pa7 = 0x47, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4F, - #endif - #if defined(Dx_64_PINS) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4F, +#endif +#if defined(Dx_64_PINS) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, +#endif }; }; #endif @@ -158,12 +178,12 @@ namespace gen pin_pc1 = 0x41, pin_pc2 = 0x42, pin_pc3 = 0x43, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, +#endif pin_pd0 = 0x48, pin_pd1 = 0x49, pin_pd2 = 0x4A, @@ -192,12 +212,12 @@ namespace gen pin_pc1 = 0x41, pin_pc2 = 0x42, pin_pc3 = 0x43, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, +#endif pin_pd0 = 0x48, pin_pd1 = 0x49, pin_pd2 = 0x4A, @@ -222,26 +242,26 @@ namespace gen rtc_div4096 = 0x09, rtc_div2048 = 0x0A, rtc_div1024 = 0x0B, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, - #endif - #if defined(Dx_64_PINS) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, +#endif +#if defined(Dx_64_PINS) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, +#endif pin_pf0 = 0x48, pin_pf1 = 0x49, - #if !defined(Dx_28_PINS) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, - #endif +#if !defined(Dx_28_PINS) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, +#endif pin_pf6 = 0x4E, }; }; @@ -259,26 +279,26 @@ namespace gen rtc_div256 = 0x09, rtc_div128 = 0x0A, rtc_div64 = 0x0B, - #if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, - #endif - #if defined(Dx_64_PINS) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, - #endif +#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, +#endif +#if defined(Dx_64_PINS) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, +#endif pin_pf0 = 0x48, pin_pf1 = 0x49, - #if !defined(Dx_28_PINS) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, - #endif +#if !defined(Dx_28_PINS) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, +#endif pin_pf6 = 0x4E, }; }; @@ -296,16 +316,16 @@ namespace gen rtc_div4096 = 0x09, rtc_div2048 = 0x0A, rtc_div1024 = 0x0B, - #if defined(Dx_64_PINS) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, - #endif +#if defined(Dx_64_PINS) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif }; }; #endif @@ -322,16 +342,16 @@ namespace gen rtc_div256 = 0x09, rtc_div128 = 0x0A, rtc_div64 = 0x0B, - #if defined(Dx_64_PINS) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, - #endif +#if defined(Dx_64_PINS) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif }; }; #endif @@ -373,158 +393,219 @@ namespace user { enum user_t : uint8_t { - #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - adc0_start = 0x08, - evouta_pin_pa2 = 0x09, - #if defined(__AVR_ATmegax09__) - evoutb_pin_pb2 = 0x0A, - #endif - evoutc_pin_pc2 = 0x0B, - evoutd_pin_pd2 = 0x0C, - #if defined(__AVR_ATmegax09__) - evoute_pin_pe2 = 0x0D, - #endif - evoutf_pin_pf2 = 0x0E, - usart0_irda = 0x0F, - usart1_irda = 0x10, - usart2_irda = 0x11, - usart3_irda = 0x12, - tca0 = 0x13, - tcb0 = 0x14, - tcb1 = 0x15, - tcb2 = 0x16, - tcb3 = 0x17, - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x89, - #if defined(__AVR_ATmegax09__) - evoutc_pin_pc7 = 0x8B, - #endif - evoutd_pin_pd7 = 0x8C, - #endif - #if defined(__AVR_DA__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - ccl4_event_a = 0x08, - ccl4_event_b = 0x09, - ccl5_event_a = 0x0A, - ccl5_event_b = 0x0B, - adc0_start = 0x0C, - ptc_start = 0x0D, - evouta_pin_pa2 = 0x0E, - evoutb_pin_pb2 = 0x0F, - evoutc_pin_pc2 = 0x10, - evoutd_pin_pd2 = 0x11, - evoute_pin_pe2 = 0x12, - evoutf_pin_pf2 = 0x13, - evoutg_pin_pg2 = 0x14, - usart0_irda = 0x15, - usart1_irda = 0x16, - usart2_irda = 0x17, - usart3_irda = 0x18, - usart4_irda = 0x19, - usart5_irda = 0x1A, - tca0_cnta = 0x1B, - tca0_cntb = 0x1C, - tca1_cnta = 0x1D, - tca1_cntb = 0x1E, - tcb0_capt = 0x1F, - tcb0_cnt = 0x20, - tcb1_capt = 0x21, - tcb1_cnt = 0x22, - tcb2_capt = 0x23, - tcb2_cnt = 0x24, - tcb3_capt = 0x25, - tcb3_cnt = 0x26, - tcb4_capt = 0x27, - tcb4_cnt = 0x28, - tcd0_in_a = 0x29, - tcd0_in_b = 0x2A, - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x8E, - evoutb_pin_pb7 = 0x8F, - evoutc_pin_pc7 = 0x90, - evoutd_pin_pd7 = 0x91, - evoute_pin_pe7 = 0x92, - evoutg_pin_pg7 = 0x94, - #endif - #if defined(__AVR_DB__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - ccl4_event_a = 0x08, - ccl4_event_b = 0x09, - ccl5_event_a = 0x0A, - ccl5_event_b = 0x0B, - adc0_start = 0x0C, - evouta_pin_pa2 = 0x0D, - evoutb_pin_pb2 = 0x0E, - evoutc_pin_pc2 = 0x0F, - evoutd_pin_pd2 = 0x10, - evoute_pin_pe2 = 0x11, - evoutf_pin_pf2 = 0x12, - evoutg_pin_pg2 = 0x13, - usart0_irda = 0x14, - usart1_irda = 0x15, - usart2_irda = 0x16, - usart3_irda = 0x17, - usart4_irda = 0x18, - usart5_irda = 0x19, - tca0_cnta = 0x1A, - tca0_cntb = 0x1B, - tca1_cnta = 0x1C, - tca1_cntb = 0x1D, - tcb0_capt = 0x1E, - tcb0_cnt = 0x1F, - tcb1_capt = 0x20, - tcb1_cnt = 0x21, - tcb2_capt = 0x22, - tcb2_cnt = 0x23, - tcb3_capt = 0x24, - tcb3_cnt = 0x25, - tcb4_capt = 0x26, - tcb4_cnt = 0x27, - tcd0_in_a = 0x28, - tcd0_in_b = 0x29, - opamp0_enable = 0x2A, - opamp0_disable = 0x2B, - opamp0_dump = 0x2C, - opamp0_drive = 0x2D, - opamp1_enable = 0x2E, - opamp1_disable = 0x2F, - opamp1_dump = 0x30, - opamp1_drive = 0x31, - opamp2_enable = 0x32, - opamp2_disable = 0x33, - opamp2_dump = 0x34, - opamp2_drive = 0x35, - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x8D, - evoutb_pin_pb7 = 0x8E, - evoutc_pin_pc7 = 0x8F, - evoutd_pin_pd7 = 0x90, - evoute_pin_pe7 = 0x91, - evoutf_pin_pf7 = 0x92, - evoutg_pin_pg7 = 0x93, - #endif +#if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta_pin_pa2 = 0x09, +#if defined(__AVR_ATmegax09__) + evoutb_pin_pb2 = 0x0A, +#endif + evoutc_pin_pc2 = 0x0B, + evoutd_pin_pd2 = 0x0C, +#if defined(__AVR_ATmegax09__) + evoute_pin_pe2 = 0x0D, + #endif + evoutf_pin_pf2 = 0x0E, + usart0_irda = 0x0F, + usart1_irda = 0x10, + usart2_irda = 0x11, +#if defined(USART3) + usart3_irda = 0x12, +#endif + tca0 = 0x13, + tcb0 = 0x14, + tcb1 = 0x15, + tcb2 = 0x16, +#if defined(TCB3) + tcb3 = 0x17, +#endif + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x89, +#if defined(__AVR_ATmegax09__) + evoutc_pin_pc7 = 0x8B, +#endif + evoutd_pin_pd7 = 0x8C, +#endif // defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) +#if defined(__AVR_DA__) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, +#if defined(LUT4) + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, +#endif + adc0_start = 0x0C, + ptc_start = 0x0D, + evouta_pin_pa2 = 0x0E, +#if defined(Dx_48_PINS) || defined(Dx_64_PINS) + evoutb_pin_pb2 = 0x0F, +#endif + evoutc_pin_pc2 = 0x10, + evoutd_pin_pd2 = 0x11, +#if defined(Dx_48_PINS) || defined(Dx_64_PINS) + evoute_pin_pe2 = 0x12, +#endif +#if !defined(Dx_28_PINS) + evoutf_pin_pf2 = 0x13, +#endif +#if defined (Dx_64_PINS) + evoutg_pin_pg2 = 0x14, +#endif + usart0_irda = 0x15, + usart1_irda = 0x16, + usart2_irda = 0x17, +#if defined(USART5) + usart3_irda = 0x18, +#endif +#if defined(USART4) + usart4_irda = 0x19, +#endif +#if defined(USART5) + usart5_irda = 0x1A, +#endif + tca0_cnta = 0x1B, + tca0_cntb = 0x1C, + tca1_cnta = 0x1D, + tca1_cntb = 0x1E, + tcb0_capt = 0x1F, + tcb0_cnt = 0x20, + tcb1_capt = 0x21, + tcb1_cnt = 0x22, + tcb2_capt = 0x23, + tcb2_cnt = 0x24, +#if defined(TCB3) + tcb3_capt = 0x25, + tcb3_cnt = 0x26, +#endif +#if defined(TCB3) + tcb4_capt = 0x27, + tcb4_cnt = 0x28, +#endif + tcd0_in_a = 0x29, + tcd0_in_b = 0x2A, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8E, +#if defined(Dx_64_PINS) + evoutb_pin_pb7 = 0x8F, +#endif +#if defined(Dx_48_PINS) || defined(Dx_64_PINS) + evoutc_pin_pc7 = 0x90, +#endif + evoutd_pin_pd7 = 0x91, +#if defined(Dx_64_PINS) + evoutb_pin_pe7 = 0x92, +#endif +#if (defined(Dx_64_PINS)) + evoutb_pin_pg7 = 0x94, +#endif +#endif //defined(__AVR_DA__) +#if defined(__AVR_DB__) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, +#if defined(LUT4) + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, +#endif + adc0_start = 0x0C, + evouta_pin_pa2 = 0x0D, +#if defined(Dx_64_PINS) || defined(Dx_48_PINS) + evoutb_pin_pb2 = 0x0E, +#endif + evoutc_pin_pc2 = 0x0F, + evoutd_pin_pd2 = 0x10, +#if defined(Dx_64_PINS) || defined(Dx_48_PINS) + evoute_pin_pe2 = 0x11, +#endif +#if !defined(Dx_28_PINS) + evoutf_pin_pf2 = 0x12, +#endif +#if defined(Dx_64_PINS) + evoutg_pin_pg2 = 0x13, + #endif + usart0_irda = 0x14, + usart1_irda = 0x15, + usart2_irda = 0x16, +#if defined(USART3) + usart3_irda = 0x17, +#endif +#if defined(USART4) + usart4_irda = 0x18, +#endif +#if defined(USART5) + usart5_irda = 0x19, +#endif + tca0_cnta = 0x1A, + tca0_cntb = 0x1B, + tca1_cnta = 0x1C, + tca1_cntb = 0x1D, + tcb0_capt = 0x1E, + tcb0_cnt = 0x1F, + tcb1_capt = 0x20, + tcb1_cnt = 0x21, + tcb2_capt = 0x22, + tcb2_cnt = 0x23, +#if defined(TCB3) + tcb3_capt = 0x24, + tcb3_cnt = 0x25, +#endif +#if defined(TCB3) + tcb4_capt = 0x26, + tcb4_cnt = 0x27, +#endif + tcd0_in_a = 0x28, + tcd0_in_b = 0x29, + opamp0_enable = 0x2A, + opamp0_disable = 0x2B, + opamp0_dump = 0x2C, + opamp0_drive = 0x2D, + opamp1_enable = 0x2E, + opamp1_disable = 0x2F, + opamp1_dump = 0x30, + opamp1_drive = 0x31, +#if defined(OPAMP2) + opamp2_enable = 0x32, + opamp2_disable = 0x33, + opamp2_dump = 0x34, + opamp2_drive = 0x35, +#endif + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8D, +#if defined(Dx_64_PINS) + evoutb_pin_pb7 = 0x8E, +#endif +#if defined(Dx_48_PINS) || defined(Dx_64_PINS) + evoutc_pin_pc7 = 0x8F, +#endif + evoutd_pin_pd7 = 0x90, +#if defined(Dx_64_PINS) + evoutb_pin_pe7 = 0x91, +#endif +#if defined(Dx_64_PINS) + evoutb_pin_pg7 = 0x93, +#endif +#endif // defined(__AVR_DB__) }; }; From 6fab622afa42d313fd716fadac80cc92699f0dc6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 23 Jan 2021 12:04:03 +0100 Subject: [PATCH 222/351] Make sure Event library examples compiles on all targets --- .../Read_event_settings.ino | 21 ++++++++++--------- .../examples/Simple_event/Simple_event.ino | 10 ++++----- 2 files changed, 16 insertions(+), 15 deletions(-) diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 6cf2ec9..9d23543 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -23,6 +23,7 @@ void print_event_info(Event& my_event) Serial2.printf("This channel uses generator no. 0x%02x, which you can find in Event.h\n", my_event.get_generator()); } +// Function to print information about the passed event user void print_user_info(user::user_t my_user) { // Event::get_user_channel() returns -1 if the user isn't connected to any event generator @@ -33,27 +34,27 @@ void setup() { Serial2.begin(9600); // Initialize hardware serial port - Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator - Event5.set_generator(gen5::pin_pe1); // Set pin PE1 as event generator + Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator + Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet - Event4.set_user(user::evoute_pin_pe2); // Set EVOUTE as event user - Event5.set_user(user::evoutf_pin_pf2); // Set EVOUTF as event user + Event1.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user + Event2.set_user(user::evouta_pin_pa2); // Set EVOUTA as event user // Start event channels - Event4.start(); - Event5.start(); + Event1.start(); + Event2.start(); } void loop() { // Print info about Event4 and its event user - print_event_info(Event4); - print_user_info(user::evoute_pin_pe2); + print_event_info(Event1); + print_user_info(user::evoutc_pin_pc2); // Print info about Event5 and its event user - print_event_info(Event5); - print_user_info(user::evoutf_pin_pf2); + print_event_info(Event2); + print_user_info(user::evouta_pin_pa2); delay(5000); } diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index 73603ee..1a2d8a3 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -7,8 +7,8 @@ | Developed in 2021 by MCUdude | | https://github.com/MCUdude/ | | | -| In this example we use pin PE0 as an event generator, and pin PE2 and | -| PF2 as event users. In practive, pin PE2 and PF2 will follow | +| In this example we use pin PA7 as an event generator, and pin PC2 and | +| PD2 as event users. In practice, pin PC2 and PD2 will follow | | PE0's state. | | | | See Microchip's application note AN2451 for more information. | @@ -20,11 +20,11 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator + Event4.set_generator(gen0::pin_pa7); // Set pin PA7 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet - Event4.set_user(user::evoute_pin_pe2); // Set EVOUTE as event user - Event4.set_user(user::evoutf_pin_pf2); // Set EVOUTF as event user + Event4.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user + Event4.set_user(user::evoutd_pin_pd2); // Set EVOUTF as event user // Start the event channel Event4.start(); From b170b1e05b6686eb5de00a163262a56ae0343d77 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 23 Jan 2021 18:06:11 +0100 Subject: [PATCH 223/351] Update README --- megaavr/libraries/Event/README.md | 25 ++++++++++++++++++++++--- 1 file changed, 22 insertions(+), 3 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index ff86b67..e9110d1 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -8,6 +8,21 @@ Developed by [MCUdude](https://github.com/MCUdude/). More information about the Event system and how it works can be found in the [Microchip Application Note AN2451](http://ww1.microchip.com/downloads/en/AppNotes/DS00002451B.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). +### Level vs. Pulse events +There are two types of events - a "pulse" interrupt, which lasts for the duration of a single clock cycle (either `CLK_PER` or a relevant (slower) clock - for example, the USART XCK generator provides a pulse event which lasts one XCK period, whuich is far slower than CLK_PER), or a "level" interrupt which lasts for the duration of some condition. +Often for a given even generator or user only one or the other makes sense. Less often, for some reason or another, you may need a level event, but all you have is a pulse event - or the other way around. A [CCL module (Logic.h)](../Logic/README.md) event between the two at the cost of the logic module and one event channel. In the case of timer WO (PWM) channels, the CCL already has level inputs. + + +### Synchronization +The event system, under the hood, is asynchronous - it can react faster than the system clock (often a lot faster). +The fact that it is asynchronous usually doesn't matter, but it is one of the things one should keep in mind when using these features, because every so often it does. + + +### Some of these events are *weird* +At first glance, nore than half of the users and generators seem, at best, odd - and a good few of them might appear entirely useless. Most of the event system can only truly be understood when considering the full range of generators and users - particularly the CCL. One of the tragedies of a datasheet is that it - generally - lacks a "why". Behind every mysterious event, there is a use case that seems obscure to most people - but within some sub-field, it's common and essential. There are also times when something may seem surprising until you're more familiar with the event and logic systems in general. + + + ## Event Class for interfacing with the built-in Event system. Each event generator channel has its own object. Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make sure you use the right channel for the task. @@ -147,23 +162,27 @@ Event::clear_user(user::evouta); // Remove the user::evouta from whatever event ## soft_event() -Creates a single software event similar to what a hardware event does. Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! +Creates a single software event - users connected to that channel will react to it in the same way as they would to one caused by the generator the channel is connected to. +Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! +The software events will invert the channel, and so will trigger something regardless of whether it needs a the event channel to go high or low. ### Usage ```c++ Event0.soft_event(); // Create a single software event on Event0 ``` + ## start() -Starts an event generator channel. +Starts an event generator channel by writing the generator selected by `set_generator()` function. ### Usage ```c++ Event0.start(); // Starts the Event0 generator channel ``` + ## stop() -Stops an event generator channel. +Stops an event generator channel. The `Eventn` object retains memory of what generator it was previously set to. ### Usage ```c++ From d979a4b7fe959f94b8835288ea8b6c83b2ab14fb Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 29 Jan 2021 19:11:44 +0100 Subject: [PATCH 224/351] Mute unused parameter warnings for Nano Every --- megaavr/libraries/Wire/src/Wire.cpp | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index 7d10f19..355423a 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -79,8 +79,12 @@ bool TwoWire::pins(uint8_t sda_pin, uint8_t scl_pin) PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return false; } - +#else + (void)sda_pin; // Mute unused parameter warning + (void)scl_pin; + return false; #endif + } bool TwoWire::swap(uint8_t state) @@ -104,8 +108,10 @@ bool TwoWire::swap(uint8_t state) PORTMUX.TWISPIROUTEA = TWI_MUX | (PORTMUX.TWISPIROUTEA & ~(3 << 4)); return true; } -#endif +#else + (void)state; // Mute unused parameter warning return false; +#endif } void TwoWire::begin(void) From 2415f241715185f7a79e8bab1a571397161f8442 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 29 Jan 2021 19:27:32 +0100 Subject: [PATCH 225/351] Disable PF2and PF3 on Nano Every ... on TWI init because these are hardwired to the i2c pins. Closes #109 --- megaavr/libraries/Wire/src/utility/twi.c | 27 +++++++++++++++++++----- 1 file changed, 22 insertions(+), 5 deletions(-) diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 28743c5..8704cb9 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -68,14 +68,22 @@ void TWI_MasterInit(uint32_t frequency) // Enable input pullup for the default or pin swapped pin position if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) { - pinMode(PIN_WIRE_SDA, INPUT_PULLUP); - pinMode(PIN_WIRE_SCL, INPUT_PULLUP); + +// Disable pins hardwired to the default i2c pins (PA2 and PA3) +#if defined(NANO_EVERY_PINOUT) + PORTF_PIN2CTRL &= ~PORT_PULLUPEN_bm; // Disable PF2 pullup + PORTF_PIN3CTRL &= ~PORT_PULLUPEN_bm; // Disable PF3 pullup + PORTF_DIRCLR |= PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs +#endif + + pinMode(PIN_WIRE_SDA, INPUT_PULLUP); // Enable PA2 pullup + pinMode(PIN_WIRE_SCL, INPUT_PULLUP); // Enable PA3 pullup } #if defined(PIN_WIRE_SDA_PINSWAP_1) && defined(PIN_WIRE_SCL_PINSWAP_1) else if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX_PINSWAP) { - pinMode(PIN_WIRE_SDA_PINSWAP_1, INPUT_PULLUP); - pinMode(PIN_WIRE_SCL_PINSWAP_1, INPUT_PULLUP); + pinMode(PIN_WIRE_SDA_PINSWAP_1, INPUT_PULLUP); // Enable PC2 pullup + pinMode(PIN_WIRE_SCL_PINSWAP_1, INPUT_PULLUP); // Enable PC3 pullup } #endif @@ -105,6 +113,16 @@ void TWI_SlaveInit(uint8_t address, uint8_t receive_broadcast, uint8_t second_ad if (twi_mode != TWI_MODE_UNKNOWN) return; + // Disable pins hardwired to the default i2c pins (PA2 and PA3) +#if defined(NANO_EVERY_PINOUT) + if ((PORTMUX.TWISPIROUTEA & 0x30) == TWI_MUX) + { + PORTF_PIN2CTRL &= ~PORT_PULLUPEN_bm; // Disable PF2 pullup + PORTF_PIN3CTRL &= ~PORT_PULLUPEN_bm; // Disable PF3 pullup + PORTF_DIRCLR |= PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs + } +#endif + twi_mode = TWI_MODE_SLAVE; slave_bytesRead = 0; @@ -132,7 +150,6 @@ void TWI_Flush(void) * TWI module disable function. * Disables both master and slave modes * - * \param frequency The required baud. */ void TWI_Disable(void) { From 94fa8b8aa85ac242856c254e158b0634b0b2ec4a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 5 Feb 2021 22:02:41 +0100 Subject: [PATCH 226/351] Update PlatformIO programmers section --- PlatformIO.md | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/PlatformIO.md b/PlatformIO.md index 08e0b0e..87b885d 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -244,8 +244,19 @@ Holds the serial port used for uploading. Only needed if you're uploading using ### `upload_protocol` -Used when using a programmer rather than using a USB to serial adapter. -Supports all Avrdude compatible UPDI programmers such as `jtag2updi`, `xplainedmini_updi` and `curiosity_updi`. +Programmer used for uploading. + +| Supported UPDI programmers in Avrdude | Notes | +|---------------------------------------|------------------------------------------------------------------------------------------------------------------| +| `jtag2updi` | Requires upload port | +| `arduino` | Used when uploading using the Optiboot bootloader. Requires upload port | +| `xplainedmini_updi` | Xplained Mini (mEDBG) and [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) programmers | +| `pkobn_updi` | On-board Curiosity nano programmer (nEDBG) | +| `pickit4_updi` | PICkit4 programmer in UPDI mode | +| `snap_updi` | MPLAB SNAP programmer in UPDI mode | +| `atmelice_updi` | Atmel ICE programmer in UPDI mode | +| `xplainedpro_updi` | Xplained Pro in UPDI mode | +| `powerdebugger_updi` | Power Debugger in UPDI mode | ### `upload_flags` From 2a184bf11b91a4c55c7f1817f232f70aeda54a9b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 5 Feb 2021 22:39:30 +0100 Subject: [PATCH 227/351] Fix typos and improve language --- megaavr/libraries/Comparator/README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index a2d1ba1..74139e5 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -6,7 +6,7 @@ More useful information about the analog comparator can be found in the [Microch ## Comparator -Class for interfacing with the built-in comparator. use the predefined objects `Comparator` or `Comparator0`. +Class for interfacing with the built-in comparator. Use the predefined objects `Comparator` or `Comparator0`. ### input_p @@ -35,7 +35,7 @@ Accepted values: in_n::in0; // Use positive input pin 0 (PD3) as input in_n::in1; // Use positive input pin 1 (PD5) as input in_n::in2; // Use positive input pin 2 (PD7) as input -in_p::dacref; // Use DACREF as input +in_n::dacref; // Use DACREF as input ``` ##### Usage @@ -48,7 +48,7 @@ Comparator.input_n = in_n::in0; // Connect negative input pin 0 to the negative ### reference -Variable for setting what reference voltage the DACREF should use. This voltage is internally generated. +Variable for setting what reference voltage the DACREF should be derived from. This voltage is internally generated. Accepted values: ``` c++ ref::disable; // Do not use any reference @@ -70,7 +70,7 @@ Comparator.reference = ref::vref_2v5; // Use the internal 2.5V reference for th ### dacref -Variable for setting the DACREF value. The DACREF voltage is the voltage that the comparator uses as it's reference. +Variable for setting the DACREF value. This voltage can be selected as the input for the negative side of the comparator. This is the formula for the DACREF output voltage: From 400e5d8e095fa6c468f17c64f294808a0b134ef4 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 7 Feb 2021 21:53:06 +0100 Subject: [PATCH 228/351] Remove reference to MightyCore --- PlatformIO.md | 1 - 1 file changed, 1 deletion(-) diff --git a/PlatformIO.md b/PlatformIO.md index 87b885d..0d3a6d1 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -233,7 +233,6 @@ This parameter is used to set compiler flags. This is useful if you want to for | -DSERIAL_RX_BUFFER_SIZE=128 | 64 bytes | Sets the serial RX buffer to 128 bytes | | -DSERIAL_TX_BUFFER_SIZE=128 | 64 bytes | Sets the serial TX buffer to 128 bytes | | -DTWI_BUFFER_SIZE=64 | 32 bytes | Sets the TWI (i2c) buffer to 64 bytes | -| -DTWI1_BUFFER_SIZE=64 | 32 bytes | Sets the TWI1 (i2c) buffer to 64 bytes (ATmega324PB only) | **Example:** `build_flags = -DSERIAL_RX_BUFFER_SIZE=128 -DSERIAL_TX_BUFFER_SIZE=128` From d5b38c4fc0a55ba427186c660bac6286367a7065 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 7 Feb 2021 21:56:39 +0100 Subject: [PATCH 229/351] Rename TWI buffer size macro and make ut user definable This means you can define the TWI buffer size if you need to --- megaavr/libraries/Wire/src/Wire.cpp | 14 +++++++------- megaavr/libraries/Wire/src/Wire.h | 10 ++++++---- 2 files changed, 13 insertions(+), 11 deletions(-) diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index 355423a..8bc3ead 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -34,12 +34,12 @@ extern "C" // Initialize Class Variables ////////////////////////////////////////////////// -uint8_t TwoWire::rxBuffer[BUFFER_LENGTH]; +uint8_t TwoWire::rxBuffer[TWI_BUFFER_SIZE]; uint8_t TwoWire::rxBufferIndex = 0; //head uint8_t TwoWire::rxBufferLength = 0; //tail uint8_t TwoWire::txAddress = 0; -uint8_t TwoWire::txBuffer[BUFFER_LENGTH]; +uint8_t TwoWire::txBuffer[TWI_BUFFER_SIZE]; uint8_t TwoWire::txBufferIndex = 0; //head uint8_t TwoWire::txBufferLength = 0; //tail @@ -136,7 +136,7 @@ void TwoWire::begin(uint8_t address, bool receive_broadcast, uint8_t second_addr TWI_SlaveInit(address, receive_broadcast, second_address); TWI_attachSlaveTxEvent(onRequestService, txBuffer); // default callback must exist - TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, BUFFER_LENGTH); // default callback must exist + TWI_attachSlaveRxEvent(onReceiveService, rxBuffer, TWI_BUFFER_SIZE); // default callback must exist } void TwoWire::begin(int address, bool receive_broadcast, uint8_t second_address) @@ -176,9 +176,9 @@ void TwoWire::setClock(uint32_t frequency) uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity, bool sendStop) { - if (quantity > BUFFER_LENGTH) + if (quantity > TWI_BUFFER_SIZE) { - quantity = BUFFER_LENGTH; + quantity = TWI_BUFFER_SIZE; } uint8_t bytes_read = TWI_MasterRead(address, rxBuffer, quantity, sendStop); @@ -268,7 +268,7 @@ uint8_t TwoWire::endTransmission(void) size_t TwoWire::write(uint8_t data) { /* Check if buffer is full */ - if (txBufferLength >= BUFFER_LENGTH) + if (txBufferLength >= TWI_BUFFER_SIZE) { setWriteError(); return 0; @@ -342,7 +342,7 @@ int TwoWire::peek() void TwoWire::flush() { // /* Clear buffers */ - // for(uint8_t i = 0; i < BUFFER_LENGTH; i++){ + // for(uint8_t i = 0; i < TWI_BUFFER_SIZE; i++){ // txBuffer[i] = 0; // rxBuffer[i] = 0; // } diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index d320c61..45db79e 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -24,14 +24,16 @@ #include +#ifndef TWI_BUFFER_SIZE #if ((RAMEND - RAMSTART) < 1023) -#define BUFFER_LENGTH 16 +#define TWI_BUFFER_SIZE 16 #elif ((RAMEND - RAMSTART) < 4095) -#define BUFFER_LENGTH 32 +#define TWI_BUFFER_SIZE 32 #elif ((RAMEND - RAMSTART) < 8191) -#define BUFFER_LENGTH 64 +#define TWI_BUFFER_SIZE 64 #else -#define BUFFER_LENGTH 128 +#define TWI_BUFFER_SIZE 128 +#endif #endif // WIRE_HAS_END means Wire has end() From 112fb3e0800f1b80daf4278f07083ae86f2f8f4a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 7 Feb 2021 21:57:10 +0100 Subject: [PATCH 230/351] Formatting --- megaavr/libraries/Event/src/Event.h | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 8c64299..9fe69d2 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -61,9 +61,6 @@ namespace gen tca1_cmp0 = 0x8C, tca1_cmp1 = 0x8D, tca1_cmp2 = 0x8E, -#endif -#if defined(TCB4) - tcb4_capt = 0xA8, #endif tcb0_ovf = 0xA1, tcb1_ovf = 0xA3, @@ -72,6 +69,7 @@ namespace gen tcb3_ovf = 0xA7, #endif #if defined(TCB4) + tcb4_capt = 0xA8, tcb4_ovf = 0xA9, #endif tcd0_cmpbclr = 0xB0, From 85021fe18c3f924752e9f4612ec764955ee839ec Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 9 Feb 2021 20:46:53 +0100 Subject: [PATCH 231/351] Add another valid MPLAB SNAP USB PID --- megaavr/avrdude.conf | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 61c8b5c..d92878f 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -1252,7 +1252,7 @@ programmer desc = "MPLAB(R) PICkit 4 in UPDI mode"; type = "jtagice3_updi"; connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; + usbpid = 0x2177, 0x2178, 0x2179, 0x9018; ; programmer From 8414d1f16b3e703b1c2b251a219e0d9b4b193143 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 28 Mar 2021 13:19:48 +0200 Subject: [PATCH 232/351] Remove HID library The megaAVR-0 series doesn't have any built-in USB hardware anyways --- megaavr/libraries/HID/keywords.txt | 21 --- megaavr/libraries/HID/library.properties | 9 -- megaavr/libraries/HID/src/HID.cpp | 183 ----------------------- megaavr/libraries/HID/src/HID.h | 134 ----------------- 4 files changed, 347 deletions(-) delete mode 100644 megaavr/libraries/HID/keywords.txt delete mode 100644 megaavr/libraries/HID/library.properties delete mode 100644 megaavr/libraries/HID/src/HID.cpp delete mode 100644 megaavr/libraries/HID/src/HID.h diff --git a/megaavr/libraries/HID/keywords.txt b/megaavr/libraries/HID/keywords.txt deleted file mode 100644 index 32a9ba5..0000000 --- a/megaavr/libraries/HID/keywords.txt +++ /dev/null @@ -1,21 +0,0 @@ -####################################### -# Syntax Coloring Map HID -####################################### - -####################################### -# Datatypes (KEYWORD1) -####################################### - -HID KEYWORD1 - -####################################### -# Methods and Functions (KEYWORD2) -####################################### -begin KEYWORD2 -SendReport KEYWORD2 -AppendDescriptor KEYWORD2 - -####################################### -# Constants (LITERAL1) -####################################### -HID_TX LITERAL1 \ No newline at end of file diff --git a/megaavr/libraries/HID/library.properties b/megaavr/libraries/HID/library.properties deleted file mode 100644 index 499286d..0000000 --- a/megaavr/libraries/HID/library.properties +++ /dev/null @@ -1,9 +0,0 @@ -name=HID -version=1.0 -author=Arduino -maintainer=Arduino -sentence=Module for PluggableUSB infrastructure. Exposes an API for devices like Keyboards, Mice and Gamepads. -paragraph= -category=Communication -url=http://www.arduino.cc/en/Reference/HID -architectures=megaavr diff --git a/megaavr/libraries/HID/src/HID.cpp b/megaavr/libraries/HID/src/HID.cpp deleted file mode 100644 index 32ad860..0000000 --- a/megaavr/libraries/HID/src/HID.cpp +++ /dev/null @@ -1,183 +0,0 @@ -/* - Copyright (c) 2015, Arduino LLC - Original code (pre-library): Copyright (c) 2011, Peter Barrett - - Permission to use, copy, modify, and/or distribute this software for - any purpose with or without fee is hereby granted, provided that the - above copyright notice and this permission notice appear in all copies. - - THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL - WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED - WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR - BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES - OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, - WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, - ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS - SOFTWARE. - */ - -#include "HID.h" - -#if defined(USBCON) - -HID_& HID() -{ - static HID_ obj; - return obj; -} - -int HID_::getInterface(uint8_t* interfaceCount) -{ - *interfaceCount += 1; // uses 1 - HIDDescriptor hidInterface = { - D_INTERFACE(pluggedInterface, 1, USB_DEVICE_CLASS_HUMAN_INTERFACE, HID_SUBCLASS_NONE, HID_PROTOCOL_NONE), - D_HIDREPORT(descriptorSize), - D_ENDPOINT(USB_ENDPOINT_IN(pluggedEndpoint), USB_ENDPOINT_TYPE_INTERRUPT, USB_EP_SIZE, 0x01)}; - return USB_SendControl(0, &hidInterface, sizeof(hidInterface)); -} - -int HID_::getDescriptor(USBSetup& setup) -{ - // Check if this is a HID Class Descriptor request - if (setup.bmRequestType != REQUEST_DEVICETOHOST_STANDARD_INTERFACE) - { - return 0; - } - if (setup.wValueH != HID_REPORT_DESCRIPTOR_TYPE) - { - return 0; - } - - // In a HID Class Descriptor wIndex cointains the interface number - if (setup.wIndex != pluggedInterface) - { - return 0; - } - - int total = 0; - HIDSubDescriptor* node; - for (node = rootNode; node; node = node->next) - { - int res = USB_SendControl(TRANSFER_PGM, node->data, node->length); - if (res == -1) - return -1; - total += res; - } - - // Reset the protocol on reenumeration. Normally the host should not assume the state of the protocol - // due to the USB specs, but Windows and Linux just assumes its in report mode. - protocol = HID_REPORT_PROTOCOL; - - return total; -} - -uint8_t HID_::getShortName(char* name) -{ - name[0] = 'H'; - name[1] = 'I'; - name[2] = 'D'; - name[3] = 'A' + (descriptorSize & 0x0F); - name[4] = 'A' + ((descriptorSize >> 4) & 0x0F); - return 5; -} - -void HID_::AppendDescriptor(HIDSubDescriptor* node) -{ - if (!rootNode) - { - rootNode = node; - } - else - { - HIDSubDescriptor* current = rootNode; - while (current->next) - { - current = current->next; - } - current->next = node; - } - descriptorSize += node->length; -} - -int HID_::SendReport(uint8_t id, const void* data, int len) -{ - auto ret = USB_Send(pluggedEndpoint, &id, 1); - if (ret < 0) return ret; - auto ret2 = USB_Send(pluggedEndpoint | TRANSFER_RELEASE, data, len); - if (ret2 < 0) return ret2; - return ret + ret2; -} - -bool HID_::setup(USBSetup& setup) -{ - if (pluggedInterface != setup.wIndex) - { - return false; - } - - uint8_t request = setup.bRequest; - uint8_t requestType = setup.bmRequestType; - - if (requestType == REQUEST_DEVICETOHOST_CLASS_INTERFACE) - { - if (request == HID_GET_REPORT) - { - // TODO: HID_GetReport(); - return true; - } - if (request == HID_GET_PROTOCOL) - { - // TODO: Send8(protocol); - return true; - } - if (request == HID_GET_IDLE) - { - // TODO: Send8(idle); - } - } - - if (requestType == REQUEST_HOSTTODEVICE_CLASS_INTERFACE) - { - if (request == HID_SET_PROTOCOL) - { - // The USB Host tells us if we are in boot or report mode. - // This only works with a real boot compatible device. - protocol = setup.wValueL; - return true; - } - if (request == HID_SET_IDLE) - { - idle = setup.wValueL; - return true; - } - if (request == HID_SET_REPORT) - { - //uint8_t reportID = setup.wValueL; - //uint16_t length = setup.wLength; - //uint8_t data[length]; - // Make sure to not read more data than USB_EP_SIZE. - // You can read multiple times through a loop. - // The first byte (may!) contain the reportID on a multreport. - //USB_RecvControl(data, length); - } - } - - return false; -} - -HID_::HID_(void) : PluggableUSBModule(1, 1, epType), - rootNode(NULL), - descriptorSize(0), - protocol(HID_REPORT_PROTOCOL), - idle(1) -{ - epType[0] = EP_TYPE_INTERRUPT_IN; - PluggableUSB().plug(this); -} - -int HID_::begin(void) -{ - return 0; -} - -#endif /* if defined(USBCON) */ diff --git a/megaavr/libraries/HID/src/HID.h b/megaavr/libraries/HID/src/HID.h deleted file mode 100644 index 2f7bbb8..0000000 --- a/megaavr/libraries/HID/src/HID.h +++ /dev/null @@ -1,134 +0,0 @@ -/* - Copyright (c) 2015, Arduino LLC - Original code (pre-library): Copyright (c) 2011, Peter Barrett - - Permission to use, copy, modify, and/or distribute this software for - any purpose with or without fee is hereby granted, provided that the - above copyright notice and this permission notice appear in all copies. - - THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL - WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED - WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR - BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES - OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, - WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, - ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS - SOFTWARE. - */ - -#ifndef HID_h -#define HID_h - -#include -#include - -#include "api/PluggableUSB.h" - -#if defined(USBCON) - -#define _USING_HID - -// HID 'Driver' -// ------------ -#define HID_GET_REPORT 0x01 -#define HID_GET_IDLE 0x02 -#define HID_GET_PROTOCOL 0x03 -#define HID_SET_REPORT 0x09 -#define HID_SET_IDLE 0x0A -#define HID_SET_PROTOCOL 0x0B - -#define HID_HID_DESCRIPTOR_TYPE 0x21 -#define HID_REPORT_DESCRIPTOR_TYPE 0x22 -#define HID_PHYSICAL_DESCRIPTOR_TYPE 0x23 - -// HID subclass HID1.11 Page 8 4.2 Subclass -#define HID_SUBCLASS_NONE 0 -#define HID_SUBCLASS_BOOT_INTERFACE 1 - -// HID Keyboard/Mouse bios compatible protocols HID1.11 Page 9 4.3 Protocols -#define HID_PROTOCOL_NONE 0 -#define HID_PROTOCOL_KEYBOARD 1 -#define HID_PROTOCOL_MOUSE 2 - -// Normal or bios protocol (Keyboard/Mouse) HID1.11 Page 54 7.2.5 Get_Protocol Request -// "protocol" variable is used for this purpose. -#define HID_BOOT_PROTOCOL 0 -#define HID_REPORT_PROTOCOL 1 - -// HID Request Type HID1.11 Page 51 7.2.1 Get_Report Request -#define HID_REPORT_TYPE_INPUT 1 -#define HID_REPORT_TYPE_OUTPUT 2 -#define HID_REPORT_TYPE_FEATURE 3 - -typedef struct -{ - uint8_t len; // 9 - uint8_t dtype; // 0x21 - uint8_t addr; - uint8_t versionL; // 0x101 - uint8_t versionH; // 0x101 - uint8_t country; - uint8_t desctype; // 0x22 report - uint8_t descLenL; - uint8_t descLenH; -} HIDDescDescriptor; - -typedef struct -{ - InterfaceDescriptor hid; - HIDDescDescriptor desc; - EndpointDescriptor in; -} HIDDescriptor; - -class HIDSubDescriptor -{ - public: - HIDSubDescriptor* next = NULL; - HIDSubDescriptor(const void* d, const uint16_t l) : data(d), length(l) {} - - const void* data; - const uint16_t length; -}; - -class HID_ : public PluggableUSBModule -{ - public: - HID_(void); - int begin(void); - int SendReport(uint8_t id, const void* data, int len); - void AppendDescriptor(HIDSubDescriptor* node); - - protected: - // Implementation of the PluggableUSBModule - int getInterface(uint8_t* interfaceCount); - int getDescriptor(USBSetup& setup); - bool setup(USBSetup& setup); - uint8_t getShortName(char* name); - - private: - unsigned int epType[1]; - - HIDSubDescriptor* rootNode; - uint16_t descriptorSize; - - uint8_t protocol; - uint8_t idle; -}; - -// Replacement for global singleton. -// This function prevents static-initialization-order-fiasco -// https://isocpp.org/wiki/faq/ctors#static-init-order-on-first-use -HID_& HID(); - -#define D_HIDREPORT(length) \ - { \ - 9, 0x21, 0x01, 0x01, 0, 1, 0x22, lowByte(length), highByte(length) \ - } - -#else - -#error "No Native USB support available on this board" - -#endif // USBCON - -#endif // HID_h From cc4a1fdf6f651cd75c6fe6c700d121c822625dad Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 28 Mar 2021 13:44:11 +0200 Subject: [PATCH 233/351] Add SD library With support for the entire megaAVR-0 family --- .travis.yml | 317 +++- megaavr/libraries/SD/README.adoc | 26 + .../SD/examples/CardInfo/CardInfo.ino | 117 ++ .../SD/examples/Datalogger/Datalogger.ino | 79 + .../SD/examples/DumpFile/DumpFile.ino | 65 + megaavr/libraries/SD/examples/Files/Files.ino | 72 + .../NonBlockingWrite/NonBlockingWrite.ino | 118 ++ .../SD/examples/ReadWrite/ReadWrite.ino | 80 + .../SD/examples/listfiles/listfiles.ino | 86 + .../SD/extras/codespell-ignore-words-list.txt | 0 megaavr/libraries/SD/keywords.txt | 31 + megaavr/libraries/SD/library.properties | 9 + megaavr/libraries/SD/src/File.cpp | 168 ++ megaavr/libraries/SD/src/README.txt | 13 + megaavr/libraries/SD/src/SD.cpp | 637 +++++++ megaavr/libraries/SD/src/SD.h | 138 ++ megaavr/libraries/SD/src/utility/FatStructs.h | 418 +++++ megaavr/libraries/SD/src/utility/Sd2Card.cpp | 777 +++++++++ megaavr/libraries/SD/src/utility/Sd2Card.h | 273 +++ megaavr/libraries/SD/src/utility/Sd2PinMap.h | 528 ++++++ megaavr/libraries/SD/src/utility/SdFat.h | 641 +++++++ megaavr/libraries/SD/src/utility/SdFatUtil.h | 77 + .../libraries/SD/src/utility/SdFatmainpage.h | 202 +++ megaavr/libraries/SD/src/utility/SdFile.cpp | 1527 +++++++++++++++++ megaavr/libraries/SD/src/utility/SdInfo.h | 232 +++ megaavr/libraries/SD/src/utility/SdVolume.cpp | 351 ++++ 26 files changed, 6957 insertions(+), 25 deletions(-) create mode 100755 megaavr/libraries/SD/README.adoc create mode 100755 megaavr/libraries/SD/examples/CardInfo/CardInfo.ino create mode 100755 megaavr/libraries/SD/examples/Datalogger/Datalogger.ino create mode 100755 megaavr/libraries/SD/examples/DumpFile/DumpFile.ino create mode 100755 megaavr/libraries/SD/examples/Files/Files.ino create mode 100755 megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino create mode 100755 megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino create mode 100755 megaavr/libraries/SD/examples/listfiles/listfiles.ino create mode 100755 megaavr/libraries/SD/extras/codespell-ignore-words-list.txt create mode 100755 megaavr/libraries/SD/keywords.txt create mode 100755 megaavr/libraries/SD/library.properties create mode 100755 megaavr/libraries/SD/src/File.cpp create mode 100755 megaavr/libraries/SD/src/README.txt create mode 100755 megaavr/libraries/SD/src/SD.cpp create mode 100755 megaavr/libraries/SD/src/SD.h create mode 100755 megaavr/libraries/SD/src/utility/FatStructs.h create mode 100755 megaavr/libraries/SD/src/utility/Sd2Card.cpp create mode 100755 megaavr/libraries/SD/src/utility/Sd2Card.h create mode 100755 megaavr/libraries/SD/src/utility/Sd2PinMap.h create mode 100755 megaavr/libraries/SD/src/utility/SdFat.h create mode 100755 megaavr/libraries/SD/src/utility/SdFatUtil.h create mode 100755 megaavr/libraries/SD/src/utility/SdFatmainpage.h create mode 100755 megaavr/libraries/SD/src/utility/SdFile.cpp create mode 100755 megaavr/libraries/SD/src/utility/SdInfo.h create mode 100755 megaavr/libraries/SD/src/utility/SdVolume.cpp diff --git a/.travis.yml b/.travis.yml index 22d13fb..dc7326f 100644 --- a/.travis.yml +++ b/.travis.yml @@ -150,41 +150,308 @@ env: ## ATmega809 # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + ## ATmega808 # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + + # pinout=32pin_standard, clock=internal, bootloader=no_bootloader + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=28pin_standard, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=28pin_standard, clock=internal_16MHz, bootloader=uart0_default - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=28pin_standard, clock=external_16MHz, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=28pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" before_install: diff --git a/megaavr/libraries/SD/README.adoc b/megaavr/libraries/SD/README.adoc new file mode 100755 index 0000000..fb3ed03 --- /dev/null +++ b/megaavr/libraries/SD/README.adoc @@ -0,0 +1,26 @@ += SD Library for Arduino = + +image:https://travis-ci.org/arduino-libraries/SD.svg?branch=master[Build Status, link=https://travis-ci.org/arduino-libraries/SD] + +The SD library allows for reading from and writing to SD cards. + +For more information about this library please visit us at +http://www.arduino.cc/en/Reference/SD + +== License == + + Copyright (C) 2009 by William Greiman +Copyright (c) 2010 SparkFun Electronics + +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 . diff --git a/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino b/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino new file mode 100755 index 0000000..3418e92 --- /dev/null +++ b/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino @@ -0,0 +1,117 @@ +/* + SD card test + + This example shows how use the utility libraries on which the' + SD library is based in order to get info about your SD card. + Very useful for testing a card when you're not sure whether its working or not. + Pin numbers reflect the default SPI pins for Uno and Nano models + The circuit: + SD card attached to SPI bus as follows: + ** SDO - pin 11 on Arduino Uno/Duemilanove/Diecimila + ** SDI - pin 12 on Arduino Uno/Duemilanove/Diecimila + ** CLK - pin 13 on Arduino Uno/Duemilanove/Diecimila + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + + created 28 Mar 2011 + by Limor Fried + modified 24 July 2020 + by Tom Igoe +*/ +// include the SD library: +#include +#include + +// set up variables using the SD utility library functions: +Sd2Card card; +SdVolume volume; +SdFile root; + +// change this to match your SD shield or module; +// Default SPI on Uno and Nano: pin 10 +// Arduino Ethernet shield: pin 4 +// Adafruit SD shields and modules: pin 10 +// Sparkfun SD shield: pin 8 +// MKRZero SD: SDCARD_SS_PIN +const int chipSelect = 10; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + while (!Serial) { + ; // wait for serial port to connect. Needed for native USB port only + } + + + Serial.print("\nInitializing SD card..."); + + // we'll use the initialization code from the utility libraries + // since we're just testing if the card is working! + if (!card.init(SPI_HALF_SPEED, chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("* is a card inserted?"); + Serial.println("* is your wiring correct?"); + Serial.println("* did you change the chipSelect pin to match your shield or module?"); + while (1); + } else { + Serial.println("Wiring is correct and a card is present."); + } + + // print the type of card + Serial.println(); + Serial.print("Card type: "); + switch (card.type()) { + case SD_CARD_TYPE_SD1: + Serial.println("SD1"); + break; + case SD_CARD_TYPE_SD2: + Serial.println("SD2"); + break; + case SD_CARD_TYPE_SDHC: + Serial.println("SDHC"); + break; + default: + Serial.println("Unknown"); + } + + // Now we will try to open the 'volume'/'partition' - it should be FAT16 or FAT32 + if (!volume.init(card)) { + Serial.println("Could not find FAT16/FAT32 partition.\nMake sure you've formatted the card"); + while (1); + } + + Serial.print("Clusters: "); + Serial.println(volume.clusterCount()); + Serial.print("Blocks x Cluster: "); + Serial.println(volume.blocksPerCluster()); + + Serial.print("Total Blocks: "); + Serial.println(volume.blocksPerCluster() * volume.clusterCount()); + Serial.println(); + + // print the type and size of the first FAT-type volume + uint32_t volumesize; + Serial.print("Volume type is: FAT"); + Serial.println(volume.fatType(), DEC); + + volumesize = volume.blocksPerCluster(); // clusters are collections of blocks + volumesize *= volume.clusterCount(); // we'll have a lot of clusters + volumesize /= 2; // SD card blocks are always 512 bytes (2 blocks are 1KB) + Serial.print("Volume size (Kb): "); + Serial.println(volumesize); + Serial.print("Volume size (Mb): "); + volumesize /= 1024; + Serial.println(volumesize); + Serial.print("Volume size (Gb): "); + Serial.println((float)volumesize / 1024.0); + + Serial.println("\nFiles found on the card (name, date and size in bytes): "); + root.openRoot(volume); + + // list all files in the card with date and size + root.ls(LS_R | LS_DATE | LS_SIZE); + root.close(); +} + +void loop(void) { +} diff --git a/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino b/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino new file mode 100755 index 0000000..fdbacfd --- /dev/null +++ b/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino @@ -0,0 +1,79 @@ +/* + SD card datalogger + + This example shows how to log data from three analog sensors + to an SD card using the SD library. Pin numbers reflect the default + SPI pins for Uno and Nano models + + The circuit: + analog sensors on analog ins 0, 1, and 2 + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + (for MKRZero SD: SDCARD_SS_PIN) + + created 24 Nov 2010 + modified 24 July 2020 + by Tom Igoe + + This example code is in the public domain. + +*/ + +#include +#include + +const int chipSelect = 10; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // wait for Serial Monitor to connect. Needed for native USB port boards only: + while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("1. is a card inserted?"); + Serial.println("2. is your wiring correct?"); + Serial.println("3. did you change the chipSelect pin to match your shield or module?"); + Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!"); + while (true); + } + + Serial.println("initialization done."); +} + +void loop() { + // make a string for assembling the data to log: + String dataString = ""; + + // read three sensors and append to the string: + for (int analogPin = 0; analogPin < 3; analogPin++) { + int sensor = analogRead(analogPin); + dataString += String(sensor); + if (analogPin < 2) { + dataString += ","; + } + } + + // open the file. note that only one file can be open at a time, + // so you have to close this one before opening another. + File dataFile = SD.open("datalog.txt", FILE_WRITE); + + // if the file is available, write to it: + if (dataFile) { + dataFile.println(dataString); + dataFile.close(); + // print to the serial port too: + Serial.println(dataString); + } + // if the file isn't open, pop up an error: + else { + Serial.println("error opening datalog.txt"); + } +} diff --git a/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino b/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino new file mode 100755 index 0000000..bb114b6 --- /dev/null +++ b/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino @@ -0,0 +1,65 @@ +/* + SD card file dump + + This example shows how to read a file from the SD card using the + SD library and send it over the serial port. + Pin numbers reflect the default SPI pins for Uno and Nano models. + + The circuit: + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + (for MKRZero SD: SDCARD_SS_PIN) + + created 22 December 2010 + by Limor Fried + modified 9 Apr 2012 + by Tom Igoe + + This example code is in the public domain. +*/ +#include + +const int chipSelect = 10; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // wait for Serial Monitor to connect. Needed for native USB port boards only: + while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("1. is a card inserted?"); + Serial.println("2. is your wiring correct?"); + Serial.println("3. did you change the chipSelect pin to match your shield or module?"); + Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!"); + while (true); + } + + Serial.println("initialization done."); + + // open the file. note that only one file can be open at a time, + // so you have to close this one before opening another. + File dataFile = SD.open("datalog.txt"); + + // if the file is available, write to it: + if (dataFile) { + while (dataFile.available()) { + Serial.write(dataFile.read()); + } + dataFile.close(); + } + // if the file isn't open, pop up an error: + else { + Serial.println("error opening datalog.txt"); + } +} + +void loop() { +} diff --git a/megaavr/libraries/SD/examples/Files/Files.ino b/megaavr/libraries/SD/examples/Files/Files.ino new file mode 100755 index 0000000..85faa7c --- /dev/null +++ b/megaavr/libraries/SD/examples/Files/Files.ino @@ -0,0 +1,72 @@ +/* + SD card basic file example + + This example shows how to create and destroy an SD card file + The circuit. Pin numbers reflect the default + SPI pins for Uno and Nano models: + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + (for MKRZero SD: SDCARD_SS_PIN) + + created Nov 2010 + by David A. Mellis + modified 24 July 2020 + by Tom Igoe + + This example code is in the public domain. +*/ +#include + +const int chipSelect = 10; +File myFile; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // wait for Serial Monitor to connect. Needed for native USB port boards only: +while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(10)) { + Serial.println("initialization failed!"); + while (1); + } + Serial.println("initialization done."); + + if (SD.exists("example.txt")) { + Serial.println("example.txt exists."); + } else { + Serial.println("example.txt doesn't exist."); + } + + // open a new file and immediately close it: + Serial.println("Creating example.txt..."); + myFile = SD.open("example.txt", FILE_WRITE); + myFile.close(); + + // Check to see if the file exists: + if (SD.exists("example.txt")) { + Serial.println("example.txt exists."); + } else { + Serial.println("example.txt doesn't exist."); + } + + // delete the file: + Serial.println("Removing example.txt..."); + SD.remove("example.txt"); + + if (SD.exists("example.txt")) { + Serial.println("example.txt exists."); + } else { + Serial.println("example.txt doesn't exist."); + } +} + +void loop() { + // nothing happens after setup finishes. +} diff --git a/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino b/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino new file mode 100755 index 0000000..082a5fb --- /dev/null +++ b/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino @@ -0,0 +1,118 @@ +/* + Non-blocking Write + + This example demonstrates how to perform non-blocking writes + to a file on a SD card. The file will contain the current millis() + value every 10ms. If the SD card is busy, the data will be dataBuffered + in order to not block the sketch. + + If data is successfully written, the built in LED will flash. After a few + seconds, check the card for a file called datalog.txt + + NOTE: myFile.availableForWrite() will automatically sync the + file contents as needed. You may lose some unsynced data + still if myFile.sync() or myFile.close() is not called. + + Pin numbers reflect the default SPI pins for Uno and Nano models + Updated for clarity and uniformity with other examples + + The circuit: + analog sensors on analog ins 0, 1, and 2 + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + (for MKRZero SD: SDCARD_SS_PIN) + + modified 24 July 2020 + by Tom Igoe + + This example code is in the public domain. +*/ +#include + +const int chipSelect = 10; + +// file name to use for writing +const char filename[] = "datalog.txt"; + +// File object to represent file +File myFile; +// string to buffer output +String dataBuffer; +// last time data was written to card: +unsigned long lastMillis = 0; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // reserve 1kB for String used as a dataBuffer + dataBuffer.reserve(1024); + + // set LED pin to output, used to blink when writing + pinMode(LED_BUILTIN, OUTPUT); + + // wait for Serial Monitor to connect. Needed for native USB port boards only: + while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("1. is a card inserted?"); + Serial.println("2. is your wiring correct?"); + Serial.println("3. did you change the chipSelect pin to match your shield or module?"); + Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!"); + while (true); + } + + Serial.println("initialization done."); + + // If you want to start from an empty file, + // uncomment the next line: + // SD.remove(filename); + // try to open the file for writing + + myFile = SD.open(filename, FILE_WRITE); + if (!myFile) { + Serial.print("error opening "); + Serial.println(filename); + while (true); + } + + // add some new lines to start + myFile.println(); + myFile.println("Hello World!"); + Serial.println("Starting to write to file..."); +} + +void loop() { + // check if it's been over 10 ms since the last line added + unsigned long now = millis(); + if ((now - lastMillis) >= 10) { + // add a new line to the dataBuffer + dataBuffer += "Hello "; + dataBuffer += now; + dataBuffer += "\r\n"; + // print the buffer length. This will change depending on when + // data is actually written to the SD card file: + Serial.print("Unsaved data buffer length (in bytes): "); + Serial.println(dataBuffer.length()); + // note the time that the last line was added to the string + lastMillis = now; + } + + // check if the SD card is available to write data without blocking + // and if the dataBuffered data is enough for the full chunk size + unsigned int chunkSize = myFile.availableForWrite(); + if (chunkSize && dataBuffer.length() >= chunkSize) { + // write to file and blink LED + digitalWrite(LED_BUILTIN, HIGH); + myFile.write(dataBuffer.c_str(), chunkSize); + digitalWrite(LED_BUILTIN, LOW); + // remove written data from dataBuffer + dataBuffer.remove(0, chunkSize); + } +} diff --git a/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino b/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino new file mode 100755 index 0000000..c15ecdb --- /dev/null +++ b/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino @@ -0,0 +1,80 @@ +/* + SD card read/write + + This example shows how to read and write data to and from an SD card file + The circuit. Pin numbers reflect the default + SPI pins for Uno and Nano models: + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - pin 4 (For For Uno, Nano: pin 10. For MKRZero SD: SDCARD_SS_PIN) + + created Nov 2010 + by David A. Mellis + modified 24 July 2020 + by Tom Igoe + + This example code is in the public domain. + +*/ +#include + +const int chipSelect = 10; +File myFile; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // wait for Serial Monitor to connect. Needed for native USB port boards only: + while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("1. is a card inserted?"); + Serial.println("2. is your wiring correct?"); + Serial.println("3. did you change the chipSelect pin to match your shield or module?"); + Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!"); + while (true); + } + + Serial.println("initialization done."); + + // open the file. note that only one file can be open at a time, + // so you have to close this one before opening another. + myFile = SD.open("test.txt", FILE_WRITE); + + // if the file opened okay, write to it: + if (myFile) { + Serial.print("Writing to test.txt..."); + myFile.println("testing 1, 2, 3."); + // close the file: + myFile.close(); + Serial.println("done."); + } else { + // if the file didn't open, print an error: + Serial.println("error opening test.txt"); + } + + // re-open the file for reading: + myFile = SD.open("test.txt"); + if (myFile) { + Serial.println("test.txt:"); + + // read from the file until there's nothing else in it: + while (myFile.available()) { + Serial.write(myFile.read()); + } + // close the file: + myFile.close(); + } else { + // if the file didn't open, print an error: + Serial.println("error opening test.txt"); + } +} + +void loop() { + // nothing happens after setup +} diff --git a/megaavr/libraries/SD/examples/listfiles/listfiles.ino b/megaavr/libraries/SD/examples/listfiles/listfiles.ino new file mode 100755 index 0000000..66eebb6 --- /dev/null +++ b/megaavr/libraries/SD/examples/listfiles/listfiles.ino @@ -0,0 +1,86 @@ +/* + Listfiles + + This example shows how print out the files in a + directory on a SD card.Pin numbers reflect the default + SPI pins for Uno and Nano models + + The circuit: + SD card attached to SPI bus as follows: + ** SDO - pin 11 + ** SDI - pin 12 + ** CLK - pin 13 + ** CS - depends on your SD card shield or module. + Pin 10 used here for consistency with other Arduino examples + (for MKRZero SD: SDCARD_SS_PIN) + + created Nov 2010 + by David A. Mellis + modified 9 Apr 2012 + by Tom Igoe + modified 2 Feb 2014 + by Scott Fitzgerald + modified 24 July 2020 + by Tom Igoe + + This example code is in the public domain. + +*/ +#include + +const int chipSelect = 10; +File root; + +void setup() { + // Open serial communications and wait for port to open: + Serial.begin(9600); + // wait for Serial Monitor to connect. Needed for native USB port boards only: + while (!Serial); + + Serial.print("Initializing SD card..."); + + if (!SD.begin(chipSelect)) { + Serial.println("initialization failed. Things to check:"); + Serial.println("1. is a card inserted?"); + Serial.println("2. is your wiring correct?"); + Serial.println("3. did you change the chipSelect pin to match your shield or module?"); + Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!"); + while (true); + } + + Serial.println("initialization done."); + + root = SD.open("/"); + + printDirectory(root, 0); + + Serial.println("done!"); +} + +void loop() { + // nothing happens after setup finishes. +} + +void printDirectory(File dir, int numTabs) { + while (true) { + + File entry = dir.openNextFile(); + if (! entry) { + // no more files + break; + } + for (uint8_t i = 0; i < numTabs; i++) { + Serial.print('\t'); + } + Serial.print(entry.name()); + if (entry.isDirectory()) { + Serial.println("/"); + printDirectory(entry, numTabs + 1); + } else { + // files have sizes, directories do not + Serial.print("\t\t"); + Serial.println(entry.size(), DEC); + } + entry.close(); + } +} diff --git a/megaavr/libraries/SD/extras/codespell-ignore-words-list.txt b/megaavr/libraries/SD/extras/codespell-ignore-words-list.txt new file mode 100755 index 0000000..e69de29 diff --git a/megaavr/libraries/SD/keywords.txt b/megaavr/libraries/SD/keywords.txt new file mode 100755 index 0000000..91e74b8 --- /dev/null +++ b/megaavr/libraries/SD/keywords.txt @@ -0,0 +1,31 @@ +####################################### +# Syntax Coloring Map SD +####################################### + +####################################### +# Datatypes (KEYWORD1) +####################################### + +SD KEYWORD1 SD +File KEYWORD1 SD +SDFile KEYWORD1 SD + +####################################### +# Methods and Functions (KEYWORD2) +####################################### +begin KEYWORD2 +exists KEYWORD2 +mkdir KEYWORD2 +remove KEYWORD2 +rmdir KEYWORD2 +open KEYWORD2 +close KEYWORD2 +seek KEYWORD2 +position KEYWORD2 +size KEYWORD2 + +####################################### +# Constants (LITERAL1) +####################################### +FILE_READ LITERAL1 +FILE_WRITE LITERAL1 diff --git a/megaavr/libraries/SD/library.properties b/megaavr/libraries/SD/library.properties new file mode 100755 index 0000000..60e8859 --- /dev/null +++ b/megaavr/libraries/SD/library.properties @@ -0,0 +1,9 @@ +name=SD +version=1.2.4 +author=Arduino, SparkFun +maintainer=Arduino +sentence=Enables reading and writing on SD cards. +paragraph=Once an SD memory card is connected to the SPI interface of the Arduino or Genuino board you can create files and read/write on them. You can also move through directories on the SD card. +category=Data Storage +url=http://www.arduino.cc/en/Reference/SD +architectures=* diff --git a/megaavr/libraries/SD/src/File.cpp b/megaavr/libraries/SD/src/File.cpp new file mode 100755 index 0000000..3e27fb4 --- /dev/null +++ b/megaavr/libraries/SD/src/File.cpp @@ -0,0 +1,168 @@ +/* + + SD - a slightly more friendly wrapper for sdfatlib + + This library aims to expose a subset of SD card functionality + in the form of a higher level "wrapper" object. + + License: GNU General Public License V3 + (Because sdfatlib is licensed with this.) + + (C) Copyright 2010 SparkFun Electronics + +*/ + +#include + +/* for debugging file open/close leaks + uint8_t nfilecount=0; +*/ + +File::File(SdFile f, const char *n) { + // oh man you are kidding me, new() doesn't exist? Ok we do it by hand! + _file = (SdFile *)malloc(sizeof(SdFile)); + if (_file) { + memcpy(_file, &f, sizeof(SdFile)); + + strncpy(_name, n, 12); + _name[12] = 0; + + /* for debugging file open/close leaks + nfilecount++; + Serial.print("Created \""); + Serial.print(n); + Serial.print("\": "); + Serial.println(nfilecount, DEC); + */ + } +} + +File::File(void) { + _file = 0; + _name[0] = 0; + //Serial.print("Created empty file object"); +} + +// returns a pointer to the file name +char *File::name(void) { + return _name; +} + +// a directory is a special type of file +bool File::isDirectory(void) { + return (_file && _file->isDir()); +} + + +size_t File::write(uint8_t val) { + return write(&val, 1); +} + +size_t File::write(const uint8_t *buf, size_t size) { + size_t t; + if (!_file) { + setWriteError(); + return 0; + } + _file->clearWriteError(); + t = _file->write(buf, size); + if (_file->getWriteError()) { + setWriteError(); + return 0; + } + return t; +} + +int File::availableForWrite() { + if (_file) { + return _file->availableForWrite(); + } + return 0; +} + +int File::peek() { + if (! _file) { + return 0; + } + + int c = _file->read(); + if (c != -1) { + _file->seekCur(-1); + } + return c; +} + +int File::read() { + if (_file) { + return _file->read(); + } + return -1; +} + +// buffered read for more efficient, high speed reading +int File::read(void *buf, uint16_t nbyte) { + if (_file) { + return _file->read(buf, nbyte); + } + return 0; +} + +int File::available() { + if (! _file) { + return 0; + } + + uint32_t n = size() - position(); + + return n > 0X7FFF ? 0X7FFF : n; +} + +void File::flush() { + if (_file) { + _file->sync(); + } +} + +bool File::seek(uint32_t pos) { + if (! _file) { + return false; + } + + return _file->seekSet(pos); +} + +uint32_t File::position() { + if (! _file) { + return -1; + } + return _file->curPosition(); +} + +uint32_t File::size() { + if (! _file) { + return 0; + } + return _file->fileSize(); +} + +void File::close() { + if (_file) { + _file->close(); + free(_file); + _file = 0; + + /* for debugging file open/close leaks + nfilecount--; + Serial.print("Deleted "); + Serial.println(nfilecount, DEC); + */ + } +} + +File::operator bool() { + if (_file) { + return _file->isOpen(); + } + return false; +} + diff --git a/megaavr/libraries/SD/src/README.txt b/megaavr/libraries/SD/src/README.txt new file mode 100755 index 0000000..495ea4c --- /dev/null +++ b/megaavr/libraries/SD/src/README.txt @@ -0,0 +1,13 @@ + +** SD - a slightly more friendly wrapper for sdfatlib ** + +This library aims to expose a subset of SD card functionality in the +form of a higher level "wrapper" object. + +License: GNU General Public License V3 + (Because sdfatlib is licensed with this.) + +(C) Copyright 2010 SparkFun Electronics + +Now better than ever with optimization, multiple file support, directory handling, etc - ladyada! + diff --git a/megaavr/libraries/SD/src/SD.cpp b/megaavr/libraries/SD/src/SD.cpp new file mode 100755 index 0000000..24fcb2e --- /dev/null +++ b/megaavr/libraries/SD/src/SD.cpp @@ -0,0 +1,637 @@ +/* + + SD - a slightly more friendly wrapper for sdfatlib + + This library aims to expose a subset of SD card functionality + in the form of a higher level "wrapper" object. + + License: GNU General Public License V3 + (Because sdfatlib is licensed with this.) + + (C) Copyright 2010 SparkFun Electronics + + + This library provides four key benefits: + + Including `SD.h` automatically creates a global + `SD` object which can be interacted with in a similar + manner to other standard global objects like `Serial` and `Ethernet`. + + Boilerplate initialisation code is contained in one method named + `begin` and no further objects need to be created in order to access + the SD card. + + Calls to `open` can supply a full path name including parent + directories which simplifies interacting with files in subdirectories. + + Utility methods are provided to determine whether a file exists + and to create a directory hierarchy. + + + Note however that not all functionality provided by the underlying + sdfatlib library is exposed. + +*/ + +/* + + Implementation Notes + + In order to handle multi-directory path traversal, functionality that + requires this ability is implemented as callback functions. + + Individual methods call the `walkPath` function which performs the actual + directory traversal (swapping between two different directory/file handles + along the way) and at each level calls the supplied callback function. + + Some types of functionality will take an action at each level (e.g. exists + or make directory) which others will only take an action at the bottom + level (e.g. open). + +*/ + +#include "SD.h" + +namespace SDLib { + + // Used by `getNextPathComponent` +#define MAX_COMPONENT_LEN 12 // What is max length? +#define PATH_COMPONENT_BUFFER_LEN MAX_COMPONENT_LEN+1 + + bool getNextPathComponent(const char *path, unsigned int *p_offset, + char *buffer) { + /* + + Parse individual path components from a path. + + e.g. after repeated calls '/foo/bar/baz' will be split + into 'foo', 'bar', 'baz'. + + This is similar to `strtok()` but copies the component into the + supplied buffer rather than modifying the original string. + + + `buffer` needs to be PATH_COMPONENT_BUFFER_LEN in size. + + `p_offset` needs to point to an integer of the offset at + which the previous path component finished. + + Returns `true` if more components remain. + + Returns `false` if this is the last component. + (This means path ended with 'foo' or 'foo/'.) + + */ + + // TODO: Have buffer local to this function, so we know it's the + // correct length? + + int bufferOffset = 0; + + int offset = *p_offset; + + // Skip root or other separator + if (path[offset] == '/') { + offset++; + } + + // Copy the next next path segment + while (bufferOffset < MAX_COMPONENT_LEN + && (path[offset] != '/') + && (path[offset] != '\0')) { + buffer[bufferOffset++] = path[offset++]; + } + + buffer[bufferOffset] = '\0'; + + // Skip trailing separator so we can determine if this + // is the last component in the path or not. + if (path[offset] == '/') { + offset++; + } + + *p_offset = offset; + + return (path[offset] != '\0'); + } + + + + bool walkPath(const char *filepath, SdFile& parentDir, + bool(*callback)(SdFile& parentDir, + const char *filePathComponent, + bool isLastComponent, + void *object), + void *object = NULL) { + /* + + When given a file path (and parent directory--normally root), + this function traverses the directories in the path and at each + level calls the supplied callback function while also providing + the supplied object for context if required. + + e.g. given the path '/foo/bar/baz' + the callback would be called at the equivalent of + '/foo', '/foo/bar' and '/foo/bar/baz'. + + The implementation swaps between two different directory/file + handles as it traverses the directories and does not use recursion + in an attempt to use memory efficiently. + + If a callback wishes to stop the directory traversal it should + return false--in this case the function will stop the traversal, + tidy up and return false. + + If a directory path doesn't exist at some point this function will + also return false and not subsequently call the callback. + + If a directory path specified is complete, valid and the callback + did not indicate the traversal should be interrupted then this + function will return true. + + */ + + + SdFile subfile1; + SdFile subfile2; + + char buffer[PATH_COMPONENT_BUFFER_LEN]; + + unsigned int offset = 0; + + SdFile *p_parent; + SdFile *p_child; + + SdFile *p_tmp_sdfile; + + p_child = &subfile1; + + p_parent = &parentDir; + + while (true) { + + bool moreComponents = getNextPathComponent(filepath, &offset, buffer); + + bool shouldContinue = callback((*p_parent), buffer, !moreComponents, object); + + if (!shouldContinue) { + // TODO: Don't repeat this code? + // If it's one we've created then we + // don't need the parent handle anymore. + if (p_parent != &parentDir) { + (*p_parent).close(); + } + return false; + } + + if (!moreComponents) { + break; + } + + bool exists = (*p_child).open(*p_parent, buffer, O_RDONLY); + + // If it's one we've created then we + // don't need the parent handle anymore. + if (p_parent != &parentDir) { + (*p_parent).close(); + } + + // Handle case when it doesn't exist and we can't continue... + if (exists) { + // We alternate between two file handles as we go down + // the path. + if (p_parent == &parentDir) { + p_parent = &subfile2; + } + + p_tmp_sdfile = p_parent; + p_parent = p_child; + p_child = p_tmp_sdfile; + } else { + return false; + } + } + + if (p_parent != &parentDir) { + (*p_parent).close(); // TODO: Return/ handle different? + } + + return true; + } + + + + /* + + The callbacks used to implement various functionality follow. + + Each callback is supplied with a parent directory handle, + character string with the name of the current file path component, + a flag indicating if this component is the last in the path and + a pointer to an arbitrary object used for context. + + */ + + bool callback_pathExists(SdFile& parentDir, const char *filePathComponent, + bool /* isLastComponent */, void * /* object */) { + /* + + Callback used to determine if a file/directory exists in parent + directory. + + Returns true if file path exists. + + */ + SdFile child; + + bool exists = child.open(parentDir, filePathComponent, O_RDONLY); + + if (exists) { + child.close(); + } + + return exists; + } + + + + bool callback_makeDirPath(SdFile& parentDir, const char *filePathComponent, + bool isLastComponent, void *object) { + /* + + Callback used to create a directory in the parent directory if + it does not already exist. + + Returns true if a directory was created or it already existed. + + */ + bool result = false; + SdFile child; + + result = callback_pathExists(parentDir, filePathComponent, isLastComponent, object); + if (!result) { + result = child.makeDir(parentDir, filePathComponent); + } + + return result; + } + + + /* + + bool callback_openPath(SdFile& parentDir, char *filePathComponent, + bool isLastComponent, void *object) { + + Callback used to open a file specified by a filepath that may + specify one or more directories above it. + + Expects the context object to be an instance of `SDClass` and + will use the `file` property of the instance to open the requested + file/directory with the associated file open mode property. + + Always returns true if the directory traversal hasn't reached the + bottom of the directory hierarchy. + + Returns false once the file has been opened--to prevent the traversal + from descending further. (This may be unnecessary.) + + if (isLastComponent) { + SDClass *p_SD = static_cast(object); + p_SD->file.open(parentDir, filePathComponent, p_SD->fileOpenMode); + if (p_SD->fileOpenMode == FILE_WRITE) { + p_SD->file.seekSet(p_SD->file.fileSize()); + } + // TODO: Return file open result? + return false; + } + return true; + } + */ + + + + bool callback_remove(SdFile& parentDir, const char *filePathComponent, + bool isLastComponent, void * /* object */) { + if (isLastComponent) { + return SdFile::remove(parentDir, filePathComponent); + } + return true; + } + + bool callback_rmdir(SdFile& parentDir, const char *filePathComponent, + bool isLastComponent, void * /* object */) { + if (isLastComponent) { + SdFile f; + if (!f.open(parentDir, filePathComponent, O_READ)) { + return false; + } + return f.rmDir(); + } + return true; + } + + + + /* Implementation of class used to create `SDCard` object. */ + + + + bool SDClass::begin(uint8_t csPin) { + if (root.isOpen()) { + root.close(); + } + + /* + + Performs the initialisation required by the sdfatlib library. + + Return true if initialization succeeds, false otherwise. + + */ + return card.init(SPI_HALF_SPEED, csPin) && + volume.init(card) && + root.openRoot(volume); + } + + bool SDClass::begin(uint32_t clock, uint8_t csPin) { + if (root.isOpen()) { + root.close(); + } + + return card.init(SPI_HALF_SPEED, csPin) && + card.setSpiClock(clock) && + volume.init(card) && + root.openRoot(volume); + } + + //call this when a card is removed. It will allow you to insert and initialise a new card. + void SDClass::end() { + root.close(); + } + + // this little helper is used to traverse paths + SdFile SDClass::getParentDir(const char *filepath, int *index) { + // get parent directory + SdFile d1; + SdFile d2; + + d1.openRoot(volume); // start with the mostparent, root! + + // we'll use the pointers to swap between the two objects + SdFile *parent = &d1; + SdFile *subdir = &d2; + + const char *origpath = filepath; + + while (strchr(filepath, '/')) { + + // get rid of leading /'s + if (filepath[0] == '/') { + filepath++; + continue; + } + + if (! strchr(filepath, '/')) { + // it was in the root directory, so leave now + break; + } + + // extract just the name of the next subdirectory + uint8_t idx = strchr(filepath, '/') - filepath; + if (idx > 12) { + idx = 12; // don't let them specify long names + } + char subdirname[13]; + strncpy(subdirname, filepath, idx); + subdirname[idx] = 0; + + // close the subdir (we reuse them) if open + subdir->close(); + if (! subdir->open(parent, subdirname, O_READ)) { + // failed to open one of the subdirectories + return SdFile(); + } + // move forward to the next subdirectory + filepath += idx; + + // we reuse the objects, close it. + parent->close(); + + // swap the pointers + SdFile *t = parent; + parent = subdir; + subdir = t; + } + + *index = (int)(filepath - origpath); + // parent is now the parent directory of the file! + return *parent; + } + + + File SDClass::open(const char *filepath, uint8_t mode) { + /* + + Open the supplied file path for reading or writing. + + The file content can be accessed via the `file` property of + the `SDClass` object--this property is currently + a standard `SdFile` object from `sdfatlib`. + + Defaults to read only. + + If `write` is true, default action (when `append` is true) is to + append data to the end of the file. + + If `append` is false then the file will be truncated first. + + If the file does not exist and it is opened for writing the file + will be created. + + An attempt to open a file for reading that does not exist is an + error. + + */ + + int pathidx; + + // do the interactive search + SdFile parentdir = getParentDir(filepath, &pathidx); + // no more subdirs! + + filepath += pathidx; + + if (! filepath[0]) { + // it was the directory itself! + return File(parentdir, "/"); + } + + // Open the file itself + SdFile file; + + // failed to open a subdir! + if (!parentdir.isOpen()) { + return File(); + } + + if (! file.open(parentdir, filepath, mode)) { + return File(); + } + // close the parent + parentdir.close(); + + if ((mode & (O_APPEND | O_WRITE)) == (O_APPEND | O_WRITE)) { + file.seekSet(file.fileSize()); + } + return File(file, filepath); + } + + + /* + File SDClass::open(char *filepath, uint8_t mode) { + // + + Open the supplied file path for reading or writing. + + The file content can be accessed via the `file` property of + the `SDClass` object--this property is currently + a standard `SdFile` object from `sdfatlib`. + + Defaults to read only. + + If `write` is true, default action (when `append` is true) is to + append data to the end of the file. + + If `append` is false then the file will be truncated first. + + If the file does not exist and it is opened for writing the file + will be created. + + An attempt to open a file for reading that does not exist is an + error. + + // + + // TODO: Allow for read&write? (Possibly not, as it requires seek.) + + fileOpenMode = mode; + walkPath(filepath, root, callback_openPath, this); + + return File(); + + } + */ + + + //bool SDClass::close() { + // /* + // + // Closes the file opened by the `open` method. + // + // */ + // file.close(); + //} + + + bool SDClass::exists(const char *filepath) { + /* + + Returns true if the supplied file path exists. + + */ + return walkPath(filepath, root, callback_pathExists); + } + + + //bool SDClass::exists(char *filepath, SdFile& parentDir) { + // /* + // + // Returns true if the supplied file path rooted at `parentDir` + // exists. + // + // */ + // return walkPath(filepath, parentDir, callback_pathExists); + //} + + + bool SDClass::mkdir(const char *filepath) { + /* + + Makes a single directory or a hierarchy of directories. + + A rough equivalent to `mkdir -p`. + + */ + return walkPath(filepath, root, callback_makeDirPath); + } + + bool SDClass::rmdir(const char *filepath) { + /* + + Remove a single directory or a hierarchy of directories. + + A rough equivalent to `rm -rf`. + + */ + return walkPath(filepath, root, callback_rmdir); + } + + bool SDClass::remove(const char *filepath) { + return walkPath(filepath, root, callback_remove); + } + + + // allows you to recurse into a directory + File File::openNextFile(uint8_t mode) { + dir_t p; + + //Serial.print("\t\treading dir..."); + while (_file->readDir(&p) > 0) { + + // done if past last used entry + if (p.name[0] == DIR_NAME_FREE) { + //Serial.println("end"); + return File(); + } + + // skip deleted entry and entries for . and .. + if (p.name[0] == DIR_NAME_DELETED || p.name[0] == '.') { + //Serial.println("dots"); + continue; + } + + // only list subdirectories and files + if (!DIR_IS_FILE_OR_SUBDIR(&p)) { + //Serial.println("notafile"); + continue; + } + + // print file name with possible blank fill + SdFile f; + char name[13]; + _file->dirName(p, name); + //Serial.print("try to open file "); + //Serial.println(name); + + if (f.open(_file, name, mode)) { + //Serial.println("OK!"); + return File(f, name); + } else { + //Serial.println("ugh"); + return File(); + } + } + + //Serial.println("nothing"); + return File(); + } + + void File::rewindDirectory(void) { + if (isDirectory()) { + _file->rewind(); + } + } + + SDClass SD; + +}; diff --git a/megaavr/libraries/SD/src/SD.h b/megaavr/libraries/SD/src/SD.h new file mode 100755 index 0000000..c81a7d3 --- /dev/null +++ b/megaavr/libraries/SD/src/SD.h @@ -0,0 +1,138 @@ +/* + + SD - a slightly more friendly wrapper for sdfatlib + + This library aims to expose a subset of SD card functionality + in the form of a higher level "wrapper" object. + + License: GNU General Public License V3 + (Because sdfatlib is licensed with this.) + + (C) Copyright 2010 SparkFun Electronics + +*/ + +#ifndef __SD_H__ +#define __SD_H__ + +#include + +#include "utility/SdFat.h" +#include "utility/SdFatUtil.h" + +#define FILE_READ O_READ +#define FILE_WRITE (O_READ | O_WRITE | O_CREAT | O_APPEND) + +namespace SDLib { + + class File : public Stream { + private: + char _name[13]; // our name + SdFile *_file; // underlying file pointer + + public: + File(SdFile f, const char *name); // wraps an underlying SdFile + File(void); // 'empty' constructor + virtual size_t write(uint8_t); + virtual size_t write(const uint8_t *buf, size_t size); + virtual int availableForWrite(); + virtual int read(); + virtual int peek(); + virtual int available(); + virtual void flush(); + int read(void *buf, uint16_t nbyte); + bool seek(uint32_t pos); + uint32_t position(); + uint32_t size(); + void close(); + operator bool(); + char * name(); + + bool isDirectory(void); + File openNextFile(uint8_t mode = O_RDONLY); + void rewindDirectory(void); + + using Print::write; + }; + + class SDClass { + + private: + // These are required for initialisation and use of sdfatlib + Sd2Card card; + SdVolume volume; + SdFile root; + + // my quick&dirty iterator, should be replaced + SdFile getParentDir(const char *filepath, int *indx); + public: + // This needs to be called to set up the connection to the SD card + // before other methods are used. + bool begin(uint8_t csPin = SD_CHIP_SELECT_PIN); + bool begin(uint32_t clock, uint8_t csPin); + + //call this when a card is removed. It will allow you to insert and initialise a new card. + void end(); + + // Open the specified file/directory with the supplied mode (e.g. read or + // write, etc). Returns a File object for interacting with the file. + // Note that currently only one file can be open at a time. + File open(const char *filename, uint8_t mode = FILE_READ); + File open(const String &filename, uint8_t mode = FILE_READ) { + return open(filename.c_str(), mode); + } + + // Methods to determine if the requested file path exists. + bool exists(const char *filepath); + bool exists(const String &filepath) { + return exists(filepath.c_str()); + } + + // Create the requested directory heirarchy--if intermediate directories + // do not exist they will be created. + bool mkdir(const char *filepath); + bool mkdir(const String &filepath) { + return mkdir(filepath.c_str()); + } + + // Delete the file. + bool remove(const char *filepath); + bool remove(const String &filepath) { + return remove(filepath.c_str()); + } + + bool rmdir(const char *filepath); + bool rmdir(const String &filepath) { + return rmdir(filepath.c_str()); + } + + private: + + // This is used to determine the mode used to open a file + // it's here because it's the easiest place to pass the + // information through the directory walking function. But + // it's probably not the best place for it. + // It shouldn't be set directly--it is set via the parameters to `open`. + int fileOpenMode; + + friend class File; + friend bool callback_openPath(SdFile&, const char *, bool, void *); + }; + + extern SDClass SD; + +}; + +// We enclose File and SD classes in namespace SDLib to avoid conflicts +// with others legacy libraries that redefines File class. + +// This ensure compatibility with sketches that uses only SD library +using namespace SDLib; + +// This allows sketches to use SDLib::File with other libraries (in the +// sketch you must use SDFile instead of File to disambiguate) +typedef SDLib::File SDFile; +typedef SDLib::SDClass SDFileSystemClass; +#define SDFileSystem SDLib::SD + +#endif diff --git a/megaavr/libraries/SD/src/utility/FatStructs.h b/megaavr/libraries/SD/src/utility/FatStructs.h new file mode 100755 index 0000000..84c1cc7 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/FatStructs.h @@ -0,0 +1,418 @@ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef FatStructs_h +#define FatStructs_h +/** + \file + FAT file structures +*/ +/* + mostly from Microsoft document fatgen103.doc + http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx +*/ +//------------------------------------------------------------------------------ +/** Value for byte 510 of boot block or MBR */ +uint8_t const BOOTSIG0 = 0X55; +/** Value for byte 511 of boot block or MBR */ +uint8_t const BOOTSIG1 = 0XAA; +//------------------------------------------------------------------------------ +/** + \struct partitionTable + \brief MBR partition table entry + + A partition table entry for a MBR formatted storage device. + The MBR partition table has four entries. +*/ +struct partitionTable { + /** + Boot Indicator . Indicates whether the volume is the active + partition. Legal values include: 0X00. Do not use for booting. + 0X80 Active partition. + */ + uint8_t boot; + /** + Head part of Cylinder-head-sector address of the first block in + the partition. Legal values are 0-255. Only used in old PC BIOS. + */ + uint8_t beginHead; + /** + Sector part of Cylinder-head-sector address of the first block in + the partition. Legal values are 1-63. Only used in old PC BIOS. + */ + unsigned beginSector : 6; + /** High bits cylinder for first block in partition. */ + unsigned beginCylinderHigh : 2; + /** + Combine beginCylinderLow with beginCylinderHigh. Legal values + are 0-1023. Only used in old PC BIOS. + */ + uint8_t beginCylinderLow; + /** + Partition type. See defines that begin with PART_TYPE_ for + some Microsoft partition types. + */ + uint8_t type; + /** + head part of cylinder-head-sector address of the last sector in the + partition. Legal values are 0-255. Only used in old PC BIOS. + */ + uint8_t endHead; + /** + Sector part of cylinder-head-sector address of the last sector in + the partition. Legal values are 1-63. Only used in old PC BIOS. + */ + unsigned endSector : 6; + /** High bits of end cylinder */ + unsigned endCylinderHigh : 2; + /** + Combine endCylinderLow with endCylinderHigh. Legal values + are 0-1023. Only used in old PC BIOS. + */ + uint8_t endCylinderLow; + /** Logical block address of the first block in the partition. */ + uint32_t firstSector; + /** Length of the partition, in blocks. */ + uint32_t totalSectors; +} __attribute__((packed)); +/** Type name for partitionTable */ +typedef struct partitionTable part_t; +//------------------------------------------------------------------------------ +/** + \struct masterBootRecord + + \brief Master Boot Record + + The first block of a storage device that is formatted with a MBR. +*/ +struct masterBootRecord { + /** Code Area for master boot program. */ + uint8_t codeArea[440]; + /** Optional WindowsNT disk signature. May contain more boot code. */ + uint32_t diskSignature; + /** Usually zero but may be more boot code. */ + uint16_t usuallyZero; + /** Partition tables. */ + part_t part[4]; + /** First MBR signature byte. Must be 0X55 */ + uint8_t mbrSig0; + /** Second MBR signature byte. Must be 0XAA */ + uint8_t mbrSig1; +} __attribute__((packed)); +/** Type name for masterBootRecord */ +typedef struct masterBootRecord mbr_t; +//------------------------------------------------------------------------------ +/** + \struct biosParmBlock + + \brief BIOS parameter block + + The BIOS parameter block describes the physical layout of a FAT volume. +*/ +struct biosParmBlock { + /** + Count of bytes per sector. This value may take on only the + following values: 512, 1024, 2048 or 4096 + */ + uint16_t bytesPerSector; + /** + Number of sectors per allocation unit. This value must be a + power of 2 that is greater than 0. The legal values are + 1, 2, 4, 8, 16, 32, 64, and 128. + */ + uint8_t sectorsPerCluster; + /** + Number of sectors before the first FAT. + This value must not be zero. + */ + uint16_t reservedSectorCount; + /** The count of FAT data structures on the volume. This field should + always contain the value 2 for any FAT volume of any type. + */ + uint8_t fatCount; + /** + For FAT12 and FAT16 volumes, this field contains the count of + 32-byte directory entries in the root directory. For FAT32 volumes, + this field must be set to 0. For FAT12 and FAT16 volumes, this + value should always specify a count that when multiplied by 32 + results in a multiple of bytesPerSector. FAT16 volumes should + use the value 512. + */ + uint16_t rootDirEntryCount; + /** + This field is the old 16-bit total count of sectors on the volume. + This count includes the count of all sectors in all four regions + of the volume. This field can be 0; if it is 0, then totalSectors32 + must be non-zero. For FAT32 volumes, this field must be 0. For + FAT12 and FAT16 volumes, this field contains the sector count, and + totalSectors32 is 0 if the total sector count fits + (is less than 0x10000). + */ + uint16_t totalSectors16; + /** + This dates back to the old MS-DOS 1.x media determination and is + no longer usually used for anything. 0xF8 is the standard value + for fixed (non-removable) media. For removable media, 0xF0 is + frequently used. Legal values are 0xF0 or 0xF8-0xFF. + */ + uint8_t mediaType; + /** + Count of sectors occupied by one FAT on FAT12/FAT16 volumes. + On FAT32 volumes this field must be 0, and sectorsPerFat32 + contains the FAT size count. + */ + uint16_t sectorsPerFat16; + /** Sectors per track for interrupt 0x13. Not used otherwise. */ + uint16_t sectorsPerTrtack; + /** Number of heads for interrupt 0x13. Not used otherwise. */ + uint16_t headCount; + /** + Count of hidden sectors preceding the partition that contains this + FAT volume. This field is generally only relevant for media + visible on interrupt 0x13. + */ + uint32_t hidddenSectors; + /** + This field is the new 32-bit total count of sectors on the volume. + This count includes the count of all sectors in all four regions + of the volume. This field can be 0; if it is 0, then + totalSectors16 must be non-zero. + */ + uint32_t totalSectors32; + /** + Count of sectors occupied by one FAT on FAT32 volumes. + */ + uint32_t sectorsPerFat32; + /** + This field is only defined for FAT32 media and does not exist on + FAT12 and FAT16 media. + Bits 0-3 -- Zero-based number of active FAT. + Only valid if mirroring is disabled. + Bits 4-6 -- Reserved. + Bit 7 -- 0 means the FAT is mirrored at runtime into all FATs. + -- 1 means only one FAT is active; it is the one referenced in bits 0-3. + Bits 8-15 -- Reserved. + */ + uint16_t fat32Flags; + /** + FAT32 version. High byte is major revision number. + Low byte is minor revision number. Only 0.0 define. + */ + uint16_t fat32Version; + /** + Cluster number of the first cluster of the root directory for FAT32. + This usually 2 but not required to be 2. + */ + uint32_t fat32RootCluster; + /** + Sector number of FSINFO structure in the reserved area of the + FAT32 volume. Usually 1. + */ + uint16_t fat32FSInfo; + /** + If non-zero, indicates the sector number in the reserved area + of the volume of a copy of the boot record. Usually 6. + No value other than 6 is recommended. + */ + uint16_t fat32BackBootBlock; + /** + Reserved for future expansion. Code that formats FAT32 volumes + should always set all of the bytes of this field to 0. + */ + uint8_t fat32Reserved[12]; +} __attribute__((packed)); +/** Type name for biosParmBlock */ +typedef struct biosParmBlock bpb_t; +//------------------------------------------------------------------------------ +/** + \struct fat32BootSector + + \brief Boot sector for a FAT16 or FAT32 volume. + +*/ +struct fat32BootSector { + /** X86 jmp to boot program */ + uint8_t jmpToBootCode[3]; + /** informational only - don't depend on it */ + char oemName[8]; + /** BIOS Parameter Block */ + bpb_t bpb; + /** for int0x13 use value 0X80 for hard drive */ + uint8_t driveNumber; + /** used by Windows NT - should be zero for FAT */ + uint8_t reserved1; + /** 0X29 if next three fields are valid */ + uint8_t bootSignature; + /** usually generated by combining date and time */ + uint32_t volumeSerialNumber; + /** should match volume label in root dir */ + char volumeLabel[11]; + /** informational only - don't depend on it */ + char fileSystemType[8]; + /** X86 boot code */ + uint8_t bootCode[420]; + /** must be 0X55 */ + uint8_t bootSectorSig0; + /** must be 0XAA */ + uint8_t bootSectorSig1; +} __attribute__((packed)); +//------------------------------------------------------------------------------ +// End Of Chain values for FAT entries +/** FAT16 end of chain value used by Microsoft. */ +uint16_t const FAT16EOC = 0XFFFF; +/** Minimum value for FAT16 EOC. Use to test for EOC. */ +uint16_t const FAT16EOC_MIN = 0XFFF8; +/** FAT32 end of chain value used by Microsoft. */ +uint32_t const FAT32EOC = 0X0FFFFFFF; +/** Minimum value for FAT32 EOC. Use to test for EOC. */ +uint32_t const FAT32EOC_MIN = 0X0FFFFFF8; +/** Mask a for FAT32 entry. Entries are 28 bits. */ +uint32_t const FAT32MASK = 0X0FFFFFFF; + +/** Type name for fat32BootSector */ +typedef struct fat32BootSector fbs_t; +//------------------------------------------------------------------------------ +/** + \struct directoryEntry + \brief FAT short directory entry + + Short means short 8.3 name, not the entry size. + + Date Format. A FAT directory entry date stamp is a 16-bit field that is + basically a date relative to the MS-DOS epoch of 01/01/1980. Here is the + format (bit 0 is the LSB of the 16-bit word, bit 15 is the MSB of the + 16-bit word): + + Bits 9-15: Count of years from 1980, valid value range 0-127 + inclusive (1980-2107). + + Bits 5-8: Month of year, 1 = January, valid value range 1-12 inclusive. + + Bits 0-4: Day of month, valid value range 1-31 inclusive. + + Time Format. A FAT directory entry time stamp is a 16-bit field that has + a granularity of 2 seconds. Here is the format (bit 0 is the LSB of the + 16-bit word, bit 15 is the MSB of the 16-bit word). + + Bits 11-15: Hours, valid value range 0-23 inclusive. + + Bits 5-10: Minutes, valid value range 0-59 inclusive. + + Bits 0-4: 2-second count, valid value range 0-29 inclusive (0 - 58 seconds). + + The valid time range is from Midnight 00:00:00 to 23:59:58. +*/ +struct directoryEntry { + /** + Short 8.3 name. + The first eight bytes contain the file name with blank fill. + The last three bytes contain the file extension with blank fill. + */ + uint8_t name[11]; + /** Entry attributes. + + The upper two bits of the attribute byte are reserved and should + always be set to 0 when a file is created and never modified or + looked at after that. See defines that begin with DIR_ATT_. + */ + uint8_t attributes; + /** + Reserved for use by Windows NT. Set value to 0 when a file is + created and never modify or look at it after that. + */ + uint8_t reservedNT; + /** + The granularity of the seconds part of creationTime is 2 seconds + so this field is a count of tenths of a second and its valid + value range is 0-199 inclusive. (WHG note - seems to be hundredths) + */ + uint8_t creationTimeTenths; + /** Time file was created. */ + uint16_t creationTime; + /** Date file was created. */ + uint16_t creationDate; + /** + Last access date. Note that there is no last access time, only + a date. This is the date of last read or write. In the case of + a write, this should be set to the same date as lastWriteDate. + */ + uint16_t lastAccessDate; + /** + High word of this entry's first cluster number (always 0 for a + FAT12 or FAT16 volume). + */ + uint16_t firstClusterHigh; + /** Time of last write. File creation is considered a write. */ + uint16_t lastWriteTime; + /** Date of last write. File creation is considered a write. */ + uint16_t lastWriteDate; + /** Low word of this entry's first cluster number. */ + uint16_t firstClusterLow; + /** 32-bit unsigned holding this file's size in bytes. */ + uint32_t fileSize; +} __attribute__((packed)); +//------------------------------------------------------------------------------ +// Definitions for directory entries +// +/** Type name for directoryEntry */ +typedef struct directoryEntry dir_t; +/** escape for name[0] = 0XE5 */ +uint8_t const DIR_NAME_0XE5 = 0X05; +/** name[0] value for entry that is free after being "deleted" */ +uint8_t const DIR_NAME_DELETED = 0XE5; +/** name[0] value for entry that is free and no allocated entries follow */ +uint8_t const DIR_NAME_FREE = 0X00; +/** file is read-only */ +uint8_t const DIR_ATT_READ_ONLY = 0X01; +/** File should hidden in directory listings */ +uint8_t const DIR_ATT_HIDDEN = 0X02; +/** Entry is for a system file */ +uint8_t const DIR_ATT_SYSTEM = 0X04; +/** Directory entry contains the volume label */ +uint8_t const DIR_ATT_VOLUME_ID = 0X08; +/** Entry is for a directory */ +uint8_t const DIR_ATT_DIRECTORY = 0X10; +/** Old DOS archive bit for backup support */ +uint8_t const DIR_ATT_ARCHIVE = 0X20; +/** Test value for long name entry. Test is + (d->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME. */ +uint8_t const DIR_ATT_LONG_NAME = 0X0F; +/** Test mask for long name entry */ +uint8_t const DIR_ATT_LONG_NAME_MASK = 0X3F; +/** defined attribute bits */ +uint8_t const DIR_ATT_DEFINED_BITS = 0X3F; +/** Directory entry is part of a long name */ +static inline uint8_t DIR_IS_LONG_NAME(const dir_t* dir) { + return (dir->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME; +} +/** Mask for file/subdirectory tests */ +uint8_t const DIR_ATT_FILE_TYPE_MASK = (DIR_ATT_VOLUME_ID | DIR_ATT_DIRECTORY); +/** Directory entry is for a file */ +static inline uint8_t DIR_IS_FILE(const dir_t* dir) { + return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == 0; +} +/** Directory entry is for a subdirectory */ +static inline uint8_t DIR_IS_SUBDIR(const dir_t* dir) { + return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == DIR_ATT_DIRECTORY; +} +/** Directory entry is for a file or subdirectory */ +static inline uint8_t DIR_IS_FILE_OR_SUBDIR(const dir_t* dir) { + return (dir->attributes & DIR_ATT_VOLUME_ID) == 0; +} +#endif // FatStructs_h diff --git a/megaavr/libraries/SD/src/utility/Sd2Card.cpp b/megaavr/libraries/SD/src/utility/Sd2Card.cpp new file mode 100755 index 0000000..7cfbe73 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/Sd2Card.cpp @@ -0,0 +1,777 @@ +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#define USE_SPI_LIB +#include +#include "Sd2Card.h" +//------------------------------------------------------------------------------ +#ifndef SOFTWARE_SPI +#ifdef USE_SPI_LIB + + #ifndef SDCARD_SPI + #define SDCARD_SPI SPI + #endif + + #include + static SPISettings settings; +#endif +// functions for hardware SPI +/** Send a byte to the card */ +static void spiSend(uint8_t b) { + #ifndef USE_SPI_LIB + SPDR = b; + while (!(SPSR & (1 << SPIF))) + ; + #else + SDCARD_SPI.transfer(b); + #endif +} +/** Receive a byte from the card */ +static uint8_t spiRec(void) { + #ifndef USE_SPI_LIB + spiSend(0XFF); + return SPDR; + #else + return SDCARD_SPI.transfer(0xFF); + #endif +} +#else // SOFTWARE_SPI +//------------------------------------------------------------------------------ +/** nop to tune soft SPI timing */ +#define nop asm volatile ("nop\n\t") +//------------------------------------------------------------------------------ +/** Soft SPI receive */ +uint8_t spiRec(void) { + uint8_t data = 0; + // no interrupts during byte receive - about 8 us + cli(); + // output pin high - like sending 0XFF + fastDigitalWrite(SPI_MOSI_PIN, HIGH); + + for (uint8_t i = 0; i < 8; i++) { + fastDigitalWrite(SPI_SCK_PIN, HIGH); + + // adjust so SCK is nice + nop; + nop; + + data <<= 1; + + if (fastDigitalRead(SPI_MISO_PIN)) { + data |= 1; + } + + fastDigitalWrite(SPI_SCK_PIN, LOW); + } + // enable interrupts + sei(); + return data; +} +//------------------------------------------------------------------------------ +/** Soft SPI send */ +void spiSend(uint8_t data) { + // no interrupts during byte send - about 8 us + cli(); + for (uint8_t i = 0; i < 8; i++) { + fastDigitalWrite(SPI_SCK_PIN, LOW); + + fastDigitalWrite(SPI_MOSI_PIN, data & 0X80); + + data <<= 1; + + fastDigitalWrite(SPI_SCK_PIN, HIGH); + } + // hold SCK high for a few ns + nop; + nop; + nop; + nop; + + fastDigitalWrite(SPI_SCK_PIN, LOW); + // enable interrupts + sei(); +} +#endif // SOFTWARE_SPI +//------------------------------------------------------------------------------ +// send command and return error code. Return zero for OK +uint8_t Sd2Card::cardCommand(uint8_t cmd, uint32_t arg) { + // end read if in partialBlockRead mode + readEnd(); + + // select card + chipSelectLow(); + + // wait up to 300 ms if busy + waitNotBusy(300); + + // send command + spiSend(cmd | 0x40); + + // send argument + for (int8_t s = 24; s >= 0; s -= 8) { + spiSend(arg >> s); + } + + // send CRC + uint8_t crc = 0XFF; + if (cmd == CMD0) { + crc = 0X95; // correct crc for CMD0 with arg 0 + } + if (cmd == CMD8) { + crc = 0X87; // correct crc for CMD8 with arg 0X1AA + } + spiSend(crc); + + // wait for response + for (uint8_t i = 0; ((status_ = spiRec()) & 0X80) && i != 0XFF; i++) + ; + return status_; +} +//------------------------------------------------------------------------------ +/** + Determine the size of an SD flash memory card. + + \return The number of 512 byte data blocks in the card + or zero if an error occurs. +*/ +uint32_t Sd2Card::cardSize(void) { + csd_t csd; + if (!readCSD(&csd)) { + return 0; + } + if (csd.v1.csd_ver == 0) { + uint8_t read_bl_len = csd.v1.read_bl_len; + uint16_t c_size = (csd.v1.c_size_high << 10) + | (csd.v1.c_size_mid << 2) | csd.v1.c_size_low; + uint8_t c_size_mult = (csd.v1.c_size_mult_high << 1) + | csd.v1.c_size_mult_low; + return (uint32_t)(c_size + 1) << (c_size_mult + read_bl_len - 7); + } else if (csd.v2.csd_ver == 1) { + uint32_t c_size = ((uint32_t)csd.v2.c_size_high << 16) + | (csd.v2.c_size_mid << 8) | csd.v2.c_size_low; + return (c_size + 1) << 10; + } else { + error(SD_CARD_ERROR_BAD_CSD); + return 0; + } +} +//------------------------------------------------------------------------------ +static uint8_t chip_select_asserted = 0; + +void Sd2Card::chipSelectHigh(void) { + digitalWrite(chipSelectPin_, HIGH); + #ifdef USE_SPI_LIB + if (chip_select_asserted) { + chip_select_asserted = 0; + SDCARD_SPI.endTransaction(); + } + #endif +} +//------------------------------------------------------------------------------ +void Sd2Card::chipSelectLow(void) { + #ifdef USE_SPI_LIB + if (!chip_select_asserted) { + chip_select_asserted = 1; + SDCARD_SPI.beginTransaction(settings); + } + #endif + digitalWrite(chipSelectPin_, LOW); +} +//------------------------------------------------------------------------------ +/** Erase a range of blocks. + + \param[in] firstBlock The address of the first block in the range. + \param[in] lastBlock The address of the last block in the range. + + \note This function requests the SD card to do a flash erase for a + range of blocks. The data on the card after an erase operation is + either 0 or 1, depends on the card vendor. The card must support + single block erase. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::erase(uint32_t firstBlock, uint32_t lastBlock) { + if (!eraseSingleBlockEnable()) { + error(SD_CARD_ERROR_ERASE_SINGLE_BLOCK); + goto fail; + } + if (type_ != SD_CARD_TYPE_SDHC) { + firstBlock <<= 9; + lastBlock <<= 9; + } + if (cardCommand(CMD32, firstBlock) + || cardCommand(CMD33, lastBlock) + || cardCommand(CMD38, 0)) { + error(SD_CARD_ERROR_ERASE); + goto fail; + } + if (!waitNotBusy(SD_ERASE_TIMEOUT)) { + error(SD_CARD_ERROR_ERASE_TIMEOUT); + goto fail; + } + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Determine if card supports single block erase. + + \return The value one, true, is returned if single block erase is supported. + The value zero, false, is returned if single block erase is not supported. +*/ +uint8_t Sd2Card::eraseSingleBlockEnable(void) { + csd_t csd; + return readCSD(&csd) ? csd.v1.erase_blk_en : 0; +} +//------------------------------------------------------------------------------ +/** + Initialize an SD flash memory card. + + \param[in] sckRateID SPI clock rate selector. See setSckRate(). + \param[in] chipSelectPin SD chip select pin number. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. The reason for failure + can be determined by calling errorCode() and errorData(). +*/ +uint8_t Sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin) { + errorCode_ = inBlock_ = partialBlockRead_ = type_ = 0; + chipSelectPin_ = chipSelectPin; + // 16-bit init start time allows over a minute + unsigned int t0 = millis(); + uint32_t arg; + + // set pin modes + pinMode(chipSelectPin_, OUTPUT); + digitalWrite(chipSelectPin_, HIGH); + #ifndef USE_SPI_LIB + pinMode(SPI_MISO_PIN, INPUT); + pinMode(SPI_MOSI_PIN, OUTPUT); + pinMode(SPI_SCK_PIN, OUTPUT); + #endif + + #ifndef SOFTWARE_SPI + #ifndef USE_SPI_LIB + // SS must be in output mode even it is not chip select + pinMode(SS_PIN, OUTPUT); + digitalWrite(SS_PIN, HIGH); // disable any SPI device using hardware SS pin + // Enable SPI, Master, clock rate f_osc/128 + SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR1) | (1 << SPR0); + // clear double speed + SPSR &= ~(1 << SPI2X); + #else // USE_SPI_LIB + SDCARD_SPI.begin(); + settings = SPISettings(250000, MSBFIRST, SPI_MODE0); + #endif // USE_SPI_LIB + #endif // SOFTWARE_SPI + + // must supply min of 74 clock cycles with CS high. + #ifdef USE_SPI_LIB + SDCARD_SPI.beginTransaction(settings); + #endif + for (uint8_t i = 0; i < 10; i++) { + spiSend(0XFF); + } + #ifdef USE_SPI_LIB + SDCARD_SPI.endTransaction(); + #endif + + chipSelectLow(); + + // command to go idle in SPI mode + while ((status_ = cardCommand(CMD0, 0)) != R1_IDLE_STATE) { + unsigned int d = millis() - t0; + if (d > SD_INIT_TIMEOUT) { + error(SD_CARD_ERROR_CMD0); + goto fail; + } + } + // check SD version + if ((cardCommand(CMD8, 0x1AA) & R1_ILLEGAL_COMMAND)) { + type(SD_CARD_TYPE_SD1); + } else { + // only need last byte of r7 response + for (uint8_t i = 0; i < 4; i++) { + status_ = spiRec(); + } + if (status_ != 0XAA) { + error(SD_CARD_ERROR_CMD8); + goto fail; + } + type(SD_CARD_TYPE_SD2); + } + // initialize card and send host supports SDHC if SD2 + arg = type() == SD_CARD_TYPE_SD2 ? 0X40000000 : 0; + + while ((status_ = cardAcmd(ACMD41, arg)) != R1_READY_STATE) { + // check for timeout + unsigned int d = millis() - t0; + if (d > SD_INIT_TIMEOUT) { + error(SD_CARD_ERROR_ACMD41); + goto fail; + } + } + // if SD2 read OCR register to check for SDHC card + if (type() == SD_CARD_TYPE_SD2) { + if (cardCommand(CMD58, 0)) { + error(SD_CARD_ERROR_CMD58); + goto fail; + } + if ((spiRec() & 0XC0) == 0XC0) { + type(SD_CARD_TYPE_SDHC); + } + // discard rest of ocr - contains allowed voltage range + for (uint8_t i = 0; i < 3; i++) { + spiRec(); + } + } + chipSelectHigh(); + + #ifndef SOFTWARE_SPI + return setSckRate(sckRateID); + #else // SOFTWARE_SPI + return true; + #endif // SOFTWARE_SPI + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Enable or disable partial block reads. + + Enabling partial block reads improves performance by allowing a block + to be read over the SPI bus as several sub-blocks. Errors may occur + if the time between reads is too long since the SD card may timeout. + The SPI SS line will be held low until the entire block is read or + readEnd() is called. + + Use this for applications like the Adafruit Wave Shield. + + \param[in] value The value TRUE (non-zero) or FALSE (zero).) +*/ +void Sd2Card::partialBlockRead(uint8_t value) { + readEnd(); + partialBlockRead_ = value; +} +//------------------------------------------------------------------------------ +/** + Read a 512 byte block from an SD card device. + + \param[in] block Logical block to be read. + \param[out] dst Pointer to the location that will receive the data. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::readBlock(uint32_t block, uint8_t* dst) { + return readData(block, 0, 512, dst); +} +//------------------------------------------------------------------------------ +/** + Read part of a 512 byte block from an SD card. + + \param[in] block Logical block to be read. + \param[in] offset Number of bytes to skip at start of block + \param[out] dst Pointer to the location that will receive the data. + \param[in] count Number of bytes to read + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::readData(uint32_t block, + uint16_t offset, uint16_t count, uint8_t* dst) { + if (count == 0) { + return true; + } + if ((count + offset) > 512) { + goto fail; + } + if (!inBlock_ || block != block_ || offset < offset_) { + block_ = block; + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + block <<= 9; + } + if (cardCommand(CMD17, block)) { + error(SD_CARD_ERROR_CMD17); + goto fail; + } + if (!waitStartBlock()) { + goto fail; + } + offset_ = 0; + inBlock_ = 1; + } + + #ifdef OPTIMIZE_HARDWARE_SPI + // start first spi transfer + SPDR = 0XFF; + + // skip data before offset + for (; offset_ < offset; offset_++) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = 0XFF; + } + // transfer data + n = count - 1; + for (uint16_t i = 0; i < n; i++) { + while (!(SPSR & (1 << SPIF))) + ; + dst[i] = SPDR; + SPDR = 0XFF; + } + // wait for last byte + while (!(SPSR & (1 << SPIF))) + ; + dst[n] = SPDR; + + #else // OPTIMIZE_HARDWARE_SPI + + // skip data before offset + for (; offset_ < offset; offset_++) { + spiRec(); + } + // transfer data + for (uint16_t i = 0; i < count; i++) { + dst[i] = spiRec(); + } + #endif // OPTIMIZE_HARDWARE_SPI + + offset_ += count; + if (!partialBlockRead_ || offset_ >= 512) { + // read rest of data, checksum and set chip select high + readEnd(); + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Skip remaining data in a block when in partial block read mode. */ +void Sd2Card::readEnd(void) { + if (inBlock_) { + // skip data and crc + #ifdef OPTIMIZE_HARDWARE_SPI + // optimize skip for hardware + SPDR = 0XFF; + while (offset_++ < 513) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = 0XFF; + } + // wait for last crc byte + while (!(SPSR & (1 << SPIF))) + ; + #else // OPTIMIZE_HARDWARE_SPI + while (offset_++ < 514) { + spiRec(); + } + #endif // OPTIMIZE_HARDWARE_SPI + chipSelectHigh(); + inBlock_ = 0; + } +} +//------------------------------------------------------------------------------ +/** read CID or CSR register */ +uint8_t Sd2Card::readRegister(uint8_t cmd, void* buf) { + uint8_t* dst = reinterpret_cast(buf); + if (cardCommand(cmd, 0)) { + error(SD_CARD_ERROR_READ_REG); + goto fail; + } + if (!waitStartBlock()) { + goto fail; + } + // transfer data + for (uint16_t i = 0; i < 16; i++) { + dst[i] = spiRec(); + } + spiRec(); // get first crc byte + spiRec(); // get second crc byte + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Set the SPI clock rate. + + \param[in] sckRateID A value in the range [0, 6]. + + The SPI clock will be set to F_CPU/pow(2, 1 + sckRateID). The maximum + SPI rate is F_CPU/2 for \a sckRateID = 0 and the minimum rate is F_CPU/128 + for \a scsRateID = 6. + + \return The value one, true, is returned for success and the value zero, + false, is returned for an invalid value of \a sckRateID. +*/ +uint8_t Sd2Card::setSckRate(uint8_t sckRateID) { + if (sckRateID > 6) { + error(SD_CARD_ERROR_SCK_RATE); + return false; + } + #ifndef USE_SPI_LIB + // see avr processor datasheet for SPI register bit definitions + if ((sckRateID & 1) || sckRateID == 6) { + SPSR &= ~(1 << SPI2X); + } else { + SPSR |= (1 << SPI2X); + } + SPCR &= ~((1 << SPR1) | (1 << SPR0)); + SPCR |= (sckRateID & 4 ? (1 << SPR1) : 0) + | (sckRateID & 2 ? (1 << SPR0) : 0); + #else // USE_SPI_LIB + switch (sckRateID) { + case 0: settings = SPISettings(25000000, MSBFIRST, SPI_MODE0); break; + case 1: settings = SPISettings(4000000, MSBFIRST, SPI_MODE0); break; + case 2: settings = SPISettings(2000000, MSBFIRST, SPI_MODE0); break; + case 3: settings = SPISettings(1000000, MSBFIRST, SPI_MODE0); break; + case 4: settings = SPISettings(500000, MSBFIRST, SPI_MODE0); break; + case 5: settings = SPISettings(250000, MSBFIRST, SPI_MODE0); break; + default: settings = SPISettings(125000, MSBFIRST, SPI_MODE0); + } + #endif // USE_SPI_LIB + return true; +} +#ifdef USE_SPI_LIB +//------------------------------------------------------------------------------ +// set the SPI clock frequency +uint8_t Sd2Card::setSpiClock(uint32_t clock) { + settings = SPISettings(clock, MSBFIRST, SPI_MODE0); + return true; +} +#endif +//------------------------------------------------------------------------------ +// wait for card to go not busy +uint8_t Sd2Card::waitNotBusy(unsigned int timeoutMillis) { + unsigned int t0 = millis(); + unsigned int d; + do { + if (spiRec() == 0XFF) { + return true; + } + d = millis() - t0; + } while (d < timeoutMillis); + return false; +} +//------------------------------------------------------------------------------ +/** Wait for start block token */ +uint8_t Sd2Card::waitStartBlock(void) { + unsigned int t0 = millis(); + while ((status_ = spiRec()) == 0XFF) { + unsigned int d = millis() - t0; + if (d > SD_READ_TIMEOUT) { + error(SD_CARD_ERROR_READ_TIMEOUT); + goto fail; + } + } + if (status_ != DATA_START_BLOCK) { + error(SD_CARD_ERROR_READ); + goto fail; + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Writes a 512 byte block to an SD card. + + \param[in] blockNumber Logical block to be written. + \param[in] src Pointer to the location of the data to be written. + \param[in] blocking If the write should be blocking. + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking) { + #if SD_PROTECT_BLOCK_ZERO + // don't allow write to first block + if (blockNumber == 0) { + error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); + goto fail; + } + #endif // SD_PROTECT_BLOCK_ZERO + + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + blockNumber <<= 9; + } + if (cardCommand(CMD24, blockNumber)) { + error(SD_CARD_ERROR_CMD24); + goto fail; + } + if (!writeData(DATA_START_BLOCK, src)) { + goto fail; + } + if (blocking) { + // wait for flash programming to complete + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + error(SD_CARD_ERROR_WRITE_TIMEOUT); + goto fail; + } + // response is r2 so get and check two bytes for nonzero + if (cardCommand(CMD13, 0) || spiRec()) { + error(SD_CARD_ERROR_WRITE_PROGRAMMING); + goto fail; + } + } + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Write one data block in a multiple block write sequence */ +uint8_t Sd2Card::writeData(const uint8_t* src) { + // wait for previous write to finish + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + error(SD_CARD_ERROR_WRITE_MULTIPLE); + chipSelectHigh(); + return false; + } + return writeData(WRITE_MULTIPLE_TOKEN, src); +} +//------------------------------------------------------------------------------ +// send one block of data for write block or write multiple blocks +uint8_t Sd2Card::writeData(uint8_t token, const uint8_t* src) { + #ifdef OPTIMIZE_HARDWARE_SPI + + // send data - optimized loop + SPDR = token; + + // send two byte per iteration + for (uint16_t i = 0; i < 512; i += 2) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = src[i]; + while (!(SPSR & (1 << SPIF))) + ; + SPDR = src[i + 1]; + } + + // wait for last data byte + while (!(SPSR & (1 << SPIF))) + ; + + #else // OPTIMIZE_HARDWARE_SPI + spiSend(token); + for (uint16_t i = 0; i < 512; i++) { + spiSend(src[i]); + } + #endif // OPTIMIZE_HARDWARE_SPI + spiSend(0xff); // dummy crc + spiSend(0xff); // dummy crc + + status_ = spiRec(); + if ((status_ & DATA_RES_MASK) != DATA_RES_ACCEPTED) { + error(SD_CARD_ERROR_WRITE); + chipSelectHigh(); + return false; + } + return true; +} +//------------------------------------------------------------------------------ +/** Start a write multiple blocks sequence. + + \param[in] blockNumber Address of first block in sequence. + \param[in] eraseCount The number of blocks to be pre-erased. + + \note This function is used with writeData() and writeStop() + for optimized multiple block writes. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeStart(uint32_t blockNumber, uint32_t eraseCount) { + #if SD_PROTECT_BLOCK_ZERO + // don't allow write to first block + if (blockNumber == 0) { + error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); + goto fail; + } + #endif // SD_PROTECT_BLOCK_ZERO + // send pre-erase count + if (cardAcmd(ACMD23, eraseCount)) { + error(SD_CARD_ERROR_ACMD23); + goto fail; + } + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + blockNumber <<= 9; + } + if (cardCommand(CMD25, blockNumber)) { + error(SD_CARD_ERROR_CMD25); + goto fail; + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** End a write multiple blocks sequence. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeStop(void) { + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + goto fail; + } + spiSend(STOP_TRAN_TOKEN); + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + goto fail; + } + chipSelectHigh(); + return true; + +fail: + error(SD_CARD_ERROR_STOP_TRAN); + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Check if the SD card is busy + + \return The value one, true, is returned when is busy and + the value zero, false, is returned for when is NOT busy. +*/ +uint8_t Sd2Card::isBusy(void) { + chipSelectLow(); + byte b = spiRec(); + chipSelectHigh(); + + return (b != 0XFF); +} diff --git a/megaavr/libraries/SD/src/utility/Sd2Card.h b/megaavr/libraries/SD/src/utility/Sd2Card.h new file mode 100755 index 0000000..5d91ebf --- /dev/null +++ b/megaavr/libraries/SD/src/utility/Sd2Card.h @@ -0,0 +1,273 @@ +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#ifndef Sd2Card_h +#define Sd2Card_h +/** + \file + Sd2Card class +*/ +#include "Sd2PinMap.h" +#include "SdInfo.h" +/** Set SCK to max rate of F_CPU/2. See Sd2Card::setSckRate(). */ +uint8_t const SPI_FULL_SPEED = 0; +/** Set SCK rate to F_CPU/4. See Sd2Card::setSckRate(). */ +uint8_t const SPI_HALF_SPEED = 1; +/** Set SCK rate to F_CPU/8. Sd2Card::setSckRate(). */ +uint8_t const SPI_QUARTER_SPEED = 2; +/** + USE_SPI_LIB: if set, use the SPI library bundled with Arduino IDE, otherwise + run with a standalone driver for AVR. +*/ +#define USE_SPI_LIB +/** + Define MEGA_SOFT_SPI non-zero to use software SPI on Mega Arduinos. + Pins used are SS 10, MOSI 11, MISO 12, and SCK 13. + + MEGA_SOFT_SPI allows an unmodified Adafruit GPS Shield to be used + on Mega Arduinos. Software SPI works well with GPS Shield V1.1 + but many SD cards will fail with GPS Shield V1.0. +*/ +#define MEGA_SOFT_SPI 0 +//------------------------------------------------------------------------------ +#if MEGA_SOFT_SPI && (defined(__AVR_ATmega1280__)||defined(__AVR_ATmega2560__)) + #define SOFTWARE_SPI +#endif // MEGA_SOFT_SPI +//------------------------------------------------------------------------------ +// SPI pin definitions +// +#ifndef SOFTWARE_SPI + // hardware pin defs + + // include pins_arduino.h or variant.h depending on architecture, via Arduino.h + #include + + /** + SD Chip Select pin + + Warning if this pin is redefined the hardware SS will pin will be enabled + as an output by init(). An avr processor will not function as an SPI + master unless SS is set to output mode. + */ + #ifndef SDCARD_SS_PIN + /** The default chip select pin for the SD card is SS. */ + uint8_t const SD_CHIP_SELECT_PIN = SS; + #else + uint8_t const SD_CHIP_SELECT_PIN = SDCARD_SS_PIN; + #endif + + // The following three pins must not be redefined for hardware SPI, + // so ensure that they are taken from pins_arduino.h or variant.h, depending on architecture. + #ifndef SDCARD_MOSI_PIN + /** SPI Master Out Slave In pin */ + uint8_t const SPI_MOSI_PIN = MOSI; + /** SPI Master In Slave Out pin */ + uint8_t const SPI_MISO_PIN = MISO; + /** SPI Clock pin */ + uint8_t const SPI_SCK_PIN = SCK; + #else + uint8_t const SPI_MOSI_PIN = SDCARD_MOSI_PIN; + uint8_t const SPI_MISO_PIN = SDCARD_MISO_PIN; + uint8_t const SPI_SCK_PIN = SDCARD_SCK_PIN; + #endif + + /** optimize loops for hardware SPI */ + #ifndef USE_SPI_LIB + #define OPTIMIZE_HARDWARE_SPI + #endif + +#else // SOFTWARE_SPI + // define software SPI pins so Mega can use unmodified GPS Shield + /** SPI chip select pin */ + uint8_t const SD_CHIP_SELECT_PIN = 10; + /** SPI Master Out Slave In pin */ + uint8_t const SPI_MOSI_PIN = 11; + /** SPI Master In Slave Out pin */ + uint8_t const SPI_MISO_PIN = 12; + /** SPI Clock pin */ + uint8_t const SPI_SCK_PIN = 13; +#endif // SOFTWARE_SPI +//------------------------------------------------------------------------------ +/** Protect block zero from write if nonzero */ +#define SD_PROTECT_BLOCK_ZERO 1 +/** init timeout ms */ +unsigned int const SD_INIT_TIMEOUT = 2000; +/** erase timeout ms */ +unsigned int const SD_ERASE_TIMEOUT = 10000; +/** read timeout ms */ +unsigned int const SD_READ_TIMEOUT = 300; +/** write time out ms */ +unsigned int const SD_WRITE_TIMEOUT = 600; +//------------------------------------------------------------------------------ +// SD card errors +/** timeout error for command CMD0 */ +uint8_t const SD_CARD_ERROR_CMD0 = 0X1; +/** CMD8 was not accepted - not a valid SD card*/ +uint8_t const SD_CARD_ERROR_CMD8 = 0X2; +/** card returned an error response for CMD17 (read block) */ +uint8_t const SD_CARD_ERROR_CMD17 = 0X3; +/** card returned an error response for CMD24 (write block) */ +uint8_t const SD_CARD_ERROR_CMD24 = 0X4; +/** WRITE_MULTIPLE_BLOCKS command failed */ +uint8_t const SD_CARD_ERROR_CMD25 = 0X05; +/** card returned an error response for CMD58 (read OCR) */ +uint8_t const SD_CARD_ERROR_CMD58 = 0X06; +/** SET_WR_BLK_ERASE_COUNT failed */ +uint8_t const SD_CARD_ERROR_ACMD23 = 0X07; +/** card's ACMD41 initialization process timeout */ +uint8_t const SD_CARD_ERROR_ACMD41 = 0X08; +/** card returned a bad CSR version field */ +uint8_t const SD_CARD_ERROR_BAD_CSD = 0X09; +/** erase block group command failed */ +uint8_t const SD_CARD_ERROR_ERASE = 0X0A; +/** card not capable of single block erase */ +uint8_t const SD_CARD_ERROR_ERASE_SINGLE_BLOCK = 0X0B; +/** Erase sequence timed out */ +uint8_t const SD_CARD_ERROR_ERASE_TIMEOUT = 0X0C; +/** card returned an error token instead of read data */ +uint8_t const SD_CARD_ERROR_READ = 0X0D; +/** read CID or CSD failed */ +uint8_t const SD_CARD_ERROR_READ_REG = 0X0E; +/** timeout while waiting for start of read data */ +uint8_t const SD_CARD_ERROR_READ_TIMEOUT = 0X0F; +/** card did not accept STOP_TRAN_TOKEN */ +uint8_t const SD_CARD_ERROR_STOP_TRAN = 0X10; +/** card returned an error token as a response to a write operation */ +uint8_t const SD_CARD_ERROR_WRITE = 0X11; +/** attempt to write protected block zero */ +uint8_t const SD_CARD_ERROR_WRITE_BLOCK_ZERO = 0X12; +/** card did not go ready for a multiple block write */ +uint8_t const SD_CARD_ERROR_WRITE_MULTIPLE = 0X13; +/** card returned an error to a CMD13 status check after a write */ +uint8_t const SD_CARD_ERROR_WRITE_PROGRAMMING = 0X14; +/** timeout occurred during write programming */ +uint8_t const SD_CARD_ERROR_WRITE_TIMEOUT = 0X15; +/** incorrect rate selected */ +uint8_t const SD_CARD_ERROR_SCK_RATE = 0X16; +//------------------------------------------------------------------------------ +// card types +/** Standard capacity V1 SD card */ +uint8_t const SD_CARD_TYPE_SD1 = 1; +/** Standard capacity V2 SD card */ +uint8_t const SD_CARD_TYPE_SD2 = 2; +/** High Capacity SD card */ +uint8_t const SD_CARD_TYPE_SDHC = 3; +//------------------------------------------------------------------------------ +/** + \class Sd2Card + \brief Raw access to SD and SDHC flash memory cards. +*/ +class Sd2Card { + public: + /** Construct an instance of Sd2Card. */ + Sd2Card(void) : errorCode_(0), inBlock_(0), partialBlockRead_(0), type_(0) {} + uint32_t cardSize(void); + uint8_t erase(uint32_t firstBlock, uint32_t lastBlock); + uint8_t eraseSingleBlockEnable(void); + /** + \return error code for last error. See Sd2Card.h for a list of error codes. + */ + uint8_t errorCode(void) const { + return errorCode_; + } + /** \return error data for last error. */ + uint8_t errorData(void) const { + return status_; + } + /** + Initialize an SD flash memory card with default clock rate and chip + select pin. See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). + */ + uint8_t init(void) { + return init(SPI_FULL_SPEED, SD_CHIP_SELECT_PIN); + } + /** + Initialize an SD flash memory card with the selected SPI clock rate + and the default SD chip select pin. + See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). + */ + uint8_t init(uint8_t sckRateID) { + return init(sckRateID, SD_CHIP_SELECT_PIN); + } + uint8_t init(uint8_t sckRateID, uint8_t chipSelectPin); + void partialBlockRead(uint8_t value); + /** Returns the current value, true or false, for partial block read. */ + uint8_t partialBlockRead(void) const { + return partialBlockRead_; + } + uint8_t readBlock(uint32_t block, uint8_t* dst); + uint8_t readData(uint32_t block, + uint16_t offset, uint16_t count, uint8_t* dst); + /** + Read a cards CID register. The CID contains card identification + information such as Manufacturer ID, Product name, Product serial + number and Manufacturing date. */ + uint8_t readCID(cid_t* cid) { + return readRegister(CMD10, cid); + } + /** + Read a cards CSD register. The CSD contains Card-Specific Data that + provides information regarding access to the card's contents. */ + uint8_t readCSD(csd_t* csd) { + return readRegister(CMD9, csd); + } + void readEnd(void); + uint8_t setSckRate(uint8_t sckRateID); + #ifdef USE_SPI_LIB + uint8_t setSpiClock(uint32_t clock); + #endif + /** Return the card type: SD V1, SD V2 or SDHC */ + uint8_t type(void) const { + return type_; + } + uint8_t writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking = 1); + uint8_t writeData(const uint8_t* src); + uint8_t writeStart(uint32_t blockNumber, uint32_t eraseCount); + uint8_t writeStop(void); + uint8_t isBusy(void); + private: + uint32_t block_; + uint8_t chipSelectPin_; + uint8_t errorCode_; + uint8_t inBlock_; + uint16_t offset_; + uint8_t partialBlockRead_; + uint8_t status_; + uint8_t type_; + // private functions + uint8_t cardAcmd(uint8_t cmd, uint32_t arg) { + cardCommand(CMD55, 0); + return cardCommand(cmd, arg); + } + uint8_t cardCommand(uint8_t cmd, uint32_t arg); + void error(uint8_t code) { + errorCode_ = code; + } + uint8_t readRegister(uint8_t cmd, void* buf); + uint8_t sendWriteCommand(uint32_t blockNumber, uint32_t eraseCount); + void chipSelectHigh(void); + void chipSelectLow(void); + void type(uint8_t value) { + type_ = value; + } + uint8_t waitNotBusy(unsigned int timeoutMillis); + uint8_t writeData(uint8_t token, const uint8_t* src); + uint8_t waitStartBlock(void); +}; +#endif // Sd2Card_h diff --git a/megaavr/libraries/SD/src/utility/Sd2PinMap.h b/megaavr/libraries/SD/src/utility/Sd2PinMap.h new file mode 100755 index 0000000..12d8926 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/Sd2PinMap.h @@ -0,0 +1,528 @@ +/* Arduino SdFat Library + Copyright (C) 2010 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#if defined(__arm__) // Arduino Due Board follows + +#ifndef Sd2PinMap_h + #define Sd2PinMap_h + + #include + + uint8_t const SS_PIN = SS; + uint8_t const MOSI_PIN = MOSI; + uint8_t const MISO_PIN = MISO; + uint8_t const SCK_PIN = SCK; + +#endif // Sd2PinMap_h + +#elif defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) || \ +defined(__AVR_ATmega3209__) || defined(__AVR_ATmega3208__) || \ +defined(__AVR_ATmega1609__) || defined(__AVR_ATmega1608__) || \ +defined(__AVR_ATmega809__) || defined(__AVR_ATmega808__) + +#ifndef Sd2PinMap_h + #define Sd2PinMap_h + + #include + + uint8_t const SS_PIN = SS; + uint8_t const MOSI_PIN = MOSI; + uint8_t const MISO_PIN = MISO; + uint8_t const SCK_PIN = SCK; + +#endif // Sd2PinMap_h + +#elif defined(__AVR__) // Other AVR based Boards follows + +// Warning this file was generated by a program. +#ifndef Sd2PinMap_h +#define Sd2PinMap_h +#include + +//------------------------------------------------------------------------------ +/** struct for mapping digital pins */ +struct pin_map_t { + volatile uint8_t* ddr; + volatile uint8_t* pin; + volatile uint8_t* port; + uint8_t bit; +}; +//------------------------------------------------------------------------------ +#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +// Mega + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 20; +uint8_t const SCL_PIN = 21; + +// SPI port +uint8_t const SS_PIN = 53; +uint8_t const MOSI_PIN = 51; +uint8_t const MISO_PIN = 50; +uint8_t const SCK_PIN = 52; + +static const pin_map_t digitalPinMap[] = { + {&DDRE, &PINE, &PORTE, 0}, // E0 0 + {&DDRE, &PINE, &PORTE, 1}, // E1 1 + {&DDRE, &PINE, &PORTE, 4}, // E4 2 + {&DDRE, &PINE, &PORTE, 5}, // E5 3 + {&DDRG, &PING, &PORTG, 5}, // G5 4 + {&DDRE, &PINE, &PORTE, 3}, // E3 5 + {&DDRH, &PINH, &PORTH, 3}, // H3 6 + {&DDRH, &PINH, &PORTH, 4}, // H4 7 + {&DDRH, &PINH, &PORTH, 5}, // H5 8 + {&DDRH, &PINH, &PORTH, 6}, // H6 9 + {&DDRB, &PINB, &PORTB, 4}, // B4 10 + {&DDRB, &PINB, &PORTB, 5}, // B5 11 + {&DDRB, &PINB, &PORTB, 6}, // B6 12 + {&DDRB, &PINB, &PORTB, 7}, // B7 13 + {&DDRJ, &PINJ, &PORTJ, 1}, // J1 14 + {&DDRJ, &PINJ, &PORTJ, 0}, // J0 15 + {&DDRH, &PINH, &PORTH, 1}, // H1 16 + {&DDRH, &PINH, &PORTH, 0}, // H0 17 + {&DDRD, &PIND, &PORTD, 3}, // D3 18 + {&DDRD, &PIND, &PORTD, 2}, // D2 19 + {&DDRD, &PIND, &PORTD, 1}, // D1 20 + {&DDRD, &PIND, &PORTD, 0}, // D0 21 + {&DDRA, &PINA, &PORTA, 0}, // A0 22 + {&DDRA, &PINA, &PORTA, 1}, // A1 23 + {&DDRA, &PINA, &PORTA, 2}, // A2 24 + {&DDRA, &PINA, &PORTA, 3}, // A3 25 + {&DDRA, &PINA, &PORTA, 4}, // A4 26 + {&DDRA, &PINA, &PORTA, 5}, // A5 27 + {&DDRA, &PINA, &PORTA, 6}, // A6 28 + {&DDRA, &PINA, &PORTA, 7}, // A7 29 + {&DDRC, &PINC, &PORTC, 7}, // C7 30 + {&DDRC, &PINC, &PORTC, 6}, // C6 31 + {&DDRC, &PINC, &PORTC, 5}, // C5 32 + {&DDRC, &PINC, &PORTC, 4}, // C4 33 + {&DDRC, &PINC, &PORTC, 3}, // C3 34 + {&DDRC, &PINC, &PORTC, 2}, // C2 35 + {&DDRC, &PINC, &PORTC, 1}, // C1 36 + {&DDRC, &PINC, &PORTC, 0}, // C0 37 + {&DDRD, &PIND, &PORTD, 7}, // D7 38 + {&DDRG, &PING, &PORTG, 2}, // G2 39 + {&DDRG, &PING, &PORTG, 1}, // G1 40 + {&DDRG, &PING, &PORTG, 0}, // G0 41 + {&DDRL, &PINL, &PORTL, 7}, // L7 42 + {&DDRL, &PINL, &PORTL, 6}, // L6 43 + {&DDRL, &PINL, &PORTL, 5}, // L5 44 + {&DDRL, &PINL, &PORTL, 4}, // L4 45 + {&DDRL, &PINL, &PORTL, 3}, // L3 46 + {&DDRL, &PINL, &PORTL, 2}, // L2 47 + {&DDRL, &PINL, &PORTL, 1}, // L1 48 + {&DDRL, &PINL, &PORTL, 0}, // L0 49 + {&DDRB, &PINB, &PORTB, 3}, // B3 50 + {&DDRB, &PINB, &PORTB, 2}, // B2 51 + {&DDRB, &PINB, &PORTB, 1}, // B1 52 + {&DDRB, &PINB, &PORTB, 0}, // B0 53 + {&DDRF, &PINF, &PORTF, 0}, // F0 54 + {&DDRF, &PINF, &PORTF, 1}, // F1 55 + {&DDRF, &PINF, &PORTF, 2}, // F2 56 + {&DDRF, &PINF, &PORTF, 3}, // F3 57 + {&DDRF, &PINF, &PORTF, 4}, // F4 58 + {&DDRF, &PINF, &PORTF, 5}, // F5 59 + {&DDRF, &PINF, &PORTF, 6}, // F6 60 + {&DDRF, &PINF, &PORTF, 7}, // F7 61 + {&DDRK, &PINK, &PORTK, 0}, // K0 62 + {&DDRK, &PINK, &PORTK, 1}, // K1 63 + {&DDRK, &PINK, &PORTK, 2}, // K2 64 + {&DDRK, &PINK, &PORTK, 3}, // K3 65 + {&DDRK, &PINK, &PORTK, 4}, // K4 66 + {&DDRK, &PINK, &PORTK, 5}, // K5 67 + {&DDRK, &PINK, &PORTK, 6}, // K6 68 + {&DDRK, &PINK, &PORTK, 7} // K7 69 +}; +//------------------------------------------------------------------------------ +#elif (defined(__AVR_ATmega644P__) || defined(__AVR_ATmega1284P__)) && defined(CORE_MICRODUINO) +// Microduino Core+ + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 20; +uint8_t const SCL_PIN = 21; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 PD0 + {&DDRD, &PIND, &PORTD, 1}, // D1 PD1 + {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 + {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 + {&DDRB, &PINB, &PORTB, 0}, // D4 PB0 + {&DDRB, &PINB, &PORTB, 1}, // D5 PB1 + {&DDRB, &PINB, &PORTB, 2}, // D6 PB2 + {&DDRB, &PINB, &PORTB, 3}, // D7 PB3 + {&DDRD, &PIND, &PORTD, 6}, // D8 PD6 + {&DDRD, &PIND, &PORTD, 5}, // D9 PD5 + {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 + {&DDRB, &PINB, &PORTB, 5}, // D11 PB5 + {&DDRB, &PINB, &PORTB, 6}, // D12 PB6 + {&DDRB, &PINB, &PORTB, 7}, // D13 PB7 + {&DDRC, &PINC, &PORTC, 7}, // D14 PC7 + {&DDRC, &PINC, &PORTC, 6}, // D15 PC6 + {&DDRC, &PINC, &PORTC, 5}, // D16 PC5 + {&DDRC, &PINC, &PORTC, 4}, // D17 PC4 + {&DDRC, &PINC, &PORTC, 3}, // D18 PC3 + {&DDRC, &PINC, &PORTC, 2}, // D19 PC2 + {&DDRC, &PINC, &PORTC, 1}, // D20 PC1 + {&DDRC, &PINC, &PORTC, 0}, // D21 PC0 + {&DDRD, &PIND, &PORTD, 4}, // D22 PD4 + {&DDRD, &PIND, &PORTD, 7}, // D23 PD7 + {&DDRA, &PINA, &PORTA, 7}, // D24 PA7 + {&DDRA, &PINA, &PORTA, 6}, // D25 PA6 + {&DDRA, &PINA, &PORTA, 5}, // D26 PA5 + {&DDRA, &PINA, &PORTA, 4}, // D27 PA4 + {&DDRA, &PINA, &PORTA, 3}, // D28 PA3 + {&DDRA, &PINA, &PORTA, 2}, // D29 PA2 + {&DDRA, &PINA, &PORTA, 1}, // D30 PA1 + {&DDRA, &PINA, &PORTA, 0} // D31 PA0 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega128RFA1__) && defined(CORE_MICRODUINO) +// Microduino Core RF + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PINE, &PORTE, 0}, // D0 PE0 + {&DDRD, &PINE, &PORTE, 1}, // D1 PE1 + {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 + {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 + {&DDRB, &PINE, &PORTE, 3}, // D4 PE3 + {&DDRB, &PINE, &PORTE, 4}, // D5 PE4 + {&DDRB, &PINE, &PORTE, 5}, // D6 PE5 + {&DDRB, &PINB, &PORTB, 7}, // D7 PB7 + {&DDRD, &PINB, &PORTB, 6}, // D8 PB6 + {&DDRD, &PINB, &PORTB, 5}, // D9 PB5 + {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 + {&DDRB, &PINB, &PORTB, 2}, // D11 PB2 + {&DDRB, &PINB, &PORTB, 3}, // D12 PB3 + {&DDRB, &PINB, &PORTB, 1}, // D13 PB1 + {&DDRF, &PINF, &PORTF, 7}, // D14 PF7 + {&DDRF, &PINF, &PORTF, 6}, // D15 PF6 + {&DDRF, &PINF, &PORTF, 5}, // D16 PF5 + {&DDRF, &PINF, &PORTF, 4}, // D17 PF4 + {&DDRD, &PIND, &PORTD, 1}, // D18 PD1 + {&DDRD, &PIND, &PORTD, 0}, // D19 PD0 + {&DDRF, &PINF, &PORTF, 3}, // D20 PF3 + {&DDRF, &PINF, &PORTF, 2}, // D21 PF2 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega32U4__) && defined(CORE_MICRODUINO) +// Microduino Core USB + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 2}, // D0 - PD2 + {&DDRD, &PIND, &PORTD, 3}, // D1 - PD3 + {&DDRE, &PINE, &PORTE, 6}, // D2 - PE6 + {&DDRD, &PIND, &PORTD, 6}, // D3 - PD6 + {&DDRD, &PIND, &PORTD, 7}, // D4 - PD7 + {&DDRC, &PINC, &PORTC, 6}, // D5 - PC6 + {&DDRC, &PINC, &PORTC, 7}, // D6 - PC7 + {&DDRE, &PINE, &PORTE, 7}, // D7 - PE7 + {&DDRB, &PINB, &PORTB, 6}, // D8 - PB6 + {&DDRB, &PINB, &PORTB, 5}, // D9 - PB5 + {&DDRB, &PINB, &PORTB, 0}, // D10 - PB0 + {&DDRB, &PINB, &PORTB, 2}, // D11 - MOSI - PB2 + {&DDRB, &PINB, &PORTB, 3}, // D12 -MISO - PB3 + {&DDRB, &PINB, &PORTB, 1}, // D13 -SCK - PB1 + {&DDRF, &PINF, &PORTF, 7}, // D14 - A0 - PF7 + {&DDRF, &PINF, &PORTF, 6}, // D15 - A1 - PF6 + {&DDRF, &PINF, &PORTF, 5}, // D16 - A2 - PF5 + {&DDRF, &PINF, &PORTF, 4}, // D17 - A3 - PF4 + {&DDRD, &PIND, &PORTD, 1}, // D18 - PD1 + {&DDRD, &PIND, &PORTD, 0}, // D19 - PD0 + {&DDRF, &PINF, &PORTF, 1}, // D20 - A6 - PF1 + {&DDRF, &PINF, &PORTF, 0}, // D21 - A7 - PF0 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega644P__) || defined(__AVR_ATmega644__) +// Sanguino + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 17; +uint8_t const SCL_PIN = 18; + +// SPI port +uint8_t const SS_PIN = 4; +uint8_t const MOSI_PIN = 5; +uint8_t const MISO_PIN = 6; +uint8_t const SCK_PIN = 7; + +static const pin_map_t digitalPinMap[] = { + {&DDRB, &PINB, &PORTB, 0}, // B0 0 + {&DDRB, &PINB, &PORTB, 1}, // B1 1 + {&DDRB, &PINB, &PORTB, 2}, // B2 2 + {&DDRB, &PINB, &PORTB, 3}, // B3 3 + {&DDRB, &PINB, &PORTB, 4}, // B4 4 + {&DDRB, &PINB, &PORTB, 5}, // B5 5 + {&DDRB, &PINB, &PORTB, 6}, // B6 6 + {&DDRB, &PINB, &PORTB, 7}, // B7 7 + {&DDRD, &PIND, &PORTD, 0}, // D0 8 + {&DDRD, &PIND, &PORTD, 1}, // D1 9 + {&DDRD, &PIND, &PORTD, 2}, // D2 10 + {&DDRD, &PIND, &PORTD, 3}, // D3 11 + {&DDRD, &PIND, &PORTD, 4}, // D4 12 + {&DDRD, &PIND, &PORTD, 5}, // D5 13 + {&DDRD, &PIND, &PORTD, 6}, // D6 14 + {&DDRD, &PIND, &PORTD, 7}, // D7 15 + {&DDRC, &PINC, &PORTC, 0}, // C0 16 + {&DDRC, &PINC, &PORTC, 1}, // C1 17 + {&DDRC, &PINC, &PORTC, 2}, // C2 18 + {&DDRC, &PINC, &PORTC, 3}, // C3 19 + {&DDRC, &PINC, &PORTC, 4}, // C4 20 + {&DDRC, &PINC, &PORTC, 5}, // C5 21 + {&DDRC, &PINC, &PORTC, 6}, // C6 22 + {&DDRC, &PINC, &PORTC, 7}, // C7 23 + {&DDRA, &PINA, &PORTA, 7}, // A7 24 + {&DDRA, &PINA, &PORTA, 6}, // A6 25 + {&DDRA, &PINA, &PORTA, 5}, // A5 26 + {&DDRA, &PINA, &PORTA, 4}, // A4 27 + {&DDRA, &PINA, &PORTA, 3}, // A3 28 + {&DDRA, &PINA, &PORTA, 2}, // A2 29 + {&DDRA, &PINA, &PORTA, 1}, // A1 30 + {&DDRA, &PINA, &PORTA, 0} // A0 31 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega32U4__) +// Leonardo + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 2; +uint8_t const SCL_PIN = 3; + +// SPI port +uint8_t const SS_PIN = 17; +uint8_t const MOSI_PIN = 16; +uint8_t const MISO_PIN = 14; +uint8_t const SCK_PIN = 15; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 2}, // D2 0 + {&DDRD, &PIND, &PORTD, 3}, // D3 1 + {&DDRD, &PIND, &PORTD, 1}, // D1 2 + {&DDRD, &PIND, &PORTD, 0}, // D0 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRC, &PINC, &PORTC, 6}, // C6 5 + {&DDRD, &PIND, &PORTD, 7}, // D7 6 + {&DDRE, &PINE, &PORTE, 6}, // E6 7 + {&DDRB, &PINB, &PORTB, 4}, // B4 8 + {&DDRB, &PINB, &PORTB, 5}, // B5 9 + {&DDRB, &PINB, &PORTB, 6}, // B6 10 + {&DDRB, &PINB, &PORTB, 7}, // B7 11 + {&DDRD, &PIND, &PORTD, 6}, // D6 12 + {&DDRC, &PINC, &PORTC, 7}, // C7 13 + {&DDRB, &PINB, &PORTB, 3}, // B3 14 + {&DDRB, &PINB, &PORTB, 1}, // B1 15 + {&DDRB, &PINB, &PORTB, 2}, // B2 16 + {&DDRB, &PINB, &PORTB, 0}, // B0 17 + {&DDRF, &PINF, &PORTF, 7}, // F7 18 + {&DDRF, &PINF, &PORTF, 6}, // F6 19 + {&DDRF, &PINF, &PORTF, 5}, // F5 20 + {&DDRF, &PINF, &PORTF, 4}, // F4 21 + {&DDRF, &PINF, &PORTF, 1}, // F1 22 + {&DDRF, &PINF, &PORTF, 0}, // F0 23 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) +// Teensy++ 1.0 & 2.0 + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 1; +uint8_t const SCL_PIN = 0; + +// SPI port +uint8_t const SS_PIN = 20; +uint8_t const MOSI_PIN = 22; +uint8_t const MISO_PIN = 23; +uint8_t const SCK_PIN = 21; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 0 + {&DDRD, &PIND, &PORTD, 1}, // D1 1 + {&DDRD, &PIND, &PORTD, 2}, // D2 2 + {&DDRD, &PIND, &PORTD, 3}, // D3 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRD, &PIND, &PORTD, 5}, // D5 5 + {&DDRD, &PIND, &PORTD, 6}, // D6 6 + {&DDRD, &PIND, &PORTD, 7}, // D7 7 + {&DDRE, &PINE, &PORTE, 0}, // E0 8 + {&DDRE, &PINE, &PORTE, 1}, // E1 9 + {&DDRC, &PINC, &PORTC, 0}, // C0 10 + {&DDRC, &PINC, &PORTC, 1}, // C1 11 + {&DDRC, &PINC, &PORTC, 2}, // C2 12 + {&DDRC, &PINC, &PORTC, 3}, // C3 13 + {&DDRC, &PINC, &PORTC, 4}, // C4 14 + {&DDRC, &PINC, &PORTC, 5}, // C5 15 + {&DDRC, &PINC, &PORTC, 6}, // C6 16 + {&DDRC, &PINC, &PORTC, 7}, // C7 17 + {&DDRE, &PINE, &PORTE, 6}, // E6 18 + {&DDRE, &PINE, &PORTE, 7}, // E7 19 + {&DDRB, &PINB, &PORTB, 0}, // B0 20 + {&DDRB, &PINB, &PORTB, 1}, // B1 21 + {&DDRB, &PINB, &PORTB, 2}, // B2 22 + {&DDRB, &PINB, &PORTB, 3}, // B3 23 + {&DDRB, &PINB, &PORTB, 4}, // B4 24 + {&DDRB, &PINB, &PORTB, 5}, // B5 25 + {&DDRB, &PINB, &PORTB, 6}, // B6 26 + {&DDRB, &PINB, &PORTB, 7}, // B7 27 + {&DDRA, &PINA, &PORTA, 0}, // A0 28 + {&DDRA, &PINA, &PORTA, 1}, // A1 29 + {&DDRA, &PINA, &PORTA, 2}, // A2 30 + {&DDRA, &PINA, &PORTA, 3}, // A3 31 + {&DDRA, &PINA, &PORTA, 4}, // A4 32 + {&DDRA, &PINA, &PORTA, 5}, // A5 33 + {&DDRA, &PINA, &PORTA, 6}, // A6 34 + {&DDRA, &PINA, &PORTA, 7}, // A7 35 + {&DDRE, &PINE, &PORTE, 4}, // E4 36 + {&DDRE, &PINE, &PORTE, 5}, // E5 37 + {&DDRF, &PINF, &PORTF, 0}, // F0 38 + {&DDRF, &PINF, &PORTF, 1}, // F1 39 + {&DDRF, &PINF, &PORTF, 2}, // F2 40 + {&DDRF, &PINF, &PORTF, 3}, // F3 41 + {&DDRF, &PINF, &PORTF, 4}, // F4 42 + {&DDRF, &PINF, &PORTF, 5}, // F5 43 + {&DDRF, &PINF, &PORTF, 6}, // F6 44 + {&DDRF, &PINF, &PORTF, 7} // F7 45 +}; +//------------------------------------------------------------------------------ +#else // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +// 168 and 328 Arduinos + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 0 + {&DDRD, &PIND, &PORTD, 1}, // D1 1 + {&DDRD, &PIND, &PORTD, 2}, // D2 2 + {&DDRD, &PIND, &PORTD, 3}, // D3 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRD, &PIND, &PORTD, 5}, // D5 5 + {&DDRD, &PIND, &PORTD, 6}, // D6 6 + {&DDRD, &PIND, &PORTD, 7}, // D7 7 + {&DDRB, &PINB, &PORTB, 0}, // B0 8 + {&DDRB, &PINB, &PORTB, 1}, // B1 9 + {&DDRB, &PINB, &PORTB, 2}, // B2 10 + {&DDRB, &PINB, &PORTB, 3}, // B3 11 + {&DDRB, &PINB, &PORTB, 4}, // B4 12 + {&DDRB, &PINB, &PORTB, 5}, // B5 13 + {&DDRC, &PINC, &PORTC, 0}, // C0 14 + {&DDRC, &PINC, &PORTC, 1}, // C1 15 + {&DDRC, &PINC, &PORTC, 2}, // C2 16 + {&DDRC, &PINC, &PORTC, 3}, // C3 17 + {&DDRC, &PINC, &PORTC, 4}, // C4 18 + {&DDRC, &PINC, &PORTC, 5} // C5 19 +}; +#endif // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +//------------------------------------------------------------------------------ +static const uint8_t digitalPinCount = sizeof(digitalPinMap) / sizeof(pin_map_t); + +uint8_t badPinNumber(void) +__attribute__((error("Pin number is too large or not a constant"))); + +static inline __attribute__((always_inline)) +uint8_t getPinMode(uint8_t pin) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + return (*digitalPinMap[pin].ddr >> digitalPinMap[pin].bit) & 1; + } else { + return badPinNumber(); + } +} +static inline __attribute__((always_inline)) +void setPinMode(uint8_t pin, uint8_t mode) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + if (mode) { + *digitalPinMap[pin].ddr |= 1 << digitalPinMap[pin].bit; + } else { + *digitalPinMap[pin].ddr &= ~(1 << digitalPinMap[pin].bit); + } + } else { + badPinNumber(); + } +} +static inline __attribute__((always_inline)) +uint8_t fastDigitalRead(uint8_t pin) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + return (*digitalPinMap[pin].pin >> digitalPinMap[pin].bit) & 1; + } else { + return badPinNumber(); + } +} +static inline __attribute__((always_inline)) +void fastDigitalWrite(uint8_t pin, uint8_t value) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + if (value) { + *digitalPinMap[pin].port |= 1 << digitalPinMap[pin].bit; + } else { + *digitalPinMap[pin].port &= ~(1 << digitalPinMap[pin].bit); + } + } else { + badPinNumber(); + } +} +#endif // Sd2PinMap_h + +#elif defined (__CPU_ARC__) + +#if defined (__ARDUINO_ARC__) + // Two Wire (aka I2C) ports + uint8_t const SDA_PIN = 18; + uint8_t const SCL_PIN = 19; + + // SPI port + uint8_t const SS_PIN = 10; + uint8_t const MOSI_PIN = 11; + uint8_t const MISO_PIN = 12; + uint8_t const SCK_PIN = 13; + +#endif // Arduino ARC + +#else +#error Architecture or board not supported. +#endif diff --git a/megaavr/libraries/SD/src/utility/SdFat.h b/megaavr/libraries/SD/src/utility/SdFat.h new file mode 100755 index 0000000..46b880b --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdFat.h @@ -0,0 +1,641 @@ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef SdFat_h +#define SdFat_h +/** + \file + SdFile and SdVolume classes +*/ +#if defined (__AVR__) || defined (__CPU_ARC__) + #include +#endif +#include "Sd2Card.h" +#include "FatStructs.h" +#include +//------------------------------------------------------------------------------ +/** + Allow use of deprecated functions if non-zero +*/ +#define ALLOW_DEPRECATED_FUNCTIONS 1 +//------------------------------------------------------------------------------ +// forward declaration since SdVolume is used in SdFile +class SdVolume; +//============================================================================== +// SdFile class + +#ifdef O_RDONLY //ARDUINO_ARCH_MBED + #undef O_READ + #undef O_RDONLY + #undef O_WRITE + #undef O_WRONLY + #undef O_RDWR + #undef O_ACCMODE + #undef O_APPEND + #undef O_SYNC + #undef O_CREAT + #undef O_EXCL + #undef O_TRUNC +#endif + +// flags for ls() +/** ls() flag to print modify date */ +uint8_t const LS_DATE = 1; +/** ls() flag to print file size */ +uint8_t const LS_SIZE = 2; +/** ls() flag for recursive list of subdirectories */ +uint8_t const LS_R = 4; + +// use the gnu style oflag in open() +/** open() oflag for reading */ +uint8_t const O_READ = 0X01; +/** open() oflag - same as O_READ */ +uint8_t const O_RDONLY = O_READ; +/** open() oflag for write */ +uint8_t const O_WRITE = 0X02; +/** open() oflag - same as O_WRITE */ +uint8_t const O_WRONLY = O_WRITE; +/** open() oflag for reading and writing */ +uint8_t const O_RDWR = (O_READ | O_WRITE); +/** open() oflag mask for access modes */ +uint8_t const O_ACCMODE = (O_READ | O_WRITE); +/** The file offset shall be set to the end of the file prior to each write. */ +uint8_t const O_APPEND = 0X04; +/** synchronous writes - call sync() after each write */ +uint8_t const O_SYNC = 0X08; +/** create the file if nonexistent */ +uint8_t const O_CREAT = 0X10; +/** If O_CREAT and O_EXCL are set, open() shall fail if the file exists */ +uint8_t const O_EXCL = 0X20; +/** truncate the file to zero length */ +uint8_t const O_TRUNC = 0X40; + +// flags for timestamp +/** set the file's last access date */ +uint8_t const T_ACCESS = 1; +/** set the file's creation date and time */ +uint8_t const T_CREATE = 2; +/** Set the file's write date and time */ +uint8_t const T_WRITE = 4; +// values for type_ +/** This SdFile has not been opened. */ +uint8_t const FAT_FILE_TYPE_CLOSED = 0; +/** SdFile for a file */ +uint8_t const FAT_FILE_TYPE_NORMAL = 1; +/** SdFile for a FAT16 root directory */ +uint8_t const FAT_FILE_TYPE_ROOT16 = 2; +/** SdFile for a FAT32 root directory */ +uint8_t const FAT_FILE_TYPE_ROOT32 = 3; +/** SdFile for a subdirectory */ +uint8_t const FAT_FILE_TYPE_SUBDIR = 4; +/** Test value for directory type */ +uint8_t const FAT_FILE_TYPE_MIN_DIR = FAT_FILE_TYPE_ROOT16; + +/** date field for FAT directory entry */ +static inline uint16_t FAT_DATE(uint16_t year, uint8_t month, uint8_t day) { + return (year - 1980) << 9 | month << 5 | day; +} +/** year part of FAT directory date field */ +static inline uint16_t FAT_YEAR(uint16_t fatDate) { + return 1980 + (fatDate >> 9); +} +/** month part of FAT directory date field */ +static inline uint8_t FAT_MONTH(uint16_t fatDate) { + return (fatDate >> 5) & 0XF; +} +/** day part of FAT directory date field */ +static inline uint8_t FAT_DAY(uint16_t fatDate) { + return fatDate & 0X1F; +} +/** time field for FAT directory entry */ +static inline uint16_t FAT_TIME(uint8_t hour, uint8_t minute, uint8_t second) { + return hour << 11 | minute << 5 | second >> 1; +} +/** hour part of FAT directory time field */ +static inline uint8_t FAT_HOUR(uint16_t fatTime) { + return fatTime >> 11; +} +/** minute part of FAT directory time field */ +static inline uint8_t FAT_MINUTE(uint16_t fatTime) { + return (fatTime >> 5) & 0X3F; +} +/** second part of FAT directory time field */ +static inline uint8_t FAT_SECOND(uint16_t fatTime) { + return 2 * (fatTime & 0X1F); +} +/** Default date for file timestamps is 1 Jan 2000 */ +uint16_t const FAT_DEFAULT_DATE = ((2000 - 1980) << 9) | (1 << 5) | 1; +/** Default time for file timestamp is 1 am */ +uint16_t const FAT_DEFAULT_TIME = (1 << 11); +//------------------------------------------------------------------------------ +/** + \class SdFile + \brief Access FAT16 and FAT32 files on SD and SDHC cards. +*/ +class SdFile : public Print { + public: + /** Create an instance of SdFile. */ + SdFile(void) : type_(FAT_FILE_TYPE_CLOSED) {} + /** + writeError is set to true if an error occurs during a write(). + Set writeError to false before calling print() and/or write() and check + for true after calls to print() and/or write(). + */ + //bool writeError; + /** + Cancel unbuffered reads for this file. + See setUnbufferedRead() + */ + void clearUnbufferedRead(void) { + flags_ &= ~F_FILE_UNBUFFERED_READ; + } + uint8_t close(void); + uint8_t contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); + uint8_t createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size); + /** \return The current cluster number for a file or directory. */ + uint32_t curCluster(void) const { + return curCluster_; + } + /** \return The current position for a file or directory. */ + uint32_t curPosition(void) const { + return curPosition_; + } + /** + Set the date/time callback function + + \param[in] dateTime The user's call back function. The callback + function is of the form: + + \code + void dateTime(uint16_t* date, uint16_t* time) { + uint16_t year; + uint8_t month, day, hour, minute, second; + + // User gets date and time from GPS or real-time clock here + + // return date using FAT_DATE macro to format fields + * *date = FAT_DATE(year, month, day); + + // return time using FAT_TIME macro to format fields + * *time = FAT_TIME(hour, minute, second); + } + \endcode + + Sets the function that is called when a file is created or when + a file's directory entry is modified by sync(). All timestamps, + access, creation, and modify, are set when a file is created. + sync() maintains the last access date and last modify date/time. + + See the timestamp() function. + */ + static void dateTimeCallback( + void (*dateTime)(uint16_t* date, uint16_t* time)) { + dateTime_ = dateTime; + } + /** + Cancel the date/time callback function. + */ + static void dateTimeCallbackCancel(void) { + // use explicit zero since NULL is not defined for Sanguino + dateTime_ = 0; + } + /** \return Address of the block that contains this file's directory. */ + uint32_t dirBlock(void) const { + return dirBlock_; + } + uint8_t dirEntry(dir_t* dir); + /** \return Index of this file's directory in the block dirBlock. */ + uint8_t dirIndex(void) const { + return dirIndex_; + } + static void dirName(const dir_t& dir, char* name); + /** \return The total number of bytes in a file or directory. */ + uint32_t fileSize(void) const { + return fileSize_; + } + /** \return The first cluster number for a file or directory. */ + uint32_t firstCluster(void) const { + return firstCluster_; + } + /** \return True if this is a SdFile for a directory else false. */ + uint8_t isDir(void) const { + return type_ >= FAT_FILE_TYPE_MIN_DIR; + } + /** \return True if this is a SdFile for a file else false. */ + uint8_t isFile(void) const { + return type_ == FAT_FILE_TYPE_NORMAL; + } + /** \return True if this is a SdFile for an open file/directory else false. */ + uint8_t isOpen(void) const { + return type_ != FAT_FILE_TYPE_CLOSED; + } + /** \return True if this is a SdFile for a subdirectory else false. */ + uint8_t isSubDir(void) const { + return type_ == FAT_FILE_TYPE_SUBDIR; + } + /** \return True if this is a SdFile for the root directory. */ + uint8_t isRoot(void) const { + return type_ == FAT_FILE_TYPE_ROOT16 || type_ == FAT_FILE_TYPE_ROOT32; + } + void ls(uint8_t flags = 0, uint8_t indent = 0); + uint8_t makeDir(SdFile* dir, const char* dirName); + uint8_t open(SdFile* dirFile, uint16_t index, uint8_t oflag); + uint8_t open(SdFile* dirFile, const char* fileName, uint8_t oflag); + + uint8_t openRoot(SdVolume* vol); + static void printDirName(const dir_t& dir, uint8_t width); + static void printFatDate(uint16_t fatDate); + static void printFatTime(uint16_t fatTime); + static void printTwoDigits(uint8_t v); + /** + Read the next byte from a file. + + \return For success read returns the next byte in the file as an int. + If an error occurs or end of file is reached -1 is returned. + */ + int16_t read(void) { + uint8_t b; + return read(&b, 1) == 1 ? b : -1; + } + int16_t read(void* buf, uint16_t nbyte); + int8_t readDir(dir_t* dir); + static uint8_t remove(SdFile* dirFile, const char* fileName); + uint8_t remove(void); + /** Set the file's current position to zero. */ + void rewind(void) { + curPosition_ = curCluster_ = 0; + } + uint8_t rmDir(void); + uint8_t rmRfStar(void); + /** Set the files position to current position + \a pos. See seekSet(). */ + uint8_t seekCur(uint32_t pos) { + return seekSet(curPosition_ + pos); + } + /** + Set the files current position to end of file. Useful to position + a file for append. See seekSet(). + */ + uint8_t seekEnd(void) { + return seekSet(fileSize_); + } + uint8_t seekSet(uint32_t pos); + /** + Use unbuffered reads to access this file. Used with Wave + Shield ISR. Used with Sd2Card::partialBlockRead() in WaveRP. + + Not recommended for normal applications. + */ + void setUnbufferedRead(void) { + if (isFile()) { + flags_ |= F_FILE_UNBUFFERED_READ; + } + } + uint8_t timestamp(uint8_t flag, uint16_t year, uint8_t month, uint8_t day, + uint8_t hour, uint8_t minute, uint8_t second); + uint8_t sync(uint8_t blocking = 1); + /** Type of this SdFile. You should use isFile() or isDir() instead of type() + if possible. + + \return The file or directory type. + */ + uint8_t type(void) const { + return type_; + } + uint8_t truncate(uint32_t size); + /** \return Unbuffered read flag. */ + uint8_t unbufferedRead(void) const { + return flags_ & F_FILE_UNBUFFERED_READ; + } + /** \return SdVolume that contains this file. */ + SdVolume* volume(void) const { + return vol_; + } + size_t write(uint8_t b); + size_t write(const void* buf, uint16_t nbyte); + size_t write(const char* str); + #ifdef __AVR__ + void write_P(PGM_P str); + void writeln_P(PGM_P str); + #endif + int availableForWrite(void); + //------------------------------------------------------------------------------ + #if ALLOW_DEPRECATED_FUNCTIONS + // Deprecated functions - suppress cpplint warnings with NOLINT comment + /** \deprecated Use: + uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); + */ + uint8_t contiguousRange(uint32_t& bgnBlock, uint32_t& endBlock) { // NOLINT + return contiguousRange(&bgnBlock, &endBlock); + } + /** \deprecated Use: + uint8_t SdFile::createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size) + */ + uint8_t createContiguous(SdFile& dirFile, // NOLINT + const char* fileName, uint32_t size) { + return createContiguous(&dirFile, fileName, size); + } + + /** + \deprecated Use: + static void SdFile::dateTimeCallback( + void (*dateTime)(uint16_t* date, uint16_t* time)); + */ + static void dateTimeCallback( + void (*dateTime)(uint16_t& date, uint16_t& time)) { // NOLINT + oldDateTime_ = dateTime; + dateTime_ = dateTime ? oldToNew : 0; + } + /** \deprecated Use: uint8_t SdFile::dirEntry(dir_t* dir); */ + uint8_t dirEntry(dir_t& dir) { + return dirEntry(&dir); // NOLINT + } + /** \deprecated Use: + uint8_t SdFile::makeDir(SdFile* dir, const char* dirName); + */ + uint8_t makeDir(SdFile& dir, const char* dirName) { // NOLINT + return makeDir(&dir, dirName); + } + /** \deprecated Use: + uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag); + */ + uint8_t open(SdFile& dirFile, // NOLINT + const char* fileName, uint8_t oflag) { + return open(&dirFile, fileName, oflag); + } + /** \deprecated Do not use in new apps */ + uint8_t open(SdFile& dirFile, const char* fileName) { // NOLINT + return open(dirFile, fileName, O_RDWR); + } + /** \deprecated Use: + uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag); + */ + uint8_t open(SdFile& dirFile, uint16_t index, uint8_t oflag) { // NOLINT + return open(&dirFile, index, oflag); + } + /** \deprecated Use: uint8_t SdFile::openRoot(SdVolume* vol); */ + uint8_t openRoot(SdVolume& vol) { + return openRoot(&vol); // NOLINT + } + + /** \deprecated Use: int8_t SdFile::readDir(dir_t* dir); */ + int8_t readDir(dir_t& dir) { + return readDir(&dir); // NOLINT + } + /** \deprecated Use: + static uint8_t SdFile::remove(SdFile* dirFile, const char* fileName); + */ + static uint8_t remove(SdFile& dirFile, const char* fileName) { // NOLINT + return remove(&dirFile, fileName); + } + //------------------------------------------------------------------------------ + // rest are private + private: + static void (*oldDateTime_)(uint16_t& date, uint16_t& time); // NOLINT + static void oldToNew(uint16_t* date, uint16_t* time) { + uint16_t d; + uint16_t t; + oldDateTime_(d, t); + *date = d; + *time = t; + } + #endif // ALLOW_DEPRECATED_FUNCTIONS + private: + // bits defined in flags_ + // should be 0XF + static uint8_t const F_OFLAG = (O_ACCMODE | O_APPEND | O_SYNC); + // available bits + static uint8_t const F_FILE_NON_BLOCKING_WRITE = 0X10; + // a new cluster was added to the file + static uint8_t const F_FILE_CLUSTER_ADDED = 0X20; + // use unbuffered SD read + static uint8_t const F_FILE_UNBUFFERED_READ = 0X40; + // sync of directory entry required + static uint8_t const F_FILE_DIR_DIRTY = 0X80; + + // make sure F_OFLAG is ok + #if ((F_FILE_NON_BLOCKING_WRITE | F_FILE_CLUSTER_ADDED | F_FILE_UNBUFFERED_READ | F_FILE_DIR_DIRTY) & F_OFLAG) +#error flags_ bits conflict + #endif // flags_ bits + + // private data + uint8_t flags_; // See above for definition of flags_ bits + uint8_t type_; // type of file see above for values + uint32_t curCluster_; // cluster for current file position + uint32_t curPosition_; // current file position in bytes from beginning + uint32_t dirBlock_; // SD block that contains directory entry for file + uint8_t dirIndex_; // index of entry in dirBlock 0 <= dirIndex_ <= 0XF + uint32_t fileSize_; // file size in bytes + uint32_t firstCluster_; // first cluster of file + SdVolume* vol_; // volume where file is located + + // private functions + uint8_t addCluster(void); + uint8_t addDirCluster(void); + dir_t* cacheDirEntry(uint8_t action); + static void (*dateTime_)(uint16_t* date, uint16_t* time); + static uint8_t make83Name(const char* str, uint8_t* name); + uint8_t openCachedEntry(uint8_t cacheIndex, uint8_t oflags); + dir_t* readDirCache(void); +}; +//============================================================================== +// SdVolume class +/** + \brief Cache for an SD data block +*/ +union cache_t { + /** Used to access cached file data blocks. */ + uint8_t data[512]; + /** Used to access cached FAT16 entries. */ + uint16_t fat16[256]; + /** Used to access cached FAT32 entries. */ + uint32_t fat32[128]; + /** Used to access cached directory entries. */ + dir_t dir[16]; + /** Used to access a cached MasterBoot Record. */ + mbr_t mbr; + /** Used to access to a cached FAT boot sector. */ + fbs_t fbs; +}; +//------------------------------------------------------------------------------ +/** + \class SdVolume + \brief Access FAT16 and FAT32 volumes on SD and SDHC cards. +*/ +class SdVolume { + public: + /** Create an instance of SdVolume */ + SdVolume(void) : allocSearchStart_(2), fatType_(0) {} + /** Clear the cache and returns a pointer to the cache. Used by the WaveRP + recorder to do raw write to the SD card. Not for normal apps. + */ + static uint8_t* cacheClear(void) { + cacheFlush(); + cacheBlockNumber_ = 0XFFFFFFFF; + return cacheBuffer_.data; + } + /** + Initialize a FAT volume. Try partition one first then try super + floppy format. + + \param[in] dev The Sd2Card where the volume is located. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. Reasons for + failure include not finding a valid partition, not finding a valid + FAT file system or an I/O error. + */ + uint8_t init(Sd2Card* dev) { + return init(dev, 1) ? true : init(dev, 0); + } + uint8_t init(Sd2Card* dev, uint8_t part); + + // inline functions that return volume info + /** \return The volume's cluster size in blocks. */ + uint8_t blocksPerCluster(void) const { + return blocksPerCluster_; + } + /** \return The number of blocks in one FAT. */ + uint32_t blocksPerFat(void) const { + return blocksPerFat_; + } + /** \return The total number of clusters in the volume. */ + uint32_t clusterCount(void) const { + return clusterCount_; + } + /** \return The shift count required to multiply by blocksPerCluster. */ + uint8_t clusterSizeShift(void) const { + return clusterSizeShift_; + } + /** \return The logical block number for the start of file data. */ + uint32_t dataStartBlock(void) const { + return dataStartBlock_; + } + /** \return The number of FAT structures on the volume. */ + uint8_t fatCount(void) const { + return fatCount_; + } + /** \return The logical block number for the start of the first FAT. */ + uint32_t fatStartBlock(void) const { + return fatStartBlock_; + } + /** \return The FAT type of the volume. Values are 12, 16 or 32. */ + uint8_t fatType(void) const { + return fatType_; + } + /** \return The number of entries in the root directory for FAT16 volumes. */ + uint32_t rootDirEntryCount(void) const { + return rootDirEntryCount_; + } + /** \return The logical block number for the start of the root directory + on FAT16 volumes or the first cluster number on FAT32 volumes. */ + uint32_t rootDirStart(void) const { + return rootDirStart_; + } + /** return a pointer to the Sd2Card object for this volume */ + static Sd2Card* sdCard(void) { + return sdCard_; + } + //------------------------------------------------------------------------------ + #if ALLOW_DEPRECATED_FUNCTIONS + // Deprecated functions - suppress cpplint warnings with NOLINT comment + /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev); */ + uint8_t init(Sd2Card& dev) { + return init(&dev); // NOLINT + } + + /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev, uint8_t vol); */ + uint8_t init(Sd2Card& dev, uint8_t part) { // NOLINT + return init(&dev, part); + } + #endif // ALLOW_DEPRECATED_FUNCTIONS + //------------------------------------------------------------------------------ + private: + // Allow SdFile access to SdVolume private data. + friend class SdFile; + + // value for action argument in cacheRawBlock to indicate read from cache + static uint8_t const CACHE_FOR_READ = 0; + // value for action argument in cacheRawBlock to indicate cache dirty + static uint8_t const CACHE_FOR_WRITE = 1; + + static cache_t cacheBuffer_; // 512 byte cache for device blocks + static uint32_t cacheBlockNumber_; // Logical number of block in the cache + static Sd2Card* sdCard_; // Sd2Card object for cache + static uint8_t cacheDirty_; // cacheFlush() will write block if true + static uint32_t cacheMirrorBlock_; // block number for mirror FAT + // + uint32_t allocSearchStart_; // start cluster for alloc search + uint8_t blocksPerCluster_; // cluster size in blocks + uint32_t blocksPerFat_; // FAT size in blocks + uint32_t clusterCount_; // clusters in one FAT + uint8_t clusterSizeShift_; // shift to convert cluster count to block count + uint32_t dataStartBlock_; // first data block number + uint8_t fatCount_; // number of FATs on volume + uint32_t fatStartBlock_; // start block for first FAT + uint8_t fatType_; // volume type (12, 16, OR 32) + uint16_t rootDirEntryCount_; // number of entries in FAT16 root dir + uint32_t rootDirStart_; // root start block for FAT16, cluster for FAT32 + //---------------------------------------------------------------------------- + uint8_t allocContiguous(uint32_t count, uint32_t* curCluster); + uint8_t blockOfCluster(uint32_t position) const { + return (position >> 9) & (blocksPerCluster_ - 1); + } + uint32_t clusterStartBlock(uint32_t cluster) const { + return dataStartBlock_ + ((cluster - 2) << clusterSizeShift_); + } + uint32_t blockNumber(uint32_t cluster, uint32_t position) const { + return clusterStartBlock(cluster) + blockOfCluster(position); + } + static uint8_t cacheFlush(uint8_t blocking = 1); + static uint8_t cacheMirrorBlockFlush(uint8_t blocking); + static uint8_t cacheRawBlock(uint32_t blockNumber, uint8_t action); + static void cacheSetDirty(void) { + cacheDirty_ |= CACHE_FOR_WRITE; + } + static uint8_t cacheZeroBlock(uint32_t blockNumber); + uint8_t chainSize(uint32_t beginCluster, uint32_t* size) const; + uint8_t fatGet(uint32_t cluster, uint32_t* value) const; + uint8_t fatPut(uint32_t cluster, uint32_t value); + uint8_t fatPutEOC(uint32_t cluster) { + return fatPut(cluster, 0x0FFFFFFF); + } + uint8_t freeChain(uint32_t cluster); + uint8_t isEOC(uint32_t cluster) const { + return cluster >= (fatType_ == 16 ? FAT16EOC_MIN : FAT32EOC_MIN); + } + uint8_t readBlock(uint32_t block, uint8_t* dst) { + return sdCard_->readBlock(block, dst); + } + uint8_t readData(uint32_t block, uint16_t offset, + uint16_t count, uint8_t* dst) { + return sdCard_->readData(block, offset, count, dst); + } + uint8_t writeBlock(uint32_t block, const uint8_t* dst, uint8_t blocking = 1) { + return sdCard_->writeBlock(block, dst, blocking); + } + uint8_t isBusy(void) { + return sdCard_->isBusy(); + } + uint8_t isCacheMirrorBlockDirty(void) { + return (cacheMirrorBlock_ != 0); + } +}; +#endif // SdFat_h diff --git a/megaavr/libraries/SD/src/utility/SdFatUtil.h b/megaavr/libraries/SD/src/utility/SdFatUtil.h new file mode 100755 index 0000000..4b93de8 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdFatUtil.h @@ -0,0 +1,77 @@ +/* Arduino SdFat Library + Copyright (C) 2008 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef SdFatUtil_h +#define SdFatUtil_h +/** + \file + Useful utility functions. +*/ +#include +#ifdef __AVR__ + #include + /** Store and print a string in flash memory.*/ + #define PgmPrint(x) SerialPrint_P(PSTR(x)) + /** Store and print a string in flash memory followed by a CR/LF.*/ + #define PgmPrintln(x) SerialPrintln_P(PSTR(x)) + /** Defined so doxygen works for function definitions. */ +#endif +#define NOINLINE __attribute__((noinline,unused)) +#define UNUSEDOK __attribute__((unused)) +//------------------------------------------------------------------------------ +/** Return the number of bytes currently free in RAM. */ +static UNUSEDOK int FreeRam(void) { + extern int __bss_end; + extern int* __brkval; + int free_memory; + if (reinterpret_cast(__brkval) == 0) { + // if no heap use from end of bss section + free_memory = reinterpret_cast(&free_memory) + - reinterpret_cast(&__bss_end); + } else { + // use from top of stack to heap + free_memory = reinterpret_cast(&free_memory) + - reinterpret_cast(__brkval); + } + return free_memory; +} +#ifdef __AVR__ +//------------------------------------------------------------------------------ +/** + %Print a string in flash memory to the serial port. + + \param[in] str Pointer to string stored in flash memory. +*/ +static NOINLINE void SerialPrint_P(PGM_P str) { + for (uint8_t c; (c = pgm_read_byte(str)); str++) { + Serial.write(c); + } +} +//------------------------------------------------------------------------------ +/** + %Print a string in flash memory followed by a CR/LF. + + \param[in] str Pointer to string stored in flash memory. +*/ +static NOINLINE void SerialPrintln_P(PGM_P str) { + SerialPrint_P(str); + Serial.println(); +} +#endif // __AVR__ +#endif // #define SdFatUtil_h diff --git a/megaavr/libraries/SD/src/utility/SdFatmainpage.h b/megaavr/libraries/SD/src/utility/SdFatmainpage.h new file mode 100755 index 0000000..1e6d96f --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdFatmainpage.h @@ -0,0 +1,202 @@ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ + +/** + \mainpage Arduino SdFat Library +
Copyright © 2009 by William Greiman +
+ + \section Intro Introduction + The Arduino SdFat Library is a minimal implementation of FAT16 and FAT32 + file systems on SD flash memory cards. Standard SD and high capacity + SDHC cards are supported. + + The SdFat only supports short 8.3 names. + + The main classes in SdFat are Sd2Card, SdVolume, and SdFile. + + The Sd2Card class supports access to standard SD cards and SDHC cards. Most + applications will only need to call the Sd2Card::init() member function. + + The SdVolume class supports FAT16 and FAT32 partitions. Most applications + will only need to call the SdVolume::init() member function. + + The SdFile class provides file access functions such as open(), read(), + remove(), write(), close() and sync(). This class supports access to the root + directory and subdirectories. + + A number of example are provided in the SdFat/examples folder. These were + developed to test SdFat and illustrate its use. + + SdFat was developed for high speed data recording. SdFat was used to implement + an audio record/play class, WaveRP, for the Adafruit Wave Shield. This + application uses special Sd2Card calls to write to contiguous files in raw mode. + These functions reduce write latency so that audio can be recorded with the + small amount of RAM in the Arduino. + + \section SDcard SD\SDHC Cards + + Arduinos access SD cards using the cards SPI protocol. PCs, Macs, and + most consumer devices use the 4-bit parallel SD protocol. A card that + functions well on A PC or Mac may not work well on the Arduino. + + Most cards have good SPI read performance but cards vary widely in SPI + write performance. Write performance is limited by how efficiently the + card manages internal erase/remapping operations. The Arduino cannot + optimize writes to reduce erase operations because of its limit RAM. + + SanDisk cards generally have good write performance. They seem to have + more internal RAM buffering than other cards and therefore can limit + the number of flash erase operations that the Arduino forces due to its + limited RAM. + + \section Hardware Hardware Configuration + + SdFat was developed using an + Adafruit Industries + Wave Shield. + + The hardware interface to the SD card should not use a resistor based level + shifter. SdFat sets the SPI bus frequency to 8 MHz which results in signal + rise times that are too slow for the edge detectors in many newer SD card + controllers when resistor voltage dividers are used. + + The 5 to 3.3 V level shifter for 5 V Arduinos should be IC based like the + 74HC4050N based circuit shown in the file SdLevel.png. The Adafruit Wave Shield + uses a 74AHC125N. Gravitech sells SD and MicroSD Card Adapters based on the + 74LCX245. + + If you are using a resistor based level shifter and are having problems try + setting the SPI bus frequency to 4 MHz. This can be done by using + card.init(SPI_HALF_SPEED) to initialize the SD card. + + \section comment Bugs and Comments + + If you wish to report bugs or have comments, send email to fat16lib@sbcglobal.net. + + \section SdFatClass SdFat Usage + + SdFat uses a slightly restricted form of short names. + Only printable ASCII characters are supported. No characters with code point + values greater than 127 are allowed. Space is not allowed even though space + was allowed in the API of early versions of DOS. + + Short names are limited to 8 characters followed by an optional period (.) + and extension of up to 3 characters. The characters may be any combination + of letters and digits. The following special characters are also allowed: + + $ % ' - _ @ ~ ` ! ( ) { } ^ # & + + Short names are always converted to upper case and their original case + value is lost. + + \note + The Arduino Print class uses character + at a time writes so it was necessary to use a \link SdFile::sync() sync() \endlink + function to control when data is written to the SD card. + + \par + An application which writes to a file using \link Print::print() print()\endlink, + \link Print::println() println() \endlink + or \link SdFile::write write() \endlink must call \link SdFile::sync() sync() \endlink + at the appropriate time to force data and directory information to be written + to the SD Card. Data and directory information are also written to the SD card + when \link SdFile::close() close() \endlink is called. + + \par + Applications must use care calling \link SdFile::sync() sync() \endlink + since 2048 bytes of I/O is required to update file and + directory information. This includes writing the current data block, reading + the block that contains the directory entry for update, writing the directory + block back and reading back the current data block. + + It is possible to open a file with two or more instances of SdFile. A file may + be corrupted if data is written to the file by more than one instance of SdFile. + + \section HowTo How to format SD Cards as FAT Volumes + + You should use a freshly formatted SD card for best performance. FAT + file systems become slower if many files have been created and deleted. + This is because the directory entry for a deleted file is marked as deleted, + but is not deleted. When a new file is created, these entries must be scanned + before creating the file, a flaw in the FAT design. Also files can become + fragmented which causes reads and writes to be slower. + + Microsoft operating systems support removable media formatted with a + Master Boot Record, MBR, or formatted as a super floppy with a FAT Boot Sector + in block zero. + + Microsoft operating systems expect MBR formatted removable media + to have only one partition. The first partition should be used. + + Microsoft operating systems do not support partitioning SD flash cards. + If you erase an SD card with a program like KillDisk, Most versions of + Windows will format the card as a super floppy. + + The best way to restore an SD card's format is to use SDFormatter + which can be downloaded from: + + http://www.sdcard.org/consumers/formatter/ + + SDFormatter aligns flash erase boundaries with file + system structures which reduces write latency and file system overhead. + + SDFormatter does not have an option for FAT type so it may format + small cards as FAT12. + + After the MBR is restored by SDFormatter you may need to reformat small + cards that have been formatted FAT12 to force the volume type to be FAT16. + + If you reformat the SD card with an OS utility, choose a cluster size that + will result in: + + 4084 < CountOfClusters && CountOfClusters < 65525 + + The volume will then be FAT16. + + If you are formatting an SD card on OS X or Linux, be sure to use the first + partition. Format this partition with a cluster count in above range. + + \section References References + + Adafruit Industries: + + http://www.adafruit.com/ + + http://www.ladyada.net/make/waveshield/ + + The Arduino site: + + http://www.arduino.cc/ + + For more information about FAT file systems see: + + http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx + + For information about using SD cards as SPI devices see: + + http://www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf + + The ATmega328 datasheet: + + http://www.atmel.com/dyn/resources/prod_documents/doc8161.pdf + + +*/ diff --git a/megaavr/libraries/SD/src/utility/SdFile.cpp b/megaavr/libraries/SD/src/utility/SdFile.cpp new file mode 100755 index 0000000..18a1db6 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdFile.cpp @@ -0,0 +1,1527 @@ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#include "SdFat.h" +#ifdef __AVR__ + #include +#endif +#include +//------------------------------------------------------------------------------ +// callback function for date/time +void (*SdFile::dateTime_)(uint16_t* date, uint16_t* time) = NULL; + +#if ALLOW_DEPRECATED_FUNCTIONS + // suppress cpplint warnings with NOLINT comment + void (*SdFile::oldDateTime_)(uint16_t& date, uint16_t& time) = NULL; // NOLINT +#endif // ALLOW_DEPRECATED_FUNCTIONS +//------------------------------------------------------------------------------ +// add a cluster to a file +uint8_t SdFile::addCluster() { + if (!vol_->allocContiguous(1, &curCluster_)) { + return false; + } + + // if first cluster of file link to directory entry + if (firstCluster_ == 0) { + firstCluster_ = curCluster_; + flags_ |= F_FILE_DIR_DIRTY; + } + flags_ |= F_FILE_CLUSTER_ADDED; + return true; +} +//------------------------------------------------------------------------------ +// Add a cluster to a directory file and zero the cluster. +// return with first block of cluster in the cache +uint8_t SdFile::addDirCluster(void) { + if (!addCluster()) { + return false; + } + + // zero data in cluster insure first cluster is in cache + uint32_t block = vol_->clusterStartBlock(curCluster_); + for (uint8_t i = vol_->blocksPerCluster_; i != 0; i--) { + if (!SdVolume::cacheZeroBlock(block + i - 1)) { + return false; + } + } + // Increase directory file size by cluster size + fileSize_ += 512UL << vol_->clusterSizeShift_; + return true; +} +//------------------------------------------------------------------------------ +// cache a file's directory entry +// return pointer to cached entry or null for failure +dir_t* SdFile::cacheDirEntry(uint8_t action) { + if (!SdVolume::cacheRawBlock(dirBlock_, action)) { + return NULL; + } + return SdVolume::cacheBuffer_.dir + dirIndex_; +} +//------------------------------------------------------------------------------ +/** + Close a file and force cached data and directory information + to be written to the storage device. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include no file is open or an I/O error. +*/ +uint8_t SdFile::close(void) { + if (!sync()) { + return false; + } + type_ = FAT_FILE_TYPE_CLOSED; + return true; +} +//------------------------------------------------------------------------------ +/** + Check for contiguous file and return its raw block range. + + \param[out] bgnBlock the first block address for the file. + \param[out] endBlock the last block address for the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include file is not contiguous, file has zero length + or an I/O error occurred. +*/ +uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock) { + // error if no blocks + if (firstCluster_ == 0) { + return false; + } + + for (uint32_t c = firstCluster_; ; c++) { + uint32_t next; + if (!vol_->fatGet(c, &next)) { + return false; + } + + // check for contiguous + if (next != (c + 1)) { + // error if not end of chain + if (!vol_->isEOC(next)) { + return false; + } + *bgnBlock = vol_->clusterStartBlock(firstCluster_); + *endBlock = vol_->clusterStartBlock(c) + + vol_->blocksPerCluster_ - 1; + return true; + } + } +} +//------------------------------------------------------------------------------ +/** + Create and open a new contiguous file of a specified size. + + \note This function only supports short DOS 8.3 names. + See open() for more information. + + \param[in] dirFile The directory where the file will be created. + \param[in] fileName A valid DOS 8.3 file name. + \param[in] size The desired file size. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include \a fileName contains + an invalid DOS 8.3 file name, the FAT volume has not been initialized, + a file is already open, the file already exists, the root + directory is full or an I/O error. + +*/ +uint8_t SdFile::createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size) { + // don't allow zero length file + if (size == 0) { + return false; + } + if (!open(dirFile, fileName, O_CREAT | O_EXCL | O_RDWR)) { + return false; + } + + // calculate number of clusters needed + uint32_t count = ((size - 1) >> (vol_->clusterSizeShift_ + 9)) + 1; + + // allocate clusters + if (!vol_->allocContiguous(count, &firstCluster_)) { + remove(); + return false; + } + fileSize_ = size; + + // insure sync() will update dir entry + flags_ |= F_FILE_DIR_DIRTY; + return sync(); +} +//------------------------------------------------------------------------------ +/** + Return a files directory entry + + \param[out] dir Location for return of the files directory entry. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::dirEntry(dir_t* dir) { + // make sure fields on SD are correct + if (!sync()) { + return false; + } + + // read entry + dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_READ); + if (!p) { + return false; + } + + // copy to caller's struct + memcpy(dir, p, sizeof(dir_t)); + return true; +} +//------------------------------------------------------------------------------ +/** + Format the name field of \a dir into the 13 byte array + \a name in standard 8.3 short name format. + + \param[in] dir The directory structure containing the name. + \param[out] name A 13 byte char array for the formatted name. +*/ +void SdFile::dirName(const dir_t& dir, char* name) { + uint8_t j = 0; + for (uint8_t i = 0; i < 11; i++) { + if (dir.name[i] == ' ') { + continue; + } + if (i == 8) { + name[j++] = '.'; + } + name[j++] = dir.name[i]; + } + name[j] = 0; +} +//------------------------------------------------------------------------------ +/** List directory contents to Serial. + + \param[in] flags The inclusive OR of + + LS_DATE - %Print file modification date + + LS_SIZE - %Print file size. + + LS_R - Recursive list of subdirectories. + + \param[in] indent Amount of space before file name. Used for recursive + list to indicate subdirectory level. +*/ +void SdFile::ls(uint8_t flags, uint8_t indent) { + dir_t* p; + + rewind(); + while ((p = readDirCache())) { + // done if past last used entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + + // skip deleted entry and entries for . and .. + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + + // only list subdirectories and files + if (!DIR_IS_FILE_OR_SUBDIR(p)) { + continue; + } + + // print any indent spaces + for (int8_t i = 0; i < indent; i++) { + Serial.print(' '); + } + + // print file name with possible blank fill + printDirName(*p, flags & (LS_DATE | LS_SIZE) ? 14 : 0); + + // print modify date/time if requested + if (flags & LS_DATE) { + printFatDate(p->lastWriteDate); + Serial.print(' '); + printFatTime(p->lastWriteTime); + } + // print size if requested + if (!DIR_IS_SUBDIR(p) && (flags & LS_SIZE)) { + Serial.print(' '); + Serial.print(p->fileSize); + } + Serial.println(); + + // list subdirectory content if requested + if ((flags & LS_R) && DIR_IS_SUBDIR(p)) { + uint16_t index = curPosition() / 32 - 1; + SdFile s; + if (s.open(this, index, O_READ)) { + s.ls(flags, indent + 2); + } + seekSet(32 * (index + 1)); + } + } +} +//------------------------------------------------------------------------------ +// format directory name field from a 8.3 name string +uint8_t SdFile::make83Name(const char* str, uint8_t* name) { + uint8_t c; + uint8_t n = 7; // max index for part before dot + uint8_t i = 0; + // blank fill name and extension + while (i < 11) { + name[i++] = ' '; + } + i = 0; + while ((c = *str++) != '\0') { + if (c == '.') { + if (n == 10) { + return false; // only one dot allowed + } + n = 10; // max index for full 8.3 name + i = 8; // place for extension + } else { + // illegal FAT characters + uint8_t b; + #if defined(__AVR__) + PGM_P p = PSTR("|<>^+=?/[];,*\"\\"); + while ((b = pgm_read_byte(p++))) if (b == c) { + return false; + } + #elif defined(__arm__) + const uint8_t valid[] = "|<>^+=?/[];,*\"\\"; + const uint8_t *p = valid; + while ((b = *p++)) if (b == c) { + return false; + } + #endif + // check size and only allow ASCII printable characters + if (i > n || c < 0X21 || c > 0X7E) { + return false; + } + // only upper case allowed in 8.3 names - convert lower to upper + name[i++] = c < 'a' || c > 'z' ? c : c + ('A' - 'a'); + } + } + // must have a file name, extension is optional + return name[0] != ' '; +} +//------------------------------------------------------------------------------ +/** Make a new directory. + + \param[in] dir An open SdFat instance for the directory that will containing + the new directory. + + \param[in] dirName A valid 8.3 DOS name for the new directory. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include this SdFile is already open, \a dir is not a + directory, \a dirName is invalid or already exists in \a dir. +*/ +uint8_t SdFile::makeDir(SdFile* dir, const char* dirName) { + dir_t d; + + // create a normal file + if (!open(dir, dirName, O_CREAT | O_EXCL | O_RDWR)) { + return false; + } + + // convert SdFile to directory + flags_ = O_READ; + type_ = FAT_FILE_TYPE_SUBDIR; + + // allocate and zero first cluster + if (!addDirCluster()) { + return false; + } + + // force entry to SD + if (!sync()) { + return false; + } + + // cache entry - should already be in cache due to sync() call + dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!p) { + return false; + } + + // change directory entry attribute + p->attributes = DIR_ATT_DIRECTORY; + + // make entry for '.' + memcpy(&d, p, sizeof(d)); + for (uint8_t i = 1; i < 11; i++) { + d.name[i] = ' '; + } + d.name[0] = '.'; + + // cache block for '.' and '..' + uint32_t block = vol_->clusterStartBlock(firstCluster_); + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { + return false; + } + + // copy '.' to block + memcpy(&SdVolume::cacheBuffer_.dir[0], &d, sizeof(d)); + + // make entry for '..' + d.name[1] = '.'; + if (dir->isRoot()) { + d.firstClusterLow = 0; + d.firstClusterHigh = 0; + } else { + d.firstClusterLow = dir->firstCluster_ & 0XFFFF; + d.firstClusterHigh = dir->firstCluster_ >> 16; + } + // copy '..' to block + memcpy(&SdVolume::cacheBuffer_.dir[1], &d, sizeof(d)); + + // set position after '..' + curPosition_ = 2 * sizeof(d); + + // write first block + return SdVolume::cacheFlush(); +} +//------------------------------------------------------------------------------ +/** + Open a file or directory by name. + + \param[in] dirFile An open SdFat instance for the directory containing the + file to be opened. + + \param[in] fileName A valid 8.3 DOS name for a file to be opened. + + \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive + OR of flags from the following list + + O_READ - Open for reading. + + O_RDONLY - Same as O_READ. + + O_WRITE - Open for writing. + + O_WRONLY - Same as O_WRITE. + + O_RDWR - Open for reading and writing. + + O_APPEND - If set, the file offset shall be set to the end of the + file prior to each write. + + O_CREAT - If the file exists, this flag has no effect except as noted + under O_EXCL below. Otherwise, the file shall be created + + O_EXCL - If O_CREAT and O_EXCL are set, open() shall fail if the file exists. + + O_SYNC - Call sync() after each write. This flag should not be used with + write(uint8_t), write_P(PGM_P), writeln_P(PGM_P), or the Arduino Print class. + These functions do character at a time writes so sync() will be called + after each byte. + + O_TRUNC - If the file exists and is a regular file, and the file is + successfully opened and is not read only, its length shall be truncated to 0. + + \note Directory files must be opened read only. Write and truncation is + not allowed for directory files. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include this SdFile is already open, \a difFile is not + a directory, \a fileName is invalid, the file does not exist + or can't be opened in the access mode specified by oflag. +*/ +uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag) { + uint8_t dname[11]; + dir_t* p; + + // error if already open + if (isOpen()) { + return false; + } + + if (!make83Name(fileName, dname)) { + return false; + } + vol_ = dirFile->vol_; + dirFile->rewind(); + + // bool for empty entry found + uint8_t emptyFound = false; + + // search for file + while (dirFile->curPosition_ < dirFile->fileSize_) { + uint8_t index = 0XF & (dirFile->curPosition_ >> 5); + p = dirFile->readDirCache(); + if (p == NULL) { + return false; + } + + if (p->name[0] == DIR_NAME_FREE || p->name[0] == DIR_NAME_DELETED) { + // remember first empty slot + if (!emptyFound) { + emptyFound = true; + dirIndex_ = index; + dirBlock_ = SdVolume::cacheBlockNumber_; + } + // done if no entries follow + if (p->name[0] == DIR_NAME_FREE) { + break; + } + } else if (!memcmp(dname, p->name, 11)) { + // don't open existing file if O_CREAT and O_EXCL + if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { + return false; + } + + // open found file + return openCachedEntry(0XF & index, oflag); + } + } + // only create file if O_CREAT and O_WRITE + if ((oflag & (O_CREAT | O_WRITE)) != (O_CREAT | O_WRITE)) { + return false; + } + + // cache found slot or add cluster if end of file + if (emptyFound) { + p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!p) { + return false; + } + } else { + if (dirFile->type_ == FAT_FILE_TYPE_ROOT16) { + return false; + } + + // add and zero cluster for dirFile - first cluster is in cache for write + if (!dirFile->addDirCluster()) { + return false; + } + + // use first entry in cluster + dirIndex_ = 0; + p = SdVolume::cacheBuffer_.dir; + } + // initialize as empty file + memset(p, 0, sizeof(dir_t)); + memcpy(p->name, dname, 11); + + // set timestamps + if (dateTime_) { + // call user function + dateTime_(&p->creationDate, &p->creationTime); + } else { + // use default date/time + p->creationDate = FAT_DEFAULT_DATE; + p->creationTime = FAT_DEFAULT_TIME; + } + p->lastAccessDate = p->creationDate; + p->lastWriteDate = p->creationDate; + p->lastWriteTime = p->creationTime; + + // force write of entry to SD + if (!SdVolume::cacheFlush()) { + return false; + } + + // open entry in cache + return openCachedEntry(dirIndex_, oflag); +} +//------------------------------------------------------------------------------ +/** + Open a file by index. + + \param[in] dirFile An open SdFat instance for the directory. + + \param[in] index The \a index of the directory entry for the file to be + opened. The value for \a index is (directory file position)/32. + + \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive + OR of flags O_READ, O_WRITE, O_TRUNC, and O_SYNC. + + See open() by fileName for definition of flags and return values. + +*/ +uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag) { + // error if already open + if (isOpen()) { + return false; + } + + // don't open existing file if O_CREAT and O_EXCL - user call error + if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { + return false; + } + + vol_ = dirFile->vol_; + + // seek to location of entry + if (!dirFile->seekSet(32 * index)) { + return false; + } + + // read entry into cache + dir_t* p = dirFile->readDirCache(); + if (p == NULL) { + return false; + } + + // error if empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_FREE || + p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + return false; + } + // open cached entry + return openCachedEntry(index & 0XF, oflag); +} +//------------------------------------------------------------------------------ +// open a cached directory entry. Assumes vol_ is initializes +uint8_t SdFile::openCachedEntry(uint8_t dirIndex, uint8_t oflag) { + // location of entry in cache + dir_t* p = SdVolume::cacheBuffer_.dir + dirIndex; + + // write or truncate is an error for a directory or read-only file + if (p->attributes & (DIR_ATT_READ_ONLY | DIR_ATT_DIRECTORY)) { + if (oflag & (O_WRITE | O_TRUNC)) { + return false; + } + } + // remember location of directory entry on SD + dirIndex_ = dirIndex; + dirBlock_ = SdVolume::cacheBlockNumber_; + + // copy first cluster number for directory fields + firstCluster_ = (uint32_t)p->firstClusterHigh << 16; + firstCluster_ |= p->firstClusterLow; + + // make sure it is a normal file or subdirectory + if (DIR_IS_FILE(p)) { + fileSize_ = p->fileSize; + type_ = FAT_FILE_TYPE_NORMAL; + } else if (DIR_IS_SUBDIR(p)) { + if (!vol_->chainSize(firstCluster_, &fileSize_)) { + return false; + } + type_ = FAT_FILE_TYPE_SUBDIR; + } else { + return false; + } + // save open flags for read/write + flags_ = oflag & (O_ACCMODE | O_SYNC | O_APPEND); + + // set to start of file + curCluster_ = 0; + curPosition_ = 0; + + // truncate file to zero length if requested + if (oflag & O_TRUNC) { + return truncate(0); + } + return true; +} +//------------------------------------------------------------------------------ +/** + Open a volume's root directory. + + \param[in] vol The FAT volume containing the root directory to be opened. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the FAT volume has not been initialized + or it a FAT12 volume. +*/ +uint8_t SdFile::openRoot(SdVolume* vol) { + // error if file is already open + if (isOpen()) { + return false; + } + + if (vol->fatType() == 16) { + type_ = FAT_FILE_TYPE_ROOT16; + firstCluster_ = 0; + fileSize_ = 32 * vol->rootDirEntryCount(); + } else if (vol->fatType() == 32) { + type_ = FAT_FILE_TYPE_ROOT32; + firstCluster_ = vol->rootDirStart(); + if (!vol->chainSize(firstCluster_, &fileSize_)) { + return false; + } + } else { + // volume is not initialized or FAT12 + return false; + } + vol_ = vol; + // read only + flags_ = O_READ; + + // set to start of file + curCluster_ = 0; + curPosition_ = 0; + + // root has no directory entry + dirBlock_ = 0; + dirIndex_ = 0; + return true; +} +//------------------------------------------------------------------------------ +/** %Print the name field of a directory entry in 8.3 format to Serial. + + \param[in] dir The directory structure containing the name. + \param[in] width Blank fill name if length is less than \a width. +*/ +void SdFile::printDirName(const dir_t& dir, uint8_t width) { + uint8_t w = 0; + for (uint8_t i = 0; i < 11; i++) { + if (dir.name[i] == ' ') { + continue; + } + if (i == 8) { + Serial.print('.'); + w++; + } + Serial.write(dir.name[i]); + w++; + } + if (DIR_IS_SUBDIR(&dir)) { + Serial.print('/'); + w++; + } + while (w < width) { + Serial.print(' '); + w++; + } +} +//------------------------------------------------------------------------------ +/** %Print a directory date field to Serial. + + Format is yyyy-mm-dd. + + \param[in] fatDate The date field from a directory entry. +*/ +void SdFile::printFatDate(uint16_t fatDate) { + Serial.print(FAT_YEAR(fatDate)); + Serial.print('-'); + printTwoDigits(FAT_MONTH(fatDate)); + Serial.print('-'); + printTwoDigits(FAT_DAY(fatDate)); +} +//------------------------------------------------------------------------------ +/** %Print a directory time field to Serial. + + Format is hh:mm:ss. + + \param[in] fatTime The time field from a directory entry. +*/ +void SdFile::printFatTime(uint16_t fatTime) { + printTwoDigits(FAT_HOUR(fatTime)); + Serial.print(':'); + printTwoDigits(FAT_MINUTE(fatTime)); + Serial.print(':'); + printTwoDigits(FAT_SECOND(fatTime)); +} +//------------------------------------------------------------------------------ +/** %Print a value as two digits to Serial. + + \param[in] v Value to be printed, 0 <= \a v <= 99 +*/ +void SdFile::printTwoDigits(uint8_t v) { + char str[3]; + str[0] = '0' + v / 10; + str[1] = '0' + v % 10; + str[2] = 0; + Serial.print(str); +} +//------------------------------------------------------------------------------ +/** + Read data from a file starting at the current position. + + \param[out] buf Pointer to the location that will receive the data. + + \param[in] nbyte Maximum number of bytes to read. + + \return For success read() returns the number of bytes read. + A value less than \a nbyte, including zero, will be returned + if end of file is reached. + If an error occurs, read() returns -1. Possible errors include + read() called before a file has been opened, corrupt file system + or an I/O error occurred. +*/ +int16_t SdFile::read(void* buf, uint16_t nbyte) { + uint8_t* dst = reinterpret_cast(buf); + + // error if not open or write only + if (!isOpen() || !(flags_ & O_READ)) { + return -1; + } + + // max bytes left in file + if (nbyte > (fileSize_ - curPosition_)) { + nbyte = fileSize_ - curPosition_; + } + + // amount left to read + uint16_t toRead = nbyte; + while (toRead > 0) { + uint32_t block; // raw device block number + uint16_t offset = curPosition_ & 0X1FF; // offset in block + if (type_ == FAT_FILE_TYPE_ROOT16) { + block = vol_->rootDirStart() + (curPosition_ >> 9); + } else { + uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); + if (offset == 0 && blockOfCluster == 0) { + // start of new cluster + if (curPosition_ == 0) { + // use first cluster in file + curCluster_ = firstCluster_; + } else { + // get next cluster from FAT + if (!vol_->fatGet(curCluster_, &curCluster_)) { + return -1; + } + } + } + block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; + } + uint16_t n = toRead; + + // amount to be read from current block + if (n > (512 - offset)) { + n = 512 - offset; + } + + // no buffering needed if n == 512 or user requests no buffering + if ((unbufferedRead() || n == 512) && + block != SdVolume::cacheBlockNumber_) { + if (!vol_->readData(block, offset, n, dst)) { + return -1; + } + dst += n; + } else { + // read block to cache and copy data to caller + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_READ)) { + return -1; + } + uint8_t* src = SdVolume::cacheBuffer_.data + offset; + uint8_t* end = src + n; + while (src != end) { + *dst++ = *src++; + } + } + curPosition_ += n; + toRead -= n; + } + return nbyte; +} +//------------------------------------------------------------------------------ +/** + Read the next directory entry from a directory file. + + \param[out] dir The dir_t struct that will receive the data. + + \return For success readDir() returns the number of bytes read. + A value of zero will be returned if end of file is reached. + If an error occurs, readDir() returns -1. Possible errors include + readDir() called before a directory has been opened, this is not + a directory file or an I/O error occurred. +*/ +int8_t SdFile::readDir(dir_t* dir) { + int8_t n; + // if not a directory file or miss-positioned return an error + if (!isDir() || (0X1F & curPosition_)) { + return -1; + } + + while ((n = read(dir, sizeof(dir_t))) == sizeof(dir_t)) { + // last entry if DIR_NAME_FREE + if (dir->name[0] == DIR_NAME_FREE) { + break; + } + // skip empty entries and entry for . and .. + if (dir->name[0] == DIR_NAME_DELETED || dir->name[0] == '.') { + continue; + } + // return if normal file or subdirectory + if (DIR_IS_FILE_OR_SUBDIR(dir)) { + return n; + } + } + // error, end of file, or past last entry + return n < 0 ? -1 : 0; +} +//------------------------------------------------------------------------------ +// Read next directory entry into the cache +// Assumes file is correctly positioned +dir_t* SdFile::readDirCache(void) { + // error if not directory + if (!isDir()) { + return NULL; + } + + // index of entry in cache + uint8_t i = (curPosition_ >> 5) & 0XF; + + // use read to locate and cache block + if (read() < 0) { + return NULL; + } + + // advance to next entry + curPosition_ += 31; + + // return pointer to entry + return (SdVolume::cacheBuffer_.dir + i); +} +//------------------------------------------------------------------------------ +/** + Remove a file. + + The directory entry and all data for the file are deleted. + + \note This function should not be used to delete the 8.3 version of a + file that has a long name. For example if a file has the long name + "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file read-only, is a directory, + or an I/O error occurred. +*/ +uint8_t SdFile::remove(void) { + // free any clusters - will fail if read-only or directory + if (!truncate(0)) { + return false; + } + + // cache directory entry + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + // mark entry deleted + d->name[0] = DIR_NAME_DELETED; + + // set this SdFile closed + type_ = FAT_FILE_TYPE_CLOSED; + + // write entry to SD + return SdVolume::cacheFlush(); +} +//------------------------------------------------------------------------------ +/** + Remove a file. + + The directory entry and all data for the file are deleted. + + \param[in] dirFile The directory that contains the file. + \param[in] fileName The name of the file to be removed. + + \note This function should not be used to delete the 8.3 version of a + file that has a long name. For example if a file has the long name + "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file is a directory, is read only, + \a dirFile is not a directory, \a fileName is not found + or an I/O error occurred. +*/ +uint8_t SdFile::remove(SdFile* dirFile, const char* fileName) { + SdFile file; + if (!file.open(dirFile, fileName, O_WRITE)) { + return false; + } + return file.remove(); +} +//------------------------------------------------------------------------------ +/** Remove a directory file. + + The directory file will be removed only if it is empty and is not the + root directory. rmDir() follows DOS and Windows and ignores the + read-only attribute for the directory. + + \note This function should not be used to delete the 8.3 version of a + directory that has a long name. For example if a directory has the + long name "New folder" you should not delete the 8.3 name "NEWFOL~1". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file is not a directory, is the root + directory, is not empty, or an I/O error occurred. +*/ +uint8_t SdFile::rmDir(void) { + // must be open subdirectory + if (!isSubDir()) { + return false; + } + + rewind(); + + // make sure directory is empty + while (curPosition_ < fileSize_) { + dir_t* p = readDirCache(); + if (p == NULL) { + return false; + } + // done if past last used entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + // skip empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + // error not empty + if (DIR_IS_FILE_OR_SUBDIR(p)) { + return false; + } + } + // convert empty directory to normal file for remove + type_ = FAT_FILE_TYPE_NORMAL; + flags_ |= O_WRITE; + return remove(); +} +//------------------------------------------------------------------------------ +/** Recursively delete a directory and all contained files. + + This is like the Unix/Linux 'rm -rf *' if called with the root directory + hence the name. + + Warning - This will remove all contents of the directory including + subdirectories. The directory will then be removed if it is not root. + The read-only attribute for files will be ignored. + + \note This function should not be used to delete the 8.3 version of + a directory that has a long name. See remove() and rmDir(). + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::rmRfStar(void) { + rewind(); + while (curPosition_ < fileSize_) { + SdFile f; + + // remember position + uint16_t index = curPosition_ / 32; + + dir_t* p = readDirCache(); + if (!p) { + return false; + } + + // done if past last entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + + // skip empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + + // skip if part of long file name or volume label in root + if (!DIR_IS_FILE_OR_SUBDIR(p)) { + continue; + } + + if (!f.open(this, index, O_READ)) { + return false; + } + if (f.isSubDir()) { + // recursively delete + if (!f.rmRfStar()) { + return false; + } + } else { + // ignore read-only + f.flags_ |= O_WRITE; + if (!f.remove()) { + return false; + } + } + // position to next entry if required + if (curPosition_ != (32u * (index + 1))) { + if (!seekSet(32u * (index + 1))) { + return false; + } + } + } + // don't try to delete root + if (isRoot()) { + return true; + } + return rmDir(); +} +//------------------------------------------------------------------------------ +/** + Sets a file's position. + + \param[in] pos The new position in bytes from the beginning of the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::seekSet(uint32_t pos) { + // error if file not open or seek past end of file + if (!isOpen() || pos > fileSize_) { + return false; + } + + if (type_ == FAT_FILE_TYPE_ROOT16) { + curPosition_ = pos; + return true; + } + if (pos == 0) { + // set position to start of file + curCluster_ = 0; + curPosition_ = 0; + return true; + } + // calculate cluster index for cur and new position + uint32_t nCur = (curPosition_ - 1) >> (vol_->clusterSizeShift_ + 9); + uint32_t nNew = (pos - 1) >> (vol_->clusterSizeShift_ + 9); + + if (nNew < nCur || curPosition_ == 0) { + // must follow chain from first cluster + curCluster_ = firstCluster_; + } else { + // advance from curPosition + nNew -= nCur; + } + while (nNew--) { + if (!vol_->fatGet(curCluster_, &curCluster_)) { + return false; + } + } + curPosition_ = pos; + return true; +} +//------------------------------------------------------------------------------ +/** + The sync() call causes all modified data and directory fields + to be written to the storage device. + + \param[in] blocking If the sync should block until fully complete. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include a call to sync() before a file has been + opened or an I/O error. +*/ +uint8_t SdFile::sync(uint8_t blocking) { + // only allow open files and directories + if (!isOpen()) { + return false; + } + + if (flags_ & F_FILE_DIR_DIRTY) { + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + // do not set filesize for dir files + if (!isDir()) { + d->fileSize = fileSize_; + } + + // update first cluster fields + d->firstClusterLow = firstCluster_ & 0XFFFF; + d->firstClusterHigh = firstCluster_ >> 16; + + // set modify time if user supplied a callback date/time function + if (dateTime_) { + dateTime_(&d->lastWriteDate, &d->lastWriteTime); + d->lastAccessDate = d->lastWriteDate; + } + // clear directory dirty + flags_ &= ~F_FILE_DIR_DIRTY; + } + + if (!blocking) { + flags_ &= ~F_FILE_NON_BLOCKING_WRITE; + } + + return SdVolume::cacheFlush(blocking); +} +//------------------------------------------------------------------------------ +/** + Set a file's timestamps in its directory entry. + + \param[in] flags Values for \a flags are constructed by a bitwise-inclusive + OR of flags from the following list + + T_ACCESS - Set the file's last access date. + + T_CREATE - Set the file's creation date and time. + + T_WRITE - Set the file's last write/modification date and time. + + \param[in] year Valid range 1980 - 2107 inclusive. + + \param[in] month Valid range 1 - 12 inclusive. + + \param[in] day Valid range 1 - 31 inclusive. + + \param[in] hour Valid range 0 - 23 inclusive. + + \param[in] minute Valid range 0 - 59 inclusive. + + \param[in] second Valid range 0 - 59 inclusive + + \note It is possible to set an invalid date since there is no check for + the number of days in a month. + + \note + Modify and access timestamps may be overwritten if a date time callback + function has been set by dateTimeCallback(). + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::timestamp(uint8_t flags, uint16_t year, uint8_t month, + uint8_t day, uint8_t hour, uint8_t minute, uint8_t second) { + if (!isOpen() + || year < 1980 + || year > 2107 + || month < 1 + || month > 12 + || day < 1 + || day > 31 + || hour > 23 + || minute > 59 + || second > 59) { + return false; + } + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + uint16_t dirDate = FAT_DATE(year, month, day); + uint16_t dirTime = FAT_TIME(hour, minute, second); + if (flags & T_ACCESS) { + d->lastAccessDate = dirDate; + } + if (flags & T_CREATE) { + d->creationDate = dirDate; + d->creationTime = dirTime; + // seems to be units of 1/100 second not 1/10 as Microsoft states + d->creationTimeTenths = second & 1 ? 100 : 0; + } + if (flags & T_WRITE) { + d->lastWriteDate = dirDate; + d->lastWriteTime = dirTime; + } + SdVolume::cacheSetDirty(); + return sync(); +} +//------------------------------------------------------------------------------ +/** + Truncate a file to a specified length. The current file position + will be maintained if it is less than or equal to \a length otherwise + it will be set to end of file. + + \param[in] length The desired length for the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include file is read only, file is a directory, + \a length is greater than the current file size or an I/O error occurs. +*/ +uint8_t SdFile::truncate(uint32_t length) { + // error if not a normal file or read-only + if (!isFile() || !(flags_ & O_WRITE)) { + return false; + } + + // error if length is greater than current size + if (length > fileSize_) { + return false; + } + + // fileSize and length are zero - nothing to do + if (fileSize_ == 0) { + return true; + } + + // remember position for seek after truncation + uint32_t newPos = curPosition_ > length ? length : curPosition_; + + // position to last cluster in truncated file + if (!seekSet(length)) { + return false; + } + + if (length == 0) { + // free all clusters + if (!vol_->freeChain(firstCluster_)) { + return false; + } + firstCluster_ = 0; + } else { + uint32_t toFree; + if (!vol_->fatGet(curCluster_, &toFree)) { + return false; + } + + if (!vol_->isEOC(toFree)) { + // free extra clusters + if (!vol_->freeChain(toFree)) { + return false; + } + + // current cluster is end of chain + if (!vol_->fatPutEOC(curCluster_)) { + return false; + } + } + } + fileSize_ = length; + + // need to update directory entry + flags_ |= F_FILE_DIR_DIRTY; + + if (!sync()) { + return false; + } + + // set file to correct position + return seekSet(newPos); +} +//------------------------------------------------------------------------------ +/** + Write data to an open file. + + \note Data is moved to the cache but may not be written to the + storage device until sync() is called. + + \param[in] buf Pointer to the location of the data to be written. + + \param[in] nbyte Number of bytes to write. + + \return For success write() returns the number of bytes written, always + \a nbyte. If an error occurs, write() returns 0. Possible errors + include write() is called before a file has been opened, write is called + for a read-only file, device is full, a corrupt file system or an I/O error. + +*/ +size_t SdFile::write(const void* buf, uint16_t nbyte) { + // convert void* to uint8_t* - must be before goto statements + const uint8_t* src = reinterpret_cast(buf); + + // number of bytes left to write - must be before goto statements + uint16_t nToWrite = nbyte; + // if blocking writes should be used + uint8_t blocking = (flags_ & F_FILE_NON_BLOCKING_WRITE) == 0x00; + + // error if not a normal file or is read-only + if (!isFile() || !(flags_ & O_WRITE)) { + goto writeErrorReturn; + } + + // seek to end of file if append flag + if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { + if (!seekEnd()) { + goto writeErrorReturn; + } + } + + while (nToWrite > 0) { + uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); + uint16_t blockOffset = curPosition_ & 0X1FF; + if (blockOfCluster == 0 && blockOffset == 0) { + // start of new cluster + if (curCluster_ == 0) { + if (firstCluster_ == 0) { + // allocate first cluster of file + if (!addCluster()) { + goto writeErrorReturn; + } + } else { + curCluster_ = firstCluster_; + } + } else { + uint32_t next; + if (!vol_->fatGet(curCluster_, &next)) { + return false; + } + if (vol_->isEOC(next)) { + // add cluster if at end of chain + if (!addCluster()) { + goto writeErrorReturn; + } + } else { + curCluster_ = next; + } + } + } + // max space in block + uint16_t n = 512 - blockOffset; + + // lesser of space and amount to write + if (n > nToWrite) { + n = nToWrite; + } + + // block for data write + uint32_t block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; + if (n == 512) { + // full block - don't need to use cache + // invalidate cache if block is in cache + if (SdVolume::cacheBlockNumber_ == block) { + SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; + } + if (!vol_->writeBlock(block, src, blocking)) { + goto writeErrorReturn; + } + src += 512; + } else { + if (blockOffset == 0 && curPosition_ >= fileSize_) { + // start of new block don't need to read into cache + if (!SdVolume::cacheFlush()) { + goto writeErrorReturn; + } + SdVolume::cacheBlockNumber_ = block; + SdVolume::cacheSetDirty(); + } else { + // rewrite part of block + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { + goto writeErrorReturn; + } + } + uint8_t* dst = SdVolume::cacheBuffer_.data + blockOffset; + uint8_t* end = dst + n; + while (dst != end) { + *dst++ = *src++; + } + } + nToWrite -= n; + curPosition_ += n; + } + if (curPosition_ > fileSize_) { + // update fileSize and insure sync will update dir entry + fileSize_ = curPosition_; + flags_ |= F_FILE_DIR_DIRTY; + } else if (dateTime_ && nbyte) { + // insure sync will update modified date and time + flags_ |= F_FILE_DIR_DIRTY; + } + + if (flags_ & O_SYNC) { + if (!sync()) { + goto writeErrorReturn; + } + } + return nbyte; + +writeErrorReturn: + // return for write error + //writeError = true; + setWriteError(); + return 0; +} +//------------------------------------------------------------------------------ +/** + Write a byte to a file. Required by the Arduino Print class. + + Use SdFile::writeError to check for errors. +*/ +size_t SdFile::write(uint8_t b) { + return write(&b, 1); +} +//------------------------------------------------------------------------------ +/** + Write a string to a file. Used by the Arduino Print class. + + Use SdFile::writeError to check for errors. +*/ +size_t SdFile::write(const char* str) { + return write(str, strlen(str)); +} +#ifdef __AVR__ +//------------------------------------------------------------------------------ +/** + Write a PROGMEM string to a file. + + Use SdFile::writeError to check for errors. +*/ +void SdFile::write_P(PGM_P str) { + for (uint8_t c; (c = pgm_read_byte(str)); str++) { + write(c); + } +} +//------------------------------------------------------------------------------ +/** + Write a PROGMEM string followed by CR/LF to a file. + + Use SdFile::writeError to check for errors. +*/ +void SdFile::writeln_P(PGM_P str) { + write_P(str); + println(); +} +#endif +//------------------------------------------------------------------------------ +/** + Check how many bytes can be written without blocking. + + \return The number of bytes that can be written without blocking. +*/ +int SdFile::availableForWrite() { + if (!isFile() || !(flags_ & O_WRITE)) { + return 0; + } + + // seek to end of file if append flag + if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { + if (!seekEnd()) { + return 0; + } + } + + if (vol_->isBusy()) { + return 0; + } + + if (flags_ & F_FILE_CLUSTER_ADDED) { + // new cluster added, trigger a non-blocking sync + sync(0); + flags_ &= ~F_FILE_CLUSTER_ADDED; + return 0; + } + + if (vol_->isCacheMirrorBlockDirty()) { + // cache mirror block is dirty, trigger a non-blocking sync + vol_->cacheMirrorBlockFlush(0); + return 0; + } + + flags_ |= F_FILE_NON_BLOCKING_WRITE; + + uint16_t blockOffset = curPosition_ & 0X1FF; + uint16_t n = 512 - blockOffset; + + return n; +} diff --git a/megaavr/libraries/SD/src/utility/SdInfo.h b/megaavr/libraries/SD/src/utility/SdInfo.h new file mode 100755 index 0000000..6a0e087 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdInfo.h @@ -0,0 +1,232 @@ +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#ifndef SdInfo_h +#define SdInfo_h +#include +// Based on the document: +// +// SD Specifications +// Part 1 +// Physical Layer +// Simplified Specification +// Version 2.00 +// September 25, 2006 +// +// www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf +//------------------------------------------------------------------------------ +// SD card commands +/** GO_IDLE_STATE - init card in spi mode if CS low */ +uint8_t const CMD0 = 0X00; +/** SEND_IF_COND - verify SD Memory Card interface operating condition.*/ +uint8_t const CMD8 = 0X08; +/** SEND_CSD - read the Card Specific Data (CSD register) */ +uint8_t const CMD9 = 0X09; +/** SEND_CID - read the card identification information (CID register) */ +uint8_t const CMD10 = 0X0A; +/** SEND_STATUS - read the card status register */ +uint8_t const CMD13 = 0X0D; +/** READ_BLOCK - read a single data block from the card */ +uint8_t const CMD17 = 0X11; +/** WRITE_BLOCK - write a single data block to the card */ +uint8_t const CMD24 = 0X18; +/** WRITE_MULTIPLE_BLOCK - write blocks of data until a STOP_TRANSMISSION */ +uint8_t const CMD25 = 0X19; +/** ERASE_WR_BLK_START - sets the address of the first block to be erased */ +uint8_t const CMD32 = 0X20; +/** ERASE_WR_BLK_END - sets the address of the last block of the continuous + range to be erased*/ +uint8_t const CMD33 = 0X21; +/** ERASE - erase all previously selected blocks */ +uint8_t const CMD38 = 0X26; +/** APP_CMD - escape for application specific command */ +uint8_t const CMD55 = 0X37; +/** READ_OCR - read the OCR register of a card */ +uint8_t const CMD58 = 0X3A; +/** SET_WR_BLK_ERASE_COUNT - Set the number of write blocks to be + pre-erased before writing */ +uint8_t const ACMD23 = 0X17; +/** SD_SEND_OP_COMD - Sends host capacity support information and + activates the card's initialization process */ +uint8_t const ACMD41 = 0X29; +//------------------------------------------------------------------------------ +/** status for card in the ready state */ +uint8_t const R1_READY_STATE = 0X00; +/** status for card in the idle state */ +uint8_t const R1_IDLE_STATE = 0X01; +/** status bit for illegal command */ +uint8_t const R1_ILLEGAL_COMMAND = 0X04; +/** start data token for read or write single block*/ +uint8_t const DATA_START_BLOCK = 0XFE; +/** stop token for write multiple blocks*/ +uint8_t const STOP_TRAN_TOKEN = 0XFD; +/** start data token for write multiple blocks*/ +uint8_t const WRITE_MULTIPLE_TOKEN = 0XFC; +/** mask for data response tokens after a write block operation */ +uint8_t const DATA_RES_MASK = 0X1F; +/** write data accepted token */ +uint8_t const DATA_RES_ACCEPTED = 0X05; +//------------------------------------------------------------------------------ +typedef struct CID { + // byte 0 + uint8_t mid; // Manufacturer ID + // byte 1-2 + char oid[2]; // OEM/Application ID + // byte 3-7 + char pnm[5]; // Product name + // byte 8 + unsigned prv_m : 4; // Product revision n.m + unsigned prv_n : 4; + // byte 9-12 + uint32_t psn; // Product serial number + // byte 13 + unsigned mdt_year_high : 4; // Manufacturing date + unsigned reserved : 4; + // byte 14 + unsigned mdt_month : 4; + unsigned mdt_year_low : 4; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} cid_t; +//------------------------------------------------------------------------------ +// CSD for version 1.00 cards +typedef struct CSDV1 { + // byte 0 + unsigned reserved1 : 6; + unsigned csd_ver : 2; + // byte 1 + uint8_t taac; + // byte 2 + uint8_t nsac; + // byte 3 + uint8_t tran_speed; + // byte 4 + uint8_t ccc_high; + // byte 5 + unsigned read_bl_len : 4; + unsigned ccc_low : 4; + // byte 6 + unsigned c_size_high : 2; + unsigned reserved2 : 2; + unsigned dsr_imp : 1; + unsigned read_blk_misalign : 1; + unsigned write_blk_misalign : 1; + unsigned read_bl_partial : 1; + // byte 7 + uint8_t c_size_mid; + // byte 8 + unsigned vdd_r_curr_max : 3; + unsigned vdd_r_curr_min : 3; + unsigned c_size_low : 2; + // byte 9 + unsigned c_size_mult_high : 2; + unsigned vdd_w_cur_max : 3; + unsigned vdd_w_curr_min : 3; + // byte 10 + unsigned sector_size_high : 6; + unsigned erase_blk_en : 1; + unsigned c_size_mult_low : 1; + // byte 11 + unsigned wp_grp_size : 7; + unsigned sector_size_low : 1; + // byte 12 + unsigned write_bl_len_high : 2; + unsigned r2w_factor : 3; + unsigned reserved3 : 2; + unsigned wp_grp_enable : 1; + // byte 13 + unsigned reserved4 : 5; + unsigned write_partial : 1; + unsigned write_bl_len_low : 2; + // byte 14 + unsigned reserved5: 2; + unsigned file_format : 2; + unsigned tmp_write_protect : 1; + unsigned perm_write_protect : 1; + unsigned copy : 1; + unsigned file_format_grp : 1; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} csd1_t; +//------------------------------------------------------------------------------ +// CSD for version 2.00 cards +typedef struct CSDV2 { + // byte 0 + unsigned reserved1 : 6; + unsigned csd_ver : 2; + // byte 1 + uint8_t taac; + // byte 2 + uint8_t nsac; + // byte 3 + uint8_t tran_speed; + // byte 4 + uint8_t ccc_high; + // byte 5 + unsigned read_bl_len : 4; + unsigned ccc_low : 4; + // byte 6 + unsigned reserved2 : 4; + unsigned dsr_imp : 1; + unsigned read_blk_misalign : 1; + unsigned write_blk_misalign : 1; + unsigned read_bl_partial : 1; + // byte 7 + unsigned reserved3 : 2; + unsigned c_size_high : 6; + // byte 8 + uint8_t c_size_mid; + // byte 9 + uint8_t c_size_low; + // byte 10 + unsigned sector_size_high : 6; + unsigned erase_blk_en : 1; + unsigned reserved4 : 1; + // byte 11 + unsigned wp_grp_size : 7; + unsigned sector_size_low : 1; + // byte 12 + unsigned write_bl_len_high : 2; + unsigned r2w_factor : 3; + unsigned reserved5 : 2; + unsigned wp_grp_enable : 1; + // byte 13 + unsigned reserved6 : 5; + unsigned write_partial : 1; + unsigned write_bl_len_low : 2; + // byte 14 + unsigned reserved7: 2; + unsigned file_format : 2; + unsigned tmp_write_protect : 1; + unsigned perm_write_protect : 1; + unsigned copy : 1; + unsigned file_format_grp : 1; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} csd2_t; +//------------------------------------------------------------------------------ +// union of old and new style CSD register +union csd_t { + csd1_t v1; + csd2_t v2; +}; +#endif // SdInfo_h diff --git a/megaavr/libraries/SD/src/utility/SdVolume.cpp b/megaavr/libraries/SD/src/utility/SdVolume.cpp new file mode 100755 index 0000000..60375c4 --- /dev/null +++ b/megaavr/libraries/SD/src/utility/SdVolume.cpp @@ -0,0 +1,351 @@ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#include "SdFat.h" +//------------------------------------------------------------------------------ +// raw block cache +// init cacheBlockNumber_to invalid SD block number +uint32_t SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; +cache_t SdVolume::cacheBuffer_; // 512 byte cache for Sd2Card +Sd2Card* SdVolume::sdCard_; // pointer to SD card object +uint8_t SdVolume::cacheDirty_ = 0; // cacheFlush() will write block if true +uint32_t SdVolume::cacheMirrorBlock_ = 0; // mirror block for second FAT +//------------------------------------------------------------------------------ +// find a contiguous group of clusters +uint8_t SdVolume::allocContiguous(uint32_t count, uint32_t* curCluster) { + // start of group + uint32_t bgnCluster; + + // flag to save place to start next search + uint8_t setStart; + + // set search start cluster + if (*curCluster) { + // try to make file contiguous + bgnCluster = *curCluster + 1; + + // don't save new start location + setStart = false; + } else { + // start at likely place for free cluster + bgnCluster = allocSearchStart_; + + // save next search start if one cluster + setStart = 1 == count; + } + // end of group + uint32_t endCluster = bgnCluster; + + // last cluster of FAT + uint32_t fatEnd = clusterCount_ + 1; + + // search the FAT for free clusters + for (uint32_t n = 0;; n++, endCluster++) { + // can't find space checked all clusters + if (n >= clusterCount_) { + return false; + } + + // past end - start from beginning of FAT + if (endCluster > fatEnd) { + bgnCluster = endCluster = 2; + } + uint32_t f; + if (!fatGet(endCluster, &f)) { + return false; + } + + if (f != 0) { + // cluster in use try next cluster as bgnCluster + bgnCluster = endCluster + 1; + } else if ((endCluster - bgnCluster + 1) == count) { + // done - found space + break; + } + } + // mark end of chain + if (!fatPutEOC(endCluster)) { + return false; + } + + // link clusters + while (endCluster > bgnCluster) { + if (!fatPut(endCluster - 1, endCluster)) { + return false; + } + endCluster--; + } + if (*curCluster != 0) { + // connect chains + if (!fatPut(*curCluster, bgnCluster)) { + return false; + } + } + // return first cluster number to caller + *curCluster = bgnCluster; + + // remember possible next free cluster + if (setStart) { + allocSearchStart_ = bgnCluster + 1; + } + + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheFlush(uint8_t blocking) { + if (cacheDirty_) { + if (!sdCard_->writeBlock(cacheBlockNumber_, cacheBuffer_.data, blocking)) { + return false; + } + + if (!blocking) { + return true; + } + + // mirror FAT tables + if (!cacheMirrorBlockFlush(blocking)) { + return false; + } + cacheDirty_ = 0; + } + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheMirrorBlockFlush(uint8_t blocking) { + if (cacheMirrorBlock_) { + if (!sdCard_->writeBlock(cacheMirrorBlock_, cacheBuffer_.data, blocking)) { + return false; + } + cacheMirrorBlock_ = 0; + } + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheRawBlock(uint32_t blockNumber, uint8_t action) { + if (cacheBlockNumber_ != blockNumber) { + if (!cacheFlush()) { + return false; + } + if (!sdCard_->readBlock(blockNumber, cacheBuffer_.data)) { + return false; + } + cacheBlockNumber_ = blockNumber; + } + cacheDirty_ |= action; + return true; +} +//------------------------------------------------------------------------------ +// cache a zero block for blockNumber +uint8_t SdVolume::cacheZeroBlock(uint32_t blockNumber) { + if (!cacheFlush()) { + return false; + } + + // loop take less flash than memset(cacheBuffer_.data, 0, 512); + for (uint16_t i = 0; i < 512; i++) { + cacheBuffer_.data[i] = 0; + } + cacheBlockNumber_ = blockNumber; + cacheSetDirty(); + return true; +} +//------------------------------------------------------------------------------ +// return the size in bytes of a cluster chain +uint8_t SdVolume::chainSize(uint32_t cluster, uint32_t* size) const { + uint32_t s = 0; + do { + if (!fatGet(cluster, &cluster)) { + return false; + } + s += 512UL << clusterSizeShift_; + } while (!isEOC(cluster)); + *size = s; + return true; +} +//------------------------------------------------------------------------------ +// Fetch a FAT entry +uint8_t SdVolume::fatGet(uint32_t cluster, uint32_t* value) const { + if (cluster > (clusterCount_ + 1)) { + return false; + } + uint32_t lba = fatStartBlock_; + lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; + if (lba != cacheBlockNumber_) { + if (!cacheRawBlock(lba, CACHE_FOR_READ)) { + return false; + } + } + if (fatType_ == 16) { + *value = cacheBuffer_.fat16[cluster & 0XFF]; + } else { + *value = cacheBuffer_.fat32[cluster & 0X7F] & FAT32MASK; + } + return true; +} +//------------------------------------------------------------------------------ +// Store a FAT entry +uint8_t SdVolume::fatPut(uint32_t cluster, uint32_t value) { + // error if reserved cluster + if (cluster < 2) { + return false; + } + + // error if not in FAT + if (cluster > (clusterCount_ + 1)) { + return false; + } + + // calculate block address for entry + uint32_t lba = fatStartBlock_; + lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; + + if (lba != cacheBlockNumber_) { + if (!cacheRawBlock(lba, CACHE_FOR_READ)) { + return false; + } + } + // store entry + if (fatType_ == 16) { + cacheBuffer_.fat16[cluster & 0XFF] = value; + } else { + cacheBuffer_.fat32[cluster & 0X7F] = value; + } + cacheSetDirty(); + + // mirror second FAT + if (fatCount_ > 1) { + cacheMirrorBlock_ = lba + blocksPerFat_; + } + return true; +} +//------------------------------------------------------------------------------ +// free a cluster chain +uint8_t SdVolume::freeChain(uint32_t cluster) { + // clear free cluster location + allocSearchStart_ = 2; + + do { + uint32_t next; + if (!fatGet(cluster, &next)) { + return false; + } + + // free cluster + if (!fatPut(cluster, 0)) { + return false; + } + + cluster = next; + } while (!isEOC(cluster)); + + return true; +} +//------------------------------------------------------------------------------ +/** + Initialize a FAT volume. + + \param[in] dev The SD card where the volume is located. + + \param[in] part The partition to be used. Legal values for \a part are + 1-4 to use the corresponding partition on a device formatted with + a MBR, Master Boot Record, or zero if the device is formatted as + a super floppy with the FAT boot sector in block zero. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. Reasons for + failure include not finding a valid partition, not finding a valid + FAT file system in the specified partition or an I/O error. +*/ +uint8_t SdVolume::init(Sd2Card* dev, uint8_t part) { + uint32_t volumeStartBlock = 0; + sdCard_ = dev; + // if part == 0 assume super floppy with FAT boot sector in block zero + // if part > 0 assume mbr volume with partition table + if (part) { + if (part > 4) { + return false; + } + if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { + return false; + } + part_t* p = &cacheBuffer_.mbr.part[part - 1]; + if ((p->boot & 0X7F) != 0 || + p->totalSectors < 100 || + p->firstSector == 0) { + // not a valid partition + return false; + } + volumeStartBlock = p->firstSector; + } + if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { + return false; + } + bpb_t* bpb = &cacheBuffer_.fbs.bpb; + if (bpb->bytesPerSector != 512 || + bpb->fatCount == 0 || + bpb->reservedSectorCount == 0 || + bpb->sectorsPerCluster == 0) { + // not valid FAT volume + return false; + } + fatCount_ = bpb->fatCount; + blocksPerCluster_ = bpb->sectorsPerCluster; + + // determine shift that is same as multiply by blocksPerCluster_ + clusterSizeShift_ = 0; + while (blocksPerCluster_ != (1 << clusterSizeShift_)) { + // error if not power of 2 + if (clusterSizeShift_++ > 7) { + return false; + } + } + blocksPerFat_ = bpb->sectorsPerFat16 ? + bpb->sectorsPerFat16 : bpb->sectorsPerFat32; + + fatStartBlock_ = volumeStartBlock + bpb->reservedSectorCount; + + // count for FAT16 zero for FAT32 + rootDirEntryCount_ = bpb->rootDirEntryCount; + + // directory start for FAT16 dataStart for FAT32 + rootDirStart_ = fatStartBlock_ + bpb->fatCount * blocksPerFat_; + + // data start for FAT16 and FAT32 + dataStartBlock_ = rootDirStart_ + ((32 * bpb->rootDirEntryCount + 511) / 512); + + // total blocks for FAT16 or FAT32 + uint32_t totalBlocks = bpb->totalSectors16 ? + bpb->totalSectors16 : bpb->totalSectors32; + // total data blocks + clusterCount_ = totalBlocks - (dataStartBlock_ - volumeStartBlock); + + // divide by cluster size to get cluster count + clusterCount_ >>= clusterSizeShift_; + + // FAT type is determined by cluster count + if (clusterCount_ < 4085) { + fatType_ = 12; + } else if (clusterCount_ < 65525) { + fatType_ = 16; + } else { + rootDirStart_ = bpb->fat32RootCluster; + fatType_ = 32; + } + return true; +} From b4bd151296bd4386e6a745c2531928b167326bfa Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 28 Mar 2021 13:44:39 +0200 Subject: [PATCH 234/351] Rename registers --- megaavr/libraries/Event/src/Event.h | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 9fe69d2..2d643ec 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -475,10 +475,10 @@ namespace user #if defined(USART5) usart5_irda = 0x1A, #endif - tca0_cnta = 0x1B, - tca0_cntb = 0x1C, - tca1_cnta = 0x1D, - tca1_cntb = 0x1E, + tca0_cnt_a = 0x1B, + tca0_cnt_b = 0x1C, + tca1_cnt_a = 0x1D, + tca1_cnt_b = 0x1E, tcb0_capt = 0x1F, tcb0_cnt = 0x20, tcb1_capt = 0x21, @@ -554,10 +554,10 @@ namespace user #if defined(USART5) usart5_irda = 0x19, #endif - tca0_cnta = 0x1A, - tca0_cntb = 0x1B, - tca1_cnta = 0x1C, - tca1_cntb = 0x1D, + tca0_cnt_a = 0x1A, + tca0_cnt_b = 0x1B, + tca1_cnt_a = 0x1C, + tca1_cnt_b = 0x1D, tcb0_capt = 0x1E, tcb0_cnt = 0x1F, tcb1_capt = 0x20, From 93560611ec3a83f212081d8491d1b360e1cfb059 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 11:55:38 +0200 Subject: [PATCH 235/351] Add Optiboot Flash library --- README.md | 8 + .../examples/Flash_iterate/Flash_iterate.ino | 100 ++++++++ .../examples/Flash_put_get/Flash_put_get.ino | 134 ++++++++++ .../Serial_read_write/Serial_read_write.ino | 234 ++++++++++++++++++ .../libraries/Optiboot_flasher/keywords.txt | 39 +++ .../Optiboot_flasher/library.properties | 11 + .../libraries/Optiboot_flasher/src/Flash.cpp | 182 ++++++++++++++ .../libraries/Optiboot_flasher/src/Flash.h | 52 ++++ .../Optiboot_flasher/src/optiboot.cpp | 141 +++++++++++ .../libraries/Optiboot_flasher/src/optiboot.h | 62 +++++ 10 files changed, 963 insertions(+) create mode 100644 megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino create mode 100644 megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino create mode 100644 megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino create mode 100644 megaavr/libraries/Optiboot_flasher/keywords.txt create mode 100644 megaavr/libraries/Optiboot_flasher/library.properties create mode 100644 megaavr/libraries/Optiboot_flasher/src/Flash.cpp create mode 100644 megaavr/libraries/Optiboot_flasher/src/Flash.h create mode 100755 megaavr/libraries/Optiboot_flasher/src/optiboot.cpp create mode 100755 megaavr/libraries/Optiboot_flasher/src/optiboot.h diff --git a/README.md b/README.md index 520b82a..7bc1106 100644 --- a/README.md +++ b/README.md @@ -22,6 +22,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Printf support](#printf-support) * [Fast IO](#fast-io) * [Pin macros](#pin-macros) +* [Write to own flash](#write-to-own-flash) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -138,6 +139,13 @@ digitalWrite(0, HIGH); ``` +## Write to own flash +As an alternative for UPDI, MegaCoreX uses Optiboot Flash, a bootloader that supports flash writing within the running application, thanks to the work of [@majekw](https://github.com/majekw). +This means that content from e.g. a sensor can be stored in the flash memory directly without the need of external memory. Flash memory is much faster than EEPROM, and can handle at least 10 000 write cycles before wear becomes an issue. +For more information on how it works and how you can use this in you own application, check out the [Serial_read_write](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino) for a simple proof-of-concept demo, and +[Flash_put_get](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino) + [Flash_iterate](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino) for useful examples on how you can store strings, structs and variables to flash and retrieve then afterwards. + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino new file mode 100644 index 0000000..4b26d9e --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino @@ -0,0 +1,100 @@ +/***********************************************************************| +| Optiboot Flash read/write interface library | +| | +| Flash_iterate.ino | +| | +| A library for interfacing with Optiboot Flash's write functionality | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we fill the flash[] buffer with numbers and write it | +| to flash page 0. After a reset or power cycle, we read the values | +| back and prints them to the serial monitor. | +| | +| A RAM buffer (ram_buffer) is required for this library to work. It | +| acts as a memory pool you can read from and write to, and recommended | +| size for this buffer is one flash page, 256/128/64 bytes depending on | +| what chip you're using. ram_buffer[] and flash[] is the exact same | +| array, flash[] is just pointing to ram_buffer[]. | +|***********************************************************************/ + +#include + +// RAM buffer needed by the Flash library. Use flash[] to access the buffer +uint8_t ram_buffer[SPM_PAGESIZE]; + +// Allocate two flash pages for storing data +#define NUMBER_OF_PAGES 2 +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; + +// Flash constructor +Flash flash(flashSpace, sizeof(flashSpace), ram_buffer, sizeof(ram_buffer)); + +void write_data() +{ + // First, make sure there are no content in out buffer + flash.clear_buffer(); + + // Fill buffer with numbers, starting from 0 + for(uint8_t i = 0; i < 64; i++) + flash[i] = i + 100; + + // Write buffer to the first allocated flash page (page 0) + flash.write_page(0); + + // Now let's set a flag on another flash page to indicate that the flash memory contains content + // Here we're treating the object as an array + flash.clear_buffer(); + flash[5] = 'X'; + flash.write_page(1); + + Serial.println(F("Page 0 written to!\nReset your board to view the contents!\n")); +} + +void read_data() +{ + Serial.println(F("Read float from flash page 0: ")); + + // Fetch first flash page + flash.fetch_page(0); + + for(uint16_t i = 0; i < flash.buffer_size(); i++) + { + Serial.print(F("Addr: ")); + Serial.print(i); + Serial.print(F(" \tData: ")); + Serial.println(flash[i]); + } +} + +void setup() +{ + delay(2000); + Serial.begin(9600); + + // Fetch flash page 1, where we may have a flag + flash.fetch_page(1); + + // Check if our flag is present + if(flash[5] == 'X') + { + Serial.println(F("Content found!")); + read_data(); + } + else + { + Serial.print(F("Flash page size for this chip: ")); + Serial.print(SPM_PAGESIZE); + Serial.print(F(" bytes\nTotal assigned flash space: ")); + Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); + Serial.println(F(" bytes")); + + Serial.println(F("No content found! Writing new content...")); + write_data(); + } +} + +void loop() +{ + +} diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino new file mode 100644 index 0000000..7c5d956 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino @@ -0,0 +1,134 @@ +/***********************************************************************| +| Optiboot Flash read/write interface library | +| | +| Flash_get_put.ino | +| | +| A library for interfacing with Optiboot Flash's write functionality | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this example we write a float and a struct to flash page 0, and we | +| set a flag on flash page 1 to indicate there is content to be read | +| afterwards. After a reset we read back the flash content and prints | +| them to the serial monitor. | +| | +| A RAM buffer (ram_buffer) is required for this library to work. It | +| acts as a memory pool you can read from and write to, and recommended | +| size for this buffer is one flash page, 256/128/64 bytes depending on | +| what chip you're using. ram_buffer[] and flash[] is the exact same | +| array, flash[] is just pointing to ram_buffer[]. | +|***********************************************************************/ + +#include + +struct MyObject +{ + float field1; + uint8_t field2; + char name[10]; +}; + +// RAM buffer needed by the Flash library. Use flash[] to access the buffer +uint8_t ram_buffer[SPM_PAGESIZE]; + +// Allocate two flash pages for storing data +#define NUMBER_OF_PAGES 2 +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; + +// Flash constructor +Flash flash(flashSpace, sizeof(flashSpace), ram_buffer, sizeof(ram_buffer)); + +void write_data() +{ + float f = 123.456f; + uint8_t buffer_address = 0; + + // First, make sure there are no content in out buffer + flash.clear_buffer(); + + // One simple call, with the address first and the object second + flash.put(buffer_address, f); + + Serial.println(F("Written float data type!")); + + // Data to store + MyObject customVar = + { + 3.14f, + 65, + "MCUdude" + }; + + // Move address to the next byte after float 'f' + buffer_address += sizeof(float); + flash.put(buffer_address, customVar); + + // Write buffer to the first allocated flash page (page 0) + flash.write_page(0); + + // Now let's set a flag on another flash page to indicate that the flash memory contains content + // Here we're treating the object as an array + flash.clear_buffer(); + flash[5] = 'X'; + flash.write_page(1); + + Serial.println(F("Written custom data type!\nReset your board to view the contents!\n")); +} + +void read_data() +{ + Serial.println(F("Read float from flash: ")); + + // Fetch first flash page + flash.fetch_page(0); + + float f = 0.00f; // Variable to store data read from flash + uint8_t buffer_address = 0; // Buffer address to start from + + // Get the float data from flash at position 'buffer_address' + flash.get(buffer_address, f); + Serial.print(F("The value of f is now: ")); + Serial.println(f, 3); + + buffer_address += sizeof(float); // Move address to the next byte after float 'f' + MyObject customVar; // Variable to store custom object read from flash. + + flash.get(buffer_address, customVar); + + Serial.println(F("Read custom object from flash: ")); + Serial.println(customVar.field1); + Serial.println(customVar.field2); + Serial.println(customVar.name); +} + +void setup() +{ + delay(2000); + Serial.begin(9600); + + // Fetch flash page 1, where we may have a flag + flash.fetch_page(1); + + // Check if our flag is present + if(flash[5] == 'X') + { + Serial.println(F("Content found!")); + read_data(); + } + else + { + Serial.print(F("Flash page size for this chip: ")); + Serial.print(SPM_PAGESIZE); + Serial.print(F(" bytes\nTotal assigned flash space: ")); + Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); + Serial.println(F(" bytes")); + + Serial.println(F("No content found! Writing new content...")); + write_data(); + } +} + +void loop() +{ + +} diff --git a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino new file mode 100644 index 0000000..5e8002b --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino @@ -0,0 +1,234 @@ +/*------------ Optiboot flasher example for the MightyCore -----------------| + | | + | Created May 2016 by MCUdude, https://github.com/MCUdude | + | Based on the work done by Marek Wodzinski, https://github.com/majekw | + | Released to public domain | + | | + | This is example how to use optiboot.h together with Optiboot | + | bootloader to write to FLASH memory by application code. | + | | + | IMPORTANT THINGS: | + | - All flash content gets erased after each upload cycle | + | - Buffer must be page aligned (see declaration of flash_buffer) | + | - Interrupts must be disabled during SPM | + | - Writing to EEPROM destroys temporary buffer | + | - You can write only once into one location of temporary buffer | + | - Only safely and always working sequence is erase-fill-write | + | - If you want to do fill-erase-write, you must put code in NRWW | + | and pass data!=0 for erase. It's not easy, but possible. | + | | + | WRITE SEQUENCE - OPTION 1 (used in this example) | + | 1. Erase page by optiboot_page_erase | + | 2. Write contents of page into temporary buffer by optiboot_page_fill | + | 3. Write temporary buffer to FLASH by optiboot_page_write | + | | + | WRITE SEQUENCE - OPTION 2 (works only for code in NRWW) | + | 1. Write contents of page into temporary buffer by optiboot_page_fill | + | 2. Erase page by optiboot_page_erase (set data to NOT zero) | + | 3. Write temporary buffer to FLASH by optiboot_page_write | + |-------------------------------------------------------------------------*/ + +// optiboot.h contains the functions that lets you read to +// and write from the flash memory +#include + +// Define the number of pages you want to write to here (limited by flash size) +#define NUMBER_OF_PAGES 8 + +// Define your termination and blank character here +const char terminationChar = '@'; + +// The temporary data (data that's read or is about to get written) is stored here +uint8_t ramBuffer[SPM_PAGESIZE]; + +// This array allocates the space you'll be able to write to +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__ (( aligned(SPM_PAGESIZE) )) PROGMEM = { + "This some default content stored on page one" +}; + +//#define Serial Serial3 + +void setup() +{ + // Initialize serial + Serial.begin(9600); +} + + +void loop() +{ + // Print main menu + Serial.println(); + Serial.println(F("|------------------------------------------------|")); + Serial.println(F("| Welcome to the Optiboot flash writer example! |")); + Serial.print(F("| Each flash page is ")); + Serial.print(SPM_PAGESIZE); + Serial.println(F(" bytes long. |")); + Serial.print(F("| There are ")); + Serial.print(NUMBER_OF_PAGES); + Serial.println(F(" pages that can be read/written to. |")); + Serial.print(F("| Total assigned flash space: ")); + Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); + Serial.println(F(" bytes. |")); + Serial.println(F("| Change the NUMBER_OF_PAGES constant to |")); + Serial.println(F("| increase or decrease this number. |")); + Serial.println(F("| |")); + Serial.println(F("| What do you want to do? |")); + Serial.println(F("| 1. Show current flash content |")); + Serial.println(F("| 2. Write to flash memory |")); + Serial.println(F("|------------------------------------------------|")); + + // Static variables + static uint8_t charBuffer; + static char menuOption; + static uint16_t pageNumber; + static char returnToMenu; + + // Get menu option from the serial monitor + do + { + while(!Serial.available()); + menuOption = Serial.read(); + if(menuOption != '1' && menuOption != '2') + Serial.print(F("\nPlease enter a valid option! ")); + } + while(menuOption != '1' && menuOption != '2'); + + Serial.print(F("\nOption ")); + Serial.print(menuOption); + Serial.println(F(" selected.")); + + + + // Read flash option selected + if(menuOption == '1') + { + Serial.print(F("Which page number do you want to read? Page 0 to ")); + Serial.print(NUMBER_OF_PAGES - 1); + Serial.print(F(", Page ")); + Serial.print(NUMBER_OF_PAGES); + Serial.print(F(" to show all pages: ")); + + //Get page number from the serial monitor + do + { + while(!Serial.available()); + pageNumber = Serial.read() - 0x30; + if(pageNumber > NUMBER_OF_PAGES) + { + Serial.print(F("\nPlease enter a valid page between 0 and ")); + Serial.print(NUMBER_OF_PAGES - 1); + Serial.println(F(". The number of pages can be extended by changing NUMBER_OF_PAGES constant")); + } + } + while(pageNumber > NUMBER_OF_PAGES); + + if(pageNumber <= NUMBER_OF_PAGES) + Serial.println(pageNumber); + + // READ SELECTED PAGE AND STORE THE CONTENT IN THE ramBuffer ARRAY + // flash_buffer is where the data is stored (contains the memory addresses) + // ramBuffer is where the data gets stored after reading from flash + // pageNumber is the page the data is read from + + uint8_t pageFirst = 0; + uint8_t pageLast = NUMBER_OF_PAGES; + + if(pageNumber != NUMBER_OF_PAGES) + { + pageFirst = pageNumber; + pageLast = pageNumber; + } + + for(uint8_t page = pageFirst; page < pageLast; page++) + { + optiboot_readPage(flashSpace, ramBuffer, page); + Serial.print(F("Page ")); + Serial.print(page); + Serial.print(F(": ")); + for(uint16_t i = 0; i < sizeof(ramBuffer); i++) + { + if(ramBuffer[i] == 0x00 || ramBuffer[i] == 0xff) + Serial.write('.'); + else + Serial.write(ramBuffer[i]); + } + Serial.println(""); + } + } // End of flash read option + + + + // Write flash option selected + else if(menuOption == '2') + { + // Clear pageNumber + pageNumber = 0xff; + + //Get page number from the serial monitor + Serial.print(F("\nWhich page do you want to write to? Page: ")); + do + { + while(!Serial.available()); + pageNumber = Serial.read() - 0x30; + if(pageNumber > NUMBER_OF_PAGES - 1) + { + Serial.print(F("\nPlease enter a valid page between 0 and ")); + Serial.print(NUMBER_OF_PAGES - 1); + Serial.println(F(". The number of pages can be extended by changing NUMBER_OF_PAGES constant")); + } + } + while(pageNumber >= NUMBER_OF_PAGES); + Serial.println(pageNumber); + + // Print prompt to enter some new characters to write to flash + Serial.print(F("Please type the characters you want to store (max ")); + Serial.print(SPM_PAGESIZE); + Serial.println(F(" characters)")); + Serial.print(F("End the line by sending the '")); + Serial.write(terminationChar); + Serial.println(F("' character:")); + + // Get all characters from the serial monitor and store it to the ramBuffer + memset(ramBuffer, 0, sizeof(ramBuffer)); + uint16_t counter = 0; + while (counter < SPM_PAGESIZE && charBuffer != terminationChar) + { + if(Serial.available() > 0) + { + charBuffer = Serial.read(); // read character from serial + if(charBuffer != terminationChar) + { + Serial.write(charBuffer); // echo character back + ramBuffer[counter] = charBuffer; + counter++; + } + } + } + charBuffer = 0; + Serial.println(F("\n\nAll chars received \nWriting to flash...")); + + // WRITE RECEIVED DATA TO THE CURRENT FLASH PAGE + // flash_buffer is where the data is stored (contains the memory addresses) + // ramBuffer contains the data that's going to be stored in the flash + // pageNumber is the page the data is written to + optiboot_writePage(flashSpace, ramBuffer, pageNumber); + + Serial.println(F("Writing finished. You can now reset or power cycle the board and check for new contents!")); + } // End of flash write option + + + + //Return to the main menu if 'm' is sent + Serial.println(F("\ntype the character 'm' to return to to the main menu")); + do + { + while(!Serial.available()); + returnToMenu = Serial.read(); + if(returnToMenu != 'm') + Serial.print(F("\nPlease type a valid character! ")); + } + while(returnToMenu != 'm'); + returnToMenu = 0; + +} // End of loop diff --git a/megaavr/libraries/Optiboot_flasher/keywords.txt b/megaavr/libraries/Optiboot_flasher/keywords.txt new file mode 100644 index 0000000..acb6c51 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/keywords.txt @@ -0,0 +1,39 @@ +############################################# +# Syntax Coloring Map For Flash and Optiboot +############################################# + +############################################# +# Datatypes (KEYWORD1) +############################################# + +Flash KEYWORD1 + +############################################# +# Methods and Functions (KEYWORD2) +############################################# + +# Flash class +set_far_address KEYWORD2 +check_writable KEYWORD2 +clear_buffer KEYWORD2 +read_buffer KEYWORD2 +write_buffer KEYWORD2 +buffer_size KEYWORD2 +write_page KEYWORD2 +fetch_page KEYWORD2 +fetch_data KEYWORD2 +get KEYWORD2 +put KEYWORD2 + +# Optiboot +do_spm_cli KEYWORD2 +optiboot_page_erase KEYWORD2 +optiboot_page_fill KEYWORD2 +optiboot_page_write KEYWORD2 +optiboot_readPage KEYWORD2 +optiboot_read KEYWORD2 +optiboot_writePage KEYWORD2 + +############################################ +# Constants (LITERAL1) +############################################ diff --git a/megaavr/libraries/Optiboot_flasher/library.properties b/megaavr/libraries/Optiboot_flasher/library.properties new file mode 100644 index 0000000..6ab09cf --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/library.properties @@ -0,0 +1,11 @@ +name=Optiboot Flash +version=2.0 +author=majekw/MCUdude +maintainer=MCUdude +sentence=Read and write contents to the FLASH memory +paragraph= +category=Data Storage +url= +architectures=avr +types=Arduino + diff --git a/megaavr/libraries/Optiboot_flasher/src/Flash.cpp b/megaavr/libraries/Optiboot_flasher/src/Flash.cpp new file mode 100644 index 0000000..4fd09a6 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/src/Flash.cpp @@ -0,0 +1,182 @@ +#include "Flash.h" + +/** + * @brief Construct a new Flash:: Flash object + * + * @param flash_array the flash space array the library will utilize + * @param flash_array_size total size of the flash space array in bytes + * @param ram_array the RAM buffer array the library will utilize + * @param ram_array_size total size of the ram array in bytes. This is an + * optional parameter, and defaults to SPM_PAGESIZE, the flash page size if not + * present + */ +Flash::Flash(const uint8_t *flash_array, const uint16_t flash_array_size, uint8_t *ram_array, const uint16_t ram_array_size) + : _flash_array(flash_array), + _flash_array_size(flash_array_size), + _ram_array(ram_array), + _ram_array_size(ram_array_size) +{ +} + +/** + * @brief Lets you use the created object as a placeholder for the + * passed RAM buffer + * + * @param index Array index + * @return uint8_t& + */ +uint8_t& Flash::operator[](int16_t index) +{ + return _ram_array[index]; +} + + +#ifdef RAMPZ +/** + * @brief If you have allocated flash space in the far progmem, above 64kiB, + * you can't just pass your flash space array to the constructor because a + * 16-bit pointer isn't large enough. You therefore have to specify the address + * with this function. + * + * @param address The start address of the allocated flash space. + * You can get the address by using the pgm_get_far_address macro: + * set_far_address(pgm_get_far_address(flashSpace)) + */ +void Flash::set_far_address(uint32_t address) +{ + _far_flash_array_addr = address; +} +#endif + +/** + * @brief Checks if the microcontroller contains a bootloader that has flash + * writing capabilities. It does so by checking if a spesific number is placed + * at the very end of the flash memory + * + * @return true if compatible bootloader is present + * @return false if incompatible or no bootloader is present + */ +bool Flash::check_writable() +{ + return optiboot_check_writable(); +} + +/** + * @brief Clears the RAM buffer + * + * @param fill optional parameter to set what content the buffer will be + * filled with. Defaults to 0x00 if not present + */ +void Flash::clear_buffer(uint8_t fill) +{ + memset(_ram_array, fill, sizeof(_ram_array_size)); +} + +/** + * @brief Wrapper function for the RAM buffer. Lets you read a byte from a + * given memory location + * + * @param index memory address + * @return uint8_t 8-bit value stored in this address space + */ +uint8_t Flash::read_buffer(uint8_t index) +{ + return _ram_array[index]; +} + +/** + * @brief Wrapper function for the RAM buffer. Lets you write a byte to a given + * memory address + * + * @param index memory address + * @param value 8-bit value to write to the memory location + */ +void Flash::write_buffer(uint8_t index, uint8_t value) +{ + _ram_array[index] = value; +} + +/** + * @brief Function that returns the size of the allocated RAM buffer + * + * @return uint16_t RAM buffer size in bytes + */ +uint16_t Flash::buffer_size() +{ + return _ram_array_size; +} + +/** + * @brief Writes the current content of the RAM buffer to a flash page + * + * @param flash_page_number page number to write the buffer to + */ +void Flash::write_page(uint16_t flash_page_number) +{ + // For devices with 128kiB or more, and data is stored in far progmem + #ifdef RAMPZ + if(_far_flash_array_addr != 0x0000) + { + optiboot_writePage(_far_flash_array_addr, _ram_array, flash_page_number); + } + // For devices with where flash space is allocated in near progmem, <64kiB + else + #endif + { + optiboot_writePage(_flash_array, _ram_array, flash_page_number); + } +} + +/** + * @brief Reads a flash page and write its content to the RAM buffer + * + * @param flash_page_number page number to read from + */ +void Flash::fetch_page(uint16_t flash_page_number) +{ + // For devices with 128kiB or more, and data is stored in far progmem + #ifdef RAMPZ + if(_far_flash_array_addr != 0x0000) + { + optiboot_read(_far_flash_array_addr, _ram_array, flash_page_number, 0, _ram_array_size); + } + // For devices with where flash space is allocated in near progmem, <64kiB + else + #endif + { + optiboot_read(_flash_array, _ram_array, flash_page_number, 0, _ram_array_size); + } +} + +/** + * @brief Read bytes from the flash memory and write its content to the RAM + * buffer. You can read as many or as few bytes as you want. There are no page + * numbers here, the start address represents the address number from the start + * of the allocated space. This means that if you want to read 10 bytes from + * page two you set the start address to 512 and stop address to 522. Note that + * the span between the start and stop address can't be larger than the size of + * the RAM buffer. + * + * @param start_address address to start reading from + * @param stop_address address where we stop reading at + */ +void Flash::fetch_data(uint16_t start_address, uint16_t stop_address) +{ + uint16_t end_address; + if(stop_address - start_address > _ram_array_size) + end_address = _ram_array_size; + else + end_address = stop_address; + + #ifdef RAMPZ + if(_far_flash_array_addr != 0x0000) + { + optiboot_read(_far_flash_array_addr, _ram_array, 0, start_address, end_address); + } + // For devices with where flash space is allocated in near progmem, <64kiB + else + #endif + { + optiboot_read(_flash_array, _ram_array, 0, start_address, end_address); + } +} diff --git a/megaavr/libraries/Optiboot_flasher/src/Flash.h b/megaavr/libraries/Optiboot_flasher/src/Flash.h new file mode 100644 index 0000000..9a3f6c7 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/src/Flash.h @@ -0,0 +1,52 @@ +#ifndef FLASH_H +#define FLASH_H + +#include +#include + +class Flash +{ + public: + Flash(const uint8_t *flash_array, const uint16_t flash_array_size, uint8_t *ram_array, const uint16_t ram_array_size = SPM_PAGESIZE); + #ifdef RAMPZ + void set_far_address(uint32_t address); + #endif + bool check_writable(); + void clear_buffer(uint8_t fill = 0x00); + uint8_t read_buffer(uint8_t index); + void write_buffer(uint8_t index, uint8_t value); + uint16_t buffer_size(); + void write_page(uint16_t flash_page_number); + void fetch_page(uint16_t flash_page_number); + void fetch_data(uint16_t start_address, uint16_t stop_address); + + // Operator overload to be able to read and write directly to the RAM array from a byte level + uint8_t& operator[] (int16_t index); + + // Template function to 'put' objects in RAM array + template const T &put(uint16_t idx, const T &t) + { + const uint8_t *ptr = (const uint8_t*) &t; + for(uint16_t count = 0; count < sizeof(T); count++) + _ram_array[idx + count] = *ptr++; + return t; + } + + // Template function to 'get' objects from the RAM array + template T &get(uint16_t idx, T &t) + { + uint8_t *ptr = (uint8_t*) &t; + for(uint16_t count = 0; count < sizeof(T); count++) + *ptr++ = _ram_array[idx + count]; + return t; + } + + private: + const uint8_t *_flash_array; // Pointer to allocated flash space + uint32_t _far_flash_array_addr; // Address to far memory location if allocated space is above 64kiB + const uint16_t _flash_array_size; // Size of a flash page in bytes (64, 128 or 256 bytes) + uint8_t *_ram_array; // Pointer to allocated RAM array + const uint16_t _ram_array_size; // Size of allocated RAM array +}; + +#endif diff --git a/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp new file mode 100755 index 0000000..f4b8e0f --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp @@ -0,0 +1,141 @@ +#include "optiboot.h" + + +/* + * The same as do_nvmctrl but with disable/restore interrupts state + * required to succesfull execution + * + */ +void do_nvmctrl_cli(optiboot_addr_t address, uint8_t command, uint16_t data) +{ + uint8_t sreg_save; + + sreg_save = SREG; // Save old SREG value + asm volatile("cli"); // Disable interrupts + do_nvmctrl(address, command, data); // 16 bit address - no problems to pass directly + SREG = sreg_save; // Restore last interrupts state +} + + +/** + * @brief Checks if the microcontroller contains a bootloader that has flash + * writing capabilities. It does so by checking if a spesific number is placed + * at the end of the bootloader section + * + * @return true if compatible bootloader is present + * @return false if incompatible or no bootloader is present + */ +bool optiboot_check_writable() +{ + uint8_t content = pgm_read_byte(0x1FF); + + if(content == 9) + return true; + else + return false; +} + + +/** + * @brief Erase flash page + * + * @param address flash page start address + */ +void optiboot_page_erase(optiboot_addr_t address) +{ + // Set page by writing to address + do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, 0xFF); + do_nvmctrl_cli(0, NVMCTRL_CMD_PAGEERASE_gc, 0); // do actual erase +} + + +/** + * @brief Writes a word/16-bit value to a temporary, internal buffer. Note that + * this temporary buffer gets destroyed if you read or write to EEPROM. It's + * therefore important that the buffer gets written to flash before doing + * anything EEPROM related. Also note that you can write only once to one + * location in the temporary buffer without erasing it first, which happens + * after a flash page erase or write. + * + * @param address address where to write the 16-bit data + * @param data data to write + */ +void optiboot_page_fill(optiboot_addr_t address, uint16_t data) +{ + do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data & 0xFF); + do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data >> 8); +} + + +/** + * @brief Write the temporary, internal buffer to flash + * + * @param address flash page start address + */ +void optiboot_page_write(optiboot_addr_t address) +{ + do_nvmctrl_cli(address, NVMCTRL_CMD_PAGEWRITE_gc, 0); +} + + +// Higher level functions for reading and writing from flash + + +/** + * @brief Read bytes from a given page and futher out in memory. It will + * continue to fill the storage_array until the stop_address is reached. Note + * that this function will only work for data stored in near progmem, below + * 64kiB. + * + * @param allocated_flash_space the allocated flash space to read from + * @param storage_array the array to store the flash content to + * @param page_number the flash page number to start reading from + * @param start_address the address to start reading from, relative to the flash page number + * @param stop_address the address where we stop reading, relative to the flash page number + */ +void optiboot_read(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number, uint16_t start_address, uint16_t stop_address) +{ + for(uint16_t j = start_address; j < stop_address; j++) + { + uint8_t read_character = pgm_read_byte(&allocated_flash_space[j + SPM_PAGESIZE * (page_number)]); + storage_array[j - start_address] = read_character; + } +} + + +/** + * @brief Reads an entire flash page and stores the content in storage_array. + * Note that this function will only work for data stored in near progmem, + * below 64kiB. + * + * @param allocated_flash_space the allocated flash space to read from + * @param storage_array the array to store the flash content to + * @param page_number the flash page number to read from + */ +void optiboot_readPage(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number) +{ + optiboot_read(allocated_flash_space, storage_array, page_number, 0, SPM_PAGESIZE); +} + + +/** + * @brief Writes the content of data_to_store to a flash page. + * Note that this function will only work for data stored in near progmem, + * below 64kiB. + * + * @param allocated_flash_space the allocated flash space to read from + * @param data_to_store an array that holds the data to store + * @param page_number the flash page number to write to + */ +void optiboot_writePage(const uint8_t allocated_flash_space[], uint8_t data_to_store[], uint16_t page_number) +{ + const uint8_t *adjusted_address; + // Copy ram buffer to temporary flash buffer + for(uint16_t i = 0; i < SPM_PAGESIZE; i++) + { + adjusted_address = &allocated_flash_space[i + SPM_PAGESIZE * (page_number)]; + adjusted_address += MAPPED_PROGMEM_START; + do_nvmctrl((optiboot_addr_t)adjusted_address, NVMCTRL_CMD_COPY_gc, data_to_store[i]); + } + do_nvmctrl_cli(0, NVMCTRL_CMD_PAGEERASEWRITE_gc, 0); +} diff --git a/megaavr/libraries/Optiboot_flasher/src/optiboot.h b/megaavr/libraries/Optiboot_flasher/src/optiboot.h new file mode 100755 index 0000000..b9159fd --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/src/optiboot.h @@ -0,0 +1,62 @@ +/*------------------------ Optiboot header file ---------------------------| +| | +| June 2015 by Marek Wodzinski, https://github.com/majekw | +| Modified June 2016 by MCUdude, https://github.com/MCUdude | +| Revised March 2021 by MCUdude | +| Released to public domain | +| | +| This header file gives possibility to use SPM instruction | +| from Optiboot bootloader memory. | +| | +| There are 5 convenient functions available here: | +| * optiboot_page_erase - to erase a FLASH page | +| * optiboot_page_fill - to put words into temporary buffer | +| * optiboot_page_write - to write contents of temporary buffer into FLASH | +| * optiboot_readPage - higher level function to read a flash page and | +| store it in an array | +| * optiboot_writePage - higher level function to write content to | +| a flash page | +| | +| For some hardcore users, you could use 'do_spm' as raw entry to | +| bootloader spm function. | +|-------------------------------------------------------------------------*/ + + +#ifndef OPTIBOOT_H +#define OPTIBOOT_H + +#include +#include + +#define NVMCTRL_CMD_COPY_gc (NVMCTRL_CMD_gm + 1) // one beyond existing commands. +#define SPM_PAGESIZE (PROGMEM_PAGE_SIZE) + +/* + * Main 'magic' function - enter to bootloader do_spm function + * + * address - address to write (in bytes) but must be even number + * command - one of __BOOT_PAGE_WRITE, __BOOT_PAGE_ERASE or __BOOT_PAGE_FILL + * data - data to write in __BOOT_PAGE_FILL. In __BOOT_PAGE_ERASE or + * __BOOT_PAGE_WRITE it control if boot_rww_enable is run + * (0 = run, !0 = skip running boot_rww_enable) + * + */ + +// 'typedef' (in following line) and 'const' (few lines below) are a way to define external function at some arbitrary address +typedef void (*do_spm_t)(uint16_t address, uint8_t command, uint16_t data); +typedef uint16_t optiboot_addr_t; + +// Mega0/xTiny/etc. Bootloader is in low memory. +const do_spm_t do_nvmctrl = (do_spm_t)((PROGMEM_START + 2) >> 1); + + +void do_nvmctrl_cli(optiboot_addr_t address, uint8_t command, uint16_t data); +bool optiboot_check_writable(); +void optiboot_page_erase(optiboot_addr_t address); +void optiboot_page_fill(optiboot_addr_t address, uint16_t data); +void optiboot_page_write(optiboot_addr_t address); +void optiboot_read(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number, uint16_t start_address, uint16_t stop_address); +void optiboot_readPage(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number); +void optiboot_writePage(const uint8_t allocated_flash_space[], uint8_t data_to_store[], uint16_t page_number); + +#endif From 05a0559170ffe8931aee2e3bb496fe8ed578e448 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 12:01:35 +0200 Subject: [PATCH 236/351] Change architecture to megaavr --- megaavr/libraries/Optiboot_flasher/library.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Optiboot_flasher/library.properties b/megaavr/libraries/Optiboot_flasher/library.properties index 6ab09cf..122faed 100644 --- a/megaavr/libraries/Optiboot_flasher/library.properties +++ b/megaavr/libraries/Optiboot_flasher/library.properties @@ -6,6 +6,6 @@ sentence=Read and write contents to the FLASH memory paragraph= category=Data Storage url= -architectures=avr +architectures=megaavr types=Arduino From 399c48563376dbfc000bc4114d38b67804e56997 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 12:46:22 +0200 Subject: [PATCH 237/351] Add check_writable() check and remove F() macros Now the sketch won't run if no or incompatible bootloader is used. The F() macros were removed because the megaAVR-0 series have memory-mapped flash --- .../examples/Flash_iterate/Flash_iterate.ino | 24 +++--- .../examples/Flash_put_get/Flash_put_get.ino | 26 +++--- .../Serial_read_write/Serial_read_write.ino | 79 ++++++++++--------- 3 files changed, 74 insertions(+), 55 deletions(-) diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino index 4b26d9e..d91793f 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino @@ -48,21 +48,21 @@ void write_data() flash[5] = 'X'; flash.write_page(1); - Serial.println(F("Page 0 written to!\nReset your board to view the contents!\n")); + Serial.println("Page 0 written to!\nReset your board to view the contents!\n"); } void read_data() { - Serial.println(F("Read float from flash page 0: ")); + Serial.println("Read float from flash page 0: "); // Fetch first flash page flash.fetch_page(0); for(uint16_t i = 0; i < flash.buffer_size(); i++) { - Serial.print(F("Addr: ")); + Serial.print("Addr: "); Serial.print(i); - Serial.print(F(" \tData: ")); + Serial.print(" \tData: "); Serial.println(flash[i]); } } @@ -72,24 +72,30 @@ void setup() delay(2000); Serial.begin(9600); + if(!flash.check_writable()) + { + Serial.println("Incompatible or no bootloader present! Please burn correct bootloader"); + while(1); + } + // Fetch flash page 1, where we may have a flag flash.fetch_page(1); // Check if our flag is present if(flash[5] == 'X') { - Serial.println(F("Content found!")); + Serial.println("Content found!"); read_data(); } else { - Serial.print(F("Flash page size for this chip: ")); + Serial.print("Flash page size for this chip: "); Serial.print(SPM_PAGESIZE); - Serial.print(F(" bytes\nTotal assigned flash space: ")); + Serial.print(" bytes\nTotal assigned flash space: "); Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); - Serial.println(F(" bytes")); + Serial.println(" bytes"); - Serial.println(F("No content found! Writing new content...")); + Serial.println("No content found! Writing new content..."); write_data(); } } diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino index 7c5d956..9a1e723 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino @@ -49,7 +49,7 @@ void write_data() // One simple call, with the address first and the object second flash.put(buffer_address, f); - Serial.println(F("Written float data type!")); + Serial.println("Written float data type!"); // Data to store MyObject customVar = @@ -72,12 +72,12 @@ void write_data() flash[5] = 'X'; flash.write_page(1); - Serial.println(F("Written custom data type!\nReset your board to view the contents!\n")); + Serial.println("Written custom data type!\nReset your board to view the contents!\n"); } void read_data() { - Serial.println(F("Read float from flash: ")); + Serial.println("Read float from flash: "); // Fetch first flash page flash.fetch_page(0); @@ -87,7 +87,7 @@ void read_data() // Get the float data from flash at position 'buffer_address' flash.get(buffer_address, f); - Serial.print(F("The value of f is now: ")); + Serial.print("The value of f is now: "); Serial.println(f, 3); buffer_address += sizeof(float); // Move address to the next byte after float 'f' @@ -95,7 +95,7 @@ void read_data() flash.get(buffer_address, customVar); - Serial.println(F("Read custom object from flash: ")); + Serial.println("Read custom object from flash: "); Serial.println(customVar.field1); Serial.println(customVar.field2); Serial.println(customVar.name); @@ -106,24 +106,30 @@ void setup() delay(2000); Serial.begin(9600); + if(!flash.check_writable()) + { + Serial.println("Incompatible or no bootloader present! Please burn correct bootloader"); + while(1); + } + // Fetch flash page 1, where we may have a flag flash.fetch_page(1); // Check if our flag is present if(flash[5] == 'X') { - Serial.println(F("Content found!")); + Serial.println("Content found!"); read_data(); } else { - Serial.print(F("Flash page size for this chip: ")); + Serial.print("Flash page size for this chip: "); Serial.print(SPM_PAGESIZE); - Serial.print(F(" bytes\nTotal assigned flash space: ")); + Serial.print(" bytes\nTotal assigned flash space: "); Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); - Serial.println(F(" bytes")); + Serial.println(" bytes"); - Serial.println(F("No content found! Writing new content...")); + Serial.println("No content found! Writing new content..."); write_data(); } } diff --git a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino index 5e8002b..608bbf2 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino @@ -50,8 +50,15 @@ const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__ (( aligne void setup() { + delay(1000); // Initialize serial Serial.begin(9600); + + if(!optiboot_check_writable()) + { + Serial.println("Incompatible or no bootloader present! Please burn the correct bootloader"); + while(1); + } } @@ -59,24 +66,24 @@ void loop() { // Print main menu Serial.println(); - Serial.println(F("|------------------------------------------------|")); - Serial.println(F("| Welcome to the Optiboot flash writer example! |")); - Serial.print(F("| Each flash page is ")); + Serial.println("|------------------------------------------------|"); + Serial.println("| Welcome to the Optiboot flash writer example! |"); + Serial.print("| Each flash page is "); Serial.print(SPM_PAGESIZE); - Serial.println(F(" bytes long. |")); - Serial.print(F("| There are ")); + Serial.println(" bytes long. |"); + Serial.print("| There are "); Serial.print(NUMBER_OF_PAGES); - Serial.println(F(" pages that can be read/written to. |")); - Serial.print(F("| Total assigned flash space: ")); + Serial.println(" pages that can be read/written to. |"); + Serial.print("| Total assigned flash space: "); Serial.print(NUMBER_OF_PAGES * SPM_PAGESIZE); - Serial.println(F(" bytes. |")); - Serial.println(F("| Change the NUMBER_OF_PAGES constant to |")); - Serial.println(F("| increase or decrease this number. |")); - Serial.println(F("| |")); - Serial.println(F("| What do you want to do? |")); - Serial.println(F("| 1. Show current flash content |")); - Serial.println(F("| 2. Write to flash memory |")); - Serial.println(F("|------------------------------------------------|")); + Serial.println(" bytes. |"); + Serial.println("| Change the NUMBER_OF_PAGES constant to |"); + Serial.println("| increase or decrease this number. |"); + Serial.println("| |"); + Serial.println("| What do you want to do? |"); + Serial.println("| 1. Show current flash content |"); + Serial.println("| 2. Write to flash memory |"); + Serial.println("|------------------------------------------------|"); // Static variables static uint8_t charBuffer; @@ -90,24 +97,24 @@ void loop() while(!Serial.available()); menuOption = Serial.read(); if(menuOption != '1' && menuOption != '2') - Serial.print(F("\nPlease enter a valid option! ")); + Serial.print("\nPlease enter a valid option! "); } while(menuOption != '1' && menuOption != '2'); - Serial.print(F("\nOption ")); + Serial.print("\nOption "); Serial.print(menuOption); - Serial.println(F(" selected.")); + Serial.println(" selected."); // Read flash option selected if(menuOption == '1') { - Serial.print(F("Which page number do you want to read? Page 0 to ")); + Serial.print("Which page number do you want to read? Page 0 to "); Serial.print(NUMBER_OF_PAGES - 1); - Serial.print(F(", Page ")); + Serial.print(", Page "); Serial.print(NUMBER_OF_PAGES); - Serial.print(F(" to show all pages: ")); + Serial.print(" to show all pages: "); //Get page number from the serial monitor do @@ -116,9 +123,9 @@ void loop() pageNumber = Serial.read() - 0x30; if(pageNumber > NUMBER_OF_PAGES) { - Serial.print(F("\nPlease enter a valid page between 0 and ")); + Serial.print("\nPlease enter a valid page between 0 and "); Serial.print(NUMBER_OF_PAGES - 1); - Serial.println(F(". The number of pages can be extended by changing NUMBER_OF_PAGES constant")); + Serial.println(". The number of pages can be extended by changing NUMBER_OF_PAGES constant"); } } while(pageNumber > NUMBER_OF_PAGES); @@ -143,9 +150,9 @@ void loop() for(uint8_t page = pageFirst; page < pageLast; page++) { optiboot_readPage(flashSpace, ramBuffer, page); - Serial.print(F("Page ")); + Serial.print("Page "); Serial.print(page); - Serial.print(F(": ")); + Serial.print(": "); for(uint16_t i = 0; i < sizeof(ramBuffer); i++) { if(ramBuffer[i] == 0x00 || ramBuffer[i] == 0xff) @@ -166,28 +173,28 @@ void loop() pageNumber = 0xff; //Get page number from the serial monitor - Serial.print(F("\nWhich page do you want to write to? Page: ")); + Serial.print("\nWhich page do you want to write to? Page: "); do { while(!Serial.available()); pageNumber = Serial.read() - 0x30; if(pageNumber > NUMBER_OF_PAGES - 1) { - Serial.print(F("\nPlease enter a valid page between 0 and ")); + Serial.print("\nPlease enter a valid page between 0 and "); Serial.print(NUMBER_OF_PAGES - 1); - Serial.println(F(". The number of pages can be extended by changing NUMBER_OF_PAGES constant")); + Serial.println(". The number of pages can be extended by changing NUMBER_OF_PAGES constant"); } } while(pageNumber >= NUMBER_OF_PAGES); Serial.println(pageNumber); // Print prompt to enter some new characters to write to flash - Serial.print(F("Please type the characters you want to store (max ")); + Serial.print("Please type the characters you want to store (max "); Serial.print(SPM_PAGESIZE); - Serial.println(F(" characters)")); - Serial.print(F("End the line by sending the '")); + Serial.println(" characters)"); + Serial.print("End the line by sending the '"); Serial.write(terminationChar); - Serial.println(F("' character:")); + Serial.println("' character:"); // Get all characters from the serial monitor and store it to the ramBuffer memset(ramBuffer, 0, sizeof(ramBuffer)); @@ -206,7 +213,7 @@ void loop() } } charBuffer = 0; - Serial.println(F("\n\nAll chars received \nWriting to flash...")); + Serial.println("\n\nAll chars received \nWriting to flash..."); // WRITE RECEIVED DATA TO THE CURRENT FLASH PAGE // flash_buffer is where the data is stored (contains the memory addresses) @@ -214,19 +221,19 @@ void loop() // pageNumber is the page the data is written to optiboot_writePage(flashSpace, ramBuffer, pageNumber); - Serial.println(F("Writing finished. You can now reset or power cycle the board and check for new contents!")); + Serial.println("Writing finished. You can now reset or power cycle the board and check for new contents!"); } // End of flash write option //Return to the main menu if 'm' is sent - Serial.println(F("\ntype the character 'm' to return to to the main menu")); + Serial.println("\ntype the character 'm' to return to to the main menu"); do { while(!Serial.available()); returnToMenu = Serial.read(); if(returnToMenu != 'm') - Serial.print(F("\nPlease type a valid character! ")); + Serial.print("\nPlease type a valid character! "); } while(returnToMenu != 'm'); returnToMenu = 0; From b0c68308c9509e8c7b4900c08ebb1be01f8edfcf Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 23:41:11 +0200 Subject: [PATCH 238/351] Remove define --- .../examples/Serial_read_write/Serial_read_write.ino | 1 - 1 file changed, 1 deletion(-) diff --git a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino index 608bbf2..c963e5a 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino @@ -46,7 +46,6 @@ const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__ (( aligne "This some default content stored on page one" }; -//#define Serial Serial3 void setup() { From 0a5818e75ba852e7d90c6c061db6fd98dd8edcd1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 23:43:12 +0200 Subject: [PATCH 239/351] Update Optiboot library --- .../libraries/Optiboot_flasher/keywords.txt | 1 + .../Optiboot_flasher/src/optiboot.cpp | 44 ++++++++++++++----- .../libraries/Optiboot_flasher/src/optiboot.h | 2 + 3 files changed, 37 insertions(+), 10 deletions(-) diff --git a/megaavr/libraries/Optiboot_flasher/keywords.txt b/megaavr/libraries/Optiboot_flasher/keywords.txt index acb6c51..87fae6a 100644 --- a/megaavr/libraries/Optiboot_flasher/keywords.txt +++ b/megaavr/libraries/Optiboot_flasher/keywords.txt @@ -33,6 +33,7 @@ optiboot_page_write KEYWORD2 optiboot_readPage KEYWORD2 optiboot_read KEYWORD2 optiboot_writePage KEYWORD2 +optiboot_page_erase_write KEYWORD2 ############################################ # Constants (LITERAL1) diff --git a/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp index f4b8e0f..8ab2c3f 100755 --- a/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp +++ b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp @@ -44,11 +44,28 @@ bool optiboot_check_writable() void optiboot_page_erase(optiboot_addr_t address) { // Set page by writing to address - do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, 0xFF); + optiboot_page_fill(address, (uint8_t)0xFF); do_nvmctrl_cli(0, NVMCTRL_CMD_PAGEERASE_gc, 0); // do actual erase } +/** + * @brief Writes an 8-bit value to a temporary, internal buffer. Note that + * this temporary buffer gets destroyed if you read or write to EEPROM. It's + * therefore important that the buffer gets written to flash before doing + * anything EEPROM related. Also note that you can write only once to one + * location in the temporary buffer without erasing it first, which happens + * after a flash page erase or write. + * + * @param address address where to write the 8-bit data + * @param data data to write + */ +void optiboot_page_fill(optiboot_addr_t address, uint8_t data) +{ + do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data); +} + + /** * @brief Writes a word/16-bit value to a temporary, internal buffer. Note that * this temporary buffer gets destroyed if you read or write to EEPROM. It's @@ -62,8 +79,18 @@ void optiboot_page_erase(optiboot_addr_t address) */ void optiboot_page_fill(optiboot_addr_t address, uint16_t data) { - do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data & 0xFF); - do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data >> 8); + optiboot_page_fill(address, (uint8_t)(data & 0xFF)); + optiboot_page_fill(++address, (uint8_t)(data >> 8)); +} + + +/** + * @brief Write the temporary, internal buffer to flash + * + */ +void optiboot_page_erase_write() +{ + do_nvmctrl_cli(0, NVMCTRL_CMD_PAGEERASEWRITE_gc, 0); } @@ -129,13 +156,10 @@ void optiboot_readPage(const uint8_t allocated_flash_space[], uint8_t storage_ar */ void optiboot_writePage(const uint8_t allocated_flash_space[], uint8_t data_to_store[], uint16_t page_number) { - const uint8_t *adjusted_address; // Copy ram buffer to temporary flash buffer for(uint16_t i = 0; i < SPM_PAGESIZE; i++) - { - adjusted_address = &allocated_flash_space[i + SPM_PAGESIZE * (page_number)]; - adjusted_address += MAPPED_PROGMEM_START; - do_nvmctrl((optiboot_addr_t)adjusted_address, NVMCTRL_CMD_COPY_gc, data_to_store[i]); - } - do_nvmctrl_cli(0, NVMCTRL_CMD_PAGEERASEWRITE_gc, 0); + optiboot_page_fill((optiboot_addr_t)&allocated_flash_space[i + SPM_PAGESIZE * page_number], data_to_store[i]); + + // Erase and then write page + optiboot_page_erase_write(); } diff --git a/megaavr/libraries/Optiboot_flasher/src/optiboot.h b/megaavr/libraries/Optiboot_flasher/src/optiboot.h index b9159fd..e3999ec 100755 --- a/megaavr/libraries/Optiboot_flasher/src/optiboot.h +++ b/megaavr/libraries/Optiboot_flasher/src/optiboot.h @@ -53,7 +53,9 @@ const do_spm_t do_nvmctrl = (do_spm_t)((PROGMEM_START + 2) >> 1); void do_nvmctrl_cli(optiboot_addr_t address, uint8_t command, uint16_t data); bool optiboot_check_writable(); void optiboot_page_erase(optiboot_addr_t address); +void optiboot_page_fill(optiboot_addr_t address, uint8_t data); void optiboot_page_fill(optiboot_addr_t address, uint16_t data); +void optiboot_page_erase_write(); void optiboot_page_write(optiboot_addr_t address); void optiboot_read(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number, uint16_t start_address, uint16_t stop_address); void optiboot_readPage(const uint8_t allocated_flash_space[], uint8_t storage_array[], uint16_t page_number); From 5331a498a4e78ece00eafe8961bffbdae900f3a3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 5 Apr 2021 23:43:48 +0200 Subject: [PATCH 240/351] Add Read_write_without_buffer example --- .../Read_write_without_buffer.ino | 105 ++++++++++++++++++ 1 file changed, 105 insertions(+) create mode 100644 megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino diff --git a/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino b/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino new file mode 100644 index 0000000..c11bb98 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino @@ -0,0 +1,105 @@ +/***********************************************************************| +| Optiboot Flash read/write | +| | +| Read_write_without_buffer.ino | +| | +| A library for interfacing with Optiboot Flash's write functionality | +| Developed in 2021 by MCUdude | +| https://github.com/MCUdude/ | +| | +| In this low-level example we write 16-bit values to one flash page, | +| and 8-bit values to another page. What's different about this | +| example is that we do this without using a RAM buffer where the | +| contents are stored before writing to flash. Instead, the internal, | +| temporary buffer is used. By doing this we reduce RAM usage, but it | +| is not nearly as user friendly as using the Flash library. | +| | +| IMPORTANT THINGS: | +| - All flash content gets erased after each upload cycle | +| - Allocated flash space must be page aligned (it is in this example) | +|***********************************************************************/ + + +#include + + +// Allocate one flash pages for storing data +#define NUMBER_OF_PAGES 2 +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; + + +// Function for writing 16-bit integers to a flash page +void flash_write_int(const uint8_t base_addr[], uint16_t offset_addr, int16_t data) +{ + // Write the 16-bit value to the buffer + optiboot_page_fill((uint16_t)base_addr + offset_addr, (uint16_t)data); + + // Write the buffer to flash when the buffer is full + if ((offset_addr & 0xFF) == (SPM_PAGESIZE - 2)) + optiboot_page_erase_write(); +} + + +// Function to write bytes to a flash page +void flash_write_byte(const uint8_t base_addr[], uint16_t offset_addr, uint8_t data) +{ + // Write the 8-bit value to the buffer + optiboot_page_fill((uint16_t)base_addr + offset_addr, data); + + if ((offset_addr & 0xFF) == (SPM_PAGESIZE - 2)) + optiboot_page_erase_write(); +} + + +// Function to force a flash page write operation +void flash_end_write(uint16_t offset_addr) +{ + // Write the buffer to flash if there are any contents in the buffer + if ((offset_addr & 0xFF) != 0x00) + optiboot_page_erase_write(); +} + + +void setup() +{ + delay(2000); + Serial.begin(9600); + + static uint16_t addr = 0; + + Serial.print("Filling up flash page 0 with 16-bit values...\n"); + // Fill the first flash page (page 0) with 16-bit values (0x100 to 0x01FF) + for(uint8_t data = 0; data < (SPM_PAGESIZE / 2); data++) + { + flash_write_int(flashSpace, addr, data + 0x0100); // Write data + addr += 2; // Increase memory address by two since we're writing 16-bit values + } + // Force an end write in case it hasn't already been done in flash_write_int + flash_end_write(--addr); + + + Serial.print("Filling up flash page 1 with 8-bit values...\n"); + // Fill the second flash page (page 1) with 0-bit values (0x00 to 0x0FF) + for(uint16_t data = 0; data < SPM_PAGESIZE; data++) + { + addr++; // Increase memory address by one since we're writing 8-bit values + flash_write_byte(flashSpace, addr, data); // Write data + } + // Force an end write in case it hasn't already been done in flash_write_byte + flash_end_write(addr); + + + Serial.print("Flash pages filled. Reading back their content.\nPage 0:\n"); + for(uint16_t i = 0; i < SPM_PAGESIZE; i += 2) + Serial.printf("Flash mem addr: 0x%04x, content: 0x%04x\n", flashSpace + i, (pgm_read_byte(flashSpace + i + 1) << 8) + (pgm_read_byte(flashSpace + i))); + + Serial.println(F("\n\nPage 1:")); + for(uint16_t i = 0; i < SPM_PAGESIZE; i++) + Serial.printf("Flash mem addr: 0x%04x, content: 0x%02x\n", flashSpace + SPM_PAGESIZE + i, pgm_read_byte(flashSpace + SPM_PAGESIZE + i)); +} + + +void loop() +{ + +} From 8e14e3365e03d846ae22ea533caa5098e1278408 Mon Sep 17 00:00:00 2001 From: Franz Hennies Date: Tue, 6 Apr 2021 21:18:30 +0200 Subject: [PATCH 241/351] Update PlatformIO.md Typo in ### `board_build.variant` definition, should read `48pin-standard` etc. not `48pin-default` --- PlatformIO.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/PlatformIO.md b/PlatformIO.md index 0d3a6d1..03af516 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -209,11 +209,11 @@ Specifies what functionality the reset pin should have. Note that the option `re Holds the current pinout in use. See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. -| Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | -|---------------------------|-----------------------------------|---------------------------|---------------------------| -| `48pin-default` (default) | `40pin-default` (must be defined) | `32pin-default` (default) | `28pin-default` (default) | -| `nano-every` | | | | -| `uno-wifi` | | | | +| Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | +|----------------------------|------------------------------------|----------------------------|----------------------------| +| `48pin-standard` (default) | `40pin-standard` (must be defined) | `32pin-standard` (default) | `28pin-standard` (default) | +| `nano-every` | | | | +| `uno-wifi` | | | | ### `build_unflags` From 4ed967aff5a7009b8de695350b10ff0ec26c91b3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 8 Apr 2021 21:06:17 +0200 Subject: [PATCH 242/351] Add comparator read function And remove tailing whitespaces --- megaavr/libraries/Comparator/README.md | 10 +++++++++ .../libraries/Comparator/src/Comparator.cpp | 21 ++++++++++++------- megaavr/libraries/Comparator/src/Comparator.h | 3 ++- 3 files changed, 25 insertions(+), 9 deletions(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index 74139e5..f295125 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -129,6 +129,7 @@ Method for initializing the comparator. Comparator.init(); // Initialize comparator ``` + ## start() Method for starting the analog comparator. ##### Usage @@ -146,6 +147,15 @@ Comparator.stop(); // Stop comparator ``` +## read() +Reads the state of the analog comparator output. + +##### Usage +```c++ +bool comp_state = Comparator.read(); // Read comparator +``` + + ## attachInterrupt() Method for enabling analog comparator interrupt. The interrupt will trigger when the the comparator output changes. Valid arguments for the third parameters are `RISING`, `FALLING` and `CHANGE`. diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index 032f061..c4ec800 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -14,7 +14,7 @@ static volatile voidFuncPtr intFuncAC[1]; #endif -AnalogComparator::AnalogComparator(const uint8_t comp_number, AC_t& ac) : comparator_number(comp_number), AC(ac) +AnalogComparator::AnalogComparator(const uint8_t comp_number, AC_t& ac) : comparator_number(comp_number), AC(ac) { } @@ -34,7 +34,7 @@ void AnalogComparator::init() // Set hysteresis AC.CTRLA = (AC.CTRLA & ~AC_HYSMODE_gm) | hysteresis; - + // Set inputs if(input_p == in_p::in0) PORTD.PIN2CTRL = PORT_ISC_INPUT_DISABLE_gc; @@ -86,10 +86,15 @@ void AnalogComparator::stop() start(false); } +bool AnalogComparator::read() +{ + return !!(AC0.STATUS & AC_STATE_bm); +} + void AnalogComparator::attachInterrupt(void (*userFunc)(void), uint8_t mode) { AC_INTMODE_t intmode; - switch (mode) + switch (mode) { // Set RISING, FALLING or CHANGE interrupt trigger for the comparator output case RISING: @@ -106,10 +111,10 @@ void AnalogComparator::attachInterrupt(void (*userFunc)(void), uint8_t mode) return; } AC.CTRLA = (AC.CTRLA & ~AC_INTMODE_POSEDGE_gc) | intmode; - + // Store function pointer intFuncAC[comparator_number] = userFunc; - + // Enable interrupt AC.INTCTRL |= AC_CMP_bm; } @@ -125,7 +130,7 @@ ISR(AC0_AC_vect) { // Run user function intFuncAC[0](); - + // Clear flag AC0.STATUS = AC_CMP_bm; } @@ -136,7 +141,7 @@ ISR(AC1_AC_vect) { // Run user function intFuncAC[1](); - + // Clear flag AC1.STATUS = AC_CMP_bm; } @@ -147,7 +152,7 @@ ISR(AC2_AC_vect) { // Run user function intFuncAC[2](); - + // Clear flag AC2.STATUS = AC_CMP_bm; } diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 17821bd..409ebd2 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -67,6 +67,7 @@ class AnalogComparator void init(); void start(bool state = true); void stop(); + bool read(); void attachInterrupt(voidFuncPtr callback, uint8_t mode); void detachInterrupt(); @@ -80,7 +81,7 @@ class AnalogComparator private: const uint8_t comparator_number; AC_t& AC; - bool enable = false; + bool enable = false; }; #if defined(AC0_AC_vect) From 3f20e21b6ad343ce417605928371f818dbc677a3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 8 Apr 2021 21:45:07 +0200 Subject: [PATCH 243/351] Add output enable and disable invert Closes #115 --- megaavr/libraries/Comparator/README.md | 12 +++++++----- megaavr/libraries/Comparator/src/Comparator.cpp | 8 +++++++- megaavr/libraries/Comparator/src/Comparator.h | 8 +++++--- 3 files changed, 19 insertions(+), 9 deletions(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index f295125..0de4494 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -104,12 +104,14 @@ Comparator.hysteresis = hyst::large; // Use 50V hysteresis ### output -Variable for setting the comparator output pin (PA7). +Variable for setting the comparator output, internally and/or externally. Accepted values: ``` c++ -out::disable; // No output pin -out::enable; // Enable output pin (PA7) -out::invert; // Invert output pin (PA7) +out::disable; // No output pin, signal not inverted internally +out::disable_invert; // No output pin, signal inverted internally +out::enable; // Enable output pin (PA7), signal not inverted internally +out::invert; // Enable output pin (PA7), signal inverted internally +out::enable_invert; // Identical to out::invert ``` ##### Usage @@ -148,7 +150,7 @@ Comparator.stop(); // Stop comparator ## read() -Reads the state of the analog comparator output. +Reads the state of the analog comparator output. Works also when the physical output pin is disabled. ##### Usage ```c++ diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index c4ec800..6f5afdf 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -59,7 +59,7 @@ void AnalogComparator::init() AC.CTRLA |= out::enable; PORTA.DIRSET = PIN7_bm; } - else if(output == out::invert) + else if(output == out::invert /* || output == out::invert_enable */) { AC.MUXCTRLA |= out::invert; AC.CTRLA |= out::enable; @@ -71,6 +71,12 @@ void AnalogComparator::init() AC.CTRLA &= ~out::enable; PORTA.DIRCLR = PIN7_bm; } + else if(output == out::disable_invert) + { + AC.MUXCTRLA |= out::invert; + AC.CTRLA &= ~out::enable; + PORTA.DIRCLR = PIN7_bm; + } } void AnalogComparator::start(bool state) diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 409ebd2..30450a4 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -7,9 +7,11 @@ namespace out { enum output_t : uint8_t { - disable = 0x00, - enable = 0x40, - invert = 0x80, + disable = 0x00, + disable_invert = 0xC0, + enable = 0x40, + invert = 0x80, + enable_invert = 0x80, }; }; From de8679a194aeb6f42dd12c861e2ed988312e26fc Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 9 Apr 2021 18:46:22 +0200 Subject: [PATCH 244/351] Reduce number of jobs to less than 200 #118 related --- .travis.yml | 156 +++++++++------------------------------------------- 1 file changed, 27 insertions(+), 129 deletions(-) diff --git a/.travis.yml b/.travis.yml index dc7326f..0efd7bc 100644 --- a/.travis.yml +++ b/.travis.yml @@ -19,35 +19,35 @@ env: # Each line in the matrix will be run as a separate job in the Travis CI build ## ATmega4809 - # pinout=48pin_standard, clock=internal, bootloader=no_bootloader + # pinout=48pin_standard, resetpin=reset, BOD=2v6, clock=internal_16MHz, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader + # pinout=40pin_standard, resetpin=gpio, BOD=4v3, clock=internal_20MHz, bootloader=uart0_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=gpio,BOD=4v3,clock=internal_20MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=uno_wifi, BOD=4v0, clock=internal_10MHz, bootloader=uart0_alternative + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=4v0,clock=internal_10MHz,bootloader=uart0_alternative" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # pinout=nano_every, BOD=3v7, clock=internal_8MHz, bootloader=uart1_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=3v7,clock=internal_8MHz,bootloader=uart1_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # BOD=3v3, clock=internal_5MHz, bootloader=uart1_alternative + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=3v3,clock=internal_5MHz,bootloader=uart1_alternative" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # BOD=2v9, clock=internal_4MHz, bootloader=uart2_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v9,clock=internal_4MHz,bootloader=uart2_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # BOD=2v1, clock=internal_2MHz, bootloader=uart2_alternative + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v1,clock=internal_2MHz,bootloader=uart2_alternative" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # BOD=1v8, clock=internal_1MHz, bootloader=uart3_default + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=1v8,clock=internal_1MHz,bootloader=uart3_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # BOD=disabled, clock=external_20MHz, bootloader=uart3_alternative + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=disabled,clock=external_20MHz,bootloader=uart3_alternative" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # clock=external_16MHz - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=40pin_standard, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=40pin_standard, clock=internal_16MHz, bootloader=uart0_default - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=40pin_standard, clock=external_16MHz, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=40pin_standard,resetpin=reset,BOD=2v6,clock=external_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=uno_wifi, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=uno_wifi,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - # pinout=nano_every, clock=internal, bootloader=no_bootloader - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=nano_every,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # clock=external_12MHz + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_12MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # clock=external_8MHz + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # clock=external_4MHz + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + # clock=external_1MHz + - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries" BOARD_ID="MegaCoreX:megaavr:4809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=external_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" + ## ATmega4808 # pinout=32pin_standard, clock=internal, bootloader=no_bootloader @@ -151,13 +151,7 @@ env: ## ATmega809 # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -165,13 +159,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -179,13 +167,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -193,13 +175,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -207,13 +183,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -221,13 +191,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -235,13 +199,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -249,13 +207,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -263,13 +215,7 @@ env: # pinout=48pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:809:pinout=48pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=48pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -279,13 +225,7 @@ env: ## ATmega808 # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Comparator" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -301,13 +241,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/EEPROM" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -323,13 +257,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Event" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -345,13 +273,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Logic" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -367,13 +289,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Servo" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -389,13 +305,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SoftwareSerial" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -411,13 +321,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/SPI" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader @@ -433,13 +337,7 @@ env: # pinout=32pin_standard, clock=internal, bootloader=no_bootloader - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_20MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_10MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_8MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_5MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_4MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_2MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" - - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_1MHz,bootloader=no_bootloader" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=internal_16MHz, bootloader=uart0_default - SKETCH_PATH="${SKETCHBOOK_FOLDER}/hardware/MegaCoreX/megaavr/libraries/Wire" BOARD_ID="MegaCoreX:megaavr:808:pinout=32pin_standard,resetpin=reset,BOD=2v6,clock=internal_16MHz,bootloader=uart0_default" ALLOW_FAILURE="false" IDE_VERSIONS="$IDE_VERSION_LIST_FULL" # pinout=32pin_standard, clock=external_16MHz, bootloader=no_bootloader From 7cdb2c7d005cd4ec690dc8ba6428a7ccc92ef36c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 9 Apr 2021 19:51:13 +0200 Subject: [PATCH 245/351] Formatting --- .../SD/examples/CardInfo/CardInfo.ino | 2 +- .../SD/examples/Datalogger/Datalogger.ino | 3 +- .../SD/examples/DumpFile/DumpFile.ino | 3 +- megaavr/libraries/SD/examples/Files/Files.ino | 4 +- .../NonBlockingWrite/NonBlockingWrite.ino | 1 - .../SD/examples/ReadWrite/ReadWrite.ino | 2 +- .../SD/examples/listfiles/listfiles.ino | 4 +- megaavr/libraries/SD/src/SD.cpp | 2 +- megaavr/libraries/SD/src/utility/FatStructs.h | 836 ++--- megaavr/libraries/SD/src/utility/Sd2Card.cpp | 1554 ++++----- megaavr/libraries/SD/src/utility/Sd2Card.h | 546 +-- megaavr/libraries/SD/src/utility/Sd2PinMap.h | 1056 +++--- megaavr/libraries/SD/src/utility/SdFat.h | 1282 +++---- megaavr/libraries/SD/src/utility/SdFatUtil.h | 154 +- .../libraries/SD/src/utility/SdFatmainpage.h | 404 +-- megaavr/libraries/SD/src/utility/SdFile.cpp | 3054 ++++++++--------- megaavr/libraries/SD/src/utility/SdInfo.h | 464 +-- megaavr/libraries/SD/src/utility/SdVolume.cpp | 702 ++-- 18 files changed, 5035 insertions(+), 5038 deletions(-) diff --git a/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino b/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino index 3418e92..c48dcbd 100755 --- a/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino +++ b/megaavr/libraries/SD/examples/CardInfo/CardInfo.ino @@ -11,7 +11,7 @@ ** SDI - pin 12 on Arduino Uno/Duemilanove/Diecimila ** CLK - pin 13 on Arduino Uno/Duemilanove/Diecimila ** CS - depends on your SD card shield or module. - Pin 10 used here for consistency with other Arduino examples + Pin 10 used here for consistency with other Arduino examples created 28 Mar 2011 by Limor Fried diff --git a/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino b/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino index fdbacfd..f265b76 100755 --- a/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino +++ b/megaavr/libraries/SD/examples/Datalogger/Datalogger.ino @@ -12,8 +12,7 @@ ** SDI - pin 12 ** CLK - pin 13 ** CS - depends on your SD card shield or module. - Pin 10 used here for consistency with other Arduino examples - (for MKRZero SD: SDCARD_SS_PIN) + Pin 10 used here for consistency with other Arduino examples created 24 Nov 2010 modified 24 July 2020 diff --git a/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino b/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino index bb114b6..49f14d9 100755 --- a/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino +++ b/megaavr/libraries/SD/examples/DumpFile/DumpFile.ino @@ -11,8 +11,7 @@ ** SDI - pin 12 ** CLK - pin 13 ** CS - depends on your SD card shield or module. - Pin 10 used here for consistency with other Arduino examples - (for MKRZero SD: SDCARD_SS_PIN) + Pin 10 used here for consistency with other Arduino examples created 22 December 2010 by Limor Fried diff --git a/megaavr/libraries/SD/examples/Files/Files.ino b/megaavr/libraries/SD/examples/Files/Files.ino index 85faa7c..e79aae5 100755 --- a/megaavr/libraries/SD/examples/Files/Files.ino +++ b/megaavr/libraries/SD/examples/Files/Files.ino @@ -9,8 +9,8 @@ ** SDI - pin 12 ** CLK - pin 13 ** CS - depends on your SD card shield or module. - Pin 10 used here for consistency with other Arduino examples - (for MKRZero SD: SDCARD_SS_PIN) + Pin 10 used here for consistency with other Arduino examples + created Nov 2010 by David A. Mellis diff --git a/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino b/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino index 082a5fb..d7b785f 100755 --- a/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino +++ b/megaavr/libraries/SD/examples/NonBlockingWrite/NonBlockingWrite.ino @@ -24,7 +24,6 @@ ** CLK - pin 13 ** CS - depends on your SD card shield or module. Pin 10 used here for consistency with other Arduino examples - (for MKRZero SD: SDCARD_SS_PIN) modified 24 July 2020 by Tom Igoe diff --git a/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino b/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino index c15ecdb..a48e0c6 100755 --- a/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino +++ b/megaavr/libraries/SD/examples/ReadWrite/ReadWrite.ino @@ -8,7 +8,7 @@ ** SDO - pin 11 ** SDI - pin 12 ** CLK - pin 13 - ** CS - pin 4 (For For Uno, Nano: pin 10. For MKRZero SD: SDCARD_SS_PIN) + ** CS - pin 4 (For For Uno, Nano: pin 10) created Nov 2010 by David A. Mellis diff --git a/megaavr/libraries/SD/examples/listfiles/listfiles.ino b/megaavr/libraries/SD/examples/listfiles/listfiles.ino index 66eebb6..7064563 100755 --- a/megaavr/libraries/SD/examples/listfiles/listfiles.ino +++ b/megaavr/libraries/SD/examples/listfiles/listfiles.ino @@ -11,8 +11,8 @@ ** SDI - pin 12 ** CLK - pin 13 ** CS - depends on your SD card shield or module. - Pin 10 used here for consistency with other Arduino examples - (for MKRZero SD: SDCARD_SS_PIN) + Pin 10 used here for consistency with other Arduino examples + created Nov 2010 by David A. Mellis diff --git a/megaavr/libraries/SD/src/SD.cpp b/megaavr/libraries/SD/src/SD.cpp index 24fcb2e..69f348a 100755 --- a/megaavr/libraries/SD/src/SD.cpp +++ b/megaavr/libraries/SD/src/SD.cpp @@ -280,7 +280,7 @@ namespace SDLib { /* bool callback_openPath(SdFile& parentDir, char *filePathComponent, - bool isLastComponent, void *object) { + bool isLastComponent, void *object) { Callback used to open a file specified by a filepath that may specify one or more directories above it. diff --git a/megaavr/libraries/SD/src/utility/FatStructs.h b/megaavr/libraries/SD/src/utility/FatStructs.h index 84c1cc7..aefef9c 100755 --- a/megaavr/libraries/SD/src/utility/FatStructs.h +++ b/megaavr/libraries/SD/src/utility/FatStructs.h @@ -1,418 +1,418 @@ -/* Arduino SdFat Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#ifndef FatStructs_h -#define FatStructs_h -/** - \file - FAT file structures -*/ -/* - mostly from Microsoft document fatgen103.doc - http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx -*/ -//------------------------------------------------------------------------------ -/** Value for byte 510 of boot block or MBR */ -uint8_t const BOOTSIG0 = 0X55; -/** Value for byte 511 of boot block or MBR */ -uint8_t const BOOTSIG1 = 0XAA; -//------------------------------------------------------------------------------ -/** - \struct partitionTable - \brief MBR partition table entry - - A partition table entry for a MBR formatted storage device. - The MBR partition table has four entries. -*/ -struct partitionTable { - /** - Boot Indicator . Indicates whether the volume is the active - partition. Legal values include: 0X00. Do not use for booting. - 0X80 Active partition. - */ - uint8_t boot; - /** - Head part of Cylinder-head-sector address of the first block in - the partition. Legal values are 0-255. Only used in old PC BIOS. - */ - uint8_t beginHead; - /** - Sector part of Cylinder-head-sector address of the first block in - the partition. Legal values are 1-63. Only used in old PC BIOS. - */ - unsigned beginSector : 6; - /** High bits cylinder for first block in partition. */ - unsigned beginCylinderHigh : 2; - /** - Combine beginCylinderLow with beginCylinderHigh. Legal values - are 0-1023. Only used in old PC BIOS. - */ - uint8_t beginCylinderLow; - /** - Partition type. See defines that begin with PART_TYPE_ for - some Microsoft partition types. - */ - uint8_t type; - /** - head part of cylinder-head-sector address of the last sector in the - partition. Legal values are 0-255. Only used in old PC BIOS. - */ - uint8_t endHead; - /** - Sector part of cylinder-head-sector address of the last sector in - the partition. Legal values are 1-63. Only used in old PC BIOS. - */ - unsigned endSector : 6; - /** High bits of end cylinder */ - unsigned endCylinderHigh : 2; - /** - Combine endCylinderLow with endCylinderHigh. Legal values - are 0-1023. Only used in old PC BIOS. - */ - uint8_t endCylinderLow; - /** Logical block address of the first block in the partition. */ - uint32_t firstSector; - /** Length of the partition, in blocks. */ - uint32_t totalSectors; -} __attribute__((packed)); -/** Type name for partitionTable */ -typedef struct partitionTable part_t; -//------------------------------------------------------------------------------ -/** - \struct masterBootRecord - - \brief Master Boot Record - - The first block of a storage device that is formatted with a MBR. -*/ -struct masterBootRecord { - /** Code Area for master boot program. */ - uint8_t codeArea[440]; - /** Optional WindowsNT disk signature. May contain more boot code. */ - uint32_t diskSignature; - /** Usually zero but may be more boot code. */ - uint16_t usuallyZero; - /** Partition tables. */ - part_t part[4]; - /** First MBR signature byte. Must be 0X55 */ - uint8_t mbrSig0; - /** Second MBR signature byte. Must be 0XAA */ - uint8_t mbrSig1; -} __attribute__((packed)); -/** Type name for masterBootRecord */ -typedef struct masterBootRecord mbr_t; -//------------------------------------------------------------------------------ -/** - \struct biosParmBlock - - \brief BIOS parameter block - - The BIOS parameter block describes the physical layout of a FAT volume. -*/ -struct biosParmBlock { - /** - Count of bytes per sector. This value may take on only the - following values: 512, 1024, 2048 or 4096 - */ - uint16_t bytesPerSector; - /** - Number of sectors per allocation unit. This value must be a - power of 2 that is greater than 0. The legal values are - 1, 2, 4, 8, 16, 32, 64, and 128. - */ - uint8_t sectorsPerCluster; - /** - Number of sectors before the first FAT. - This value must not be zero. - */ - uint16_t reservedSectorCount; - /** The count of FAT data structures on the volume. This field should - always contain the value 2 for any FAT volume of any type. - */ - uint8_t fatCount; - /** - For FAT12 and FAT16 volumes, this field contains the count of - 32-byte directory entries in the root directory. For FAT32 volumes, - this field must be set to 0. For FAT12 and FAT16 volumes, this - value should always specify a count that when multiplied by 32 - results in a multiple of bytesPerSector. FAT16 volumes should - use the value 512. - */ - uint16_t rootDirEntryCount; - /** - This field is the old 16-bit total count of sectors on the volume. - This count includes the count of all sectors in all four regions - of the volume. This field can be 0; if it is 0, then totalSectors32 - must be non-zero. For FAT32 volumes, this field must be 0. For - FAT12 and FAT16 volumes, this field contains the sector count, and - totalSectors32 is 0 if the total sector count fits - (is less than 0x10000). - */ - uint16_t totalSectors16; - /** - This dates back to the old MS-DOS 1.x media determination and is - no longer usually used for anything. 0xF8 is the standard value - for fixed (non-removable) media. For removable media, 0xF0 is - frequently used. Legal values are 0xF0 or 0xF8-0xFF. - */ - uint8_t mediaType; - /** - Count of sectors occupied by one FAT on FAT12/FAT16 volumes. - On FAT32 volumes this field must be 0, and sectorsPerFat32 - contains the FAT size count. - */ - uint16_t sectorsPerFat16; - /** Sectors per track for interrupt 0x13. Not used otherwise. */ - uint16_t sectorsPerTrtack; - /** Number of heads for interrupt 0x13. Not used otherwise. */ - uint16_t headCount; - /** - Count of hidden sectors preceding the partition that contains this - FAT volume. This field is generally only relevant for media - visible on interrupt 0x13. - */ - uint32_t hidddenSectors; - /** - This field is the new 32-bit total count of sectors on the volume. - This count includes the count of all sectors in all four regions - of the volume. This field can be 0; if it is 0, then - totalSectors16 must be non-zero. - */ - uint32_t totalSectors32; - /** - Count of sectors occupied by one FAT on FAT32 volumes. - */ - uint32_t sectorsPerFat32; - /** - This field is only defined for FAT32 media and does not exist on - FAT12 and FAT16 media. - Bits 0-3 -- Zero-based number of active FAT. - Only valid if mirroring is disabled. - Bits 4-6 -- Reserved. - Bit 7 -- 0 means the FAT is mirrored at runtime into all FATs. - -- 1 means only one FAT is active; it is the one referenced in bits 0-3. - Bits 8-15 -- Reserved. - */ - uint16_t fat32Flags; - /** - FAT32 version. High byte is major revision number. - Low byte is minor revision number. Only 0.0 define. - */ - uint16_t fat32Version; - /** - Cluster number of the first cluster of the root directory for FAT32. - This usually 2 but not required to be 2. - */ - uint32_t fat32RootCluster; - /** - Sector number of FSINFO structure in the reserved area of the - FAT32 volume. Usually 1. - */ - uint16_t fat32FSInfo; - /** - If non-zero, indicates the sector number in the reserved area - of the volume of a copy of the boot record. Usually 6. - No value other than 6 is recommended. - */ - uint16_t fat32BackBootBlock; - /** - Reserved for future expansion. Code that formats FAT32 volumes - should always set all of the bytes of this field to 0. - */ - uint8_t fat32Reserved[12]; -} __attribute__((packed)); -/** Type name for biosParmBlock */ -typedef struct biosParmBlock bpb_t; -//------------------------------------------------------------------------------ -/** - \struct fat32BootSector - - \brief Boot sector for a FAT16 or FAT32 volume. - -*/ -struct fat32BootSector { - /** X86 jmp to boot program */ - uint8_t jmpToBootCode[3]; - /** informational only - don't depend on it */ - char oemName[8]; - /** BIOS Parameter Block */ - bpb_t bpb; - /** for int0x13 use value 0X80 for hard drive */ - uint8_t driveNumber; - /** used by Windows NT - should be zero for FAT */ - uint8_t reserved1; - /** 0X29 if next three fields are valid */ - uint8_t bootSignature; - /** usually generated by combining date and time */ - uint32_t volumeSerialNumber; - /** should match volume label in root dir */ - char volumeLabel[11]; - /** informational only - don't depend on it */ - char fileSystemType[8]; - /** X86 boot code */ - uint8_t bootCode[420]; - /** must be 0X55 */ - uint8_t bootSectorSig0; - /** must be 0XAA */ - uint8_t bootSectorSig1; -} __attribute__((packed)); -//------------------------------------------------------------------------------ -// End Of Chain values for FAT entries -/** FAT16 end of chain value used by Microsoft. */ -uint16_t const FAT16EOC = 0XFFFF; -/** Minimum value for FAT16 EOC. Use to test for EOC. */ -uint16_t const FAT16EOC_MIN = 0XFFF8; -/** FAT32 end of chain value used by Microsoft. */ -uint32_t const FAT32EOC = 0X0FFFFFFF; -/** Minimum value for FAT32 EOC. Use to test for EOC. */ -uint32_t const FAT32EOC_MIN = 0X0FFFFFF8; -/** Mask a for FAT32 entry. Entries are 28 bits. */ -uint32_t const FAT32MASK = 0X0FFFFFFF; - -/** Type name for fat32BootSector */ -typedef struct fat32BootSector fbs_t; -//------------------------------------------------------------------------------ -/** - \struct directoryEntry - \brief FAT short directory entry - - Short means short 8.3 name, not the entry size. - - Date Format. A FAT directory entry date stamp is a 16-bit field that is - basically a date relative to the MS-DOS epoch of 01/01/1980. Here is the - format (bit 0 is the LSB of the 16-bit word, bit 15 is the MSB of the - 16-bit word): - - Bits 9-15: Count of years from 1980, valid value range 0-127 - inclusive (1980-2107). - - Bits 5-8: Month of year, 1 = January, valid value range 1-12 inclusive. - - Bits 0-4: Day of month, valid value range 1-31 inclusive. - - Time Format. A FAT directory entry time stamp is a 16-bit field that has - a granularity of 2 seconds. Here is the format (bit 0 is the LSB of the - 16-bit word, bit 15 is the MSB of the 16-bit word). - - Bits 11-15: Hours, valid value range 0-23 inclusive. - - Bits 5-10: Minutes, valid value range 0-59 inclusive. - - Bits 0-4: 2-second count, valid value range 0-29 inclusive (0 - 58 seconds). - - The valid time range is from Midnight 00:00:00 to 23:59:58. -*/ -struct directoryEntry { - /** - Short 8.3 name. - The first eight bytes contain the file name with blank fill. - The last three bytes contain the file extension with blank fill. - */ - uint8_t name[11]; - /** Entry attributes. - - The upper two bits of the attribute byte are reserved and should - always be set to 0 when a file is created and never modified or - looked at after that. See defines that begin with DIR_ATT_. - */ - uint8_t attributes; - /** - Reserved for use by Windows NT. Set value to 0 when a file is - created and never modify or look at it after that. - */ - uint8_t reservedNT; - /** - The granularity of the seconds part of creationTime is 2 seconds - so this field is a count of tenths of a second and its valid - value range is 0-199 inclusive. (WHG note - seems to be hundredths) - */ - uint8_t creationTimeTenths; - /** Time file was created. */ - uint16_t creationTime; - /** Date file was created. */ - uint16_t creationDate; - /** - Last access date. Note that there is no last access time, only - a date. This is the date of last read or write. In the case of - a write, this should be set to the same date as lastWriteDate. - */ - uint16_t lastAccessDate; - /** - High word of this entry's first cluster number (always 0 for a - FAT12 or FAT16 volume). - */ - uint16_t firstClusterHigh; - /** Time of last write. File creation is considered a write. */ - uint16_t lastWriteTime; - /** Date of last write. File creation is considered a write. */ - uint16_t lastWriteDate; - /** Low word of this entry's first cluster number. */ - uint16_t firstClusterLow; - /** 32-bit unsigned holding this file's size in bytes. */ - uint32_t fileSize; -} __attribute__((packed)); -//------------------------------------------------------------------------------ -// Definitions for directory entries -// -/** Type name for directoryEntry */ -typedef struct directoryEntry dir_t; -/** escape for name[0] = 0XE5 */ -uint8_t const DIR_NAME_0XE5 = 0X05; -/** name[0] value for entry that is free after being "deleted" */ -uint8_t const DIR_NAME_DELETED = 0XE5; -/** name[0] value for entry that is free and no allocated entries follow */ -uint8_t const DIR_NAME_FREE = 0X00; -/** file is read-only */ -uint8_t const DIR_ATT_READ_ONLY = 0X01; -/** File should hidden in directory listings */ -uint8_t const DIR_ATT_HIDDEN = 0X02; -/** Entry is for a system file */ -uint8_t const DIR_ATT_SYSTEM = 0X04; -/** Directory entry contains the volume label */ -uint8_t const DIR_ATT_VOLUME_ID = 0X08; -/** Entry is for a directory */ -uint8_t const DIR_ATT_DIRECTORY = 0X10; -/** Old DOS archive bit for backup support */ -uint8_t const DIR_ATT_ARCHIVE = 0X20; -/** Test value for long name entry. Test is - (d->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME. */ -uint8_t const DIR_ATT_LONG_NAME = 0X0F; -/** Test mask for long name entry */ -uint8_t const DIR_ATT_LONG_NAME_MASK = 0X3F; -/** defined attribute bits */ -uint8_t const DIR_ATT_DEFINED_BITS = 0X3F; -/** Directory entry is part of a long name */ -static inline uint8_t DIR_IS_LONG_NAME(const dir_t* dir) { - return (dir->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME; -} -/** Mask for file/subdirectory tests */ -uint8_t const DIR_ATT_FILE_TYPE_MASK = (DIR_ATT_VOLUME_ID | DIR_ATT_DIRECTORY); -/** Directory entry is for a file */ -static inline uint8_t DIR_IS_FILE(const dir_t* dir) { - return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == 0; -} -/** Directory entry is for a subdirectory */ -static inline uint8_t DIR_IS_SUBDIR(const dir_t* dir) { - return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == DIR_ATT_DIRECTORY; -} -/** Directory entry is for a file or subdirectory */ -static inline uint8_t DIR_IS_FILE_OR_SUBDIR(const dir_t* dir) { - return (dir->attributes & DIR_ATT_VOLUME_ID) == 0; -} -#endif // FatStructs_h +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef FatStructs_h +#define FatStructs_h +/** + \file + FAT file structures +*/ +/* + mostly from Microsoft document fatgen103.doc + http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx +*/ +//------------------------------------------------------------------------------ +/** Value for byte 510 of boot block or MBR */ +uint8_t const BOOTSIG0 = 0X55; +/** Value for byte 511 of boot block or MBR */ +uint8_t const BOOTSIG1 = 0XAA; +//------------------------------------------------------------------------------ +/** + \struct partitionTable + \brief MBR partition table entry + + A partition table entry for a MBR formatted storage device. + The MBR partition table has four entries. +*/ +struct partitionTable { + /** + Boot Indicator . Indicates whether the volume is the active + partition. Legal values include: 0X00. Do not use for booting. + 0X80 Active partition. + */ + uint8_t boot; + /** + Head part of Cylinder-head-sector address of the first block in + the partition. Legal values are 0-255. Only used in old PC BIOS. + */ + uint8_t beginHead; + /** + Sector part of Cylinder-head-sector address of the first block in + the partition. Legal values are 1-63. Only used in old PC BIOS. + */ + unsigned beginSector : 6; + /** High bits cylinder for first block in partition. */ + unsigned beginCylinderHigh : 2; + /** + Combine beginCylinderLow with beginCylinderHigh. Legal values + are 0-1023. Only used in old PC BIOS. + */ + uint8_t beginCylinderLow; + /** + Partition type. See defines that begin with PART_TYPE_ for + some Microsoft partition types. + */ + uint8_t type; + /** + head part of cylinder-head-sector address of the last sector in the + partition. Legal values are 0-255. Only used in old PC BIOS. + */ + uint8_t endHead; + /** + Sector part of cylinder-head-sector address of the last sector in + the partition. Legal values are 1-63. Only used in old PC BIOS. + */ + unsigned endSector : 6; + /** High bits of end cylinder */ + unsigned endCylinderHigh : 2; + /** + Combine endCylinderLow with endCylinderHigh. Legal values + are 0-1023. Only used in old PC BIOS. + */ + uint8_t endCylinderLow; + /** Logical block address of the first block in the partition. */ + uint32_t firstSector; + /** Length of the partition, in blocks. */ + uint32_t totalSectors; +} __attribute__((packed)); +/** Type name for partitionTable */ +typedef struct partitionTable part_t; +//------------------------------------------------------------------------------ +/** + \struct masterBootRecord + + \brief Master Boot Record + + The first block of a storage device that is formatted with a MBR. +*/ +struct masterBootRecord { + /** Code Area for master boot program. */ + uint8_t codeArea[440]; + /** Optional WindowsNT disk signature. May contain more boot code. */ + uint32_t diskSignature; + /** Usually zero but may be more boot code. */ + uint16_t usuallyZero; + /** Partition tables. */ + part_t part[4]; + /** First MBR signature byte. Must be 0X55 */ + uint8_t mbrSig0; + /** Second MBR signature byte. Must be 0XAA */ + uint8_t mbrSig1; +} __attribute__((packed)); +/** Type name for masterBootRecord */ +typedef struct masterBootRecord mbr_t; +//------------------------------------------------------------------------------ +/** + \struct biosParmBlock + + \brief BIOS parameter block + + The BIOS parameter block describes the physical layout of a FAT volume. +*/ +struct biosParmBlock { + /** + Count of bytes per sector. This value may take on only the + following values: 512, 1024, 2048 or 4096 + */ + uint16_t bytesPerSector; + /** + Number of sectors per allocation unit. This value must be a + power of 2 that is greater than 0. The legal values are + 1, 2, 4, 8, 16, 32, 64, and 128. + */ + uint8_t sectorsPerCluster; + /** + Number of sectors before the first FAT. + This value must not be zero. + */ + uint16_t reservedSectorCount; + /** The count of FAT data structures on the volume. This field should + always contain the value 2 for any FAT volume of any type. + */ + uint8_t fatCount; + /** + For FAT12 and FAT16 volumes, this field contains the count of + 32-byte directory entries in the root directory. For FAT32 volumes, + this field must be set to 0. For FAT12 and FAT16 volumes, this + value should always specify a count that when multiplied by 32 + results in a multiple of bytesPerSector. FAT16 volumes should + use the value 512. + */ + uint16_t rootDirEntryCount; + /** + This field is the old 16-bit total count of sectors on the volume. + This count includes the count of all sectors in all four regions + of the volume. This field can be 0; if it is 0, then totalSectors32 + must be non-zero. For FAT32 volumes, this field must be 0. For + FAT12 and FAT16 volumes, this field contains the sector count, and + totalSectors32 is 0 if the total sector count fits + (is less than 0x10000). + */ + uint16_t totalSectors16; + /** + This dates back to the old MS-DOS 1.x media determination and is + no longer usually used for anything. 0xF8 is the standard value + for fixed (non-removable) media. For removable media, 0xF0 is + frequently used. Legal values are 0xF0 or 0xF8-0xFF. + */ + uint8_t mediaType; + /** + Count of sectors occupied by one FAT on FAT12/FAT16 volumes. + On FAT32 volumes this field must be 0, and sectorsPerFat32 + contains the FAT size count. + */ + uint16_t sectorsPerFat16; + /** Sectors per track for interrupt 0x13. Not used otherwise. */ + uint16_t sectorsPerTrtack; + /** Number of heads for interrupt 0x13. Not used otherwise. */ + uint16_t headCount; + /** + Count of hidden sectors preceding the partition that contains this + FAT volume. This field is generally only relevant for media + visible on interrupt 0x13. + */ + uint32_t hidddenSectors; + /** + This field is the new 32-bit total count of sectors on the volume. + This count includes the count of all sectors in all four regions + of the volume. This field can be 0; if it is 0, then + totalSectors16 must be non-zero. + */ + uint32_t totalSectors32; + /** + Count of sectors occupied by one FAT on FAT32 volumes. + */ + uint32_t sectorsPerFat32; + /** + This field is only defined for FAT32 media and does not exist on + FAT12 and FAT16 media. + Bits 0-3 -- Zero-based number of active FAT. + Only valid if mirroring is disabled. + Bits 4-6 -- Reserved. + Bit 7 -- 0 means the FAT is mirrored at runtime into all FATs. + -- 1 means only one FAT is active; it is the one referenced in bits 0-3. + Bits 8-15 -- Reserved. + */ + uint16_t fat32Flags; + /** + FAT32 version. High byte is major revision number. + Low byte is minor revision number. Only 0.0 define. + */ + uint16_t fat32Version; + /** + Cluster number of the first cluster of the root directory for FAT32. + This usually 2 but not required to be 2. + */ + uint32_t fat32RootCluster; + /** + Sector number of FSINFO structure in the reserved area of the + FAT32 volume. Usually 1. + */ + uint16_t fat32FSInfo; + /** + If non-zero, indicates the sector number in the reserved area + of the volume of a copy of the boot record. Usually 6. + No value other than 6 is recommended. + */ + uint16_t fat32BackBootBlock; + /** + Reserved for future expansion. Code that formats FAT32 volumes + should always set all of the bytes of this field to 0. + */ + uint8_t fat32Reserved[12]; +} __attribute__((packed)); +/** Type name for biosParmBlock */ +typedef struct biosParmBlock bpb_t; +//------------------------------------------------------------------------------ +/** + \struct fat32BootSector + + \brief Boot sector for a FAT16 or FAT32 volume. + +*/ +struct fat32BootSector { + /** X86 jmp to boot program */ + uint8_t jmpToBootCode[3]; + /** informational only - don't depend on it */ + char oemName[8]; + /** BIOS Parameter Block */ + bpb_t bpb; + /** for int0x13 use value 0X80 for hard drive */ + uint8_t driveNumber; + /** used by Windows NT - should be zero for FAT */ + uint8_t reserved1; + /** 0X29 if next three fields are valid */ + uint8_t bootSignature; + /** usually generated by combining date and time */ + uint32_t volumeSerialNumber; + /** should match volume label in root dir */ + char volumeLabel[11]; + /** informational only - don't depend on it */ + char fileSystemType[8]; + /** X86 boot code */ + uint8_t bootCode[420]; + /** must be 0X55 */ + uint8_t bootSectorSig0; + /** must be 0XAA */ + uint8_t bootSectorSig1; +} __attribute__((packed)); +//------------------------------------------------------------------------------ +// End Of Chain values for FAT entries +/** FAT16 end of chain value used by Microsoft. */ +uint16_t const FAT16EOC = 0XFFFF; +/** Minimum value for FAT16 EOC. Use to test for EOC. */ +uint16_t const FAT16EOC_MIN = 0XFFF8; +/** FAT32 end of chain value used by Microsoft. */ +uint32_t const FAT32EOC = 0X0FFFFFFF; +/** Minimum value for FAT32 EOC. Use to test for EOC. */ +uint32_t const FAT32EOC_MIN = 0X0FFFFFF8; +/** Mask a for FAT32 entry. Entries are 28 bits. */ +uint32_t const FAT32MASK = 0X0FFFFFFF; + +/** Type name for fat32BootSector */ +typedef struct fat32BootSector fbs_t; +//------------------------------------------------------------------------------ +/** + \struct directoryEntry + \brief FAT short directory entry + + Short means short 8.3 name, not the entry size. + + Date Format. A FAT directory entry date stamp is a 16-bit field that is + basically a date relative to the MS-DOS epoch of 01/01/1980. Here is the + format (bit 0 is the LSB of the 16-bit word, bit 15 is the MSB of the + 16-bit word): + + Bits 9-15: Count of years from 1980, valid value range 0-127 + inclusive (1980-2107). + + Bits 5-8: Month of year, 1 = January, valid value range 1-12 inclusive. + + Bits 0-4: Day of month, valid value range 1-31 inclusive. + + Time Format. A FAT directory entry time stamp is a 16-bit field that has + a granularity of 2 seconds. Here is the format (bit 0 is the LSB of the + 16-bit word, bit 15 is the MSB of the 16-bit word). + + Bits 11-15: Hours, valid value range 0-23 inclusive. + + Bits 5-10: Minutes, valid value range 0-59 inclusive. + + Bits 0-4: 2-second count, valid value range 0-29 inclusive (0 - 58 seconds). + + The valid time range is from Midnight 00:00:00 to 23:59:58. +*/ +struct directoryEntry { + /** + Short 8.3 name. + The first eight bytes contain the file name with blank fill. + The last three bytes contain the file extension with blank fill. + */ + uint8_t name[11]; + /** Entry attributes. + + The upper two bits of the attribute byte are reserved and should + always be set to 0 when a file is created and never modified or + looked at after that. See defines that begin with DIR_ATT_. + */ + uint8_t attributes; + /** + Reserved for use by Windows NT. Set value to 0 when a file is + created and never modify or look at it after that. + */ + uint8_t reservedNT; + /** + The granularity of the seconds part of creationTime is 2 seconds + so this field is a count of tenths of a second and its valid + value range is 0-199 inclusive. (WHG note - seems to be hundredths) + */ + uint8_t creationTimeTenths; + /** Time file was created. */ + uint16_t creationTime; + /** Date file was created. */ + uint16_t creationDate; + /** + Last access date. Note that there is no last access time, only + a date. This is the date of last read or write. In the case of + a write, this should be set to the same date as lastWriteDate. + */ + uint16_t lastAccessDate; + /** + High word of this entry's first cluster number (always 0 for a + FAT12 or FAT16 volume). + */ + uint16_t firstClusterHigh; + /** Time of last write. File creation is considered a write. */ + uint16_t lastWriteTime; + /** Date of last write. File creation is considered a write. */ + uint16_t lastWriteDate; + /** Low word of this entry's first cluster number. */ + uint16_t firstClusterLow; + /** 32-bit unsigned holding this file's size in bytes. */ + uint32_t fileSize; +} __attribute__((packed)); +//------------------------------------------------------------------------------ +// Definitions for directory entries +// +/** Type name for directoryEntry */ +typedef struct directoryEntry dir_t; +/** escape for name[0] = 0XE5 */ +uint8_t const DIR_NAME_0XE5 = 0X05; +/** name[0] value for entry that is free after being "deleted" */ +uint8_t const DIR_NAME_DELETED = 0XE5; +/** name[0] value for entry that is free and no allocated entries follow */ +uint8_t const DIR_NAME_FREE = 0X00; +/** file is read-only */ +uint8_t const DIR_ATT_READ_ONLY = 0X01; +/** File should hidden in directory listings */ +uint8_t const DIR_ATT_HIDDEN = 0X02; +/** Entry is for a system file */ +uint8_t const DIR_ATT_SYSTEM = 0X04; +/** Directory entry contains the volume label */ +uint8_t const DIR_ATT_VOLUME_ID = 0X08; +/** Entry is for a directory */ +uint8_t const DIR_ATT_DIRECTORY = 0X10; +/** Old DOS archive bit for backup support */ +uint8_t const DIR_ATT_ARCHIVE = 0X20; +/** Test value for long name entry. Test is + (d->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME. */ +uint8_t const DIR_ATT_LONG_NAME = 0X0F; +/** Test mask for long name entry */ +uint8_t const DIR_ATT_LONG_NAME_MASK = 0X3F; +/** defined attribute bits */ +uint8_t const DIR_ATT_DEFINED_BITS = 0X3F; +/** Directory entry is part of a long name */ +static inline uint8_t DIR_IS_LONG_NAME(const dir_t* dir) { + return (dir->attributes & DIR_ATT_LONG_NAME_MASK) == DIR_ATT_LONG_NAME; +} +/** Mask for file/subdirectory tests */ +uint8_t const DIR_ATT_FILE_TYPE_MASK = (DIR_ATT_VOLUME_ID | DIR_ATT_DIRECTORY); +/** Directory entry is for a file */ +static inline uint8_t DIR_IS_FILE(const dir_t* dir) { + return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == 0; +} +/** Directory entry is for a subdirectory */ +static inline uint8_t DIR_IS_SUBDIR(const dir_t* dir) { + return (dir->attributes & DIR_ATT_FILE_TYPE_MASK) == DIR_ATT_DIRECTORY; +} +/** Directory entry is for a file or subdirectory */ +static inline uint8_t DIR_IS_FILE_OR_SUBDIR(const dir_t* dir) { + return (dir->attributes & DIR_ATT_VOLUME_ID) == 0; +} +#endif // FatStructs_h diff --git a/megaavr/libraries/SD/src/utility/Sd2Card.cpp b/megaavr/libraries/SD/src/utility/Sd2Card.cpp index 7cfbe73..fc3d857 100755 --- a/megaavr/libraries/SD/src/utility/Sd2Card.cpp +++ b/megaavr/libraries/SD/src/utility/Sd2Card.cpp @@ -1,777 +1,777 @@ -/* Arduino Sd2Card Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino Sd2Card Library - - This Library 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 Library 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 the Arduino Sd2Card Library. If not, see - . -*/ -#define USE_SPI_LIB -#include -#include "Sd2Card.h" -//------------------------------------------------------------------------------ -#ifndef SOFTWARE_SPI -#ifdef USE_SPI_LIB - - #ifndef SDCARD_SPI - #define SDCARD_SPI SPI - #endif - - #include - static SPISettings settings; -#endif -// functions for hardware SPI -/** Send a byte to the card */ -static void spiSend(uint8_t b) { - #ifndef USE_SPI_LIB - SPDR = b; - while (!(SPSR & (1 << SPIF))) - ; - #else - SDCARD_SPI.transfer(b); - #endif -} -/** Receive a byte from the card */ -static uint8_t spiRec(void) { - #ifndef USE_SPI_LIB - spiSend(0XFF); - return SPDR; - #else - return SDCARD_SPI.transfer(0xFF); - #endif -} -#else // SOFTWARE_SPI -//------------------------------------------------------------------------------ -/** nop to tune soft SPI timing */ -#define nop asm volatile ("nop\n\t") -//------------------------------------------------------------------------------ -/** Soft SPI receive */ -uint8_t spiRec(void) { - uint8_t data = 0; - // no interrupts during byte receive - about 8 us - cli(); - // output pin high - like sending 0XFF - fastDigitalWrite(SPI_MOSI_PIN, HIGH); - - for (uint8_t i = 0; i < 8; i++) { - fastDigitalWrite(SPI_SCK_PIN, HIGH); - - // adjust so SCK is nice - nop; - nop; - - data <<= 1; - - if (fastDigitalRead(SPI_MISO_PIN)) { - data |= 1; - } - - fastDigitalWrite(SPI_SCK_PIN, LOW); - } - // enable interrupts - sei(); - return data; -} -//------------------------------------------------------------------------------ -/** Soft SPI send */ -void spiSend(uint8_t data) { - // no interrupts during byte send - about 8 us - cli(); - for (uint8_t i = 0; i < 8; i++) { - fastDigitalWrite(SPI_SCK_PIN, LOW); - - fastDigitalWrite(SPI_MOSI_PIN, data & 0X80); - - data <<= 1; - - fastDigitalWrite(SPI_SCK_PIN, HIGH); - } - // hold SCK high for a few ns - nop; - nop; - nop; - nop; - - fastDigitalWrite(SPI_SCK_PIN, LOW); - // enable interrupts - sei(); -} -#endif // SOFTWARE_SPI -//------------------------------------------------------------------------------ -// send command and return error code. Return zero for OK -uint8_t Sd2Card::cardCommand(uint8_t cmd, uint32_t arg) { - // end read if in partialBlockRead mode - readEnd(); - - // select card - chipSelectLow(); - - // wait up to 300 ms if busy - waitNotBusy(300); - - // send command - spiSend(cmd | 0x40); - - // send argument - for (int8_t s = 24; s >= 0; s -= 8) { - spiSend(arg >> s); - } - - // send CRC - uint8_t crc = 0XFF; - if (cmd == CMD0) { - crc = 0X95; // correct crc for CMD0 with arg 0 - } - if (cmd == CMD8) { - crc = 0X87; // correct crc for CMD8 with arg 0X1AA - } - spiSend(crc); - - // wait for response - for (uint8_t i = 0; ((status_ = spiRec()) & 0X80) && i != 0XFF; i++) - ; - return status_; -} -//------------------------------------------------------------------------------ -/** - Determine the size of an SD flash memory card. - - \return The number of 512 byte data blocks in the card - or zero if an error occurs. -*/ -uint32_t Sd2Card::cardSize(void) { - csd_t csd; - if (!readCSD(&csd)) { - return 0; - } - if (csd.v1.csd_ver == 0) { - uint8_t read_bl_len = csd.v1.read_bl_len; - uint16_t c_size = (csd.v1.c_size_high << 10) - | (csd.v1.c_size_mid << 2) | csd.v1.c_size_low; - uint8_t c_size_mult = (csd.v1.c_size_mult_high << 1) - | csd.v1.c_size_mult_low; - return (uint32_t)(c_size + 1) << (c_size_mult + read_bl_len - 7); - } else if (csd.v2.csd_ver == 1) { - uint32_t c_size = ((uint32_t)csd.v2.c_size_high << 16) - | (csd.v2.c_size_mid << 8) | csd.v2.c_size_low; - return (c_size + 1) << 10; - } else { - error(SD_CARD_ERROR_BAD_CSD); - return 0; - } -} -//------------------------------------------------------------------------------ -static uint8_t chip_select_asserted = 0; - -void Sd2Card::chipSelectHigh(void) { - digitalWrite(chipSelectPin_, HIGH); - #ifdef USE_SPI_LIB - if (chip_select_asserted) { - chip_select_asserted = 0; - SDCARD_SPI.endTransaction(); - } - #endif -} -//------------------------------------------------------------------------------ -void Sd2Card::chipSelectLow(void) { - #ifdef USE_SPI_LIB - if (!chip_select_asserted) { - chip_select_asserted = 1; - SDCARD_SPI.beginTransaction(settings); - } - #endif - digitalWrite(chipSelectPin_, LOW); -} -//------------------------------------------------------------------------------ -/** Erase a range of blocks. - - \param[in] firstBlock The address of the first block in the range. - \param[in] lastBlock The address of the last block in the range. - - \note This function requests the SD card to do a flash erase for a - range of blocks. The data on the card after an erase operation is - either 0 or 1, depends on the card vendor. The card must support - single block erase. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::erase(uint32_t firstBlock, uint32_t lastBlock) { - if (!eraseSingleBlockEnable()) { - error(SD_CARD_ERROR_ERASE_SINGLE_BLOCK); - goto fail; - } - if (type_ != SD_CARD_TYPE_SDHC) { - firstBlock <<= 9; - lastBlock <<= 9; - } - if (cardCommand(CMD32, firstBlock) - || cardCommand(CMD33, lastBlock) - || cardCommand(CMD38, 0)) { - error(SD_CARD_ERROR_ERASE); - goto fail; - } - if (!waitNotBusy(SD_ERASE_TIMEOUT)) { - error(SD_CARD_ERROR_ERASE_TIMEOUT); - goto fail; - } - chipSelectHigh(); - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** Determine if card supports single block erase. - - \return The value one, true, is returned if single block erase is supported. - The value zero, false, is returned if single block erase is not supported. -*/ -uint8_t Sd2Card::eraseSingleBlockEnable(void) { - csd_t csd; - return readCSD(&csd) ? csd.v1.erase_blk_en : 0; -} -//------------------------------------------------------------------------------ -/** - Initialize an SD flash memory card. - - \param[in] sckRateID SPI clock rate selector. See setSckRate(). - \param[in] chipSelectPin SD chip select pin number. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. The reason for failure - can be determined by calling errorCode() and errorData(). -*/ -uint8_t Sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin) { - errorCode_ = inBlock_ = partialBlockRead_ = type_ = 0; - chipSelectPin_ = chipSelectPin; - // 16-bit init start time allows over a minute - unsigned int t0 = millis(); - uint32_t arg; - - // set pin modes - pinMode(chipSelectPin_, OUTPUT); - digitalWrite(chipSelectPin_, HIGH); - #ifndef USE_SPI_LIB - pinMode(SPI_MISO_PIN, INPUT); - pinMode(SPI_MOSI_PIN, OUTPUT); - pinMode(SPI_SCK_PIN, OUTPUT); - #endif - - #ifndef SOFTWARE_SPI - #ifndef USE_SPI_LIB - // SS must be in output mode even it is not chip select - pinMode(SS_PIN, OUTPUT); - digitalWrite(SS_PIN, HIGH); // disable any SPI device using hardware SS pin - // Enable SPI, Master, clock rate f_osc/128 - SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR1) | (1 << SPR0); - // clear double speed - SPSR &= ~(1 << SPI2X); - #else // USE_SPI_LIB - SDCARD_SPI.begin(); - settings = SPISettings(250000, MSBFIRST, SPI_MODE0); - #endif // USE_SPI_LIB - #endif // SOFTWARE_SPI - - // must supply min of 74 clock cycles with CS high. - #ifdef USE_SPI_LIB - SDCARD_SPI.beginTransaction(settings); - #endif - for (uint8_t i = 0; i < 10; i++) { - spiSend(0XFF); - } - #ifdef USE_SPI_LIB - SDCARD_SPI.endTransaction(); - #endif - - chipSelectLow(); - - // command to go idle in SPI mode - while ((status_ = cardCommand(CMD0, 0)) != R1_IDLE_STATE) { - unsigned int d = millis() - t0; - if (d > SD_INIT_TIMEOUT) { - error(SD_CARD_ERROR_CMD0); - goto fail; - } - } - // check SD version - if ((cardCommand(CMD8, 0x1AA) & R1_ILLEGAL_COMMAND)) { - type(SD_CARD_TYPE_SD1); - } else { - // only need last byte of r7 response - for (uint8_t i = 0; i < 4; i++) { - status_ = spiRec(); - } - if (status_ != 0XAA) { - error(SD_CARD_ERROR_CMD8); - goto fail; - } - type(SD_CARD_TYPE_SD2); - } - // initialize card and send host supports SDHC if SD2 - arg = type() == SD_CARD_TYPE_SD2 ? 0X40000000 : 0; - - while ((status_ = cardAcmd(ACMD41, arg)) != R1_READY_STATE) { - // check for timeout - unsigned int d = millis() - t0; - if (d > SD_INIT_TIMEOUT) { - error(SD_CARD_ERROR_ACMD41); - goto fail; - } - } - // if SD2 read OCR register to check for SDHC card - if (type() == SD_CARD_TYPE_SD2) { - if (cardCommand(CMD58, 0)) { - error(SD_CARD_ERROR_CMD58); - goto fail; - } - if ((spiRec() & 0XC0) == 0XC0) { - type(SD_CARD_TYPE_SDHC); - } - // discard rest of ocr - contains allowed voltage range - for (uint8_t i = 0; i < 3; i++) { - spiRec(); - } - } - chipSelectHigh(); - - #ifndef SOFTWARE_SPI - return setSckRate(sckRateID); - #else // SOFTWARE_SPI - return true; - #endif // SOFTWARE_SPI - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** - Enable or disable partial block reads. - - Enabling partial block reads improves performance by allowing a block - to be read over the SPI bus as several sub-blocks. Errors may occur - if the time between reads is too long since the SD card may timeout. - The SPI SS line will be held low until the entire block is read or - readEnd() is called. - - Use this for applications like the Adafruit Wave Shield. - - \param[in] value The value TRUE (non-zero) or FALSE (zero).) -*/ -void Sd2Card::partialBlockRead(uint8_t value) { - readEnd(); - partialBlockRead_ = value; -} -//------------------------------------------------------------------------------ -/** - Read a 512 byte block from an SD card device. - - \param[in] block Logical block to be read. - \param[out] dst Pointer to the location that will receive the data. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::readBlock(uint32_t block, uint8_t* dst) { - return readData(block, 0, 512, dst); -} -//------------------------------------------------------------------------------ -/** - Read part of a 512 byte block from an SD card. - - \param[in] block Logical block to be read. - \param[in] offset Number of bytes to skip at start of block - \param[out] dst Pointer to the location that will receive the data. - \param[in] count Number of bytes to read - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::readData(uint32_t block, - uint16_t offset, uint16_t count, uint8_t* dst) { - if (count == 0) { - return true; - } - if ((count + offset) > 512) { - goto fail; - } - if (!inBlock_ || block != block_ || offset < offset_) { - block_ = block; - // use address if not SDHC card - if (type() != SD_CARD_TYPE_SDHC) { - block <<= 9; - } - if (cardCommand(CMD17, block)) { - error(SD_CARD_ERROR_CMD17); - goto fail; - } - if (!waitStartBlock()) { - goto fail; - } - offset_ = 0; - inBlock_ = 1; - } - - #ifdef OPTIMIZE_HARDWARE_SPI - // start first spi transfer - SPDR = 0XFF; - - // skip data before offset - for (; offset_ < offset; offset_++) { - while (!(SPSR & (1 << SPIF))) - ; - SPDR = 0XFF; - } - // transfer data - n = count - 1; - for (uint16_t i = 0; i < n; i++) { - while (!(SPSR & (1 << SPIF))) - ; - dst[i] = SPDR; - SPDR = 0XFF; - } - // wait for last byte - while (!(SPSR & (1 << SPIF))) - ; - dst[n] = SPDR; - - #else // OPTIMIZE_HARDWARE_SPI - - // skip data before offset - for (; offset_ < offset; offset_++) { - spiRec(); - } - // transfer data - for (uint16_t i = 0; i < count; i++) { - dst[i] = spiRec(); - } - #endif // OPTIMIZE_HARDWARE_SPI - - offset_ += count; - if (!partialBlockRead_ || offset_ >= 512) { - // read rest of data, checksum and set chip select high - readEnd(); - } - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** Skip remaining data in a block when in partial block read mode. */ -void Sd2Card::readEnd(void) { - if (inBlock_) { - // skip data and crc - #ifdef OPTIMIZE_HARDWARE_SPI - // optimize skip for hardware - SPDR = 0XFF; - while (offset_++ < 513) { - while (!(SPSR & (1 << SPIF))) - ; - SPDR = 0XFF; - } - // wait for last crc byte - while (!(SPSR & (1 << SPIF))) - ; - #else // OPTIMIZE_HARDWARE_SPI - while (offset_++ < 514) { - spiRec(); - } - #endif // OPTIMIZE_HARDWARE_SPI - chipSelectHigh(); - inBlock_ = 0; - } -} -//------------------------------------------------------------------------------ -/** read CID or CSR register */ -uint8_t Sd2Card::readRegister(uint8_t cmd, void* buf) { - uint8_t* dst = reinterpret_cast(buf); - if (cardCommand(cmd, 0)) { - error(SD_CARD_ERROR_READ_REG); - goto fail; - } - if (!waitStartBlock()) { - goto fail; - } - // transfer data - for (uint16_t i = 0; i < 16; i++) { - dst[i] = spiRec(); - } - spiRec(); // get first crc byte - spiRec(); // get second crc byte - chipSelectHigh(); - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** - Set the SPI clock rate. - - \param[in] sckRateID A value in the range [0, 6]. - - The SPI clock will be set to F_CPU/pow(2, 1 + sckRateID). The maximum - SPI rate is F_CPU/2 for \a sckRateID = 0 and the minimum rate is F_CPU/128 - for \a scsRateID = 6. - - \return The value one, true, is returned for success and the value zero, - false, is returned for an invalid value of \a sckRateID. -*/ -uint8_t Sd2Card::setSckRate(uint8_t sckRateID) { - if (sckRateID > 6) { - error(SD_CARD_ERROR_SCK_RATE); - return false; - } - #ifndef USE_SPI_LIB - // see avr processor datasheet for SPI register bit definitions - if ((sckRateID & 1) || sckRateID == 6) { - SPSR &= ~(1 << SPI2X); - } else { - SPSR |= (1 << SPI2X); - } - SPCR &= ~((1 << SPR1) | (1 << SPR0)); - SPCR |= (sckRateID & 4 ? (1 << SPR1) : 0) - | (sckRateID & 2 ? (1 << SPR0) : 0); - #else // USE_SPI_LIB - switch (sckRateID) { - case 0: settings = SPISettings(25000000, MSBFIRST, SPI_MODE0); break; - case 1: settings = SPISettings(4000000, MSBFIRST, SPI_MODE0); break; - case 2: settings = SPISettings(2000000, MSBFIRST, SPI_MODE0); break; - case 3: settings = SPISettings(1000000, MSBFIRST, SPI_MODE0); break; - case 4: settings = SPISettings(500000, MSBFIRST, SPI_MODE0); break; - case 5: settings = SPISettings(250000, MSBFIRST, SPI_MODE0); break; - default: settings = SPISettings(125000, MSBFIRST, SPI_MODE0); - } - #endif // USE_SPI_LIB - return true; -} -#ifdef USE_SPI_LIB -//------------------------------------------------------------------------------ -// set the SPI clock frequency -uint8_t Sd2Card::setSpiClock(uint32_t clock) { - settings = SPISettings(clock, MSBFIRST, SPI_MODE0); - return true; -} -#endif -//------------------------------------------------------------------------------ -// wait for card to go not busy -uint8_t Sd2Card::waitNotBusy(unsigned int timeoutMillis) { - unsigned int t0 = millis(); - unsigned int d; - do { - if (spiRec() == 0XFF) { - return true; - } - d = millis() - t0; - } while (d < timeoutMillis); - return false; -} -//------------------------------------------------------------------------------ -/** Wait for start block token */ -uint8_t Sd2Card::waitStartBlock(void) { - unsigned int t0 = millis(); - while ((status_ = spiRec()) == 0XFF) { - unsigned int d = millis() - t0; - if (d > SD_READ_TIMEOUT) { - error(SD_CARD_ERROR_READ_TIMEOUT); - goto fail; - } - } - if (status_ != DATA_START_BLOCK) { - error(SD_CARD_ERROR_READ); - goto fail; - } - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** - Writes a 512 byte block to an SD card. - - \param[in] blockNumber Logical block to be written. - \param[in] src Pointer to the location of the data to be written. - \param[in] blocking If the write should be blocking. - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking) { - #if SD_PROTECT_BLOCK_ZERO - // don't allow write to first block - if (blockNumber == 0) { - error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); - goto fail; - } - #endif // SD_PROTECT_BLOCK_ZERO - - // use address if not SDHC card - if (type() != SD_CARD_TYPE_SDHC) { - blockNumber <<= 9; - } - if (cardCommand(CMD24, blockNumber)) { - error(SD_CARD_ERROR_CMD24); - goto fail; - } - if (!writeData(DATA_START_BLOCK, src)) { - goto fail; - } - if (blocking) { - // wait for flash programming to complete - if (!waitNotBusy(SD_WRITE_TIMEOUT)) { - error(SD_CARD_ERROR_WRITE_TIMEOUT); - goto fail; - } - // response is r2 so get and check two bytes for nonzero - if (cardCommand(CMD13, 0) || spiRec()) { - error(SD_CARD_ERROR_WRITE_PROGRAMMING); - goto fail; - } - } - chipSelectHigh(); - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** Write one data block in a multiple block write sequence */ -uint8_t Sd2Card::writeData(const uint8_t* src) { - // wait for previous write to finish - if (!waitNotBusy(SD_WRITE_TIMEOUT)) { - error(SD_CARD_ERROR_WRITE_MULTIPLE); - chipSelectHigh(); - return false; - } - return writeData(WRITE_MULTIPLE_TOKEN, src); -} -//------------------------------------------------------------------------------ -// send one block of data for write block or write multiple blocks -uint8_t Sd2Card::writeData(uint8_t token, const uint8_t* src) { - #ifdef OPTIMIZE_HARDWARE_SPI - - // send data - optimized loop - SPDR = token; - - // send two byte per iteration - for (uint16_t i = 0; i < 512; i += 2) { - while (!(SPSR & (1 << SPIF))) - ; - SPDR = src[i]; - while (!(SPSR & (1 << SPIF))) - ; - SPDR = src[i + 1]; - } - - // wait for last data byte - while (!(SPSR & (1 << SPIF))) - ; - - #else // OPTIMIZE_HARDWARE_SPI - spiSend(token); - for (uint16_t i = 0; i < 512; i++) { - spiSend(src[i]); - } - #endif // OPTIMIZE_HARDWARE_SPI - spiSend(0xff); // dummy crc - spiSend(0xff); // dummy crc - - status_ = spiRec(); - if ((status_ & DATA_RES_MASK) != DATA_RES_ACCEPTED) { - error(SD_CARD_ERROR_WRITE); - chipSelectHigh(); - return false; - } - return true; -} -//------------------------------------------------------------------------------ -/** Start a write multiple blocks sequence. - - \param[in] blockNumber Address of first block in sequence. - \param[in] eraseCount The number of blocks to be pre-erased. - - \note This function is used with writeData() and writeStop() - for optimized multiple block writes. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::writeStart(uint32_t blockNumber, uint32_t eraseCount) { - #if SD_PROTECT_BLOCK_ZERO - // don't allow write to first block - if (blockNumber == 0) { - error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); - goto fail; - } - #endif // SD_PROTECT_BLOCK_ZERO - // send pre-erase count - if (cardAcmd(ACMD23, eraseCount)) { - error(SD_CARD_ERROR_ACMD23); - goto fail; - } - // use address if not SDHC card - if (type() != SD_CARD_TYPE_SDHC) { - blockNumber <<= 9; - } - if (cardCommand(CMD25, blockNumber)) { - error(SD_CARD_ERROR_CMD25); - goto fail; - } - return true; - -fail: - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** End a write multiple blocks sequence. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t Sd2Card::writeStop(void) { - if (!waitNotBusy(SD_WRITE_TIMEOUT)) { - goto fail; - } - spiSend(STOP_TRAN_TOKEN); - if (!waitNotBusy(SD_WRITE_TIMEOUT)) { - goto fail; - } - chipSelectHigh(); - return true; - -fail: - error(SD_CARD_ERROR_STOP_TRAN); - chipSelectHigh(); - return false; -} -//------------------------------------------------------------------------------ -/** Check if the SD card is busy - - \return The value one, true, is returned when is busy and - the value zero, false, is returned for when is NOT busy. -*/ -uint8_t Sd2Card::isBusy(void) { - chipSelectLow(); - byte b = spiRec(); - chipSelectHigh(); - - return (b != 0XFF); -} +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#define USE_SPI_LIB +#include +#include "Sd2Card.h" +//------------------------------------------------------------------------------ +#ifndef SOFTWARE_SPI +#ifdef USE_SPI_LIB + + #ifndef SDCARD_SPI + #define SDCARD_SPI SPI + #endif + + #include + static SPISettings settings; +#endif +// functions for hardware SPI +/** Send a byte to the card */ +static void spiSend(uint8_t b) { + #ifndef USE_SPI_LIB + SPDR = b; + while (!(SPSR & (1 << SPIF))) + ; + #else + SDCARD_SPI.transfer(b); + #endif +} +/** Receive a byte from the card */ +static uint8_t spiRec(void) { + #ifndef USE_SPI_LIB + spiSend(0XFF); + return SPDR; + #else + return SDCARD_SPI.transfer(0xFF); + #endif +} +#else // SOFTWARE_SPI +//------------------------------------------------------------------------------ +/** nop to tune soft SPI timing */ +#define nop asm volatile ("nop\n\t") +//------------------------------------------------------------------------------ +/** Soft SPI receive */ +uint8_t spiRec(void) { + uint8_t data = 0; + // no interrupts during byte receive - about 8 us + cli(); + // output pin high - like sending 0XFF + fastDigitalWrite(SPI_MOSI_PIN, HIGH); + + for (uint8_t i = 0; i < 8; i++) { + fastDigitalWrite(SPI_SCK_PIN, HIGH); + + // adjust so SCK is nice + nop; + nop; + + data <<= 1; + + if (fastDigitalRead(SPI_MISO_PIN)) { + data |= 1; + } + + fastDigitalWrite(SPI_SCK_PIN, LOW); + } + // enable interrupts + sei(); + return data; +} +//------------------------------------------------------------------------------ +/** Soft SPI send */ +void spiSend(uint8_t data) { + // no interrupts during byte send - about 8 us + cli(); + for (uint8_t i = 0; i < 8; i++) { + fastDigitalWrite(SPI_SCK_PIN, LOW); + + fastDigitalWrite(SPI_MOSI_PIN, data & 0X80); + + data <<= 1; + + fastDigitalWrite(SPI_SCK_PIN, HIGH); + } + // hold SCK high for a few ns + nop; + nop; + nop; + nop; + + fastDigitalWrite(SPI_SCK_PIN, LOW); + // enable interrupts + sei(); +} +#endif // SOFTWARE_SPI +//------------------------------------------------------------------------------ +// send command and return error code. Return zero for OK +uint8_t Sd2Card::cardCommand(uint8_t cmd, uint32_t arg) { + // end read if in partialBlockRead mode + readEnd(); + + // select card + chipSelectLow(); + + // wait up to 300 ms if busy + waitNotBusy(300); + + // send command + spiSend(cmd | 0x40); + + // send argument + for (int8_t s = 24; s >= 0; s -= 8) { + spiSend(arg >> s); + } + + // send CRC + uint8_t crc = 0XFF; + if (cmd == CMD0) { + crc = 0X95; // correct crc for CMD0 with arg 0 + } + if (cmd == CMD8) { + crc = 0X87; // correct crc for CMD8 with arg 0X1AA + } + spiSend(crc); + + // wait for response + for (uint8_t i = 0; ((status_ = spiRec()) & 0X80) && i != 0XFF; i++) + ; + return status_; +} +//------------------------------------------------------------------------------ +/** + Determine the size of an SD flash memory card. + + \return The number of 512 byte data blocks in the card + or zero if an error occurs. +*/ +uint32_t Sd2Card::cardSize(void) { + csd_t csd; + if (!readCSD(&csd)) { + return 0; + } + if (csd.v1.csd_ver == 0) { + uint8_t read_bl_len = csd.v1.read_bl_len; + uint16_t c_size = (csd.v1.c_size_high << 10) + | (csd.v1.c_size_mid << 2) | csd.v1.c_size_low; + uint8_t c_size_mult = (csd.v1.c_size_mult_high << 1) + | csd.v1.c_size_mult_low; + return (uint32_t)(c_size + 1) << (c_size_mult + read_bl_len - 7); + } else if (csd.v2.csd_ver == 1) { + uint32_t c_size = ((uint32_t)csd.v2.c_size_high << 16) + | (csd.v2.c_size_mid << 8) | csd.v2.c_size_low; + return (c_size + 1) << 10; + } else { + error(SD_CARD_ERROR_BAD_CSD); + return 0; + } +} +//------------------------------------------------------------------------------ +static uint8_t chip_select_asserted = 0; + +void Sd2Card::chipSelectHigh(void) { + digitalWrite(chipSelectPin_, HIGH); + #ifdef USE_SPI_LIB + if (chip_select_asserted) { + chip_select_asserted = 0; + SDCARD_SPI.endTransaction(); + } + #endif +} +//------------------------------------------------------------------------------ +void Sd2Card::chipSelectLow(void) { + #ifdef USE_SPI_LIB + if (!chip_select_asserted) { + chip_select_asserted = 1; + SDCARD_SPI.beginTransaction(settings); + } + #endif + digitalWrite(chipSelectPin_, LOW); +} +//------------------------------------------------------------------------------ +/** Erase a range of blocks. + + \param[in] firstBlock The address of the first block in the range. + \param[in] lastBlock The address of the last block in the range. + + \note This function requests the SD card to do a flash erase for a + range of blocks. The data on the card after an erase operation is + either 0 or 1, depends on the card vendor. The card must support + single block erase. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::erase(uint32_t firstBlock, uint32_t lastBlock) { + if (!eraseSingleBlockEnable()) { + error(SD_CARD_ERROR_ERASE_SINGLE_BLOCK); + goto fail; + } + if (type_ != SD_CARD_TYPE_SDHC) { + firstBlock <<= 9; + lastBlock <<= 9; + } + if (cardCommand(CMD32, firstBlock) + || cardCommand(CMD33, lastBlock) + || cardCommand(CMD38, 0)) { + error(SD_CARD_ERROR_ERASE); + goto fail; + } + if (!waitNotBusy(SD_ERASE_TIMEOUT)) { + error(SD_CARD_ERROR_ERASE_TIMEOUT); + goto fail; + } + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Determine if card supports single block erase. + + \return The value one, true, is returned if single block erase is supported. + The value zero, false, is returned if single block erase is not supported. +*/ +uint8_t Sd2Card::eraseSingleBlockEnable(void) { + csd_t csd; + return readCSD(&csd) ? csd.v1.erase_blk_en : 0; +} +//------------------------------------------------------------------------------ +/** + Initialize an SD flash memory card. + + \param[in] sckRateID SPI clock rate selector. See setSckRate(). + \param[in] chipSelectPin SD chip select pin number. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. The reason for failure + can be determined by calling errorCode() and errorData(). +*/ +uint8_t Sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin) { + errorCode_ = inBlock_ = partialBlockRead_ = type_ = 0; + chipSelectPin_ = chipSelectPin; + // 16-bit init start time allows over a minute + unsigned int t0 = millis(); + uint32_t arg; + + // set pin modes + pinMode(chipSelectPin_, OUTPUT); + digitalWrite(chipSelectPin_, HIGH); + #ifndef USE_SPI_LIB + pinMode(SPI_MISO_PIN, INPUT); + pinMode(SPI_MOSI_PIN, OUTPUT); + pinMode(SPI_SCK_PIN, OUTPUT); + #endif + + #ifndef SOFTWARE_SPI + #ifndef USE_SPI_LIB + // SS must be in output mode even it is not chip select + pinMode(SS_PIN, OUTPUT); + digitalWrite(SS_PIN, HIGH); // disable any SPI device using hardware SS pin + // Enable SPI, Master, clock rate f_osc/128 + SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR1) | (1 << SPR0); + // clear double speed + SPSR &= ~(1 << SPI2X); + #else // USE_SPI_LIB + SDCARD_SPI.begin(); + settings = SPISettings(250000, MSBFIRST, SPI_MODE0); + #endif // USE_SPI_LIB + #endif // SOFTWARE_SPI + + // must supply min of 74 clock cycles with CS high. + #ifdef USE_SPI_LIB + SDCARD_SPI.beginTransaction(settings); + #endif + for (uint8_t i = 0; i < 10; i++) { + spiSend(0XFF); + } + #ifdef USE_SPI_LIB + SDCARD_SPI.endTransaction(); + #endif + + chipSelectLow(); + + // command to go idle in SPI mode + while ((status_ = cardCommand(CMD0, 0)) != R1_IDLE_STATE) { + unsigned int d = millis() - t0; + if (d > SD_INIT_TIMEOUT) { + error(SD_CARD_ERROR_CMD0); + goto fail; + } + } + // check SD version + if ((cardCommand(CMD8, 0x1AA) & R1_ILLEGAL_COMMAND)) { + type(SD_CARD_TYPE_SD1); + } else { + // only need last byte of r7 response + for (uint8_t i = 0; i < 4; i++) { + status_ = spiRec(); + } + if (status_ != 0XAA) { + error(SD_CARD_ERROR_CMD8); + goto fail; + } + type(SD_CARD_TYPE_SD2); + } + // initialize card and send host supports SDHC if SD2 + arg = type() == SD_CARD_TYPE_SD2 ? 0X40000000 : 0; + + while ((status_ = cardAcmd(ACMD41, arg)) != R1_READY_STATE) { + // check for timeout + unsigned int d = millis() - t0; + if (d > SD_INIT_TIMEOUT) { + error(SD_CARD_ERROR_ACMD41); + goto fail; + } + } + // if SD2 read OCR register to check for SDHC card + if (type() == SD_CARD_TYPE_SD2) { + if (cardCommand(CMD58, 0)) { + error(SD_CARD_ERROR_CMD58); + goto fail; + } + if ((spiRec() & 0XC0) == 0XC0) { + type(SD_CARD_TYPE_SDHC); + } + // discard rest of ocr - contains allowed voltage range + for (uint8_t i = 0; i < 3; i++) { + spiRec(); + } + } + chipSelectHigh(); + + #ifndef SOFTWARE_SPI + return setSckRate(sckRateID); + #else // SOFTWARE_SPI + return true; + #endif // SOFTWARE_SPI + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Enable or disable partial block reads. + + Enabling partial block reads improves performance by allowing a block + to be read over the SPI bus as several sub-blocks. Errors may occur + if the time between reads is too long since the SD card may timeout. + The SPI SS line will be held low until the entire block is read or + readEnd() is called. + + Use this for applications like the Adafruit Wave Shield. + + \param[in] value The value TRUE (non-zero) or FALSE (zero).) +*/ +void Sd2Card::partialBlockRead(uint8_t value) { + readEnd(); + partialBlockRead_ = value; +} +//------------------------------------------------------------------------------ +/** + Read a 512 byte block from an SD card device. + + \param[in] block Logical block to be read. + \param[out] dst Pointer to the location that will receive the data. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::readBlock(uint32_t block, uint8_t* dst) { + return readData(block, 0, 512, dst); +} +//------------------------------------------------------------------------------ +/** + Read part of a 512 byte block from an SD card. + + \param[in] block Logical block to be read. + \param[in] offset Number of bytes to skip at start of block + \param[out] dst Pointer to the location that will receive the data. + \param[in] count Number of bytes to read + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::readData(uint32_t block, + uint16_t offset, uint16_t count, uint8_t* dst) { + if (count == 0) { + return true; + } + if ((count + offset) > 512) { + goto fail; + } + if (!inBlock_ || block != block_ || offset < offset_) { + block_ = block; + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + block <<= 9; + } + if (cardCommand(CMD17, block)) { + error(SD_CARD_ERROR_CMD17); + goto fail; + } + if (!waitStartBlock()) { + goto fail; + } + offset_ = 0; + inBlock_ = 1; + } + + #ifdef OPTIMIZE_HARDWARE_SPI + // start first spi transfer + SPDR = 0XFF; + + // skip data before offset + for (; offset_ < offset; offset_++) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = 0XFF; + } + // transfer data + n = count - 1; + for (uint16_t i = 0; i < n; i++) { + while (!(SPSR & (1 << SPIF))) + ; + dst[i] = SPDR; + SPDR = 0XFF; + } + // wait for last byte + while (!(SPSR & (1 << SPIF))) + ; + dst[n] = SPDR; + + #else // OPTIMIZE_HARDWARE_SPI + + // skip data before offset + for (; offset_ < offset; offset_++) { + spiRec(); + } + // transfer data + for (uint16_t i = 0; i < count; i++) { + dst[i] = spiRec(); + } + #endif // OPTIMIZE_HARDWARE_SPI + + offset_ += count; + if (!partialBlockRead_ || offset_ >= 512) { + // read rest of data, checksum and set chip select high + readEnd(); + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Skip remaining data in a block when in partial block read mode. */ +void Sd2Card::readEnd(void) { + if (inBlock_) { + // skip data and crc + #ifdef OPTIMIZE_HARDWARE_SPI + // optimize skip for hardware + SPDR = 0XFF; + while (offset_++ < 513) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = 0XFF; + } + // wait for last crc byte + while (!(SPSR & (1 << SPIF))) + ; + #else // OPTIMIZE_HARDWARE_SPI + while (offset_++ < 514) { + spiRec(); + } + #endif // OPTIMIZE_HARDWARE_SPI + chipSelectHigh(); + inBlock_ = 0; + } +} +//------------------------------------------------------------------------------ +/** read CID or CSR register */ +uint8_t Sd2Card::readRegister(uint8_t cmd, void* buf) { + uint8_t* dst = reinterpret_cast(buf); + if (cardCommand(cmd, 0)) { + error(SD_CARD_ERROR_READ_REG); + goto fail; + } + if (!waitStartBlock()) { + goto fail; + } + // transfer data + for (uint16_t i = 0; i < 16; i++) { + dst[i] = spiRec(); + } + spiRec(); // get first crc byte + spiRec(); // get second crc byte + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Set the SPI clock rate. + + \param[in] sckRateID A value in the range [0, 6]. + + The SPI clock will be set to F_CPU/pow(2, 1 + sckRateID). The maximum + SPI rate is F_CPU/2 for \a sckRateID = 0 and the minimum rate is F_CPU/128 + for \a scsRateID = 6. + + \return The value one, true, is returned for success and the value zero, + false, is returned for an invalid value of \a sckRateID. +*/ +uint8_t Sd2Card::setSckRate(uint8_t sckRateID) { + if (sckRateID > 6) { + error(SD_CARD_ERROR_SCK_RATE); + return false; + } + #ifndef USE_SPI_LIB + // see avr processor datasheet for SPI register bit definitions + if ((sckRateID & 1) || sckRateID == 6) { + SPSR &= ~(1 << SPI2X); + } else { + SPSR |= (1 << SPI2X); + } + SPCR &= ~((1 << SPR1) | (1 << SPR0)); + SPCR |= (sckRateID & 4 ? (1 << SPR1) : 0) + | (sckRateID & 2 ? (1 << SPR0) : 0); + #else // USE_SPI_LIB + switch (sckRateID) { + case 0: settings = SPISettings(25000000, MSBFIRST, SPI_MODE0); break; + case 1: settings = SPISettings(4000000, MSBFIRST, SPI_MODE0); break; + case 2: settings = SPISettings(2000000, MSBFIRST, SPI_MODE0); break; + case 3: settings = SPISettings(1000000, MSBFIRST, SPI_MODE0); break; + case 4: settings = SPISettings(500000, MSBFIRST, SPI_MODE0); break; + case 5: settings = SPISettings(250000, MSBFIRST, SPI_MODE0); break; + default: settings = SPISettings(125000, MSBFIRST, SPI_MODE0); + } + #endif // USE_SPI_LIB + return true; +} +#ifdef USE_SPI_LIB +//------------------------------------------------------------------------------ +// set the SPI clock frequency +uint8_t Sd2Card::setSpiClock(uint32_t clock) { + settings = SPISettings(clock, MSBFIRST, SPI_MODE0); + return true; +} +#endif +//------------------------------------------------------------------------------ +// wait for card to go not busy +uint8_t Sd2Card::waitNotBusy(unsigned int timeoutMillis) { + unsigned int t0 = millis(); + unsigned int d; + do { + if (spiRec() == 0XFF) { + return true; + } + d = millis() - t0; + } while (d < timeoutMillis); + return false; +} +//------------------------------------------------------------------------------ +/** Wait for start block token */ +uint8_t Sd2Card::waitStartBlock(void) { + unsigned int t0 = millis(); + while ((status_ = spiRec()) == 0XFF) { + unsigned int d = millis() - t0; + if (d > SD_READ_TIMEOUT) { + error(SD_CARD_ERROR_READ_TIMEOUT); + goto fail; + } + } + if (status_ != DATA_START_BLOCK) { + error(SD_CARD_ERROR_READ); + goto fail; + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** + Writes a 512 byte block to an SD card. + + \param[in] blockNumber Logical block to be written. + \param[in] src Pointer to the location of the data to be written. + \param[in] blocking If the write should be blocking. + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking) { + #if SD_PROTECT_BLOCK_ZERO + // don't allow write to first block + if (blockNumber == 0) { + error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); + goto fail; + } + #endif // SD_PROTECT_BLOCK_ZERO + + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + blockNumber <<= 9; + } + if (cardCommand(CMD24, blockNumber)) { + error(SD_CARD_ERROR_CMD24); + goto fail; + } + if (!writeData(DATA_START_BLOCK, src)) { + goto fail; + } + if (blocking) { + // wait for flash programming to complete + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + error(SD_CARD_ERROR_WRITE_TIMEOUT); + goto fail; + } + // response is r2 so get and check two bytes for nonzero + if (cardCommand(CMD13, 0) || spiRec()) { + error(SD_CARD_ERROR_WRITE_PROGRAMMING); + goto fail; + } + } + chipSelectHigh(); + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Write one data block in a multiple block write sequence */ +uint8_t Sd2Card::writeData(const uint8_t* src) { + // wait for previous write to finish + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + error(SD_CARD_ERROR_WRITE_MULTIPLE); + chipSelectHigh(); + return false; + } + return writeData(WRITE_MULTIPLE_TOKEN, src); +} +//------------------------------------------------------------------------------ +// send one block of data for write block or write multiple blocks +uint8_t Sd2Card::writeData(uint8_t token, const uint8_t* src) { + #ifdef OPTIMIZE_HARDWARE_SPI + + // send data - optimized loop + SPDR = token; + + // send two byte per iteration + for (uint16_t i = 0; i < 512; i += 2) { + while (!(SPSR & (1 << SPIF))) + ; + SPDR = src[i]; + while (!(SPSR & (1 << SPIF))) + ; + SPDR = src[i + 1]; + } + + // wait for last data byte + while (!(SPSR & (1 << SPIF))) + ; + + #else // OPTIMIZE_HARDWARE_SPI + spiSend(token); + for (uint16_t i = 0; i < 512; i++) { + spiSend(src[i]); + } + #endif // OPTIMIZE_HARDWARE_SPI + spiSend(0xff); // dummy crc + spiSend(0xff); // dummy crc + + status_ = spiRec(); + if ((status_ & DATA_RES_MASK) != DATA_RES_ACCEPTED) { + error(SD_CARD_ERROR_WRITE); + chipSelectHigh(); + return false; + } + return true; +} +//------------------------------------------------------------------------------ +/** Start a write multiple blocks sequence. + + \param[in] blockNumber Address of first block in sequence. + \param[in] eraseCount The number of blocks to be pre-erased. + + \note This function is used with writeData() and writeStop() + for optimized multiple block writes. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeStart(uint32_t blockNumber, uint32_t eraseCount) { + #if SD_PROTECT_BLOCK_ZERO + // don't allow write to first block + if (blockNumber == 0) { + error(SD_CARD_ERROR_WRITE_BLOCK_ZERO); + goto fail; + } + #endif // SD_PROTECT_BLOCK_ZERO + // send pre-erase count + if (cardAcmd(ACMD23, eraseCount)) { + error(SD_CARD_ERROR_ACMD23); + goto fail; + } + // use address if not SDHC card + if (type() != SD_CARD_TYPE_SDHC) { + blockNumber <<= 9; + } + if (cardCommand(CMD25, blockNumber)) { + error(SD_CARD_ERROR_CMD25); + goto fail; + } + return true; + +fail: + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** End a write multiple blocks sequence. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t Sd2Card::writeStop(void) { + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + goto fail; + } + spiSend(STOP_TRAN_TOKEN); + if (!waitNotBusy(SD_WRITE_TIMEOUT)) { + goto fail; + } + chipSelectHigh(); + return true; + +fail: + error(SD_CARD_ERROR_STOP_TRAN); + chipSelectHigh(); + return false; +} +//------------------------------------------------------------------------------ +/** Check if the SD card is busy + + \return The value one, true, is returned when is busy and + the value zero, false, is returned for when is NOT busy. +*/ +uint8_t Sd2Card::isBusy(void) { + chipSelectLow(); + byte b = spiRec(); + chipSelectHigh(); + + return (b != 0XFF); +} diff --git a/megaavr/libraries/SD/src/utility/Sd2Card.h b/megaavr/libraries/SD/src/utility/Sd2Card.h index 5d91ebf..59ec95b 100755 --- a/megaavr/libraries/SD/src/utility/Sd2Card.h +++ b/megaavr/libraries/SD/src/utility/Sd2Card.h @@ -1,273 +1,273 @@ -/* Arduino Sd2Card Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino Sd2Card Library - - This Library 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 Library 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 the Arduino Sd2Card Library. If not, see - . -*/ -#ifndef Sd2Card_h -#define Sd2Card_h -/** - \file - Sd2Card class -*/ -#include "Sd2PinMap.h" -#include "SdInfo.h" -/** Set SCK to max rate of F_CPU/2. See Sd2Card::setSckRate(). */ -uint8_t const SPI_FULL_SPEED = 0; -/** Set SCK rate to F_CPU/4. See Sd2Card::setSckRate(). */ -uint8_t const SPI_HALF_SPEED = 1; -/** Set SCK rate to F_CPU/8. Sd2Card::setSckRate(). */ -uint8_t const SPI_QUARTER_SPEED = 2; -/** - USE_SPI_LIB: if set, use the SPI library bundled with Arduino IDE, otherwise - run with a standalone driver for AVR. -*/ -#define USE_SPI_LIB -/** - Define MEGA_SOFT_SPI non-zero to use software SPI on Mega Arduinos. - Pins used are SS 10, MOSI 11, MISO 12, and SCK 13. - - MEGA_SOFT_SPI allows an unmodified Adafruit GPS Shield to be used - on Mega Arduinos. Software SPI works well with GPS Shield V1.1 - but many SD cards will fail with GPS Shield V1.0. -*/ -#define MEGA_SOFT_SPI 0 -//------------------------------------------------------------------------------ -#if MEGA_SOFT_SPI && (defined(__AVR_ATmega1280__)||defined(__AVR_ATmega2560__)) - #define SOFTWARE_SPI -#endif // MEGA_SOFT_SPI -//------------------------------------------------------------------------------ -// SPI pin definitions -// -#ifndef SOFTWARE_SPI - // hardware pin defs - - // include pins_arduino.h or variant.h depending on architecture, via Arduino.h - #include - - /** - SD Chip Select pin - - Warning if this pin is redefined the hardware SS will pin will be enabled - as an output by init(). An avr processor will not function as an SPI - master unless SS is set to output mode. - */ - #ifndef SDCARD_SS_PIN - /** The default chip select pin for the SD card is SS. */ - uint8_t const SD_CHIP_SELECT_PIN = SS; - #else - uint8_t const SD_CHIP_SELECT_PIN = SDCARD_SS_PIN; - #endif - - // The following three pins must not be redefined for hardware SPI, - // so ensure that they are taken from pins_arduino.h or variant.h, depending on architecture. - #ifndef SDCARD_MOSI_PIN - /** SPI Master Out Slave In pin */ - uint8_t const SPI_MOSI_PIN = MOSI; - /** SPI Master In Slave Out pin */ - uint8_t const SPI_MISO_PIN = MISO; - /** SPI Clock pin */ - uint8_t const SPI_SCK_PIN = SCK; - #else - uint8_t const SPI_MOSI_PIN = SDCARD_MOSI_PIN; - uint8_t const SPI_MISO_PIN = SDCARD_MISO_PIN; - uint8_t const SPI_SCK_PIN = SDCARD_SCK_PIN; - #endif - - /** optimize loops for hardware SPI */ - #ifndef USE_SPI_LIB - #define OPTIMIZE_HARDWARE_SPI - #endif - -#else // SOFTWARE_SPI - // define software SPI pins so Mega can use unmodified GPS Shield - /** SPI chip select pin */ - uint8_t const SD_CHIP_SELECT_PIN = 10; - /** SPI Master Out Slave In pin */ - uint8_t const SPI_MOSI_PIN = 11; - /** SPI Master In Slave Out pin */ - uint8_t const SPI_MISO_PIN = 12; - /** SPI Clock pin */ - uint8_t const SPI_SCK_PIN = 13; -#endif // SOFTWARE_SPI -//------------------------------------------------------------------------------ -/** Protect block zero from write if nonzero */ -#define SD_PROTECT_BLOCK_ZERO 1 -/** init timeout ms */ -unsigned int const SD_INIT_TIMEOUT = 2000; -/** erase timeout ms */ -unsigned int const SD_ERASE_TIMEOUT = 10000; -/** read timeout ms */ -unsigned int const SD_READ_TIMEOUT = 300; -/** write time out ms */ -unsigned int const SD_WRITE_TIMEOUT = 600; -//------------------------------------------------------------------------------ -// SD card errors -/** timeout error for command CMD0 */ -uint8_t const SD_CARD_ERROR_CMD0 = 0X1; -/** CMD8 was not accepted - not a valid SD card*/ -uint8_t const SD_CARD_ERROR_CMD8 = 0X2; -/** card returned an error response for CMD17 (read block) */ -uint8_t const SD_CARD_ERROR_CMD17 = 0X3; -/** card returned an error response for CMD24 (write block) */ -uint8_t const SD_CARD_ERROR_CMD24 = 0X4; -/** WRITE_MULTIPLE_BLOCKS command failed */ -uint8_t const SD_CARD_ERROR_CMD25 = 0X05; -/** card returned an error response for CMD58 (read OCR) */ -uint8_t const SD_CARD_ERROR_CMD58 = 0X06; -/** SET_WR_BLK_ERASE_COUNT failed */ -uint8_t const SD_CARD_ERROR_ACMD23 = 0X07; -/** card's ACMD41 initialization process timeout */ -uint8_t const SD_CARD_ERROR_ACMD41 = 0X08; -/** card returned a bad CSR version field */ -uint8_t const SD_CARD_ERROR_BAD_CSD = 0X09; -/** erase block group command failed */ -uint8_t const SD_CARD_ERROR_ERASE = 0X0A; -/** card not capable of single block erase */ -uint8_t const SD_CARD_ERROR_ERASE_SINGLE_BLOCK = 0X0B; -/** Erase sequence timed out */ -uint8_t const SD_CARD_ERROR_ERASE_TIMEOUT = 0X0C; -/** card returned an error token instead of read data */ -uint8_t const SD_CARD_ERROR_READ = 0X0D; -/** read CID or CSD failed */ -uint8_t const SD_CARD_ERROR_READ_REG = 0X0E; -/** timeout while waiting for start of read data */ -uint8_t const SD_CARD_ERROR_READ_TIMEOUT = 0X0F; -/** card did not accept STOP_TRAN_TOKEN */ -uint8_t const SD_CARD_ERROR_STOP_TRAN = 0X10; -/** card returned an error token as a response to a write operation */ -uint8_t const SD_CARD_ERROR_WRITE = 0X11; -/** attempt to write protected block zero */ -uint8_t const SD_CARD_ERROR_WRITE_BLOCK_ZERO = 0X12; -/** card did not go ready for a multiple block write */ -uint8_t const SD_CARD_ERROR_WRITE_MULTIPLE = 0X13; -/** card returned an error to a CMD13 status check after a write */ -uint8_t const SD_CARD_ERROR_WRITE_PROGRAMMING = 0X14; -/** timeout occurred during write programming */ -uint8_t const SD_CARD_ERROR_WRITE_TIMEOUT = 0X15; -/** incorrect rate selected */ -uint8_t const SD_CARD_ERROR_SCK_RATE = 0X16; -//------------------------------------------------------------------------------ -// card types -/** Standard capacity V1 SD card */ -uint8_t const SD_CARD_TYPE_SD1 = 1; -/** Standard capacity V2 SD card */ -uint8_t const SD_CARD_TYPE_SD2 = 2; -/** High Capacity SD card */ -uint8_t const SD_CARD_TYPE_SDHC = 3; -//------------------------------------------------------------------------------ -/** - \class Sd2Card - \brief Raw access to SD and SDHC flash memory cards. -*/ -class Sd2Card { - public: - /** Construct an instance of Sd2Card. */ - Sd2Card(void) : errorCode_(0), inBlock_(0), partialBlockRead_(0), type_(0) {} - uint32_t cardSize(void); - uint8_t erase(uint32_t firstBlock, uint32_t lastBlock); - uint8_t eraseSingleBlockEnable(void); - /** - \return error code for last error. See Sd2Card.h for a list of error codes. - */ - uint8_t errorCode(void) const { - return errorCode_; - } - /** \return error data for last error. */ - uint8_t errorData(void) const { - return status_; - } - /** - Initialize an SD flash memory card with default clock rate and chip - select pin. See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). - */ - uint8_t init(void) { - return init(SPI_FULL_SPEED, SD_CHIP_SELECT_PIN); - } - /** - Initialize an SD flash memory card with the selected SPI clock rate - and the default SD chip select pin. - See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). - */ - uint8_t init(uint8_t sckRateID) { - return init(sckRateID, SD_CHIP_SELECT_PIN); - } - uint8_t init(uint8_t sckRateID, uint8_t chipSelectPin); - void partialBlockRead(uint8_t value); - /** Returns the current value, true or false, for partial block read. */ - uint8_t partialBlockRead(void) const { - return partialBlockRead_; - } - uint8_t readBlock(uint32_t block, uint8_t* dst); - uint8_t readData(uint32_t block, - uint16_t offset, uint16_t count, uint8_t* dst); - /** - Read a cards CID register. The CID contains card identification - information such as Manufacturer ID, Product name, Product serial - number and Manufacturing date. */ - uint8_t readCID(cid_t* cid) { - return readRegister(CMD10, cid); - } - /** - Read a cards CSD register. The CSD contains Card-Specific Data that - provides information regarding access to the card's contents. */ - uint8_t readCSD(csd_t* csd) { - return readRegister(CMD9, csd); - } - void readEnd(void); - uint8_t setSckRate(uint8_t sckRateID); - #ifdef USE_SPI_LIB - uint8_t setSpiClock(uint32_t clock); - #endif - /** Return the card type: SD V1, SD V2 or SDHC */ - uint8_t type(void) const { - return type_; - } - uint8_t writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking = 1); - uint8_t writeData(const uint8_t* src); - uint8_t writeStart(uint32_t blockNumber, uint32_t eraseCount); - uint8_t writeStop(void); - uint8_t isBusy(void); - private: - uint32_t block_; - uint8_t chipSelectPin_; - uint8_t errorCode_; - uint8_t inBlock_; - uint16_t offset_; - uint8_t partialBlockRead_; - uint8_t status_; - uint8_t type_; - // private functions - uint8_t cardAcmd(uint8_t cmd, uint32_t arg) { - cardCommand(CMD55, 0); - return cardCommand(cmd, arg); - } - uint8_t cardCommand(uint8_t cmd, uint32_t arg); - void error(uint8_t code) { - errorCode_ = code; - } - uint8_t readRegister(uint8_t cmd, void* buf); - uint8_t sendWriteCommand(uint32_t blockNumber, uint32_t eraseCount); - void chipSelectHigh(void); - void chipSelectLow(void); - void type(uint8_t value) { - type_ = value; - } - uint8_t waitNotBusy(unsigned int timeoutMillis); - uint8_t writeData(uint8_t token, const uint8_t* src); - uint8_t waitStartBlock(void); -}; -#endif // Sd2Card_h +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#ifndef Sd2Card_h +#define Sd2Card_h +/** + \file + Sd2Card class +*/ +#include "Sd2PinMap.h" +#include "SdInfo.h" +/** Set SCK to max rate of F_CPU/2. See Sd2Card::setSckRate(). */ +uint8_t const SPI_FULL_SPEED = 0; +/** Set SCK rate to F_CPU/4. See Sd2Card::setSckRate(). */ +uint8_t const SPI_HALF_SPEED = 1; +/** Set SCK rate to F_CPU/8. Sd2Card::setSckRate(). */ +uint8_t const SPI_QUARTER_SPEED = 2; +/** + USE_SPI_LIB: if set, use the SPI library bundled with Arduino IDE, otherwise + run with a standalone driver for AVR. +*/ +#define USE_SPI_LIB +/** + Define MEGA_SOFT_SPI non-zero to use software SPI on Mega Arduinos. + Pins used are SS 10, MOSI 11, MISO 12, and SCK 13. + + MEGA_SOFT_SPI allows an unmodified Adafruit GPS Shield to be used + on Mega Arduinos. Software SPI works well with GPS Shield V1.1 + but many SD cards will fail with GPS Shield V1.0. +*/ +#define MEGA_SOFT_SPI 0 +//------------------------------------------------------------------------------ +#if MEGA_SOFT_SPI && (defined(__AVR_ATmega1280__)||defined(__AVR_ATmega2560__)) + #define SOFTWARE_SPI +#endif // MEGA_SOFT_SPI +//------------------------------------------------------------------------------ +// SPI pin definitions +// +#ifndef SOFTWARE_SPI + // hardware pin defs + + // include pins_arduino.h or variant.h depending on architecture, via Arduino.h + #include + + /** + SD Chip Select pin + + Warning if this pin is redefined the hardware SS will pin will be enabled + as an output by init(). An avr processor will not function as an SPI + master unless SS is set to output mode. + */ + #ifndef SDCARD_SS_PIN + /** The default chip select pin for the SD card is SS. */ + uint8_t const SD_CHIP_SELECT_PIN = SS; + #else + uint8_t const SD_CHIP_SELECT_PIN = SDCARD_SS_PIN; + #endif + + // The following three pins must not be redefined for hardware SPI, + // so ensure that they are taken from pins_arduino.h or variant.h, depending on architecture. + #ifndef SDCARD_MOSI_PIN + /** SPI Master Out Slave In pin */ + uint8_t const SPI_MOSI_PIN = MOSI; + /** SPI Master In Slave Out pin */ + uint8_t const SPI_MISO_PIN = MISO; + /** SPI Clock pin */ + uint8_t const SPI_SCK_PIN = SCK; + #else + uint8_t const SPI_MOSI_PIN = SDCARD_MOSI_PIN; + uint8_t const SPI_MISO_PIN = SDCARD_MISO_PIN; + uint8_t const SPI_SCK_PIN = SDCARD_SCK_PIN; + #endif + + /** optimize loops for hardware SPI */ + #ifndef USE_SPI_LIB + #define OPTIMIZE_HARDWARE_SPI + #endif + +#else // SOFTWARE_SPI + // define software SPI pins so Mega can use unmodified GPS Shield + /** SPI chip select pin */ + uint8_t const SD_CHIP_SELECT_PIN = 10; + /** SPI Master Out Slave In pin */ + uint8_t const SPI_MOSI_PIN = 11; + /** SPI Master In Slave Out pin */ + uint8_t const SPI_MISO_PIN = 12; + /** SPI Clock pin */ + uint8_t const SPI_SCK_PIN = 13; +#endif // SOFTWARE_SPI +//------------------------------------------------------------------------------ +/** Protect block zero from write if nonzero */ +#define SD_PROTECT_BLOCK_ZERO 1 +/** init timeout ms */ +unsigned int const SD_INIT_TIMEOUT = 2000; +/** erase timeout ms */ +unsigned int const SD_ERASE_TIMEOUT = 10000; +/** read timeout ms */ +unsigned int const SD_READ_TIMEOUT = 300; +/** write time out ms */ +unsigned int const SD_WRITE_TIMEOUT = 600; +//------------------------------------------------------------------------------ +// SD card errors +/** timeout error for command CMD0 */ +uint8_t const SD_CARD_ERROR_CMD0 = 0X1; +/** CMD8 was not accepted - not a valid SD card*/ +uint8_t const SD_CARD_ERROR_CMD8 = 0X2; +/** card returned an error response for CMD17 (read block) */ +uint8_t const SD_CARD_ERROR_CMD17 = 0X3; +/** card returned an error response for CMD24 (write block) */ +uint8_t const SD_CARD_ERROR_CMD24 = 0X4; +/** WRITE_MULTIPLE_BLOCKS command failed */ +uint8_t const SD_CARD_ERROR_CMD25 = 0X05; +/** card returned an error response for CMD58 (read OCR) */ +uint8_t const SD_CARD_ERROR_CMD58 = 0X06; +/** SET_WR_BLK_ERASE_COUNT failed */ +uint8_t const SD_CARD_ERROR_ACMD23 = 0X07; +/** card's ACMD41 initialization process timeout */ +uint8_t const SD_CARD_ERROR_ACMD41 = 0X08; +/** card returned a bad CSR version field */ +uint8_t const SD_CARD_ERROR_BAD_CSD = 0X09; +/** erase block group command failed */ +uint8_t const SD_CARD_ERROR_ERASE = 0X0A; +/** card not capable of single block erase */ +uint8_t const SD_CARD_ERROR_ERASE_SINGLE_BLOCK = 0X0B; +/** Erase sequence timed out */ +uint8_t const SD_CARD_ERROR_ERASE_TIMEOUT = 0X0C; +/** card returned an error token instead of read data */ +uint8_t const SD_CARD_ERROR_READ = 0X0D; +/** read CID or CSD failed */ +uint8_t const SD_CARD_ERROR_READ_REG = 0X0E; +/** timeout while waiting for start of read data */ +uint8_t const SD_CARD_ERROR_READ_TIMEOUT = 0X0F; +/** card did not accept STOP_TRAN_TOKEN */ +uint8_t const SD_CARD_ERROR_STOP_TRAN = 0X10; +/** card returned an error token as a response to a write operation */ +uint8_t const SD_CARD_ERROR_WRITE = 0X11; +/** attempt to write protected block zero */ +uint8_t const SD_CARD_ERROR_WRITE_BLOCK_ZERO = 0X12; +/** card did not go ready for a multiple block write */ +uint8_t const SD_CARD_ERROR_WRITE_MULTIPLE = 0X13; +/** card returned an error to a CMD13 status check after a write */ +uint8_t const SD_CARD_ERROR_WRITE_PROGRAMMING = 0X14; +/** timeout occurred during write programming */ +uint8_t const SD_CARD_ERROR_WRITE_TIMEOUT = 0X15; +/** incorrect rate selected */ +uint8_t const SD_CARD_ERROR_SCK_RATE = 0X16; +//------------------------------------------------------------------------------ +// card types +/** Standard capacity V1 SD card */ +uint8_t const SD_CARD_TYPE_SD1 = 1; +/** Standard capacity V2 SD card */ +uint8_t const SD_CARD_TYPE_SD2 = 2; +/** High Capacity SD card */ +uint8_t const SD_CARD_TYPE_SDHC = 3; +//------------------------------------------------------------------------------ +/** + \class Sd2Card + \brief Raw access to SD and SDHC flash memory cards. +*/ +class Sd2Card { + public: + /** Construct an instance of Sd2Card. */ + Sd2Card(void) : errorCode_(0), inBlock_(0), partialBlockRead_(0), type_(0) {} + uint32_t cardSize(void); + uint8_t erase(uint32_t firstBlock, uint32_t lastBlock); + uint8_t eraseSingleBlockEnable(void); + /** + \return error code for last error. See Sd2Card.h for a list of error codes. + */ + uint8_t errorCode(void) const { + return errorCode_; + } + /** \return error data for last error. */ + uint8_t errorData(void) const { + return status_; + } + /** + Initialize an SD flash memory card with default clock rate and chip + select pin. See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). + */ + uint8_t init(void) { + return init(SPI_FULL_SPEED, SD_CHIP_SELECT_PIN); + } + /** + Initialize an SD flash memory card with the selected SPI clock rate + and the default SD chip select pin. + See sd2Card::init(uint8_t sckRateID, uint8_t chipSelectPin). + */ + uint8_t init(uint8_t sckRateID) { + return init(sckRateID, SD_CHIP_SELECT_PIN); + } + uint8_t init(uint8_t sckRateID, uint8_t chipSelectPin); + void partialBlockRead(uint8_t value); + /** Returns the current value, true or false, for partial block read. */ + uint8_t partialBlockRead(void) const { + return partialBlockRead_; + } + uint8_t readBlock(uint32_t block, uint8_t* dst); + uint8_t readData(uint32_t block, + uint16_t offset, uint16_t count, uint8_t* dst); + /** + Read a cards CID register. The CID contains card identification + information such as Manufacturer ID, Product name, Product serial + number and Manufacturing date. */ + uint8_t readCID(cid_t* cid) { + return readRegister(CMD10, cid); + } + /** + Read a cards CSD register. The CSD contains Card-Specific Data that + provides information regarding access to the card's contents. */ + uint8_t readCSD(csd_t* csd) { + return readRegister(CMD9, csd); + } + void readEnd(void); + uint8_t setSckRate(uint8_t sckRateID); + #ifdef USE_SPI_LIB + uint8_t setSpiClock(uint32_t clock); + #endif + /** Return the card type: SD V1, SD V2 or SDHC */ + uint8_t type(void) const { + return type_; + } + uint8_t writeBlock(uint32_t blockNumber, const uint8_t* src, uint8_t blocking = 1); + uint8_t writeData(const uint8_t* src); + uint8_t writeStart(uint32_t blockNumber, uint32_t eraseCount); + uint8_t writeStop(void); + uint8_t isBusy(void); + private: + uint32_t block_; + uint8_t chipSelectPin_; + uint8_t errorCode_; + uint8_t inBlock_; + uint16_t offset_; + uint8_t partialBlockRead_; + uint8_t status_; + uint8_t type_; + // private functions + uint8_t cardAcmd(uint8_t cmd, uint32_t arg) { + cardCommand(CMD55, 0); + return cardCommand(cmd, arg); + } + uint8_t cardCommand(uint8_t cmd, uint32_t arg); + void error(uint8_t code) { + errorCode_ = code; + } + uint8_t readRegister(uint8_t cmd, void* buf); + uint8_t sendWriteCommand(uint32_t blockNumber, uint32_t eraseCount); + void chipSelectHigh(void); + void chipSelectLow(void); + void type(uint8_t value) { + type_ = value; + } + uint8_t waitNotBusy(unsigned int timeoutMillis); + uint8_t writeData(uint8_t token, const uint8_t* src); + uint8_t waitStartBlock(void); +}; +#endif // Sd2Card_h diff --git a/megaavr/libraries/SD/src/utility/Sd2PinMap.h b/megaavr/libraries/SD/src/utility/Sd2PinMap.h index 12d8926..8a26848 100755 --- a/megaavr/libraries/SD/src/utility/Sd2PinMap.h +++ b/megaavr/libraries/SD/src/utility/Sd2PinMap.h @@ -1,528 +1,528 @@ -/* Arduino SdFat Library - Copyright (C) 2010 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#if defined(__arm__) // Arduino Due Board follows - -#ifndef Sd2PinMap_h - #define Sd2PinMap_h - - #include - - uint8_t const SS_PIN = SS; - uint8_t const MOSI_PIN = MOSI; - uint8_t const MISO_PIN = MISO; - uint8_t const SCK_PIN = SCK; - -#endif // Sd2PinMap_h - -#elif defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) || \ -defined(__AVR_ATmega3209__) || defined(__AVR_ATmega3208__) || \ -defined(__AVR_ATmega1609__) || defined(__AVR_ATmega1608__) || \ -defined(__AVR_ATmega809__) || defined(__AVR_ATmega808__) - -#ifndef Sd2PinMap_h - #define Sd2PinMap_h - - #include - - uint8_t const SS_PIN = SS; - uint8_t const MOSI_PIN = MOSI; - uint8_t const MISO_PIN = MISO; - uint8_t const SCK_PIN = SCK; - -#endif // Sd2PinMap_h - -#elif defined(__AVR__) // Other AVR based Boards follows - -// Warning this file was generated by a program. -#ifndef Sd2PinMap_h -#define Sd2PinMap_h -#include - -//------------------------------------------------------------------------------ -/** struct for mapping digital pins */ -struct pin_map_t { - volatile uint8_t* ddr; - volatile uint8_t* pin; - volatile uint8_t* port; - uint8_t bit; -}; -//------------------------------------------------------------------------------ -#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) -// Mega - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 20; -uint8_t const SCL_PIN = 21; - -// SPI port -uint8_t const SS_PIN = 53; -uint8_t const MOSI_PIN = 51; -uint8_t const MISO_PIN = 50; -uint8_t const SCK_PIN = 52; - -static const pin_map_t digitalPinMap[] = { - {&DDRE, &PINE, &PORTE, 0}, // E0 0 - {&DDRE, &PINE, &PORTE, 1}, // E1 1 - {&DDRE, &PINE, &PORTE, 4}, // E4 2 - {&DDRE, &PINE, &PORTE, 5}, // E5 3 - {&DDRG, &PING, &PORTG, 5}, // G5 4 - {&DDRE, &PINE, &PORTE, 3}, // E3 5 - {&DDRH, &PINH, &PORTH, 3}, // H3 6 - {&DDRH, &PINH, &PORTH, 4}, // H4 7 - {&DDRH, &PINH, &PORTH, 5}, // H5 8 - {&DDRH, &PINH, &PORTH, 6}, // H6 9 - {&DDRB, &PINB, &PORTB, 4}, // B4 10 - {&DDRB, &PINB, &PORTB, 5}, // B5 11 - {&DDRB, &PINB, &PORTB, 6}, // B6 12 - {&DDRB, &PINB, &PORTB, 7}, // B7 13 - {&DDRJ, &PINJ, &PORTJ, 1}, // J1 14 - {&DDRJ, &PINJ, &PORTJ, 0}, // J0 15 - {&DDRH, &PINH, &PORTH, 1}, // H1 16 - {&DDRH, &PINH, &PORTH, 0}, // H0 17 - {&DDRD, &PIND, &PORTD, 3}, // D3 18 - {&DDRD, &PIND, &PORTD, 2}, // D2 19 - {&DDRD, &PIND, &PORTD, 1}, // D1 20 - {&DDRD, &PIND, &PORTD, 0}, // D0 21 - {&DDRA, &PINA, &PORTA, 0}, // A0 22 - {&DDRA, &PINA, &PORTA, 1}, // A1 23 - {&DDRA, &PINA, &PORTA, 2}, // A2 24 - {&DDRA, &PINA, &PORTA, 3}, // A3 25 - {&DDRA, &PINA, &PORTA, 4}, // A4 26 - {&DDRA, &PINA, &PORTA, 5}, // A5 27 - {&DDRA, &PINA, &PORTA, 6}, // A6 28 - {&DDRA, &PINA, &PORTA, 7}, // A7 29 - {&DDRC, &PINC, &PORTC, 7}, // C7 30 - {&DDRC, &PINC, &PORTC, 6}, // C6 31 - {&DDRC, &PINC, &PORTC, 5}, // C5 32 - {&DDRC, &PINC, &PORTC, 4}, // C4 33 - {&DDRC, &PINC, &PORTC, 3}, // C3 34 - {&DDRC, &PINC, &PORTC, 2}, // C2 35 - {&DDRC, &PINC, &PORTC, 1}, // C1 36 - {&DDRC, &PINC, &PORTC, 0}, // C0 37 - {&DDRD, &PIND, &PORTD, 7}, // D7 38 - {&DDRG, &PING, &PORTG, 2}, // G2 39 - {&DDRG, &PING, &PORTG, 1}, // G1 40 - {&DDRG, &PING, &PORTG, 0}, // G0 41 - {&DDRL, &PINL, &PORTL, 7}, // L7 42 - {&DDRL, &PINL, &PORTL, 6}, // L6 43 - {&DDRL, &PINL, &PORTL, 5}, // L5 44 - {&DDRL, &PINL, &PORTL, 4}, // L4 45 - {&DDRL, &PINL, &PORTL, 3}, // L3 46 - {&DDRL, &PINL, &PORTL, 2}, // L2 47 - {&DDRL, &PINL, &PORTL, 1}, // L1 48 - {&DDRL, &PINL, &PORTL, 0}, // L0 49 - {&DDRB, &PINB, &PORTB, 3}, // B3 50 - {&DDRB, &PINB, &PORTB, 2}, // B2 51 - {&DDRB, &PINB, &PORTB, 1}, // B1 52 - {&DDRB, &PINB, &PORTB, 0}, // B0 53 - {&DDRF, &PINF, &PORTF, 0}, // F0 54 - {&DDRF, &PINF, &PORTF, 1}, // F1 55 - {&DDRF, &PINF, &PORTF, 2}, // F2 56 - {&DDRF, &PINF, &PORTF, 3}, // F3 57 - {&DDRF, &PINF, &PORTF, 4}, // F4 58 - {&DDRF, &PINF, &PORTF, 5}, // F5 59 - {&DDRF, &PINF, &PORTF, 6}, // F6 60 - {&DDRF, &PINF, &PORTF, 7}, // F7 61 - {&DDRK, &PINK, &PORTK, 0}, // K0 62 - {&DDRK, &PINK, &PORTK, 1}, // K1 63 - {&DDRK, &PINK, &PORTK, 2}, // K2 64 - {&DDRK, &PINK, &PORTK, 3}, // K3 65 - {&DDRK, &PINK, &PORTK, 4}, // K4 66 - {&DDRK, &PINK, &PORTK, 5}, // K5 67 - {&DDRK, &PINK, &PORTK, 6}, // K6 68 - {&DDRK, &PINK, &PORTK, 7} // K7 69 -}; -//------------------------------------------------------------------------------ -#elif (defined(__AVR_ATmega644P__) || defined(__AVR_ATmega1284P__)) && defined(CORE_MICRODUINO) -// Microduino Core+ - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 20; -uint8_t const SCL_PIN = 21; - -// SPI port -uint8_t const SS_PIN = 10; -uint8_t const MOSI_PIN = 11; -uint8_t const MISO_PIN = 12; -uint8_t const SCK_PIN = 13; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PIND, &PORTD, 0}, // D0 PD0 - {&DDRD, &PIND, &PORTD, 1}, // D1 PD1 - {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 - {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 - {&DDRB, &PINB, &PORTB, 0}, // D4 PB0 - {&DDRB, &PINB, &PORTB, 1}, // D5 PB1 - {&DDRB, &PINB, &PORTB, 2}, // D6 PB2 - {&DDRB, &PINB, &PORTB, 3}, // D7 PB3 - {&DDRD, &PIND, &PORTD, 6}, // D8 PD6 - {&DDRD, &PIND, &PORTD, 5}, // D9 PD5 - {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 - {&DDRB, &PINB, &PORTB, 5}, // D11 PB5 - {&DDRB, &PINB, &PORTB, 6}, // D12 PB6 - {&DDRB, &PINB, &PORTB, 7}, // D13 PB7 - {&DDRC, &PINC, &PORTC, 7}, // D14 PC7 - {&DDRC, &PINC, &PORTC, 6}, // D15 PC6 - {&DDRC, &PINC, &PORTC, 5}, // D16 PC5 - {&DDRC, &PINC, &PORTC, 4}, // D17 PC4 - {&DDRC, &PINC, &PORTC, 3}, // D18 PC3 - {&DDRC, &PINC, &PORTC, 2}, // D19 PC2 - {&DDRC, &PINC, &PORTC, 1}, // D20 PC1 - {&DDRC, &PINC, &PORTC, 0}, // D21 PC0 - {&DDRD, &PIND, &PORTD, 4}, // D22 PD4 - {&DDRD, &PIND, &PORTD, 7}, // D23 PD7 - {&DDRA, &PINA, &PORTA, 7}, // D24 PA7 - {&DDRA, &PINA, &PORTA, 6}, // D25 PA6 - {&DDRA, &PINA, &PORTA, 5}, // D26 PA5 - {&DDRA, &PINA, &PORTA, 4}, // D27 PA4 - {&DDRA, &PINA, &PORTA, 3}, // D28 PA3 - {&DDRA, &PINA, &PORTA, 2}, // D29 PA2 - {&DDRA, &PINA, &PORTA, 1}, // D30 PA1 - {&DDRA, &PINA, &PORTA, 0} // D31 PA0 -}; -//------------------------------------------------------------------------------ -#elif defined(__AVR_ATmega128RFA1__) && defined(CORE_MICRODUINO) -// Microduino Core RF - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 18; -uint8_t const SCL_PIN = 19; - -// SPI port -uint8_t const SS_PIN = 10; -uint8_t const MOSI_PIN = 11; -uint8_t const MISO_PIN = 12; -uint8_t const SCK_PIN = 13; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PINE, &PORTE, 0}, // D0 PE0 - {&DDRD, &PINE, &PORTE, 1}, // D1 PE1 - {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 - {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 - {&DDRB, &PINE, &PORTE, 3}, // D4 PE3 - {&DDRB, &PINE, &PORTE, 4}, // D5 PE4 - {&DDRB, &PINE, &PORTE, 5}, // D6 PE5 - {&DDRB, &PINB, &PORTB, 7}, // D7 PB7 - {&DDRD, &PINB, &PORTB, 6}, // D8 PB6 - {&DDRD, &PINB, &PORTB, 5}, // D9 PB5 - {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 - {&DDRB, &PINB, &PORTB, 2}, // D11 PB2 - {&DDRB, &PINB, &PORTB, 3}, // D12 PB3 - {&DDRB, &PINB, &PORTB, 1}, // D13 PB1 - {&DDRF, &PINF, &PORTF, 7}, // D14 PF7 - {&DDRF, &PINF, &PORTF, 6}, // D15 PF6 - {&DDRF, &PINF, &PORTF, 5}, // D16 PF5 - {&DDRF, &PINF, &PORTF, 4}, // D17 PF4 - {&DDRD, &PIND, &PORTD, 1}, // D18 PD1 - {&DDRD, &PIND, &PORTD, 0}, // D19 PD0 - {&DDRF, &PINF, &PORTF, 3}, // D20 PF3 - {&DDRF, &PINF, &PORTF, 2}, // D21 PF2 -}; -//------------------------------------------------------------------------------ -#elif defined(__AVR_ATmega32U4__) && defined(CORE_MICRODUINO) -// Microduino Core USB - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 18; -uint8_t const SCL_PIN = 19; - -// SPI port -uint8_t const SS_PIN = 10; -uint8_t const MOSI_PIN = 11; -uint8_t const MISO_PIN = 12; -uint8_t const SCK_PIN = 13; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PIND, &PORTD, 2}, // D0 - PD2 - {&DDRD, &PIND, &PORTD, 3}, // D1 - PD3 - {&DDRE, &PINE, &PORTE, 6}, // D2 - PE6 - {&DDRD, &PIND, &PORTD, 6}, // D3 - PD6 - {&DDRD, &PIND, &PORTD, 7}, // D4 - PD7 - {&DDRC, &PINC, &PORTC, 6}, // D5 - PC6 - {&DDRC, &PINC, &PORTC, 7}, // D6 - PC7 - {&DDRE, &PINE, &PORTE, 7}, // D7 - PE7 - {&DDRB, &PINB, &PORTB, 6}, // D8 - PB6 - {&DDRB, &PINB, &PORTB, 5}, // D9 - PB5 - {&DDRB, &PINB, &PORTB, 0}, // D10 - PB0 - {&DDRB, &PINB, &PORTB, 2}, // D11 - MOSI - PB2 - {&DDRB, &PINB, &PORTB, 3}, // D12 -MISO - PB3 - {&DDRB, &PINB, &PORTB, 1}, // D13 -SCK - PB1 - {&DDRF, &PINF, &PORTF, 7}, // D14 - A0 - PF7 - {&DDRF, &PINF, &PORTF, 6}, // D15 - A1 - PF6 - {&DDRF, &PINF, &PORTF, 5}, // D16 - A2 - PF5 - {&DDRF, &PINF, &PORTF, 4}, // D17 - A3 - PF4 - {&DDRD, &PIND, &PORTD, 1}, // D18 - PD1 - {&DDRD, &PIND, &PORTD, 0}, // D19 - PD0 - {&DDRF, &PINF, &PORTF, 1}, // D20 - A6 - PF1 - {&DDRF, &PINF, &PORTF, 0}, // D21 - A7 - PF0 -}; -//------------------------------------------------------------------------------ -#elif defined(__AVR_ATmega644P__) || defined(__AVR_ATmega644__) -// Sanguino - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 17; -uint8_t const SCL_PIN = 18; - -// SPI port -uint8_t const SS_PIN = 4; -uint8_t const MOSI_PIN = 5; -uint8_t const MISO_PIN = 6; -uint8_t const SCK_PIN = 7; - -static const pin_map_t digitalPinMap[] = { - {&DDRB, &PINB, &PORTB, 0}, // B0 0 - {&DDRB, &PINB, &PORTB, 1}, // B1 1 - {&DDRB, &PINB, &PORTB, 2}, // B2 2 - {&DDRB, &PINB, &PORTB, 3}, // B3 3 - {&DDRB, &PINB, &PORTB, 4}, // B4 4 - {&DDRB, &PINB, &PORTB, 5}, // B5 5 - {&DDRB, &PINB, &PORTB, 6}, // B6 6 - {&DDRB, &PINB, &PORTB, 7}, // B7 7 - {&DDRD, &PIND, &PORTD, 0}, // D0 8 - {&DDRD, &PIND, &PORTD, 1}, // D1 9 - {&DDRD, &PIND, &PORTD, 2}, // D2 10 - {&DDRD, &PIND, &PORTD, 3}, // D3 11 - {&DDRD, &PIND, &PORTD, 4}, // D4 12 - {&DDRD, &PIND, &PORTD, 5}, // D5 13 - {&DDRD, &PIND, &PORTD, 6}, // D6 14 - {&DDRD, &PIND, &PORTD, 7}, // D7 15 - {&DDRC, &PINC, &PORTC, 0}, // C0 16 - {&DDRC, &PINC, &PORTC, 1}, // C1 17 - {&DDRC, &PINC, &PORTC, 2}, // C2 18 - {&DDRC, &PINC, &PORTC, 3}, // C3 19 - {&DDRC, &PINC, &PORTC, 4}, // C4 20 - {&DDRC, &PINC, &PORTC, 5}, // C5 21 - {&DDRC, &PINC, &PORTC, 6}, // C6 22 - {&DDRC, &PINC, &PORTC, 7}, // C7 23 - {&DDRA, &PINA, &PORTA, 7}, // A7 24 - {&DDRA, &PINA, &PORTA, 6}, // A6 25 - {&DDRA, &PINA, &PORTA, 5}, // A5 26 - {&DDRA, &PINA, &PORTA, 4}, // A4 27 - {&DDRA, &PINA, &PORTA, 3}, // A3 28 - {&DDRA, &PINA, &PORTA, 2}, // A2 29 - {&DDRA, &PINA, &PORTA, 1}, // A1 30 - {&DDRA, &PINA, &PORTA, 0} // A0 31 -}; -//------------------------------------------------------------------------------ -#elif defined(__AVR_ATmega32U4__) -// Leonardo - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 2; -uint8_t const SCL_PIN = 3; - -// SPI port -uint8_t const SS_PIN = 17; -uint8_t const MOSI_PIN = 16; -uint8_t const MISO_PIN = 14; -uint8_t const SCK_PIN = 15; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PIND, &PORTD, 2}, // D2 0 - {&DDRD, &PIND, &PORTD, 3}, // D3 1 - {&DDRD, &PIND, &PORTD, 1}, // D1 2 - {&DDRD, &PIND, &PORTD, 0}, // D0 3 - {&DDRD, &PIND, &PORTD, 4}, // D4 4 - {&DDRC, &PINC, &PORTC, 6}, // C6 5 - {&DDRD, &PIND, &PORTD, 7}, // D7 6 - {&DDRE, &PINE, &PORTE, 6}, // E6 7 - {&DDRB, &PINB, &PORTB, 4}, // B4 8 - {&DDRB, &PINB, &PORTB, 5}, // B5 9 - {&DDRB, &PINB, &PORTB, 6}, // B6 10 - {&DDRB, &PINB, &PORTB, 7}, // B7 11 - {&DDRD, &PIND, &PORTD, 6}, // D6 12 - {&DDRC, &PINC, &PORTC, 7}, // C7 13 - {&DDRB, &PINB, &PORTB, 3}, // B3 14 - {&DDRB, &PINB, &PORTB, 1}, // B1 15 - {&DDRB, &PINB, &PORTB, 2}, // B2 16 - {&DDRB, &PINB, &PORTB, 0}, // B0 17 - {&DDRF, &PINF, &PORTF, 7}, // F7 18 - {&DDRF, &PINF, &PORTF, 6}, // F6 19 - {&DDRF, &PINF, &PORTF, 5}, // F5 20 - {&DDRF, &PINF, &PORTF, 4}, // F4 21 - {&DDRF, &PINF, &PORTF, 1}, // F1 22 - {&DDRF, &PINF, &PORTF, 0}, // F0 23 -}; -//------------------------------------------------------------------------------ -#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) -// Teensy++ 1.0 & 2.0 - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 1; -uint8_t const SCL_PIN = 0; - -// SPI port -uint8_t const SS_PIN = 20; -uint8_t const MOSI_PIN = 22; -uint8_t const MISO_PIN = 23; -uint8_t const SCK_PIN = 21; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PIND, &PORTD, 0}, // D0 0 - {&DDRD, &PIND, &PORTD, 1}, // D1 1 - {&DDRD, &PIND, &PORTD, 2}, // D2 2 - {&DDRD, &PIND, &PORTD, 3}, // D3 3 - {&DDRD, &PIND, &PORTD, 4}, // D4 4 - {&DDRD, &PIND, &PORTD, 5}, // D5 5 - {&DDRD, &PIND, &PORTD, 6}, // D6 6 - {&DDRD, &PIND, &PORTD, 7}, // D7 7 - {&DDRE, &PINE, &PORTE, 0}, // E0 8 - {&DDRE, &PINE, &PORTE, 1}, // E1 9 - {&DDRC, &PINC, &PORTC, 0}, // C0 10 - {&DDRC, &PINC, &PORTC, 1}, // C1 11 - {&DDRC, &PINC, &PORTC, 2}, // C2 12 - {&DDRC, &PINC, &PORTC, 3}, // C3 13 - {&DDRC, &PINC, &PORTC, 4}, // C4 14 - {&DDRC, &PINC, &PORTC, 5}, // C5 15 - {&DDRC, &PINC, &PORTC, 6}, // C6 16 - {&DDRC, &PINC, &PORTC, 7}, // C7 17 - {&DDRE, &PINE, &PORTE, 6}, // E6 18 - {&DDRE, &PINE, &PORTE, 7}, // E7 19 - {&DDRB, &PINB, &PORTB, 0}, // B0 20 - {&DDRB, &PINB, &PORTB, 1}, // B1 21 - {&DDRB, &PINB, &PORTB, 2}, // B2 22 - {&DDRB, &PINB, &PORTB, 3}, // B3 23 - {&DDRB, &PINB, &PORTB, 4}, // B4 24 - {&DDRB, &PINB, &PORTB, 5}, // B5 25 - {&DDRB, &PINB, &PORTB, 6}, // B6 26 - {&DDRB, &PINB, &PORTB, 7}, // B7 27 - {&DDRA, &PINA, &PORTA, 0}, // A0 28 - {&DDRA, &PINA, &PORTA, 1}, // A1 29 - {&DDRA, &PINA, &PORTA, 2}, // A2 30 - {&DDRA, &PINA, &PORTA, 3}, // A3 31 - {&DDRA, &PINA, &PORTA, 4}, // A4 32 - {&DDRA, &PINA, &PORTA, 5}, // A5 33 - {&DDRA, &PINA, &PORTA, 6}, // A6 34 - {&DDRA, &PINA, &PORTA, 7}, // A7 35 - {&DDRE, &PINE, &PORTE, 4}, // E4 36 - {&DDRE, &PINE, &PORTE, 5}, // E5 37 - {&DDRF, &PINF, &PORTF, 0}, // F0 38 - {&DDRF, &PINF, &PORTF, 1}, // F1 39 - {&DDRF, &PINF, &PORTF, 2}, // F2 40 - {&DDRF, &PINF, &PORTF, 3}, // F3 41 - {&DDRF, &PINF, &PORTF, 4}, // F4 42 - {&DDRF, &PINF, &PORTF, 5}, // F5 43 - {&DDRF, &PINF, &PORTF, 6}, // F6 44 - {&DDRF, &PINF, &PORTF, 7} // F7 45 -}; -//------------------------------------------------------------------------------ -#else // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) -// 168 and 328 Arduinos - -// Two Wire (aka I2C) ports -uint8_t const SDA_PIN = 18; -uint8_t const SCL_PIN = 19; - -// SPI port -uint8_t const SS_PIN = 10; -uint8_t const MOSI_PIN = 11; -uint8_t const MISO_PIN = 12; -uint8_t const SCK_PIN = 13; - -static const pin_map_t digitalPinMap[] = { - {&DDRD, &PIND, &PORTD, 0}, // D0 0 - {&DDRD, &PIND, &PORTD, 1}, // D1 1 - {&DDRD, &PIND, &PORTD, 2}, // D2 2 - {&DDRD, &PIND, &PORTD, 3}, // D3 3 - {&DDRD, &PIND, &PORTD, 4}, // D4 4 - {&DDRD, &PIND, &PORTD, 5}, // D5 5 - {&DDRD, &PIND, &PORTD, 6}, // D6 6 - {&DDRD, &PIND, &PORTD, 7}, // D7 7 - {&DDRB, &PINB, &PORTB, 0}, // B0 8 - {&DDRB, &PINB, &PORTB, 1}, // B1 9 - {&DDRB, &PINB, &PORTB, 2}, // B2 10 - {&DDRB, &PINB, &PORTB, 3}, // B3 11 - {&DDRB, &PINB, &PORTB, 4}, // B4 12 - {&DDRB, &PINB, &PORTB, 5}, // B5 13 - {&DDRC, &PINC, &PORTC, 0}, // C0 14 - {&DDRC, &PINC, &PORTC, 1}, // C1 15 - {&DDRC, &PINC, &PORTC, 2}, // C2 16 - {&DDRC, &PINC, &PORTC, 3}, // C3 17 - {&DDRC, &PINC, &PORTC, 4}, // C4 18 - {&DDRC, &PINC, &PORTC, 5} // C5 19 -}; -#endif // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) -//------------------------------------------------------------------------------ -static const uint8_t digitalPinCount = sizeof(digitalPinMap) / sizeof(pin_map_t); - -uint8_t badPinNumber(void) -__attribute__((error("Pin number is too large or not a constant"))); - -static inline __attribute__((always_inline)) -uint8_t getPinMode(uint8_t pin) { - if (__builtin_constant_p(pin) && pin < digitalPinCount) { - return (*digitalPinMap[pin].ddr >> digitalPinMap[pin].bit) & 1; - } else { - return badPinNumber(); - } -} -static inline __attribute__((always_inline)) -void setPinMode(uint8_t pin, uint8_t mode) { - if (__builtin_constant_p(pin) && pin < digitalPinCount) { - if (mode) { - *digitalPinMap[pin].ddr |= 1 << digitalPinMap[pin].bit; - } else { - *digitalPinMap[pin].ddr &= ~(1 << digitalPinMap[pin].bit); - } - } else { - badPinNumber(); - } -} -static inline __attribute__((always_inline)) -uint8_t fastDigitalRead(uint8_t pin) { - if (__builtin_constant_p(pin) && pin < digitalPinCount) { - return (*digitalPinMap[pin].pin >> digitalPinMap[pin].bit) & 1; - } else { - return badPinNumber(); - } -} -static inline __attribute__((always_inline)) -void fastDigitalWrite(uint8_t pin, uint8_t value) { - if (__builtin_constant_p(pin) && pin < digitalPinCount) { - if (value) { - *digitalPinMap[pin].port |= 1 << digitalPinMap[pin].bit; - } else { - *digitalPinMap[pin].port &= ~(1 << digitalPinMap[pin].bit); - } - } else { - badPinNumber(); - } -} -#endif // Sd2PinMap_h - -#elif defined (__CPU_ARC__) - -#if defined (__ARDUINO_ARC__) - // Two Wire (aka I2C) ports - uint8_t const SDA_PIN = 18; - uint8_t const SCL_PIN = 19; - - // SPI port - uint8_t const SS_PIN = 10; - uint8_t const MOSI_PIN = 11; - uint8_t const MISO_PIN = 12; - uint8_t const SCK_PIN = 13; - -#endif // Arduino ARC - -#else -#error Architecture or board not supported. -#endif +/* Arduino SdFat Library + Copyright (C) 2010 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#if defined(__arm__) // Arduino Due Board follows + +#ifndef Sd2PinMap_h + #define Sd2PinMap_h + + #include + + uint8_t const SS_PIN = SS; + uint8_t const MOSI_PIN = MOSI; + uint8_t const MISO_PIN = MISO; + uint8_t const SCK_PIN = SCK; + +#endif // Sd2PinMap_h + +#elif defined(__AVR_ATmega4809__) || defined(__AVR_ATmega4808__) || \ +defined(__AVR_ATmega3209__) || defined(__AVR_ATmega3208__) || \ +defined(__AVR_ATmega1609__) || defined(__AVR_ATmega1608__) || \ +defined(__AVR_ATmega809__) || defined(__AVR_ATmega808__) + +#ifndef Sd2PinMap_h + #define Sd2PinMap_h + + #include + + uint8_t const SS_PIN = SS; + uint8_t const MOSI_PIN = MOSI; + uint8_t const MISO_PIN = MISO; + uint8_t const SCK_PIN = SCK; + +#endif // Sd2PinMap_h + +#elif defined(__AVR__) // Other AVR based Boards follows + +// Warning this file was generated by a program. +#ifndef Sd2PinMap_h +#define Sd2PinMap_h +#include + +//------------------------------------------------------------------------------ +/** struct for mapping digital pins */ +struct pin_map_t { + volatile uint8_t* ddr; + volatile uint8_t* pin; + volatile uint8_t* port; + uint8_t bit; +}; +//------------------------------------------------------------------------------ +#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +// Mega + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 20; +uint8_t const SCL_PIN = 21; + +// SPI port +uint8_t const SS_PIN = 53; +uint8_t const MOSI_PIN = 51; +uint8_t const MISO_PIN = 50; +uint8_t const SCK_PIN = 52; + +static const pin_map_t digitalPinMap[] = { + {&DDRE, &PINE, &PORTE, 0}, // E0 0 + {&DDRE, &PINE, &PORTE, 1}, // E1 1 + {&DDRE, &PINE, &PORTE, 4}, // E4 2 + {&DDRE, &PINE, &PORTE, 5}, // E5 3 + {&DDRG, &PING, &PORTG, 5}, // G5 4 + {&DDRE, &PINE, &PORTE, 3}, // E3 5 + {&DDRH, &PINH, &PORTH, 3}, // H3 6 + {&DDRH, &PINH, &PORTH, 4}, // H4 7 + {&DDRH, &PINH, &PORTH, 5}, // H5 8 + {&DDRH, &PINH, &PORTH, 6}, // H6 9 + {&DDRB, &PINB, &PORTB, 4}, // B4 10 + {&DDRB, &PINB, &PORTB, 5}, // B5 11 + {&DDRB, &PINB, &PORTB, 6}, // B6 12 + {&DDRB, &PINB, &PORTB, 7}, // B7 13 + {&DDRJ, &PINJ, &PORTJ, 1}, // J1 14 + {&DDRJ, &PINJ, &PORTJ, 0}, // J0 15 + {&DDRH, &PINH, &PORTH, 1}, // H1 16 + {&DDRH, &PINH, &PORTH, 0}, // H0 17 + {&DDRD, &PIND, &PORTD, 3}, // D3 18 + {&DDRD, &PIND, &PORTD, 2}, // D2 19 + {&DDRD, &PIND, &PORTD, 1}, // D1 20 + {&DDRD, &PIND, &PORTD, 0}, // D0 21 + {&DDRA, &PINA, &PORTA, 0}, // A0 22 + {&DDRA, &PINA, &PORTA, 1}, // A1 23 + {&DDRA, &PINA, &PORTA, 2}, // A2 24 + {&DDRA, &PINA, &PORTA, 3}, // A3 25 + {&DDRA, &PINA, &PORTA, 4}, // A4 26 + {&DDRA, &PINA, &PORTA, 5}, // A5 27 + {&DDRA, &PINA, &PORTA, 6}, // A6 28 + {&DDRA, &PINA, &PORTA, 7}, // A7 29 + {&DDRC, &PINC, &PORTC, 7}, // C7 30 + {&DDRC, &PINC, &PORTC, 6}, // C6 31 + {&DDRC, &PINC, &PORTC, 5}, // C5 32 + {&DDRC, &PINC, &PORTC, 4}, // C4 33 + {&DDRC, &PINC, &PORTC, 3}, // C3 34 + {&DDRC, &PINC, &PORTC, 2}, // C2 35 + {&DDRC, &PINC, &PORTC, 1}, // C1 36 + {&DDRC, &PINC, &PORTC, 0}, // C0 37 + {&DDRD, &PIND, &PORTD, 7}, // D7 38 + {&DDRG, &PING, &PORTG, 2}, // G2 39 + {&DDRG, &PING, &PORTG, 1}, // G1 40 + {&DDRG, &PING, &PORTG, 0}, // G0 41 + {&DDRL, &PINL, &PORTL, 7}, // L7 42 + {&DDRL, &PINL, &PORTL, 6}, // L6 43 + {&DDRL, &PINL, &PORTL, 5}, // L5 44 + {&DDRL, &PINL, &PORTL, 4}, // L4 45 + {&DDRL, &PINL, &PORTL, 3}, // L3 46 + {&DDRL, &PINL, &PORTL, 2}, // L2 47 + {&DDRL, &PINL, &PORTL, 1}, // L1 48 + {&DDRL, &PINL, &PORTL, 0}, // L0 49 + {&DDRB, &PINB, &PORTB, 3}, // B3 50 + {&DDRB, &PINB, &PORTB, 2}, // B2 51 + {&DDRB, &PINB, &PORTB, 1}, // B1 52 + {&DDRB, &PINB, &PORTB, 0}, // B0 53 + {&DDRF, &PINF, &PORTF, 0}, // F0 54 + {&DDRF, &PINF, &PORTF, 1}, // F1 55 + {&DDRF, &PINF, &PORTF, 2}, // F2 56 + {&DDRF, &PINF, &PORTF, 3}, // F3 57 + {&DDRF, &PINF, &PORTF, 4}, // F4 58 + {&DDRF, &PINF, &PORTF, 5}, // F5 59 + {&DDRF, &PINF, &PORTF, 6}, // F6 60 + {&DDRF, &PINF, &PORTF, 7}, // F7 61 + {&DDRK, &PINK, &PORTK, 0}, // K0 62 + {&DDRK, &PINK, &PORTK, 1}, // K1 63 + {&DDRK, &PINK, &PORTK, 2}, // K2 64 + {&DDRK, &PINK, &PORTK, 3}, // K3 65 + {&DDRK, &PINK, &PORTK, 4}, // K4 66 + {&DDRK, &PINK, &PORTK, 5}, // K5 67 + {&DDRK, &PINK, &PORTK, 6}, // K6 68 + {&DDRK, &PINK, &PORTK, 7} // K7 69 +}; +//------------------------------------------------------------------------------ +#elif (defined(__AVR_ATmega644P__) || defined(__AVR_ATmega1284P__)) && defined(CORE_MICRODUINO) +// Microduino Core+ + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 20; +uint8_t const SCL_PIN = 21; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 PD0 + {&DDRD, &PIND, &PORTD, 1}, // D1 PD1 + {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 + {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 + {&DDRB, &PINB, &PORTB, 0}, // D4 PB0 + {&DDRB, &PINB, &PORTB, 1}, // D5 PB1 + {&DDRB, &PINB, &PORTB, 2}, // D6 PB2 + {&DDRB, &PINB, &PORTB, 3}, // D7 PB3 + {&DDRD, &PIND, &PORTD, 6}, // D8 PD6 + {&DDRD, &PIND, &PORTD, 5}, // D9 PD5 + {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 + {&DDRB, &PINB, &PORTB, 5}, // D11 PB5 + {&DDRB, &PINB, &PORTB, 6}, // D12 PB6 + {&DDRB, &PINB, &PORTB, 7}, // D13 PB7 + {&DDRC, &PINC, &PORTC, 7}, // D14 PC7 + {&DDRC, &PINC, &PORTC, 6}, // D15 PC6 + {&DDRC, &PINC, &PORTC, 5}, // D16 PC5 + {&DDRC, &PINC, &PORTC, 4}, // D17 PC4 + {&DDRC, &PINC, &PORTC, 3}, // D18 PC3 + {&DDRC, &PINC, &PORTC, 2}, // D19 PC2 + {&DDRC, &PINC, &PORTC, 1}, // D20 PC1 + {&DDRC, &PINC, &PORTC, 0}, // D21 PC0 + {&DDRD, &PIND, &PORTD, 4}, // D22 PD4 + {&DDRD, &PIND, &PORTD, 7}, // D23 PD7 + {&DDRA, &PINA, &PORTA, 7}, // D24 PA7 + {&DDRA, &PINA, &PORTA, 6}, // D25 PA6 + {&DDRA, &PINA, &PORTA, 5}, // D26 PA5 + {&DDRA, &PINA, &PORTA, 4}, // D27 PA4 + {&DDRA, &PINA, &PORTA, 3}, // D28 PA3 + {&DDRA, &PINA, &PORTA, 2}, // D29 PA2 + {&DDRA, &PINA, &PORTA, 1}, // D30 PA1 + {&DDRA, &PINA, &PORTA, 0} // D31 PA0 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega128RFA1__) && defined(CORE_MICRODUINO) +// Microduino Core RF + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PINE, &PORTE, 0}, // D0 PE0 + {&DDRD, &PINE, &PORTE, 1}, // D1 PE1 + {&DDRD, &PIND, &PORTD, 2}, // D2 PD2 + {&DDRD, &PIND, &PORTD, 3}, // D3 PD3 + {&DDRB, &PINE, &PORTE, 3}, // D4 PE3 + {&DDRB, &PINE, &PORTE, 4}, // D5 PE4 + {&DDRB, &PINE, &PORTE, 5}, // D6 PE5 + {&DDRB, &PINB, &PORTB, 7}, // D7 PB7 + {&DDRD, &PINB, &PORTB, 6}, // D8 PB6 + {&DDRD, &PINB, &PORTB, 5}, // D9 PB5 + {&DDRB, &PINB, &PORTB, 4}, // D10 PB4 + {&DDRB, &PINB, &PORTB, 2}, // D11 PB2 + {&DDRB, &PINB, &PORTB, 3}, // D12 PB3 + {&DDRB, &PINB, &PORTB, 1}, // D13 PB1 + {&DDRF, &PINF, &PORTF, 7}, // D14 PF7 + {&DDRF, &PINF, &PORTF, 6}, // D15 PF6 + {&DDRF, &PINF, &PORTF, 5}, // D16 PF5 + {&DDRF, &PINF, &PORTF, 4}, // D17 PF4 + {&DDRD, &PIND, &PORTD, 1}, // D18 PD1 + {&DDRD, &PIND, &PORTD, 0}, // D19 PD0 + {&DDRF, &PINF, &PORTF, 3}, // D20 PF3 + {&DDRF, &PINF, &PORTF, 2}, // D21 PF2 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega32U4__) && defined(CORE_MICRODUINO) +// Microduino Core USB + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 2}, // D0 - PD2 + {&DDRD, &PIND, &PORTD, 3}, // D1 - PD3 + {&DDRE, &PINE, &PORTE, 6}, // D2 - PE6 + {&DDRD, &PIND, &PORTD, 6}, // D3 - PD6 + {&DDRD, &PIND, &PORTD, 7}, // D4 - PD7 + {&DDRC, &PINC, &PORTC, 6}, // D5 - PC6 + {&DDRC, &PINC, &PORTC, 7}, // D6 - PC7 + {&DDRE, &PINE, &PORTE, 7}, // D7 - PE7 + {&DDRB, &PINB, &PORTB, 6}, // D8 - PB6 + {&DDRB, &PINB, &PORTB, 5}, // D9 - PB5 + {&DDRB, &PINB, &PORTB, 0}, // D10 - PB0 + {&DDRB, &PINB, &PORTB, 2}, // D11 - MOSI - PB2 + {&DDRB, &PINB, &PORTB, 3}, // D12 -MISO - PB3 + {&DDRB, &PINB, &PORTB, 1}, // D13 -SCK - PB1 + {&DDRF, &PINF, &PORTF, 7}, // D14 - A0 - PF7 + {&DDRF, &PINF, &PORTF, 6}, // D15 - A1 - PF6 + {&DDRF, &PINF, &PORTF, 5}, // D16 - A2 - PF5 + {&DDRF, &PINF, &PORTF, 4}, // D17 - A3 - PF4 + {&DDRD, &PIND, &PORTD, 1}, // D18 - PD1 + {&DDRD, &PIND, &PORTD, 0}, // D19 - PD0 + {&DDRF, &PINF, &PORTF, 1}, // D20 - A6 - PF1 + {&DDRF, &PINF, &PORTF, 0}, // D21 - A7 - PF0 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega644P__) || defined(__AVR_ATmega644__) +// Sanguino + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 17; +uint8_t const SCL_PIN = 18; + +// SPI port +uint8_t const SS_PIN = 4; +uint8_t const MOSI_PIN = 5; +uint8_t const MISO_PIN = 6; +uint8_t const SCK_PIN = 7; + +static const pin_map_t digitalPinMap[] = { + {&DDRB, &PINB, &PORTB, 0}, // B0 0 + {&DDRB, &PINB, &PORTB, 1}, // B1 1 + {&DDRB, &PINB, &PORTB, 2}, // B2 2 + {&DDRB, &PINB, &PORTB, 3}, // B3 3 + {&DDRB, &PINB, &PORTB, 4}, // B4 4 + {&DDRB, &PINB, &PORTB, 5}, // B5 5 + {&DDRB, &PINB, &PORTB, 6}, // B6 6 + {&DDRB, &PINB, &PORTB, 7}, // B7 7 + {&DDRD, &PIND, &PORTD, 0}, // D0 8 + {&DDRD, &PIND, &PORTD, 1}, // D1 9 + {&DDRD, &PIND, &PORTD, 2}, // D2 10 + {&DDRD, &PIND, &PORTD, 3}, // D3 11 + {&DDRD, &PIND, &PORTD, 4}, // D4 12 + {&DDRD, &PIND, &PORTD, 5}, // D5 13 + {&DDRD, &PIND, &PORTD, 6}, // D6 14 + {&DDRD, &PIND, &PORTD, 7}, // D7 15 + {&DDRC, &PINC, &PORTC, 0}, // C0 16 + {&DDRC, &PINC, &PORTC, 1}, // C1 17 + {&DDRC, &PINC, &PORTC, 2}, // C2 18 + {&DDRC, &PINC, &PORTC, 3}, // C3 19 + {&DDRC, &PINC, &PORTC, 4}, // C4 20 + {&DDRC, &PINC, &PORTC, 5}, // C5 21 + {&DDRC, &PINC, &PORTC, 6}, // C6 22 + {&DDRC, &PINC, &PORTC, 7}, // C7 23 + {&DDRA, &PINA, &PORTA, 7}, // A7 24 + {&DDRA, &PINA, &PORTA, 6}, // A6 25 + {&DDRA, &PINA, &PORTA, 5}, // A5 26 + {&DDRA, &PINA, &PORTA, 4}, // A4 27 + {&DDRA, &PINA, &PORTA, 3}, // A3 28 + {&DDRA, &PINA, &PORTA, 2}, // A2 29 + {&DDRA, &PINA, &PORTA, 1}, // A1 30 + {&DDRA, &PINA, &PORTA, 0} // A0 31 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_ATmega32U4__) +// Leonardo + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 2; +uint8_t const SCL_PIN = 3; + +// SPI port +uint8_t const SS_PIN = 17; +uint8_t const MOSI_PIN = 16; +uint8_t const MISO_PIN = 14; +uint8_t const SCK_PIN = 15; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 2}, // D2 0 + {&DDRD, &PIND, &PORTD, 3}, // D3 1 + {&DDRD, &PIND, &PORTD, 1}, // D1 2 + {&DDRD, &PIND, &PORTD, 0}, // D0 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRC, &PINC, &PORTC, 6}, // C6 5 + {&DDRD, &PIND, &PORTD, 7}, // D7 6 + {&DDRE, &PINE, &PORTE, 6}, // E6 7 + {&DDRB, &PINB, &PORTB, 4}, // B4 8 + {&DDRB, &PINB, &PORTB, 5}, // B5 9 + {&DDRB, &PINB, &PORTB, 6}, // B6 10 + {&DDRB, &PINB, &PORTB, 7}, // B7 11 + {&DDRD, &PIND, &PORTD, 6}, // D6 12 + {&DDRC, &PINC, &PORTC, 7}, // C7 13 + {&DDRB, &PINB, &PORTB, 3}, // B3 14 + {&DDRB, &PINB, &PORTB, 1}, // B1 15 + {&DDRB, &PINB, &PORTB, 2}, // B2 16 + {&DDRB, &PINB, &PORTB, 0}, // B0 17 + {&DDRF, &PINF, &PORTF, 7}, // F7 18 + {&DDRF, &PINF, &PORTF, 6}, // F6 19 + {&DDRF, &PINF, &PORTF, 5}, // F5 20 + {&DDRF, &PINF, &PORTF, 4}, // F4 21 + {&DDRF, &PINF, &PORTF, 1}, // F1 22 + {&DDRF, &PINF, &PORTF, 0}, // F0 23 +}; +//------------------------------------------------------------------------------ +#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) +// Teensy++ 1.0 & 2.0 + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 1; +uint8_t const SCL_PIN = 0; + +// SPI port +uint8_t const SS_PIN = 20; +uint8_t const MOSI_PIN = 22; +uint8_t const MISO_PIN = 23; +uint8_t const SCK_PIN = 21; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 0 + {&DDRD, &PIND, &PORTD, 1}, // D1 1 + {&DDRD, &PIND, &PORTD, 2}, // D2 2 + {&DDRD, &PIND, &PORTD, 3}, // D3 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRD, &PIND, &PORTD, 5}, // D5 5 + {&DDRD, &PIND, &PORTD, 6}, // D6 6 + {&DDRD, &PIND, &PORTD, 7}, // D7 7 + {&DDRE, &PINE, &PORTE, 0}, // E0 8 + {&DDRE, &PINE, &PORTE, 1}, // E1 9 + {&DDRC, &PINC, &PORTC, 0}, // C0 10 + {&DDRC, &PINC, &PORTC, 1}, // C1 11 + {&DDRC, &PINC, &PORTC, 2}, // C2 12 + {&DDRC, &PINC, &PORTC, 3}, // C3 13 + {&DDRC, &PINC, &PORTC, 4}, // C4 14 + {&DDRC, &PINC, &PORTC, 5}, // C5 15 + {&DDRC, &PINC, &PORTC, 6}, // C6 16 + {&DDRC, &PINC, &PORTC, 7}, // C7 17 + {&DDRE, &PINE, &PORTE, 6}, // E6 18 + {&DDRE, &PINE, &PORTE, 7}, // E7 19 + {&DDRB, &PINB, &PORTB, 0}, // B0 20 + {&DDRB, &PINB, &PORTB, 1}, // B1 21 + {&DDRB, &PINB, &PORTB, 2}, // B2 22 + {&DDRB, &PINB, &PORTB, 3}, // B3 23 + {&DDRB, &PINB, &PORTB, 4}, // B4 24 + {&DDRB, &PINB, &PORTB, 5}, // B5 25 + {&DDRB, &PINB, &PORTB, 6}, // B6 26 + {&DDRB, &PINB, &PORTB, 7}, // B7 27 + {&DDRA, &PINA, &PORTA, 0}, // A0 28 + {&DDRA, &PINA, &PORTA, 1}, // A1 29 + {&DDRA, &PINA, &PORTA, 2}, // A2 30 + {&DDRA, &PINA, &PORTA, 3}, // A3 31 + {&DDRA, &PINA, &PORTA, 4}, // A4 32 + {&DDRA, &PINA, &PORTA, 5}, // A5 33 + {&DDRA, &PINA, &PORTA, 6}, // A6 34 + {&DDRA, &PINA, &PORTA, 7}, // A7 35 + {&DDRE, &PINE, &PORTE, 4}, // E4 36 + {&DDRE, &PINE, &PORTE, 5}, // E5 37 + {&DDRF, &PINF, &PORTF, 0}, // F0 38 + {&DDRF, &PINF, &PORTF, 1}, // F1 39 + {&DDRF, &PINF, &PORTF, 2}, // F2 40 + {&DDRF, &PINF, &PORTF, 3}, // F3 41 + {&DDRF, &PINF, &PORTF, 4}, // F4 42 + {&DDRF, &PINF, &PORTF, 5}, // F5 43 + {&DDRF, &PINF, &PORTF, 6}, // F6 44 + {&DDRF, &PINF, &PORTF, 7} // F7 45 +}; +//------------------------------------------------------------------------------ +#else // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +// 168 and 328 Arduinos + +// Two Wire (aka I2C) ports +uint8_t const SDA_PIN = 18; +uint8_t const SCL_PIN = 19; + +// SPI port +uint8_t const SS_PIN = 10; +uint8_t const MOSI_PIN = 11; +uint8_t const MISO_PIN = 12; +uint8_t const SCK_PIN = 13; + +static const pin_map_t digitalPinMap[] = { + {&DDRD, &PIND, &PORTD, 0}, // D0 0 + {&DDRD, &PIND, &PORTD, 1}, // D1 1 + {&DDRD, &PIND, &PORTD, 2}, // D2 2 + {&DDRD, &PIND, &PORTD, 3}, // D3 3 + {&DDRD, &PIND, &PORTD, 4}, // D4 4 + {&DDRD, &PIND, &PORTD, 5}, // D5 5 + {&DDRD, &PIND, &PORTD, 6}, // D6 6 + {&DDRD, &PIND, &PORTD, 7}, // D7 7 + {&DDRB, &PINB, &PORTB, 0}, // B0 8 + {&DDRB, &PINB, &PORTB, 1}, // B1 9 + {&DDRB, &PINB, &PORTB, 2}, // B2 10 + {&DDRB, &PINB, &PORTB, 3}, // B3 11 + {&DDRB, &PINB, &PORTB, 4}, // B4 12 + {&DDRB, &PINB, &PORTB, 5}, // B5 13 + {&DDRC, &PINC, &PORTC, 0}, // C0 14 + {&DDRC, &PINC, &PORTC, 1}, // C1 15 + {&DDRC, &PINC, &PORTC, 2}, // C2 16 + {&DDRC, &PINC, &PORTC, 3}, // C3 17 + {&DDRC, &PINC, &PORTC, 4}, // C4 18 + {&DDRC, &PINC, &PORTC, 5} // C5 19 +}; +#endif // defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) +//------------------------------------------------------------------------------ +static const uint8_t digitalPinCount = sizeof(digitalPinMap) / sizeof(pin_map_t); + +uint8_t badPinNumber(void) +__attribute__((error("Pin number is too large or not a constant"))); + +static inline __attribute__((always_inline)) +uint8_t getPinMode(uint8_t pin) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + return (*digitalPinMap[pin].ddr >> digitalPinMap[pin].bit) & 1; + } else { + return badPinNumber(); + } +} +static inline __attribute__((always_inline)) +void setPinMode(uint8_t pin, uint8_t mode) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + if (mode) { + *digitalPinMap[pin].ddr |= 1 << digitalPinMap[pin].bit; + } else { + *digitalPinMap[pin].ddr &= ~(1 << digitalPinMap[pin].bit); + } + } else { + badPinNumber(); + } +} +static inline __attribute__((always_inline)) +uint8_t fastDigitalRead(uint8_t pin) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + return (*digitalPinMap[pin].pin >> digitalPinMap[pin].bit) & 1; + } else { + return badPinNumber(); + } +} +static inline __attribute__((always_inline)) +void fastDigitalWrite(uint8_t pin, uint8_t value) { + if (__builtin_constant_p(pin) && pin < digitalPinCount) { + if (value) { + *digitalPinMap[pin].port |= 1 << digitalPinMap[pin].bit; + } else { + *digitalPinMap[pin].port &= ~(1 << digitalPinMap[pin].bit); + } + } else { + badPinNumber(); + } +} +#endif // Sd2PinMap_h + +#elif defined (__CPU_ARC__) + +#if defined (__ARDUINO_ARC__) + // Two Wire (aka I2C) ports + uint8_t const SDA_PIN = 18; + uint8_t const SCL_PIN = 19; + + // SPI port + uint8_t const SS_PIN = 10; + uint8_t const MOSI_PIN = 11; + uint8_t const MISO_PIN = 12; + uint8_t const SCK_PIN = 13; + +#endif // Arduino ARC + +#else +#error Architecture or board not supported. +#endif diff --git a/megaavr/libraries/SD/src/utility/SdFat.h b/megaavr/libraries/SD/src/utility/SdFat.h index 46b880b..1c73615 100755 --- a/megaavr/libraries/SD/src/utility/SdFat.h +++ b/megaavr/libraries/SD/src/utility/SdFat.h @@ -1,641 +1,641 @@ -/* Arduino SdFat Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#ifndef SdFat_h -#define SdFat_h -/** - \file - SdFile and SdVolume classes -*/ -#if defined (__AVR__) || defined (__CPU_ARC__) - #include -#endif -#include "Sd2Card.h" -#include "FatStructs.h" -#include -//------------------------------------------------------------------------------ -/** - Allow use of deprecated functions if non-zero -*/ -#define ALLOW_DEPRECATED_FUNCTIONS 1 -//------------------------------------------------------------------------------ -// forward declaration since SdVolume is used in SdFile -class SdVolume; -//============================================================================== -// SdFile class - -#ifdef O_RDONLY //ARDUINO_ARCH_MBED - #undef O_READ - #undef O_RDONLY - #undef O_WRITE - #undef O_WRONLY - #undef O_RDWR - #undef O_ACCMODE - #undef O_APPEND - #undef O_SYNC - #undef O_CREAT - #undef O_EXCL - #undef O_TRUNC -#endif - -// flags for ls() -/** ls() flag to print modify date */ -uint8_t const LS_DATE = 1; -/** ls() flag to print file size */ -uint8_t const LS_SIZE = 2; -/** ls() flag for recursive list of subdirectories */ -uint8_t const LS_R = 4; - -// use the gnu style oflag in open() -/** open() oflag for reading */ -uint8_t const O_READ = 0X01; -/** open() oflag - same as O_READ */ -uint8_t const O_RDONLY = O_READ; -/** open() oflag for write */ -uint8_t const O_WRITE = 0X02; -/** open() oflag - same as O_WRITE */ -uint8_t const O_WRONLY = O_WRITE; -/** open() oflag for reading and writing */ -uint8_t const O_RDWR = (O_READ | O_WRITE); -/** open() oflag mask for access modes */ -uint8_t const O_ACCMODE = (O_READ | O_WRITE); -/** The file offset shall be set to the end of the file prior to each write. */ -uint8_t const O_APPEND = 0X04; -/** synchronous writes - call sync() after each write */ -uint8_t const O_SYNC = 0X08; -/** create the file if nonexistent */ -uint8_t const O_CREAT = 0X10; -/** If O_CREAT and O_EXCL are set, open() shall fail if the file exists */ -uint8_t const O_EXCL = 0X20; -/** truncate the file to zero length */ -uint8_t const O_TRUNC = 0X40; - -// flags for timestamp -/** set the file's last access date */ -uint8_t const T_ACCESS = 1; -/** set the file's creation date and time */ -uint8_t const T_CREATE = 2; -/** Set the file's write date and time */ -uint8_t const T_WRITE = 4; -// values for type_ -/** This SdFile has not been opened. */ -uint8_t const FAT_FILE_TYPE_CLOSED = 0; -/** SdFile for a file */ -uint8_t const FAT_FILE_TYPE_NORMAL = 1; -/** SdFile for a FAT16 root directory */ -uint8_t const FAT_FILE_TYPE_ROOT16 = 2; -/** SdFile for a FAT32 root directory */ -uint8_t const FAT_FILE_TYPE_ROOT32 = 3; -/** SdFile for a subdirectory */ -uint8_t const FAT_FILE_TYPE_SUBDIR = 4; -/** Test value for directory type */ -uint8_t const FAT_FILE_TYPE_MIN_DIR = FAT_FILE_TYPE_ROOT16; - -/** date field for FAT directory entry */ -static inline uint16_t FAT_DATE(uint16_t year, uint8_t month, uint8_t day) { - return (year - 1980) << 9 | month << 5 | day; -} -/** year part of FAT directory date field */ -static inline uint16_t FAT_YEAR(uint16_t fatDate) { - return 1980 + (fatDate >> 9); -} -/** month part of FAT directory date field */ -static inline uint8_t FAT_MONTH(uint16_t fatDate) { - return (fatDate >> 5) & 0XF; -} -/** day part of FAT directory date field */ -static inline uint8_t FAT_DAY(uint16_t fatDate) { - return fatDate & 0X1F; -} -/** time field for FAT directory entry */ -static inline uint16_t FAT_TIME(uint8_t hour, uint8_t minute, uint8_t second) { - return hour << 11 | minute << 5 | second >> 1; -} -/** hour part of FAT directory time field */ -static inline uint8_t FAT_HOUR(uint16_t fatTime) { - return fatTime >> 11; -} -/** minute part of FAT directory time field */ -static inline uint8_t FAT_MINUTE(uint16_t fatTime) { - return (fatTime >> 5) & 0X3F; -} -/** second part of FAT directory time field */ -static inline uint8_t FAT_SECOND(uint16_t fatTime) { - return 2 * (fatTime & 0X1F); -} -/** Default date for file timestamps is 1 Jan 2000 */ -uint16_t const FAT_DEFAULT_DATE = ((2000 - 1980) << 9) | (1 << 5) | 1; -/** Default time for file timestamp is 1 am */ -uint16_t const FAT_DEFAULT_TIME = (1 << 11); -//------------------------------------------------------------------------------ -/** - \class SdFile - \brief Access FAT16 and FAT32 files on SD and SDHC cards. -*/ -class SdFile : public Print { - public: - /** Create an instance of SdFile. */ - SdFile(void) : type_(FAT_FILE_TYPE_CLOSED) {} - /** - writeError is set to true if an error occurs during a write(). - Set writeError to false before calling print() and/or write() and check - for true after calls to print() and/or write(). - */ - //bool writeError; - /** - Cancel unbuffered reads for this file. - See setUnbufferedRead() - */ - void clearUnbufferedRead(void) { - flags_ &= ~F_FILE_UNBUFFERED_READ; - } - uint8_t close(void); - uint8_t contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); - uint8_t createContiguous(SdFile* dirFile, - const char* fileName, uint32_t size); - /** \return The current cluster number for a file or directory. */ - uint32_t curCluster(void) const { - return curCluster_; - } - /** \return The current position for a file or directory. */ - uint32_t curPosition(void) const { - return curPosition_; - } - /** - Set the date/time callback function - - \param[in] dateTime The user's call back function. The callback - function is of the form: - - \code - void dateTime(uint16_t* date, uint16_t* time) { - uint16_t year; - uint8_t month, day, hour, minute, second; - - // User gets date and time from GPS or real-time clock here - - // return date using FAT_DATE macro to format fields - * *date = FAT_DATE(year, month, day); - - // return time using FAT_TIME macro to format fields - * *time = FAT_TIME(hour, minute, second); - } - \endcode - - Sets the function that is called when a file is created or when - a file's directory entry is modified by sync(). All timestamps, - access, creation, and modify, are set when a file is created. - sync() maintains the last access date and last modify date/time. - - See the timestamp() function. - */ - static void dateTimeCallback( - void (*dateTime)(uint16_t* date, uint16_t* time)) { - dateTime_ = dateTime; - } - /** - Cancel the date/time callback function. - */ - static void dateTimeCallbackCancel(void) { - // use explicit zero since NULL is not defined for Sanguino - dateTime_ = 0; - } - /** \return Address of the block that contains this file's directory. */ - uint32_t dirBlock(void) const { - return dirBlock_; - } - uint8_t dirEntry(dir_t* dir); - /** \return Index of this file's directory in the block dirBlock. */ - uint8_t dirIndex(void) const { - return dirIndex_; - } - static void dirName(const dir_t& dir, char* name); - /** \return The total number of bytes in a file or directory. */ - uint32_t fileSize(void) const { - return fileSize_; - } - /** \return The first cluster number for a file or directory. */ - uint32_t firstCluster(void) const { - return firstCluster_; - } - /** \return True if this is a SdFile for a directory else false. */ - uint8_t isDir(void) const { - return type_ >= FAT_FILE_TYPE_MIN_DIR; - } - /** \return True if this is a SdFile for a file else false. */ - uint8_t isFile(void) const { - return type_ == FAT_FILE_TYPE_NORMAL; - } - /** \return True if this is a SdFile for an open file/directory else false. */ - uint8_t isOpen(void) const { - return type_ != FAT_FILE_TYPE_CLOSED; - } - /** \return True if this is a SdFile for a subdirectory else false. */ - uint8_t isSubDir(void) const { - return type_ == FAT_FILE_TYPE_SUBDIR; - } - /** \return True if this is a SdFile for the root directory. */ - uint8_t isRoot(void) const { - return type_ == FAT_FILE_TYPE_ROOT16 || type_ == FAT_FILE_TYPE_ROOT32; - } - void ls(uint8_t flags = 0, uint8_t indent = 0); - uint8_t makeDir(SdFile* dir, const char* dirName); - uint8_t open(SdFile* dirFile, uint16_t index, uint8_t oflag); - uint8_t open(SdFile* dirFile, const char* fileName, uint8_t oflag); - - uint8_t openRoot(SdVolume* vol); - static void printDirName(const dir_t& dir, uint8_t width); - static void printFatDate(uint16_t fatDate); - static void printFatTime(uint16_t fatTime); - static void printTwoDigits(uint8_t v); - /** - Read the next byte from a file. - - \return For success read returns the next byte in the file as an int. - If an error occurs or end of file is reached -1 is returned. - */ - int16_t read(void) { - uint8_t b; - return read(&b, 1) == 1 ? b : -1; - } - int16_t read(void* buf, uint16_t nbyte); - int8_t readDir(dir_t* dir); - static uint8_t remove(SdFile* dirFile, const char* fileName); - uint8_t remove(void); - /** Set the file's current position to zero. */ - void rewind(void) { - curPosition_ = curCluster_ = 0; - } - uint8_t rmDir(void); - uint8_t rmRfStar(void); - /** Set the files position to current position + \a pos. See seekSet(). */ - uint8_t seekCur(uint32_t pos) { - return seekSet(curPosition_ + pos); - } - /** - Set the files current position to end of file. Useful to position - a file for append. See seekSet(). - */ - uint8_t seekEnd(void) { - return seekSet(fileSize_); - } - uint8_t seekSet(uint32_t pos); - /** - Use unbuffered reads to access this file. Used with Wave - Shield ISR. Used with Sd2Card::partialBlockRead() in WaveRP. - - Not recommended for normal applications. - */ - void setUnbufferedRead(void) { - if (isFile()) { - flags_ |= F_FILE_UNBUFFERED_READ; - } - } - uint8_t timestamp(uint8_t flag, uint16_t year, uint8_t month, uint8_t day, - uint8_t hour, uint8_t minute, uint8_t second); - uint8_t sync(uint8_t blocking = 1); - /** Type of this SdFile. You should use isFile() or isDir() instead of type() - if possible. - - \return The file or directory type. - */ - uint8_t type(void) const { - return type_; - } - uint8_t truncate(uint32_t size); - /** \return Unbuffered read flag. */ - uint8_t unbufferedRead(void) const { - return flags_ & F_FILE_UNBUFFERED_READ; - } - /** \return SdVolume that contains this file. */ - SdVolume* volume(void) const { - return vol_; - } - size_t write(uint8_t b); - size_t write(const void* buf, uint16_t nbyte); - size_t write(const char* str); - #ifdef __AVR__ - void write_P(PGM_P str); - void writeln_P(PGM_P str); - #endif - int availableForWrite(void); - //------------------------------------------------------------------------------ - #if ALLOW_DEPRECATED_FUNCTIONS - // Deprecated functions - suppress cpplint warnings with NOLINT comment - /** \deprecated Use: - uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); - */ - uint8_t contiguousRange(uint32_t& bgnBlock, uint32_t& endBlock) { // NOLINT - return contiguousRange(&bgnBlock, &endBlock); - } - /** \deprecated Use: - uint8_t SdFile::createContiguous(SdFile* dirFile, - const char* fileName, uint32_t size) - */ - uint8_t createContiguous(SdFile& dirFile, // NOLINT - const char* fileName, uint32_t size) { - return createContiguous(&dirFile, fileName, size); - } - - /** - \deprecated Use: - static void SdFile::dateTimeCallback( - void (*dateTime)(uint16_t* date, uint16_t* time)); - */ - static void dateTimeCallback( - void (*dateTime)(uint16_t& date, uint16_t& time)) { // NOLINT - oldDateTime_ = dateTime; - dateTime_ = dateTime ? oldToNew : 0; - } - /** \deprecated Use: uint8_t SdFile::dirEntry(dir_t* dir); */ - uint8_t dirEntry(dir_t& dir) { - return dirEntry(&dir); // NOLINT - } - /** \deprecated Use: - uint8_t SdFile::makeDir(SdFile* dir, const char* dirName); - */ - uint8_t makeDir(SdFile& dir, const char* dirName) { // NOLINT - return makeDir(&dir, dirName); - } - /** \deprecated Use: - uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag); - */ - uint8_t open(SdFile& dirFile, // NOLINT - const char* fileName, uint8_t oflag) { - return open(&dirFile, fileName, oflag); - } - /** \deprecated Do not use in new apps */ - uint8_t open(SdFile& dirFile, const char* fileName) { // NOLINT - return open(dirFile, fileName, O_RDWR); - } - /** \deprecated Use: - uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag); - */ - uint8_t open(SdFile& dirFile, uint16_t index, uint8_t oflag) { // NOLINT - return open(&dirFile, index, oflag); - } - /** \deprecated Use: uint8_t SdFile::openRoot(SdVolume* vol); */ - uint8_t openRoot(SdVolume& vol) { - return openRoot(&vol); // NOLINT - } - - /** \deprecated Use: int8_t SdFile::readDir(dir_t* dir); */ - int8_t readDir(dir_t& dir) { - return readDir(&dir); // NOLINT - } - /** \deprecated Use: - static uint8_t SdFile::remove(SdFile* dirFile, const char* fileName); - */ - static uint8_t remove(SdFile& dirFile, const char* fileName) { // NOLINT - return remove(&dirFile, fileName); - } - //------------------------------------------------------------------------------ - // rest are private - private: - static void (*oldDateTime_)(uint16_t& date, uint16_t& time); // NOLINT - static void oldToNew(uint16_t* date, uint16_t* time) { - uint16_t d; - uint16_t t; - oldDateTime_(d, t); - *date = d; - *time = t; - } - #endif // ALLOW_DEPRECATED_FUNCTIONS - private: - // bits defined in flags_ - // should be 0XF - static uint8_t const F_OFLAG = (O_ACCMODE | O_APPEND | O_SYNC); - // available bits - static uint8_t const F_FILE_NON_BLOCKING_WRITE = 0X10; - // a new cluster was added to the file - static uint8_t const F_FILE_CLUSTER_ADDED = 0X20; - // use unbuffered SD read - static uint8_t const F_FILE_UNBUFFERED_READ = 0X40; - // sync of directory entry required - static uint8_t const F_FILE_DIR_DIRTY = 0X80; - - // make sure F_OFLAG is ok - #if ((F_FILE_NON_BLOCKING_WRITE | F_FILE_CLUSTER_ADDED | F_FILE_UNBUFFERED_READ | F_FILE_DIR_DIRTY) & F_OFLAG) -#error flags_ bits conflict - #endif // flags_ bits - - // private data - uint8_t flags_; // See above for definition of flags_ bits - uint8_t type_; // type of file see above for values - uint32_t curCluster_; // cluster for current file position - uint32_t curPosition_; // current file position in bytes from beginning - uint32_t dirBlock_; // SD block that contains directory entry for file - uint8_t dirIndex_; // index of entry in dirBlock 0 <= dirIndex_ <= 0XF - uint32_t fileSize_; // file size in bytes - uint32_t firstCluster_; // first cluster of file - SdVolume* vol_; // volume where file is located - - // private functions - uint8_t addCluster(void); - uint8_t addDirCluster(void); - dir_t* cacheDirEntry(uint8_t action); - static void (*dateTime_)(uint16_t* date, uint16_t* time); - static uint8_t make83Name(const char* str, uint8_t* name); - uint8_t openCachedEntry(uint8_t cacheIndex, uint8_t oflags); - dir_t* readDirCache(void); -}; -//============================================================================== -// SdVolume class -/** - \brief Cache for an SD data block -*/ -union cache_t { - /** Used to access cached file data blocks. */ - uint8_t data[512]; - /** Used to access cached FAT16 entries. */ - uint16_t fat16[256]; - /** Used to access cached FAT32 entries. */ - uint32_t fat32[128]; - /** Used to access cached directory entries. */ - dir_t dir[16]; - /** Used to access a cached MasterBoot Record. */ - mbr_t mbr; - /** Used to access to a cached FAT boot sector. */ - fbs_t fbs; -}; -//------------------------------------------------------------------------------ -/** - \class SdVolume - \brief Access FAT16 and FAT32 volumes on SD and SDHC cards. -*/ -class SdVolume { - public: - /** Create an instance of SdVolume */ - SdVolume(void) : allocSearchStart_(2), fatType_(0) {} - /** Clear the cache and returns a pointer to the cache. Used by the WaveRP - recorder to do raw write to the SD card. Not for normal apps. - */ - static uint8_t* cacheClear(void) { - cacheFlush(); - cacheBlockNumber_ = 0XFFFFFFFF; - return cacheBuffer_.data; - } - /** - Initialize a FAT volume. Try partition one first then try super - floppy format. - - \param[in] dev The Sd2Card where the volume is located. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. Reasons for - failure include not finding a valid partition, not finding a valid - FAT file system or an I/O error. - */ - uint8_t init(Sd2Card* dev) { - return init(dev, 1) ? true : init(dev, 0); - } - uint8_t init(Sd2Card* dev, uint8_t part); - - // inline functions that return volume info - /** \return The volume's cluster size in blocks. */ - uint8_t blocksPerCluster(void) const { - return blocksPerCluster_; - } - /** \return The number of blocks in one FAT. */ - uint32_t blocksPerFat(void) const { - return blocksPerFat_; - } - /** \return The total number of clusters in the volume. */ - uint32_t clusterCount(void) const { - return clusterCount_; - } - /** \return The shift count required to multiply by blocksPerCluster. */ - uint8_t clusterSizeShift(void) const { - return clusterSizeShift_; - } - /** \return The logical block number for the start of file data. */ - uint32_t dataStartBlock(void) const { - return dataStartBlock_; - } - /** \return The number of FAT structures on the volume. */ - uint8_t fatCount(void) const { - return fatCount_; - } - /** \return The logical block number for the start of the first FAT. */ - uint32_t fatStartBlock(void) const { - return fatStartBlock_; - } - /** \return The FAT type of the volume. Values are 12, 16 or 32. */ - uint8_t fatType(void) const { - return fatType_; - } - /** \return The number of entries in the root directory for FAT16 volumes. */ - uint32_t rootDirEntryCount(void) const { - return rootDirEntryCount_; - } - /** \return The logical block number for the start of the root directory - on FAT16 volumes or the first cluster number on FAT32 volumes. */ - uint32_t rootDirStart(void) const { - return rootDirStart_; - } - /** return a pointer to the Sd2Card object for this volume */ - static Sd2Card* sdCard(void) { - return sdCard_; - } - //------------------------------------------------------------------------------ - #if ALLOW_DEPRECATED_FUNCTIONS - // Deprecated functions - suppress cpplint warnings with NOLINT comment - /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev); */ - uint8_t init(Sd2Card& dev) { - return init(&dev); // NOLINT - } - - /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev, uint8_t vol); */ - uint8_t init(Sd2Card& dev, uint8_t part) { // NOLINT - return init(&dev, part); - } - #endif // ALLOW_DEPRECATED_FUNCTIONS - //------------------------------------------------------------------------------ - private: - // Allow SdFile access to SdVolume private data. - friend class SdFile; - - // value for action argument in cacheRawBlock to indicate read from cache - static uint8_t const CACHE_FOR_READ = 0; - // value for action argument in cacheRawBlock to indicate cache dirty - static uint8_t const CACHE_FOR_WRITE = 1; - - static cache_t cacheBuffer_; // 512 byte cache for device blocks - static uint32_t cacheBlockNumber_; // Logical number of block in the cache - static Sd2Card* sdCard_; // Sd2Card object for cache - static uint8_t cacheDirty_; // cacheFlush() will write block if true - static uint32_t cacheMirrorBlock_; // block number for mirror FAT - // - uint32_t allocSearchStart_; // start cluster for alloc search - uint8_t blocksPerCluster_; // cluster size in blocks - uint32_t blocksPerFat_; // FAT size in blocks - uint32_t clusterCount_; // clusters in one FAT - uint8_t clusterSizeShift_; // shift to convert cluster count to block count - uint32_t dataStartBlock_; // first data block number - uint8_t fatCount_; // number of FATs on volume - uint32_t fatStartBlock_; // start block for first FAT - uint8_t fatType_; // volume type (12, 16, OR 32) - uint16_t rootDirEntryCount_; // number of entries in FAT16 root dir - uint32_t rootDirStart_; // root start block for FAT16, cluster for FAT32 - //---------------------------------------------------------------------------- - uint8_t allocContiguous(uint32_t count, uint32_t* curCluster); - uint8_t blockOfCluster(uint32_t position) const { - return (position >> 9) & (blocksPerCluster_ - 1); - } - uint32_t clusterStartBlock(uint32_t cluster) const { - return dataStartBlock_ + ((cluster - 2) << clusterSizeShift_); - } - uint32_t blockNumber(uint32_t cluster, uint32_t position) const { - return clusterStartBlock(cluster) + blockOfCluster(position); - } - static uint8_t cacheFlush(uint8_t blocking = 1); - static uint8_t cacheMirrorBlockFlush(uint8_t blocking); - static uint8_t cacheRawBlock(uint32_t blockNumber, uint8_t action); - static void cacheSetDirty(void) { - cacheDirty_ |= CACHE_FOR_WRITE; - } - static uint8_t cacheZeroBlock(uint32_t blockNumber); - uint8_t chainSize(uint32_t beginCluster, uint32_t* size) const; - uint8_t fatGet(uint32_t cluster, uint32_t* value) const; - uint8_t fatPut(uint32_t cluster, uint32_t value); - uint8_t fatPutEOC(uint32_t cluster) { - return fatPut(cluster, 0x0FFFFFFF); - } - uint8_t freeChain(uint32_t cluster); - uint8_t isEOC(uint32_t cluster) const { - return cluster >= (fatType_ == 16 ? FAT16EOC_MIN : FAT32EOC_MIN); - } - uint8_t readBlock(uint32_t block, uint8_t* dst) { - return sdCard_->readBlock(block, dst); - } - uint8_t readData(uint32_t block, uint16_t offset, - uint16_t count, uint8_t* dst) { - return sdCard_->readData(block, offset, count, dst); - } - uint8_t writeBlock(uint32_t block, const uint8_t* dst, uint8_t blocking = 1) { - return sdCard_->writeBlock(block, dst, blocking); - } - uint8_t isBusy(void) { - return sdCard_->isBusy(); - } - uint8_t isCacheMirrorBlockDirty(void) { - return (cacheMirrorBlock_ != 0); - } -}; -#endif // SdFat_h +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef SdFat_h +#define SdFat_h +/** + \file + SdFile and SdVolume classes +*/ +#if defined (__AVR__) || defined (__CPU_ARC__) + #include +#endif +#include "Sd2Card.h" +#include "FatStructs.h" +#include +//------------------------------------------------------------------------------ +/** + Allow use of deprecated functions if non-zero +*/ +#define ALLOW_DEPRECATED_FUNCTIONS 1 +//------------------------------------------------------------------------------ +// forward declaration since SdVolume is used in SdFile +class SdVolume; +//============================================================================== +// SdFile class + +#ifdef O_RDONLY //ARDUINO_ARCH_MBED + #undef O_READ + #undef O_RDONLY + #undef O_WRITE + #undef O_WRONLY + #undef O_RDWR + #undef O_ACCMODE + #undef O_APPEND + #undef O_SYNC + #undef O_CREAT + #undef O_EXCL + #undef O_TRUNC +#endif + +// flags for ls() +/** ls() flag to print modify date */ +uint8_t const LS_DATE = 1; +/** ls() flag to print file size */ +uint8_t const LS_SIZE = 2; +/** ls() flag for recursive list of subdirectories */ +uint8_t const LS_R = 4; + +// use the gnu style oflag in open() +/** open() oflag for reading */ +uint8_t const O_READ = 0X01; +/** open() oflag - same as O_READ */ +uint8_t const O_RDONLY = O_READ; +/** open() oflag for write */ +uint8_t const O_WRITE = 0X02; +/** open() oflag - same as O_WRITE */ +uint8_t const O_WRONLY = O_WRITE; +/** open() oflag for reading and writing */ +uint8_t const O_RDWR = (O_READ | O_WRITE); +/** open() oflag mask for access modes */ +uint8_t const O_ACCMODE = (O_READ | O_WRITE); +/** The file offset shall be set to the end of the file prior to each write. */ +uint8_t const O_APPEND = 0X04; +/** synchronous writes - call sync() after each write */ +uint8_t const O_SYNC = 0X08; +/** create the file if nonexistent */ +uint8_t const O_CREAT = 0X10; +/** If O_CREAT and O_EXCL are set, open() shall fail if the file exists */ +uint8_t const O_EXCL = 0X20; +/** truncate the file to zero length */ +uint8_t const O_TRUNC = 0X40; + +// flags for timestamp +/** set the file's last access date */ +uint8_t const T_ACCESS = 1; +/** set the file's creation date and time */ +uint8_t const T_CREATE = 2; +/** Set the file's write date and time */ +uint8_t const T_WRITE = 4; +// values for type_ +/** This SdFile has not been opened. */ +uint8_t const FAT_FILE_TYPE_CLOSED = 0; +/** SdFile for a file */ +uint8_t const FAT_FILE_TYPE_NORMAL = 1; +/** SdFile for a FAT16 root directory */ +uint8_t const FAT_FILE_TYPE_ROOT16 = 2; +/** SdFile for a FAT32 root directory */ +uint8_t const FAT_FILE_TYPE_ROOT32 = 3; +/** SdFile for a subdirectory */ +uint8_t const FAT_FILE_TYPE_SUBDIR = 4; +/** Test value for directory type */ +uint8_t const FAT_FILE_TYPE_MIN_DIR = FAT_FILE_TYPE_ROOT16; + +/** date field for FAT directory entry */ +static inline uint16_t FAT_DATE(uint16_t year, uint8_t month, uint8_t day) { + return (year - 1980) << 9 | month << 5 | day; +} +/** year part of FAT directory date field */ +static inline uint16_t FAT_YEAR(uint16_t fatDate) { + return 1980 + (fatDate >> 9); +} +/** month part of FAT directory date field */ +static inline uint8_t FAT_MONTH(uint16_t fatDate) { + return (fatDate >> 5) & 0XF; +} +/** day part of FAT directory date field */ +static inline uint8_t FAT_DAY(uint16_t fatDate) { + return fatDate & 0X1F; +} +/** time field for FAT directory entry */ +static inline uint16_t FAT_TIME(uint8_t hour, uint8_t minute, uint8_t second) { + return hour << 11 | minute << 5 | second >> 1; +} +/** hour part of FAT directory time field */ +static inline uint8_t FAT_HOUR(uint16_t fatTime) { + return fatTime >> 11; +} +/** minute part of FAT directory time field */ +static inline uint8_t FAT_MINUTE(uint16_t fatTime) { + return (fatTime >> 5) & 0X3F; +} +/** second part of FAT directory time field */ +static inline uint8_t FAT_SECOND(uint16_t fatTime) { + return 2 * (fatTime & 0X1F); +} +/** Default date for file timestamps is 1 Jan 2000 */ +uint16_t const FAT_DEFAULT_DATE = ((2000 - 1980) << 9) | (1 << 5) | 1; +/** Default time for file timestamp is 1 am */ +uint16_t const FAT_DEFAULT_TIME = (1 << 11); +//------------------------------------------------------------------------------ +/** + \class SdFile + \brief Access FAT16 and FAT32 files on SD and SDHC cards. +*/ +class SdFile : public Print { + public: + /** Create an instance of SdFile. */ + SdFile(void) : type_(FAT_FILE_TYPE_CLOSED) {} + /** + writeError is set to true if an error occurs during a write(). + Set writeError to false before calling print() and/or write() and check + for true after calls to print() and/or write(). + */ + //bool writeError; + /** + Cancel unbuffered reads for this file. + See setUnbufferedRead() + */ + void clearUnbufferedRead(void) { + flags_ &= ~F_FILE_UNBUFFERED_READ; + } + uint8_t close(void); + uint8_t contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); + uint8_t createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size); + /** \return The current cluster number for a file or directory. */ + uint32_t curCluster(void) const { + return curCluster_; + } + /** \return The current position for a file or directory. */ + uint32_t curPosition(void) const { + return curPosition_; + } + /** + Set the date/time callback function + + \param[in] dateTime The user's call back function. The callback + function is of the form: + + \code + void dateTime(uint16_t* date, uint16_t* time) { + uint16_t year; + uint8_t month, day, hour, minute, second; + + // User gets date and time from GPS or real-time clock here + + // return date using FAT_DATE macro to format fields + * *date = FAT_DATE(year, month, day); + + // return time using FAT_TIME macro to format fields + * *time = FAT_TIME(hour, minute, second); + } + \endcode + + Sets the function that is called when a file is created or when + a file's directory entry is modified by sync(). All timestamps, + access, creation, and modify, are set when a file is created. + sync() maintains the last access date and last modify date/time. + + See the timestamp() function. + */ + static void dateTimeCallback( + void (*dateTime)(uint16_t* date, uint16_t* time)) { + dateTime_ = dateTime; + } + /** + Cancel the date/time callback function. + */ + static void dateTimeCallbackCancel(void) { + // use explicit zero since NULL is not defined for Sanguino + dateTime_ = 0; + } + /** \return Address of the block that contains this file's directory. */ + uint32_t dirBlock(void) const { + return dirBlock_; + } + uint8_t dirEntry(dir_t* dir); + /** \return Index of this file's directory in the block dirBlock. */ + uint8_t dirIndex(void) const { + return dirIndex_; + } + static void dirName(const dir_t& dir, char* name); + /** \return The total number of bytes in a file or directory. */ + uint32_t fileSize(void) const { + return fileSize_; + } + /** \return The first cluster number for a file or directory. */ + uint32_t firstCluster(void) const { + return firstCluster_; + } + /** \return True if this is a SdFile for a directory else false. */ + uint8_t isDir(void) const { + return type_ >= FAT_FILE_TYPE_MIN_DIR; + } + /** \return True if this is a SdFile for a file else false. */ + uint8_t isFile(void) const { + return type_ == FAT_FILE_TYPE_NORMAL; + } + /** \return True if this is a SdFile for an open file/directory else false. */ + uint8_t isOpen(void) const { + return type_ != FAT_FILE_TYPE_CLOSED; + } + /** \return True if this is a SdFile for a subdirectory else false. */ + uint8_t isSubDir(void) const { + return type_ == FAT_FILE_TYPE_SUBDIR; + } + /** \return True if this is a SdFile for the root directory. */ + uint8_t isRoot(void) const { + return type_ == FAT_FILE_TYPE_ROOT16 || type_ == FAT_FILE_TYPE_ROOT32; + } + void ls(uint8_t flags = 0, uint8_t indent = 0); + uint8_t makeDir(SdFile* dir, const char* dirName); + uint8_t open(SdFile* dirFile, uint16_t index, uint8_t oflag); + uint8_t open(SdFile* dirFile, const char* fileName, uint8_t oflag); + + uint8_t openRoot(SdVolume* vol); + static void printDirName(const dir_t& dir, uint8_t width); + static void printFatDate(uint16_t fatDate); + static void printFatTime(uint16_t fatTime); + static void printTwoDigits(uint8_t v); + /** + Read the next byte from a file. + + \return For success read returns the next byte in the file as an int. + If an error occurs or end of file is reached -1 is returned. + */ + int16_t read(void) { + uint8_t b; + return read(&b, 1) == 1 ? b : -1; + } + int16_t read(void* buf, uint16_t nbyte); + int8_t readDir(dir_t* dir); + static uint8_t remove(SdFile* dirFile, const char* fileName); + uint8_t remove(void); + /** Set the file's current position to zero. */ + void rewind(void) { + curPosition_ = curCluster_ = 0; + } + uint8_t rmDir(void); + uint8_t rmRfStar(void); + /** Set the files position to current position + \a pos. See seekSet(). */ + uint8_t seekCur(uint32_t pos) { + return seekSet(curPosition_ + pos); + } + /** + Set the files current position to end of file. Useful to position + a file for append. See seekSet(). + */ + uint8_t seekEnd(void) { + return seekSet(fileSize_); + } + uint8_t seekSet(uint32_t pos); + /** + Use unbuffered reads to access this file. Used with Wave + Shield ISR. Used with Sd2Card::partialBlockRead() in WaveRP. + + Not recommended for normal applications. + */ + void setUnbufferedRead(void) { + if (isFile()) { + flags_ |= F_FILE_UNBUFFERED_READ; + } + } + uint8_t timestamp(uint8_t flag, uint16_t year, uint8_t month, uint8_t day, + uint8_t hour, uint8_t minute, uint8_t second); + uint8_t sync(uint8_t blocking = 1); + /** Type of this SdFile. You should use isFile() or isDir() instead of type() + if possible. + + \return The file or directory type. + */ + uint8_t type(void) const { + return type_; + } + uint8_t truncate(uint32_t size); + /** \return Unbuffered read flag. */ + uint8_t unbufferedRead(void) const { + return flags_ & F_FILE_UNBUFFERED_READ; + } + /** \return SdVolume that contains this file. */ + SdVolume* volume(void) const { + return vol_; + } + size_t write(uint8_t b); + size_t write(const void* buf, uint16_t nbyte); + size_t write(const char* str); + #ifdef __AVR__ + void write_P(PGM_P str); + void writeln_P(PGM_P str); + #endif + int availableForWrite(void); + //------------------------------------------------------------------------------ + #if ALLOW_DEPRECATED_FUNCTIONS + // Deprecated functions - suppress cpplint warnings with NOLINT comment + /** \deprecated Use: + uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock); + */ + uint8_t contiguousRange(uint32_t& bgnBlock, uint32_t& endBlock) { // NOLINT + return contiguousRange(&bgnBlock, &endBlock); + } + /** \deprecated Use: + uint8_t SdFile::createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size) + */ + uint8_t createContiguous(SdFile& dirFile, // NOLINT + const char* fileName, uint32_t size) { + return createContiguous(&dirFile, fileName, size); + } + + /** + \deprecated Use: + static void SdFile::dateTimeCallback( + void (*dateTime)(uint16_t* date, uint16_t* time)); + */ + static void dateTimeCallback( + void (*dateTime)(uint16_t& date, uint16_t& time)) { // NOLINT + oldDateTime_ = dateTime; + dateTime_ = dateTime ? oldToNew : 0; + } + /** \deprecated Use: uint8_t SdFile::dirEntry(dir_t* dir); */ + uint8_t dirEntry(dir_t& dir) { + return dirEntry(&dir); // NOLINT + } + /** \deprecated Use: + uint8_t SdFile::makeDir(SdFile* dir, const char* dirName); + */ + uint8_t makeDir(SdFile& dir, const char* dirName) { // NOLINT + return makeDir(&dir, dirName); + } + /** \deprecated Use: + uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag); + */ + uint8_t open(SdFile& dirFile, // NOLINT + const char* fileName, uint8_t oflag) { + return open(&dirFile, fileName, oflag); + } + /** \deprecated Do not use in new apps */ + uint8_t open(SdFile& dirFile, const char* fileName) { // NOLINT + return open(dirFile, fileName, O_RDWR); + } + /** \deprecated Use: + uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag); + */ + uint8_t open(SdFile& dirFile, uint16_t index, uint8_t oflag) { // NOLINT + return open(&dirFile, index, oflag); + } + /** \deprecated Use: uint8_t SdFile::openRoot(SdVolume* vol); */ + uint8_t openRoot(SdVolume& vol) { + return openRoot(&vol); // NOLINT + } + + /** \deprecated Use: int8_t SdFile::readDir(dir_t* dir); */ + int8_t readDir(dir_t& dir) { + return readDir(&dir); // NOLINT + } + /** \deprecated Use: + static uint8_t SdFile::remove(SdFile* dirFile, const char* fileName); + */ + static uint8_t remove(SdFile& dirFile, const char* fileName) { // NOLINT + return remove(&dirFile, fileName); + } + //------------------------------------------------------------------------------ + // rest are private + private: + static void (*oldDateTime_)(uint16_t& date, uint16_t& time); // NOLINT + static void oldToNew(uint16_t* date, uint16_t* time) { + uint16_t d; + uint16_t t; + oldDateTime_(d, t); + *date = d; + *time = t; + } + #endif // ALLOW_DEPRECATED_FUNCTIONS + private: + // bits defined in flags_ + // should be 0XF + static uint8_t const F_OFLAG = (O_ACCMODE | O_APPEND | O_SYNC); + // available bits + static uint8_t const F_FILE_NON_BLOCKING_WRITE = 0X10; + // a new cluster was added to the file + static uint8_t const F_FILE_CLUSTER_ADDED = 0X20; + // use unbuffered SD read + static uint8_t const F_FILE_UNBUFFERED_READ = 0X40; + // sync of directory entry required + static uint8_t const F_FILE_DIR_DIRTY = 0X80; + + // make sure F_OFLAG is ok + #if ((F_FILE_NON_BLOCKING_WRITE | F_FILE_CLUSTER_ADDED | F_FILE_UNBUFFERED_READ | F_FILE_DIR_DIRTY) & F_OFLAG) +#error flags_ bits conflict + #endif // flags_ bits + + // private data + uint8_t flags_; // See above for definition of flags_ bits + uint8_t type_; // type of file see above for values + uint32_t curCluster_; // cluster for current file position + uint32_t curPosition_; // current file position in bytes from beginning + uint32_t dirBlock_; // SD block that contains directory entry for file + uint8_t dirIndex_; // index of entry in dirBlock 0 <= dirIndex_ <= 0XF + uint32_t fileSize_; // file size in bytes + uint32_t firstCluster_; // first cluster of file + SdVolume* vol_; // volume where file is located + + // private functions + uint8_t addCluster(void); + uint8_t addDirCluster(void); + dir_t* cacheDirEntry(uint8_t action); + static void (*dateTime_)(uint16_t* date, uint16_t* time); + static uint8_t make83Name(const char* str, uint8_t* name); + uint8_t openCachedEntry(uint8_t cacheIndex, uint8_t oflags); + dir_t* readDirCache(void); +}; +//============================================================================== +// SdVolume class +/** + \brief Cache for an SD data block +*/ +union cache_t { + /** Used to access cached file data blocks. */ + uint8_t data[512]; + /** Used to access cached FAT16 entries. */ + uint16_t fat16[256]; + /** Used to access cached FAT32 entries. */ + uint32_t fat32[128]; + /** Used to access cached directory entries. */ + dir_t dir[16]; + /** Used to access a cached MasterBoot Record. */ + mbr_t mbr; + /** Used to access to a cached FAT boot sector. */ + fbs_t fbs; +}; +//------------------------------------------------------------------------------ +/** + \class SdVolume + \brief Access FAT16 and FAT32 volumes on SD and SDHC cards. +*/ +class SdVolume { + public: + /** Create an instance of SdVolume */ + SdVolume(void) : allocSearchStart_(2), fatType_(0) {} + /** Clear the cache and returns a pointer to the cache. Used by the WaveRP + recorder to do raw write to the SD card. Not for normal apps. + */ + static uint8_t* cacheClear(void) { + cacheFlush(); + cacheBlockNumber_ = 0XFFFFFFFF; + return cacheBuffer_.data; + } + /** + Initialize a FAT volume. Try partition one first then try super + floppy format. + + \param[in] dev The Sd2Card where the volume is located. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. Reasons for + failure include not finding a valid partition, not finding a valid + FAT file system or an I/O error. + */ + uint8_t init(Sd2Card* dev) { + return init(dev, 1) ? true : init(dev, 0); + } + uint8_t init(Sd2Card* dev, uint8_t part); + + // inline functions that return volume info + /** \return The volume's cluster size in blocks. */ + uint8_t blocksPerCluster(void) const { + return blocksPerCluster_; + } + /** \return The number of blocks in one FAT. */ + uint32_t blocksPerFat(void) const { + return blocksPerFat_; + } + /** \return The total number of clusters in the volume. */ + uint32_t clusterCount(void) const { + return clusterCount_; + } + /** \return The shift count required to multiply by blocksPerCluster. */ + uint8_t clusterSizeShift(void) const { + return clusterSizeShift_; + } + /** \return The logical block number for the start of file data. */ + uint32_t dataStartBlock(void) const { + return dataStartBlock_; + } + /** \return The number of FAT structures on the volume. */ + uint8_t fatCount(void) const { + return fatCount_; + } + /** \return The logical block number for the start of the first FAT. */ + uint32_t fatStartBlock(void) const { + return fatStartBlock_; + } + /** \return The FAT type of the volume. Values are 12, 16 or 32. */ + uint8_t fatType(void) const { + return fatType_; + } + /** \return The number of entries in the root directory for FAT16 volumes. */ + uint32_t rootDirEntryCount(void) const { + return rootDirEntryCount_; + } + /** \return The logical block number for the start of the root directory + on FAT16 volumes or the first cluster number on FAT32 volumes. */ + uint32_t rootDirStart(void) const { + return rootDirStart_; + } + /** return a pointer to the Sd2Card object for this volume */ + static Sd2Card* sdCard(void) { + return sdCard_; + } + //------------------------------------------------------------------------------ + #if ALLOW_DEPRECATED_FUNCTIONS + // Deprecated functions - suppress cpplint warnings with NOLINT comment + /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev); */ + uint8_t init(Sd2Card& dev) { + return init(&dev); // NOLINT + } + + /** \deprecated Use: uint8_t SdVolume::init(Sd2Card* dev, uint8_t vol); */ + uint8_t init(Sd2Card& dev, uint8_t part) { // NOLINT + return init(&dev, part); + } + #endif // ALLOW_DEPRECATED_FUNCTIONS + //------------------------------------------------------------------------------ + private: + // Allow SdFile access to SdVolume private data. + friend class SdFile; + + // value for action argument in cacheRawBlock to indicate read from cache + static uint8_t const CACHE_FOR_READ = 0; + // value for action argument in cacheRawBlock to indicate cache dirty + static uint8_t const CACHE_FOR_WRITE = 1; + + static cache_t cacheBuffer_; // 512 byte cache for device blocks + static uint32_t cacheBlockNumber_; // Logical number of block in the cache + static Sd2Card* sdCard_; // Sd2Card object for cache + static uint8_t cacheDirty_; // cacheFlush() will write block if true + static uint32_t cacheMirrorBlock_; // block number for mirror FAT + // + uint32_t allocSearchStart_; // start cluster for alloc search + uint8_t blocksPerCluster_; // cluster size in blocks + uint32_t blocksPerFat_; // FAT size in blocks + uint32_t clusterCount_; // clusters in one FAT + uint8_t clusterSizeShift_; // shift to convert cluster count to block count + uint32_t dataStartBlock_; // first data block number + uint8_t fatCount_; // number of FATs on volume + uint32_t fatStartBlock_; // start block for first FAT + uint8_t fatType_; // volume type (12, 16, OR 32) + uint16_t rootDirEntryCount_; // number of entries in FAT16 root dir + uint32_t rootDirStart_; // root start block for FAT16, cluster for FAT32 + //---------------------------------------------------------------------------- + uint8_t allocContiguous(uint32_t count, uint32_t* curCluster); + uint8_t blockOfCluster(uint32_t position) const { + return (position >> 9) & (blocksPerCluster_ - 1); + } + uint32_t clusterStartBlock(uint32_t cluster) const { + return dataStartBlock_ + ((cluster - 2) << clusterSizeShift_); + } + uint32_t blockNumber(uint32_t cluster, uint32_t position) const { + return clusterStartBlock(cluster) + blockOfCluster(position); + } + static uint8_t cacheFlush(uint8_t blocking = 1); + static uint8_t cacheMirrorBlockFlush(uint8_t blocking); + static uint8_t cacheRawBlock(uint32_t blockNumber, uint8_t action); + static void cacheSetDirty(void) { + cacheDirty_ |= CACHE_FOR_WRITE; + } + static uint8_t cacheZeroBlock(uint32_t blockNumber); + uint8_t chainSize(uint32_t beginCluster, uint32_t* size) const; + uint8_t fatGet(uint32_t cluster, uint32_t* value) const; + uint8_t fatPut(uint32_t cluster, uint32_t value); + uint8_t fatPutEOC(uint32_t cluster) { + return fatPut(cluster, 0x0FFFFFFF); + } + uint8_t freeChain(uint32_t cluster); + uint8_t isEOC(uint32_t cluster) const { + return cluster >= (fatType_ == 16 ? FAT16EOC_MIN : FAT32EOC_MIN); + } + uint8_t readBlock(uint32_t block, uint8_t* dst) { + return sdCard_->readBlock(block, dst); + } + uint8_t readData(uint32_t block, uint16_t offset, + uint16_t count, uint8_t* dst) { + return sdCard_->readData(block, offset, count, dst); + } + uint8_t writeBlock(uint32_t block, const uint8_t* dst, uint8_t blocking = 1) { + return sdCard_->writeBlock(block, dst, blocking); + } + uint8_t isBusy(void) { + return sdCard_->isBusy(); + } + uint8_t isCacheMirrorBlockDirty(void) { + return (cacheMirrorBlock_ != 0); + } +}; +#endif // SdFat_h diff --git a/megaavr/libraries/SD/src/utility/SdFatUtil.h b/megaavr/libraries/SD/src/utility/SdFatUtil.h index 4b93de8..2fb6289 100755 --- a/megaavr/libraries/SD/src/utility/SdFatUtil.h +++ b/megaavr/libraries/SD/src/utility/SdFatUtil.h @@ -1,77 +1,77 @@ -/* Arduino SdFat Library - Copyright (C) 2008 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#ifndef SdFatUtil_h -#define SdFatUtil_h -/** - \file - Useful utility functions. -*/ -#include -#ifdef __AVR__ - #include - /** Store and print a string in flash memory.*/ - #define PgmPrint(x) SerialPrint_P(PSTR(x)) - /** Store and print a string in flash memory followed by a CR/LF.*/ - #define PgmPrintln(x) SerialPrintln_P(PSTR(x)) - /** Defined so doxygen works for function definitions. */ -#endif -#define NOINLINE __attribute__((noinline,unused)) -#define UNUSEDOK __attribute__((unused)) -//------------------------------------------------------------------------------ -/** Return the number of bytes currently free in RAM. */ -static UNUSEDOK int FreeRam(void) { - extern int __bss_end; - extern int* __brkval; - int free_memory; - if (reinterpret_cast(__brkval) == 0) { - // if no heap use from end of bss section - free_memory = reinterpret_cast(&free_memory) - - reinterpret_cast(&__bss_end); - } else { - // use from top of stack to heap - free_memory = reinterpret_cast(&free_memory) - - reinterpret_cast(__brkval); - } - return free_memory; -} -#ifdef __AVR__ -//------------------------------------------------------------------------------ -/** - %Print a string in flash memory to the serial port. - - \param[in] str Pointer to string stored in flash memory. -*/ -static NOINLINE void SerialPrint_P(PGM_P str) { - for (uint8_t c; (c = pgm_read_byte(str)); str++) { - Serial.write(c); - } -} -//------------------------------------------------------------------------------ -/** - %Print a string in flash memory followed by a CR/LF. - - \param[in] str Pointer to string stored in flash memory. -*/ -static NOINLINE void SerialPrintln_P(PGM_P str) { - SerialPrint_P(str); - Serial.println(); -} -#endif // __AVR__ -#endif // #define SdFatUtil_h +/* Arduino SdFat Library + Copyright (C) 2008 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#ifndef SdFatUtil_h +#define SdFatUtil_h +/** + \file + Useful utility functions. +*/ +#include +#ifdef __AVR__ + #include + /** Store and print a string in flash memory.*/ + #define PgmPrint(x) SerialPrint_P(PSTR(x)) + /** Store and print a string in flash memory followed by a CR/LF.*/ + #define PgmPrintln(x) SerialPrintln_P(PSTR(x)) + /** Defined so doxygen works for function definitions. */ +#endif +#define NOINLINE __attribute__((noinline,unused)) +#define UNUSEDOK __attribute__((unused)) +//------------------------------------------------------------------------------ +/** Return the number of bytes currently free in RAM. */ +static UNUSEDOK int FreeRam(void) { + extern int __bss_end; + extern int* __brkval; + int free_memory; + if (reinterpret_cast(__brkval) == 0) { + // if no heap use from end of bss section + free_memory = reinterpret_cast(&free_memory) + - reinterpret_cast(&__bss_end); + } else { + // use from top of stack to heap + free_memory = reinterpret_cast(&free_memory) + - reinterpret_cast(__brkval); + } + return free_memory; +} +#ifdef __AVR__ +//------------------------------------------------------------------------------ +/** + %Print a string in flash memory to the serial port. + + \param[in] str Pointer to string stored in flash memory. +*/ +static NOINLINE void SerialPrint_P(PGM_P str) { + for (uint8_t c; (c = pgm_read_byte(str)); str++) { + Serial.write(c); + } +} +//------------------------------------------------------------------------------ +/** + %Print a string in flash memory followed by a CR/LF. + + \param[in] str Pointer to string stored in flash memory. +*/ +static NOINLINE void SerialPrintln_P(PGM_P str) { + SerialPrint_P(str); + Serial.println(); +} +#endif // __AVR__ +#endif // #define SdFatUtil_h diff --git a/megaavr/libraries/SD/src/utility/SdFatmainpage.h b/megaavr/libraries/SD/src/utility/SdFatmainpage.h index 1e6d96f..0a42e85 100755 --- a/megaavr/libraries/SD/src/utility/SdFatmainpage.h +++ b/megaavr/libraries/SD/src/utility/SdFatmainpage.h @@ -1,202 +1,202 @@ -/* Arduino SdFat Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ - -/** - \mainpage Arduino SdFat Library -
Copyright © 2009 by William Greiman -
- - \section Intro Introduction - The Arduino SdFat Library is a minimal implementation of FAT16 and FAT32 - file systems on SD flash memory cards. Standard SD and high capacity - SDHC cards are supported. - - The SdFat only supports short 8.3 names. - - The main classes in SdFat are Sd2Card, SdVolume, and SdFile. - - The Sd2Card class supports access to standard SD cards and SDHC cards. Most - applications will only need to call the Sd2Card::init() member function. - - The SdVolume class supports FAT16 and FAT32 partitions. Most applications - will only need to call the SdVolume::init() member function. - - The SdFile class provides file access functions such as open(), read(), - remove(), write(), close() and sync(). This class supports access to the root - directory and subdirectories. - - A number of example are provided in the SdFat/examples folder. These were - developed to test SdFat and illustrate its use. - - SdFat was developed for high speed data recording. SdFat was used to implement - an audio record/play class, WaveRP, for the Adafruit Wave Shield. This - application uses special Sd2Card calls to write to contiguous files in raw mode. - These functions reduce write latency so that audio can be recorded with the - small amount of RAM in the Arduino. - - \section SDcard SD\SDHC Cards - - Arduinos access SD cards using the cards SPI protocol. PCs, Macs, and - most consumer devices use the 4-bit parallel SD protocol. A card that - functions well on A PC or Mac may not work well on the Arduino. - - Most cards have good SPI read performance but cards vary widely in SPI - write performance. Write performance is limited by how efficiently the - card manages internal erase/remapping operations. The Arduino cannot - optimize writes to reduce erase operations because of its limit RAM. - - SanDisk cards generally have good write performance. They seem to have - more internal RAM buffering than other cards and therefore can limit - the number of flash erase operations that the Arduino forces due to its - limited RAM. - - \section Hardware Hardware Configuration - - SdFat was developed using an - Adafruit Industries - Wave Shield. - - The hardware interface to the SD card should not use a resistor based level - shifter. SdFat sets the SPI bus frequency to 8 MHz which results in signal - rise times that are too slow for the edge detectors in many newer SD card - controllers when resistor voltage dividers are used. - - The 5 to 3.3 V level shifter for 5 V Arduinos should be IC based like the - 74HC4050N based circuit shown in the file SdLevel.png. The Adafruit Wave Shield - uses a 74AHC125N. Gravitech sells SD and MicroSD Card Adapters based on the - 74LCX245. - - If you are using a resistor based level shifter and are having problems try - setting the SPI bus frequency to 4 MHz. This can be done by using - card.init(SPI_HALF_SPEED) to initialize the SD card. - - \section comment Bugs and Comments - - If you wish to report bugs or have comments, send email to fat16lib@sbcglobal.net. - - \section SdFatClass SdFat Usage - - SdFat uses a slightly restricted form of short names. - Only printable ASCII characters are supported. No characters with code point - values greater than 127 are allowed. Space is not allowed even though space - was allowed in the API of early versions of DOS. - - Short names are limited to 8 characters followed by an optional period (.) - and extension of up to 3 characters. The characters may be any combination - of letters and digits. The following special characters are also allowed: - - $ % ' - _ @ ~ ` ! ( ) { } ^ # & - - Short names are always converted to upper case and their original case - value is lost. - - \note - The Arduino Print class uses character - at a time writes so it was necessary to use a \link SdFile::sync() sync() \endlink - function to control when data is written to the SD card. - - \par - An application which writes to a file using \link Print::print() print()\endlink, - \link Print::println() println() \endlink - or \link SdFile::write write() \endlink must call \link SdFile::sync() sync() \endlink - at the appropriate time to force data and directory information to be written - to the SD Card. Data and directory information are also written to the SD card - when \link SdFile::close() close() \endlink is called. - - \par - Applications must use care calling \link SdFile::sync() sync() \endlink - since 2048 bytes of I/O is required to update file and - directory information. This includes writing the current data block, reading - the block that contains the directory entry for update, writing the directory - block back and reading back the current data block. - - It is possible to open a file with two or more instances of SdFile. A file may - be corrupted if data is written to the file by more than one instance of SdFile. - - \section HowTo How to format SD Cards as FAT Volumes - - You should use a freshly formatted SD card for best performance. FAT - file systems become slower if many files have been created and deleted. - This is because the directory entry for a deleted file is marked as deleted, - but is not deleted. When a new file is created, these entries must be scanned - before creating the file, a flaw in the FAT design. Also files can become - fragmented which causes reads and writes to be slower. - - Microsoft operating systems support removable media formatted with a - Master Boot Record, MBR, or formatted as a super floppy with a FAT Boot Sector - in block zero. - - Microsoft operating systems expect MBR formatted removable media - to have only one partition. The first partition should be used. - - Microsoft operating systems do not support partitioning SD flash cards. - If you erase an SD card with a program like KillDisk, Most versions of - Windows will format the card as a super floppy. - - The best way to restore an SD card's format is to use SDFormatter - which can be downloaded from: - - http://www.sdcard.org/consumers/formatter/ - - SDFormatter aligns flash erase boundaries with file - system structures which reduces write latency and file system overhead. - - SDFormatter does not have an option for FAT type so it may format - small cards as FAT12. - - After the MBR is restored by SDFormatter you may need to reformat small - cards that have been formatted FAT12 to force the volume type to be FAT16. - - If you reformat the SD card with an OS utility, choose a cluster size that - will result in: - - 4084 < CountOfClusters && CountOfClusters < 65525 - - The volume will then be FAT16. - - If you are formatting an SD card on OS X or Linux, be sure to use the first - partition. Format this partition with a cluster count in above range. - - \section References References - - Adafruit Industries: - - http://www.adafruit.com/ - - http://www.ladyada.net/make/waveshield/ - - The Arduino site: - - http://www.arduino.cc/ - - For more information about FAT file systems see: - - http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx - - For information about using SD cards as SPI devices see: - - http://www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf - - The ATmega328 datasheet: - - http://www.atmel.com/dyn/resources/prod_documents/doc8161.pdf - - -*/ +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ + +/** + \mainpage Arduino SdFat Library +
Copyright © 2009 by William Greiman +
+ + \section Intro Introduction + The Arduino SdFat Library is a minimal implementation of FAT16 and FAT32 + file systems on SD flash memory cards. Standard SD and high capacity + SDHC cards are supported. + + The SdFat only supports short 8.3 names. + + The main classes in SdFat are Sd2Card, SdVolume, and SdFile. + + The Sd2Card class supports access to standard SD cards and SDHC cards. Most + applications will only need to call the Sd2Card::init() member function. + + The SdVolume class supports FAT16 and FAT32 partitions. Most applications + will only need to call the SdVolume::init() member function. + + The SdFile class provides file access functions such as open(), read(), + remove(), write(), close() and sync(). This class supports access to the root + directory and subdirectories. + + A number of example are provided in the SdFat/examples folder. These were + developed to test SdFat and illustrate its use. + + SdFat was developed for high speed data recording. SdFat was used to implement + an audio record/play class, WaveRP, for the Adafruit Wave Shield. This + application uses special Sd2Card calls to write to contiguous files in raw mode. + These functions reduce write latency so that audio can be recorded with the + small amount of RAM in the Arduino. + + \section SDcard SD\SDHC Cards + + Arduinos access SD cards using the cards SPI protocol. PCs, Macs, and + most consumer devices use the 4-bit parallel SD protocol. A card that + functions well on A PC or Mac may not work well on the Arduino. + + Most cards have good SPI read performance but cards vary widely in SPI + write performance. Write performance is limited by how efficiently the + card manages internal erase/remapping operations. The Arduino cannot + optimize writes to reduce erase operations because of its limit RAM. + + SanDisk cards generally have good write performance. They seem to have + more internal RAM buffering than other cards and therefore can limit + the number of flash erase operations that the Arduino forces due to its + limited RAM. + + \section Hardware Hardware Configuration + + SdFat was developed using an + Adafruit Industries + Wave Shield. + + The hardware interface to the SD card should not use a resistor based level + shifter. SdFat sets the SPI bus frequency to 8 MHz which results in signal + rise times that are too slow for the edge detectors in many newer SD card + controllers when resistor voltage dividers are used. + + The 5 to 3.3 V level shifter for 5 V Arduinos should be IC based like the + 74HC4050N based circuit shown in the file SdLevel.png. The Adafruit Wave Shield + uses a 74AHC125N. Gravitech sells SD and MicroSD Card Adapters based on the + 74LCX245. + + If you are using a resistor based level shifter and are having problems try + setting the SPI bus frequency to 4 MHz. This can be done by using + card.init(SPI_HALF_SPEED) to initialize the SD card. + + \section comment Bugs and Comments + + If you wish to report bugs or have comments, send email to fat16lib@sbcglobal.net. + + \section SdFatClass SdFat Usage + + SdFat uses a slightly restricted form of short names. + Only printable ASCII characters are supported. No characters with code point + values greater than 127 are allowed. Space is not allowed even though space + was allowed in the API of early versions of DOS. + + Short names are limited to 8 characters followed by an optional period (.) + and extension of up to 3 characters. The characters may be any combination + of letters and digits. The following special characters are also allowed: + + $ % ' - _ @ ~ ` ! ( ) { } ^ # & + + Short names are always converted to upper case and their original case + value is lost. + + \note + The Arduino Print class uses character + at a time writes so it was necessary to use a \link SdFile::sync() sync() \endlink + function to control when data is written to the SD card. + + \par + An application which writes to a file using \link Print::print() print()\endlink, + \link Print::println() println() \endlink + or \link SdFile::write write() \endlink must call \link SdFile::sync() sync() \endlink + at the appropriate time to force data and directory information to be written + to the SD Card. Data and directory information are also written to the SD card + when \link SdFile::close() close() \endlink is called. + + \par + Applications must use care calling \link SdFile::sync() sync() \endlink + since 2048 bytes of I/O is required to update file and + directory information. This includes writing the current data block, reading + the block that contains the directory entry for update, writing the directory + block back and reading back the current data block. + + It is possible to open a file with two or more instances of SdFile. A file may + be corrupted if data is written to the file by more than one instance of SdFile. + + \section HowTo How to format SD Cards as FAT Volumes + + You should use a freshly formatted SD card for best performance. FAT + file systems become slower if many files have been created and deleted. + This is because the directory entry for a deleted file is marked as deleted, + but is not deleted. When a new file is created, these entries must be scanned + before creating the file, a flaw in the FAT design. Also files can become + fragmented which causes reads and writes to be slower. + + Microsoft operating systems support removable media formatted with a + Master Boot Record, MBR, or formatted as a super floppy with a FAT Boot Sector + in block zero. + + Microsoft operating systems expect MBR formatted removable media + to have only one partition. The first partition should be used. + + Microsoft operating systems do not support partitioning SD flash cards. + If you erase an SD card with a program like KillDisk, Most versions of + Windows will format the card as a super floppy. + + The best way to restore an SD card's format is to use SDFormatter + which can be downloaded from: + + http://www.sdcard.org/consumers/formatter/ + + SDFormatter aligns flash erase boundaries with file + system structures which reduces write latency and file system overhead. + + SDFormatter does not have an option for FAT type so it may format + small cards as FAT12. + + After the MBR is restored by SDFormatter you may need to reformat small + cards that have been formatted FAT12 to force the volume type to be FAT16. + + If you reformat the SD card with an OS utility, choose a cluster size that + will result in: + + 4084 < CountOfClusters && CountOfClusters < 65525 + + The volume will then be FAT16. + + If you are formatting an SD card on OS X or Linux, be sure to use the first + partition. Format this partition with a cluster count in above range. + + \section References References + + Adafruit Industries: + + http://www.adafruit.com/ + + http://www.ladyada.net/make/waveshield/ + + The Arduino site: + + http://www.arduino.cc/ + + For more information about FAT file systems see: + + http://www.microsoft.com/whdc/system/platform/firmware/fatgen.mspx + + For information about using SD cards as SPI devices see: + + http://www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf + + The ATmega328 datasheet: + + http://www.atmel.com/dyn/resources/prod_documents/doc8161.pdf + + +*/ diff --git a/megaavr/libraries/SD/src/utility/SdFile.cpp b/megaavr/libraries/SD/src/utility/SdFile.cpp index 18a1db6..70be4b5 100755 --- a/megaavr/libraries/SD/src/utility/SdFile.cpp +++ b/megaavr/libraries/SD/src/utility/SdFile.cpp @@ -1,1527 +1,1527 @@ -/* Arduino SdFat Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#include "SdFat.h" -#ifdef __AVR__ - #include -#endif -#include -//------------------------------------------------------------------------------ -// callback function for date/time -void (*SdFile::dateTime_)(uint16_t* date, uint16_t* time) = NULL; - -#if ALLOW_DEPRECATED_FUNCTIONS - // suppress cpplint warnings with NOLINT comment - void (*SdFile::oldDateTime_)(uint16_t& date, uint16_t& time) = NULL; // NOLINT -#endif // ALLOW_DEPRECATED_FUNCTIONS -//------------------------------------------------------------------------------ -// add a cluster to a file -uint8_t SdFile::addCluster() { - if (!vol_->allocContiguous(1, &curCluster_)) { - return false; - } - - // if first cluster of file link to directory entry - if (firstCluster_ == 0) { - firstCluster_ = curCluster_; - flags_ |= F_FILE_DIR_DIRTY; - } - flags_ |= F_FILE_CLUSTER_ADDED; - return true; -} -//------------------------------------------------------------------------------ -// Add a cluster to a directory file and zero the cluster. -// return with first block of cluster in the cache -uint8_t SdFile::addDirCluster(void) { - if (!addCluster()) { - return false; - } - - // zero data in cluster insure first cluster is in cache - uint32_t block = vol_->clusterStartBlock(curCluster_); - for (uint8_t i = vol_->blocksPerCluster_; i != 0; i--) { - if (!SdVolume::cacheZeroBlock(block + i - 1)) { - return false; - } - } - // Increase directory file size by cluster size - fileSize_ += 512UL << vol_->clusterSizeShift_; - return true; -} -//------------------------------------------------------------------------------ -// cache a file's directory entry -// return pointer to cached entry or null for failure -dir_t* SdFile::cacheDirEntry(uint8_t action) { - if (!SdVolume::cacheRawBlock(dirBlock_, action)) { - return NULL; - } - return SdVolume::cacheBuffer_.dir + dirIndex_; -} -//------------------------------------------------------------------------------ -/** - Close a file and force cached data and directory information - to be written to the storage device. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include no file is open or an I/O error. -*/ -uint8_t SdFile::close(void) { - if (!sync()) { - return false; - } - type_ = FAT_FILE_TYPE_CLOSED; - return true; -} -//------------------------------------------------------------------------------ -/** - Check for contiguous file and return its raw block range. - - \param[out] bgnBlock the first block address for the file. - \param[out] endBlock the last block address for the file. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include file is not contiguous, file has zero length - or an I/O error occurred. -*/ -uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock) { - // error if no blocks - if (firstCluster_ == 0) { - return false; - } - - for (uint32_t c = firstCluster_; ; c++) { - uint32_t next; - if (!vol_->fatGet(c, &next)) { - return false; - } - - // check for contiguous - if (next != (c + 1)) { - // error if not end of chain - if (!vol_->isEOC(next)) { - return false; - } - *bgnBlock = vol_->clusterStartBlock(firstCluster_); - *endBlock = vol_->clusterStartBlock(c) - + vol_->blocksPerCluster_ - 1; - return true; - } - } -} -//------------------------------------------------------------------------------ -/** - Create and open a new contiguous file of a specified size. - - \note This function only supports short DOS 8.3 names. - See open() for more information. - - \param[in] dirFile The directory where the file will be created. - \param[in] fileName A valid DOS 8.3 file name. - \param[in] size The desired file size. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include \a fileName contains - an invalid DOS 8.3 file name, the FAT volume has not been initialized, - a file is already open, the file already exists, the root - directory is full or an I/O error. - -*/ -uint8_t SdFile::createContiguous(SdFile* dirFile, - const char* fileName, uint32_t size) { - // don't allow zero length file - if (size == 0) { - return false; - } - if (!open(dirFile, fileName, O_CREAT | O_EXCL | O_RDWR)) { - return false; - } - - // calculate number of clusters needed - uint32_t count = ((size - 1) >> (vol_->clusterSizeShift_ + 9)) + 1; - - // allocate clusters - if (!vol_->allocContiguous(count, &firstCluster_)) { - remove(); - return false; - } - fileSize_ = size; - - // insure sync() will update dir entry - flags_ |= F_FILE_DIR_DIRTY; - return sync(); -} -//------------------------------------------------------------------------------ -/** - Return a files directory entry - - \param[out] dir Location for return of the files directory entry. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t SdFile::dirEntry(dir_t* dir) { - // make sure fields on SD are correct - if (!sync()) { - return false; - } - - // read entry - dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_READ); - if (!p) { - return false; - } - - // copy to caller's struct - memcpy(dir, p, sizeof(dir_t)); - return true; -} -//------------------------------------------------------------------------------ -/** - Format the name field of \a dir into the 13 byte array - \a name in standard 8.3 short name format. - - \param[in] dir The directory structure containing the name. - \param[out] name A 13 byte char array for the formatted name. -*/ -void SdFile::dirName(const dir_t& dir, char* name) { - uint8_t j = 0; - for (uint8_t i = 0; i < 11; i++) { - if (dir.name[i] == ' ') { - continue; - } - if (i == 8) { - name[j++] = '.'; - } - name[j++] = dir.name[i]; - } - name[j] = 0; -} -//------------------------------------------------------------------------------ -/** List directory contents to Serial. - - \param[in] flags The inclusive OR of - - LS_DATE - %Print file modification date - - LS_SIZE - %Print file size. - - LS_R - Recursive list of subdirectories. - - \param[in] indent Amount of space before file name. Used for recursive - list to indicate subdirectory level. -*/ -void SdFile::ls(uint8_t flags, uint8_t indent) { - dir_t* p; - - rewind(); - while ((p = readDirCache())) { - // done if past last used entry - if (p->name[0] == DIR_NAME_FREE) { - break; - } - - // skip deleted entry and entries for . and .. - if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { - continue; - } - - // only list subdirectories and files - if (!DIR_IS_FILE_OR_SUBDIR(p)) { - continue; - } - - // print any indent spaces - for (int8_t i = 0; i < indent; i++) { - Serial.print(' '); - } - - // print file name with possible blank fill - printDirName(*p, flags & (LS_DATE | LS_SIZE) ? 14 : 0); - - // print modify date/time if requested - if (flags & LS_DATE) { - printFatDate(p->lastWriteDate); - Serial.print(' '); - printFatTime(p->lastWriteTime); - } - // print size if requested - if (!DIR_IS_SUBDIR(p) && (flags & LS_SIZE)) { - Serial.print(' '); - Serial.print(p->fileSize); - } - Serial.println(); - - // list subdirectory content if requested - if ((flags & LS_R) && DIR_IS_SUBDIR(p)) { - uint16_t index = curPosition() / 32 - 1; - SdFile s; - if (s.open(this, index, O_READ)) { - s.ls(flags, indent + 2); - } - seekSet(32 * (index + 1)); - } - } -} -//------------------------------------------------------------------------------ -// format directory name field from a 8.3 name string -uint8_t SdFile::make83Name(const char* str, uint8_t* name) { - uint8_t c; - uint8_t n = 7; // max index for part before dot - uint8_t i = 0; - // blank fill name and extension - while (i < 11) { - name[i++] = ' '; - } - i = 0; - while ((c = *str++) != '\0') { - if (c == '.') { - if (n == 10) { - return false; // only one dot allowed - } - n = 10; // max index for full 8.3 name - i = 8; // place for extension - } else { - // illegal FAT characters - uint8_t b; - #if defined(__AVR__) - PGM_P p = PSTR("|<>^+=?/[];,*\"\\"); - while ((b = pgm_read_byte(p++))) if (b == c) { - return false; - } - #elif defined(__arm__) - const uint8_t valid[] = "|<>^+=?/[];,*\"\\"; - const uint8_t *p = valid; - while ((b = *p++)) if (b == c) { - return false; - } - #endif - // check size and only allow ASCII printable characters - if (i > n || c < 0X21 || c > 0X7E) { - return false; - } - // only upper case allowed in 8.3 names - convert lower to upper - name[i++] = c < 'a' || c > 'z' ? c : c + ('A' - 'a'); - } - } - // must have a file name, extension is optional - return name[0] != ' '; -} -//------------------------------------------------------------------------------ -/** Make a new directory. - - \param[in] dir An open SdFat instance for the directory that will containing - the new directory. - - \param[in] dirName A valid 8.3 DOS name for the new directory. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include this SdFile is already open, \a dir is not a - directory, \a dirName is invalid or already exists in \a dir. -*/ -uint8_t SdFile::makeDir(SdFile* dir, const char* dirName) { - dir_t d; - - // create a normal file - if (!open(dir, dirName, O_CREAT | O_EXCL | O_RDWR)) { - return false; - } - - // convert SdFile to directory - flags_ = O_READ; - type_ = FAT_FILE_TYPE_SUBDIR; - - // allocate and zero first cluster - if (!addDirCluster()) { - return false; - } - - // force entry to SD - if (!sync()) { - return false; - } - - // cache entry - should already be in cache due to sync() call - dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); - if (!p) { - return false; - } - - // change directory entry attribute - p->attributes = DIR_ATT_DIRECTORY; - - // make entry for '.' - memcpy(&d, p, sizeof(d)); - for (uint8_t i = 1; i < 11; i++) { - d.name[i] = ' '; - } - d.name[0] = '.'; - - // cache block for '.' and '..' - uint32_t block = vol_->clusterStartBlock(firstCluster_); - if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { - return false; - } - - // copy '.' to block - memcpy(&SdVolume::cacheBuffer_.dir[0], &d, sizeof(d)); - - // make entry for '..' - d.name[1] = '.'; - if (dir->isRoot()) { - d.firstClusterLow = 0; - d.firstClusterHigh = 0; - } else { - d.firstClusterLow = dir->firstCluster_ & 0XFFFF; - d.firstClusterHigh = dir->firstCluster_ >> 16; - } - // copy '..' to block - memcpy(&SdVolume::cacheBuffer_.dir[1], &d, sizeof(d)); - - // set position after '..' - curPosition_ = 2 * sizeof(d); - - // write first block - return SdVolume::cacheFlush(); -} -//------------------------------------------------------------------------------ -/** - Open a file or directory by name. - - \param[in] dirFile An open SdFat instance for the directory containing the - file to be opened. - - \param[in] fileName A valid 8.3 DOS name for a file to be opened. - - \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive - OR of flags from the following list - - O_READ - Open for reading. - - O_RDONLY - Same as O_READ. - - O_WRITE - Open for writing. - - O_WRONLY - Same as O_WRITE. - - O_RDWR - Open for reading and writing. - - O_APPEND - If set, the file offset shall be set to the end of the - file prior to each write. - - O_CREAT - If the file exists, this flag has no effect except as noted - under O_EXCL below. Otherwise, the file shall be created - - O_EXCL - If O_CREAT and O_EXCL are set, open() shall fail if the file exists. - - O_SYNC - Call sync() after each write. This flag should not be used with - write(uint8_t), write_P(PGM_P), writeln_P(PGM_P), or the Arduino Print class. - These functions do character at a time writes so sync() will be called - after each byte. - - O_TRUNC - If the file exists and is a regular file, and the file is - successfully opened and is not read only, its length shall be truncated to 0. - - \note Directory files must be opened read only. Write and truncation is - not allowed for directory files. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include this SdFile is already open, \a difFile is not - a directory, \a fileName is invalid, the file does not exist - or can't be opened in the access mode specified by oflag. -*/ -uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag) { - uint8_t dname[11]; - dir_t* p; - - // error if already open - if (isOpen()) { - return false; - } - - if (!make83Name(fileName, dname)) { - return false; - } - vol_ = dirFile->vol_; - dirFile->rewind(); - - // bool for empty entry found - uint8_t emptyFound = false; - - // search for file - while (dirFile->curPosition_ < dirFile->fileSize_) { - uint8_t index = 0XF & (dirFile->curPosition_ >> 5); - p = dirFile->readDirCache(); - if (p == NULL) { - return false; - } - - if (p->name[0] == DIR_NAME_FREE || p->name[0] == DIR_NAME_DELETED) { - // remember first empty slot - if (!emptyFound) { - emptyFound = true; - dirIndex_ = index; - dirBlock_ = SdVolume::cacheBlockNumber_; - } - // done if no entries follow - if (p->name[0] == DIR_NAME_FREE) { - break; - } - } else if (!memcmp(dname, p->name, 11)) { - // don't open existing file if O_CREAT and O_EXCL - if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { - return false; - } - - // open found file - return openCachedEntry(0XF & index, oflag); - } - } - // only create file if O_CREAT and O_WRITE - if ((oflag & (O_CREAT | O_WRITE)) != (O_CREAT | O_WRITE)) { - return false; - } - - // cache found slot or add cluster if end of file - if (emptyFound) { - p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); - if (!p) { - return false; - } - } else { - if (dirFile->type_ == FAT_FILE_TYPE_ROOT16) { - return false; - } - - // add and zero cluster for dirFile - first cluster is in cache for write - if (!dirFile->addDirCluster()) { - return false; - } - - // use first entry in cluster - dirIndex_ = 0; - p = SdVolume::cacheBuffer_.dir; - } - // initialize as empty file - memset(p, 0, sizeof(dir_t)); - memcpy(p->name, dname, 11); - - // set timestamps - if (dateTime_) { - // call user function - dateTime_(&p->creationDate, &p->creationTime); - } else { - // use default date/time - p->creationDate = FAT_DEFAULT_DATE; - p->creationTime = FAT_DEFAULT_TIME; - } - p->lastAccessDate = p->creationDate; - p->lastWriteDate = p->creationDate; - p->lastWriteTime = p->creationTime; - - // force write of entry to SD - if (!SdVolume::cacheFlush()) { - return false; - } - - // open entry in cache - return openCachedEntry(dirIndex_, oflag); -} -//------------------------------------------------------------------------------ -/** - Open a file by index. - - \param[in] dirFile An open SdFat instance for the directory. - - \param[in] index The \a index of the directory entry for the file to be - opened. The value for \a index is (directory file position)/32. - - \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive - OR of flags O_READ, O_WRITE, O_TRUNC, and O_SYNC. - - See open() by fileName for definition of flags and return values. - -*/ -uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag) { - // error if already open - if (isOpen()) { - return false; - } - - // don't open existing file if O_CREAT and O_EXCL - user call error - if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { - return false; - } - - vol_ = dirFile->vol_; - - // seek to location of entry - if (!dirFile->seekSet(32 * index)) { - return false; - } - - // read entry into cache - dir_t* p = dirFile->readDirCache(); - if (p == NULL) { - return false; - } - - // error if empty slot or '.' or '..' - if (p->name[0] == DIR_NAME_FREE || - p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { - return false; - } - // open cached entry - return openCachedEntry(index & 0XF, oflag); -} -//------------------------------------------------------------------------------ -// open a cached directory entry. Assumes vol_ is initializes -uint8_t SdFile::openCachedEntry(uint8_t dirIndex, uint8_t oflag) { - // location of entry in cache - dir_t* p = SdVolume::cacheBuffer_.dir + dirIndex; - - // write or truncate is an error for a directory or read-only file - if (p->attributes & (DIR_ATT_READ_ONLY | DIR_ATT_DIRECTORY)) { - if (oflag & (O_WRITE | O_TRUNC)) { - return false; - } - } - // remember location of directory entry on SD - dirIndex_ = dirIndex; - dirBlock_ = SdVolume::cacheBlockNumber_; - - // copy first cluster number for directory fields - firstCluster_ = (uint32_t)p->firstClusterHigh << 16; - firstCluster_ |= p->firstClusterLow; - - // make sure it is a normal file or subdirectory - if (DIR_IS_FILE(p)) { - fileSize_ = p->fileSize; - type_ = FAT_FILE_TYPE_NORMAL; - } else if (DIR_IS_SUBDIR(p)) { - if (!vol_->chainSize(firstCluster_, &fileSize_)) { - return false; - } - type_ = FAT_FILE_TYPE_SUBDIR; - } else { - return false; - } - // save open flags for read/write - flags_ = oflag & (O_ACCMODE | O_SYNC | O_APPEND); - - // set to start of file - curCluster_ = 0; - curPosition_ = 0; - - // truncate file to zero length if requested - if (oflag & O_TRUNC) { - return truncate(0); - } - return true; -} -//------------------------------------------------------------------------------ -/** - Open a volume's root directory. - - \param[in] vol The FAT volume containing the root directory to be opened. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include the FAT volume has not been initialized - or it a FAT12 volume. -*/ -uint8_t SdFile::openRoot(SdVolume* vol) { - // error if file is already open - if (isOpen()) { - return false; - } - - if (vol->fatType() == 16) { - type_ = FAT_FILE_TYPE_ROOT16; - firstCluster_ = 0; - fileSize_ = 32 * vol->rootDirEntryCount(); - } else if (vol->fatType() == 32) { - type_ = FAT_FILE_TYPE_ROOT32; - firstCluster_ = vol->rootDirStart(); - if (!vol->chainSize(firstCluster_, &fileSize_)) { - return false; - } - } else { - // volume is not initialized or FAT12 - return false; - } - vol_ = vol; - // read only - flags_ = O_READ; - - // set to start of file - curCluster_ = 0; - curPosition_ = 0; - - // root has no directory entry - dirBlock_ = 0; - dirIndex_ = 0; - return true; -} -//------------------------------------------------------------------------------ -/** %Print the name field of a directory entry in 8.3 format to Serial. - - \param[in] dir The directory structure containing the name. - \param[in] width Blank fill name if length is less than \a width. -*/ -void SdFile::printDirName(const dir_t& dir, uint8_t width) { - uint8_t w = 0; - for (uint8_t i = 0; i < 11; i++) { - if (dir.name[i] == ' ') { - continue; - } - if (i == 8) { - Serial.print('.'); - w++; - } - Serial.write(dir.name[i]); - w++; - } - if (DIR_IS_SUBDIR(&dir)) { - Serial.print('/'); - w++; - } - while (w < width) { - Serial.print(' '); - w++; - } -} -//------------------------------------------------------------------------------ -/** %Print a directory date field to Serial. - - Format is yyyy-mm-dd. - - \param[in] fatDate The date field from a directory entry. -*/ -void SdFile::printFatDate(uint16_t fatDate) { - Serial.print(FAT_YEAR(fatDate)); - Serial.print('-'); - printTwoDigits(FAT_MONTH(fatDate)); - Serial.print('-'); - printTwoDigits(FAT_DAY(fatDate)); -} -//------------------------------------------------------------------------------ -/** %Print a directory time field to Serial. - - Format is hh:mm:ss. - - \param[in] fatTime The time field from a directory entry. -*/ -void SdFile::printFatTime(uint16_t fatTime) { - printTwoDigits(FAT_HOUR(fatTime)); - Serial.print(':'); - printTwoDigits(FAT_MINUTE(fatTime)); - Serial.print(':'); - printTwoDigits(FAT_SECOND(fatTime)); -} -//------------------------------------------------------------------------------ -/** %Print a value as two digits to Serial. - - \param[in] v Value to be printed, 0 <= \a v <= 99 -*/ -void SdFile::printTwoDigits(uint8_t v) { - char str[3]; - str[0] = '0' + v / 10; - str[1] = '0' + v % 10; - str[2] = 0; - Serial.print(str); -} -//------------------------------------------------------------------------------ -/** - Read data from a file starting at the current position. - - \param[out] buf Pointer to the location that will receive the data. - - \param[in] nbyte Maximum number of bytes to read. - - \return For success read() returns the number of bytes read. - A value less than \a nbyte, including zero, will be returned - if end of file is reached. - If an error occurs, read() returns -1. Possible errors include - read() called before a file has been opened, corrupt file system - or an I/O error occurred. -*/ -int16_t SdFile::read(void* buf, uint16_t nbyte) { - uint8_t* dst = reinterpret_cast(buf); - - // error if not open or write only - if (!isOpen() || !(flags_ & O_READ)) { - return -1; - } - - // max bytes left in file - if (nbyte > (fileSize_ - curPosition_)) { - nbyte = fileSize_ - curPosition_; - } - - // amount left to read - uint16_t toRead = nbyte; - while (toRead > 0) { - uint32_t block; // raw device block number - uint16_t offset = curPosition_ & 0X1FF; // offset in block - if (type_ == FAT_FILE_TYPE_ROOT16) { - block = vol_->rootDirStart() + (curPosition_ >> 9); - } else { - uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); - if (offset == 0 && blockOfCluster == 0) { - // start of new cluster - if (curPosition_ == 0) { - // use first cluster in file - curCluster_ = firstCluster_; - } else { - // get next cluster from FAT - if (!vol_->fatGet(curCluster_, &curCluster_)) { - return -1; - } - } - } - block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; - } - uint16_t n = toRead; - - // amount to be read from current block - if (n > (512 - offset)) { - n = 512 - offset; - } - - // no buffering needed if n == 512 or user requests no buffering - if ((unbufferedRead() || n == 512) && - block != SdVolume::cacheBlockNumber_) { - if (!vol_->readData(block, offset, n, dst)) { - return -1; - } - dst += n; - } else { - // read block to cache and copy data to caller - if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_READ)) { - return -1; - } - uint8_t* src = SdVolume::cacheBuffer_.data + offset; - uint8_t* end = src + n; - while (src != end) { - *dst++ = *src++; - } - } - curPosition_ += n; - toRead -= n; - } - return nbyte; -} -//------------------------------------------------------------------------------ -/** - Read the next directory entry from a directory file. - - \param[out] dir The dir_t struct that will receive the data. - - \return For success readDir() returns the number of bytes read. - A value of zero will be returned if end of file is reached. - If an error occurs, readDir() returns -1. Possible errors include - readDir() called before a directory has been opened, this is not - a directory file or an I/O error occurred. -*/ -int8_t SdFile::readDir(dir_t* dir) { - int8_t n; - // if not a directory file or miss-positioned return an error - if (!isDir() || (0X1F & curPosition_)) { - return -1; - } - - while ((n = read(dir, sizeof(dir_t))) == sizeof(dir_t)) { - // last entry if DIR_NAME_FREE - if (dir->name[0] == DIR_NAME_FREE) { - break; - } - // skip empty entries and entry for . and .. - if (dir->name[0] == DIR_NAME_DELETED || dir->name[0] == '.') { - continue; - } - // return if normal file or subdirectory - if (DIR_IS_FILE_OR_SUBDIR(dir)) { - return n; - } - } - // error, end of file, or past last entry - return n < 0 ? -1 : 0; -} -//------------------------------------------------------------------------------ -// Read next directory entry into the cache -// Assumes file is correctly positioned -dir_t* SdFile::readDirCache(void) { - // error if not directory - if (!isDir()) { - return NULL; - } - - // index of entry in cache - uint8_t i = (curPosition_ >> 5) & 0XF; - - // use read to locate and cache block - if (read() < 0) { - return NULL; - } - - // advance to next entry - curPosition_ += 31; - - // return pointer to entry - return (SdVolume::cacheBuffer_.dir + i); -} -//------------------------------------------------------------------------------ -/** - Remove a file. - - The directory entry and all data for the file are deleted. - - \note This function should not be used to delete the 8.3 version of a - file that has a long name. For example if a file has the long name - "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include the file read-only, is a directory, - or an I/O error occurred. -*/ -uint8_t SdFile::remove(void) { - // free any clusters - will fail if read-only or directory - if (!truncate(0)) { - return false; - } - - // cache directory entry - dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); - if (!d) { - return false; - } - - // mark entry deleted - d->name[0] = DIR_NAME_DELETED; - - // set this SdFile closed - type_ = FAT_FILE_TYPE_CLOSED; - - // write entry to SD - return SdVolume::cacheFlush(); -} -//------------------------------------------------------------------------------ -/** - Remove a file. - - The directory entry and all data for the file are deleted. - - \param[in] dirFile The directory that contains the file. - \param[in] fileName The name of the file to be removed. - - \note This function should not be used to delete the 8.3 version of a - file that has a long name. For example if a file has the long name - "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include the file is a directory, is read only, - \a dirFile is not a directory, \a fileName is not found - or an I/O error occurred. -*/ -uint8_t SdFile::remove(SdFile* dirFile, const char* fileName) { - SdFile file; - if (!file.open(dirFile, fileName, O_WRITE)) { - return false; - } - return file.remove(); -} -//------------------------------------------------------------------------------ -/** Remove a directory file. - - The directory file will be removed only if it is empty and is not the - root directory. rmDir() follows DOS and Windows and ignores the - read-only attribute for the directory. - - \note This function should not be used to delete the 8.3 version of a - directory that has a long name. For example if a directory has the - long name "New folder" you should not delete the 8.3 name "NEWFOL~1". - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include the file is not a directory, is the root - directory, is not empty, or an I/O error occurred. -*/ -uint8_t SdFile::rmDir(void) { - // must be open subdirectory - if (!isSubDir()) { - return false; - } - - rewind(); - - // make sure directory is empty - while (curPosition_ < fileSize_) { - dir_t* p = readDirCache(); - if (p == NULL) { - return false; - } - // done if past last used entry - if (p->name[0] == DIR_NAME_FREE) { - break; - } - // skip empty slot or '.' or '..' - if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { - continue; - } - // error not empty - if (DIR_IS_FILE_OR_SUBDIR(p)) { - return false; - } - } - // convert empty directory to normal file for remove - type_ = FAT_FILE_TYPE_NORMAL; - flags_ |= O_WRITE; - return remove(); -} -//------------------------------------------------------------------------------ -/** Recursively delete a directory and all contained files. - - This is like the Unix/Linux 'rm -rf *' if called with the root directory - hence the name. - - Warning - This will remove all contents of the directory including - subdirectories. The directory will then be removed if it is not root. - The read-only attribute for files will be ignored. - - \note This function should not be used to delete the 8.3 version of - a directory that has a long name. See remove() and rmDir(). - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t SdFile::rmRfStar(void) { - rewind(); - while (curPosition_ < fileSize_) { - SdFile f; - - // remember position - uint16_t index = curPosition_ / 32; - - dir_t* p = readDirCache(); - if (!p) { - return false; - } - - // done if past last entry - if (p->name[0] == DIR_NAME_FREE) { - break; - } - - // skip empty slot or '.' or '..' - if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { - continue; - } - - // skip if part of long file name or volume label in root - if (!DIR_IS_FILE_OR_SUBDIR(p)) { - continue; - } - - if (!f.open(this, index, O_READ)) { - return false; - } - if (f.isSubDir()) { - // recursively delete - if (!f.rmRfStar()) { - return false; - } - } else { - // ignore read-only - f.flags_ |= O_WRITE; - if (!f.remove()) { - return false; - } - } - // position to next entry if required - if (curPosition_ != (32u * (index + 1))) { - if (!seekSet(32u * (index + 1))) { - return false; - } - } - } - // don't try to delete root - if (isRoot()) { - return true; - } - return rmDir(); -} -//------------------------------------------------------------------------------ -/** - Sets a file's position. - - \param[in] pos The new position in bytes from the beginning of the file. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t SdFile::seekSet(uint32_t pos) { - // error if file not open or seek past end of file - if (!isOpen() || pos > fileSize_) { - return false; - } - - if (type_ == FAT_FILE_TYPE_ROOT16) { - curPosition_ = pos; - return true; - } - if (pos == 0) { - // set position to start of file - curCluster_ = 0; - curPosition_ = 0; - return true; - } - // calculate cluster index for cur and new position - uint32_t nCur = (curPosition_ - 1) >> (vol_->clusterSizeShift_ + 9); - uint32_t nNew = (pos - 1) >> (vol_->clusterSizeShift_ + 9); - - if (nNew < nCur || curPosition_ == 0) { - // must follow chain from first cluster - curCluster_ = firstCluster_; - } else { - // advance from curPosition - nNew -= nCur; - } - while (nNew--) { - if (!vol_->fatGet(curCluster_, &curCluster_)) { - return false; - } - } - curPosition_ = pos; - return true; -} -//------------------------------------------------------------------------------ -/** - The sync() call causes all modified data and directory fields - to be written to the storage device. - - \param[in] blocking If the sync should block until fully complete. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include a call to sync() before a file has been - opened or an I/O error. -*/ -uint8_t SdFile::sync(uint8_t blocking) { - // only allow open files and directories - if (!isOpen()) { - return false; - } - - if (flags_ & F_FILE_DIR_DIRTY) { - dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); - if (!d) { - return false; - } - - // do not set filesize for dir files - if (!isDir()) { - d->fileSize = fileSize_; - } - - // update first cluster fields - d->firstClusterLow = firstCluster_ & 0XFFFF; - d->firstClusterHigh = firstCluster_ >> 16; - - // set modify time if user supplied a callback date/time function - if (dateTime_) { - dateTime_(&d->lastWriteDate, &d->lastWriteTime); - d->lastAccessDate = d->lastWriteDate; - } - // clear directory dirty - flags_ &= ~F_FILE_DIR_DIRTY; - } - - if (!blocking) { - flags_ &= ~F_FILE_NON_BLOCKING_WRITE; - } - - return SdVolume::cacheFlush(blocking); -} -//------------------------------------------------------------------------------ -/** - Set a file's timestamps in its directory entry. - - \param[in] flags Values for \a flags are constructed by a bitwise-inclusive - OR of flags from the following list - - T_ACCESS - Set the file's last access date. - - T_CREATE - Set the file's creation date and time. - - T_WRITE - Set the file's last write/modification date and time. - - \param[in] year Valid range 1980 - 2107 inclusive. - - \param[in] month Valid range 1 - 12 inclusive. - - \param[in] day Valid range 1 - 31 inclusive. - - \param[in] hour Valid range 0 - 23 inclusive. - - \param[in] minute Valid range 0 - 59 inclusive. - - \param[in] second Valid range 0 - 59 inclusive - - \note It is possible to set an invalid date since there is no check for - the number of days in a month. - - \note - Modify and access timestamps may be overwritten if a date time callback - function has been set by dateTimeCallback(). - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. -*/ -uint8_t SdFile::timestamp(uint8_t flags, uint16_t year, uint8_t month, - uint8_t day, uint8_t hour, uint8_t minute, uint8_t second) { - if (!isOpen() - || year < 1980 - || year > 2107 - || month < 1 - || month > 12 - || day < 1 - || day > 31 - || hour > 23 - || minute > 59 - || second > 59) { - return false; - } - dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); - if (!d) { - return false; - } - - uint16_t dirDate = FAT_DATE(year, month, day); - uint16_t dirTime = FAT_TIME(hour, minute, second); - if (flags & T_ACCESS) { - d->lastAccessDate = dirDate; - } - if (flags & T_CREATE) { - d->creationDate = dirDate; - d->creationTime = dirTime; - // seems to be units of 1/100 second not 1/10 as Microsoft states - d->creationTimeTenths = second & 1 ? 100 : 0; - } - if (flags & T_WRITE) { - d->lastWriteDate = dirDate; - d->lastWriteTime = dirTime; - } - SdVolume::cacheSetDirty(); - return sync(); -} -//------------------------------------------------------------------------------ -/** - Truncate a file to a specified length. The current file position - will be maintained if it is less than or equal to \a length otherwise - it will be set to end of file. - - \param[in] length The desired length for the file. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. - Reasons for failure include file is read only, file is a directory, - \a length is greater than the current file size or an I/O error occurs. -*/ -uint8_t SdFile::truncate(uint32_t length) { - // error if not a normal file or read-only - if (!isFile() || !(flags_ & O_WRITE)) { - return false; - } - - // error if length is greater than current size - if (length > fileSize_) { - return false; - } - - // fileSize and length are zero - nothing to do - if (fileSize_ == 0) { - return true; - } - - // remember position for seek after truncation - uint32_t newPos = curPosition_ > length ? length : curPosition_; - - // position to last cluster in truncated file - if (!seekSet(length)) { - return false; - } - - if (length == 0) { - // free all clusters - if (!vol_->freeChain(firstCluster_)) { - return false; - } - firstCluster_ = 0; - } else { - uint32_t toFree; - if (!vol_->fatGet(curCluster_, &toFree)) { - return false; - } - - if (!vol_->isEOC(toFree)) { - // free extra clusters - if (!vol_->freeChain(toFree)) { - return false; - } - - // current cluster is end of chain - if (!vol_->fatPutEOC(curCluster_)) { - return false; - } - } - } - fileSize_ = length; - - // need to update directory entry - flags_ |= F_FILE_DIR_DIRTY; - - if (!sync()) { - return false; - } - - // set file to correct position - return seekSet(newPos); -} -//------------------------------------------------------------------------------ -/** - Write data to an open file. - - \note Data is moved to the cache but may not be written to the - storage device until sync() is called. - - \param[in] buf Pointer to the location of the data to be written. - - \param[in] nbyte Number of bytes to write. - - \return For success write() returns the number of bytes written, always - \a nbyte. If an error occurs, write() returns 0. Possible errors - include write() is called before a file has been opened, write is called - for a read-only file, device is full, a corrupt file system or an I/O error. - -*/ -size_t SdFile::write(const void* buf, uint16_t nbyte) { - // convert void* to uint8_t* - must be before goto statements - const uint8_t* src = reinterpret_cast(buf); - - // number of bytes left to write - must be before goto statements - uint16_t nToWrite = nbyte; - // if blocking writes should be used - uint8_t blocking = (flags_ & F_FILE_NON_BLOCKING_WRITE) == 0x00; - - // error if not a normal file or is read-only - if (!isFile() || !(flags_ & O_WRITE)) { - goto writeErrorReturn; - } - - // seek to end of file if append flag - if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { - if (!seekEnd()) { - goto writeErrorReturn; - } - } - - while (nToWrite > 0) { - uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); - uint16_t blockOffset = curPosition_ & 0X1FF; - if (blockOfCluster == 0 && blockOffset == 0) { - // start of new cluster - if (curCluster_ == 0) { - if (firstCluster_ == 0) { - // allocate first cluster of file - if (!addCluster()) { - goto writeErrorReturn; - } - } else { - curCluster_ = firstCluster_; - } - } else { - uint32_t next; - if (!vol_->fatGet(curCluster_, &next)) { - return false; - } - if (vol_->isEOC(next)) { - // add cluster if at end of chain - if (!addCluster()) { - goto writeErrorReturn; - } - } else { - curCluster_ = next; - } - } - } - // max space in block - uint16_t n = 512 - blockOffset; - - // lesser of space and amount to write - if (n > nToWrite) { - n = nToWrite; - } - - // block for data write - uint32_t block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; - if (n == 512) { - // full block - don't need to use cache - // invalidate cache if block is in cache - if (SdVolume::cacheBlockNumber_ == block) { - SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; - } - if (!vol_->writeBlock(block, src, blocking)) { - goto writeErrorReturn; - } - src += 512; - } else { - if (blockOffset == 0 && curPosition_ >= fileSize_) { - // start of new block don't need to read into cache - if (!SdVolume::cacheFlush()) { - goto writeErrorReturn; - } - SdVolume::cacheBlockNumber_ = block; - SdVolume::cacheSetDirty(); - } else { - // rewrite part of block - if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { - goto writeErrorReturn; - } - } - uint8_t* dst = SdVolume::cacheBuffer_.data + blockOffset; - uint8_t* end = dst + n; - while (dst != end) { - *dst++ = *src++; - } - } - nToWrite -= n; - curPosition_ += n; - } - if (curPosition_ > fileSize_) { - // update fileSize and insure sync will update dir entry - fileSize_ = curPosition_; - flags_ |= F_FILE_DIR_DIRTY; - } else if (dateTime_ && nbyte) { - // insure sync will update modified date and time - flags_ |= F_FILE_DIR_DIRTY; - } - - if (flags_ & O_SYNC) { - if (!sync()) { - goto writeErrorReturn; - } - } - return nbyte; - -writeErrorReturn: - // return for write error - //writeError = true; - setWriteError(); - return 0; -} -//------------------------------------------------------------------------------ -/** - Write a byte to a file. Required by the Arduino Print class. - - Use SdFile::writeError to check for errors. -*/ -size_t SdFile::write(uint8_t b) { - return write(&b, 1); -} -//------------------------------------------------------------------------------ -/** - Write a string to a file. Used by the Arduino Print class. - - Use SdFile::writeError to check for errors. -*/ -size_t SdFile::write(const char* str) { - return write(str, strlen(str)); -} -#ifdef __AVR__ -//------------------------------------------------------------------------------ -/** - Write a PROGMEM string to a file. - - Use SdFile::writeError to check for errors. -*/ -void SdFile::write_P(PGM_P str) { - for (uint8_t c; (c = pgm_read_byte(str)); str++) { - write(c); - } -} -//------------------------------------------------------------------------------ -/** - Write a PROGMEM string followed by CR/LF to a file. - - Use SdFile::writeError to check for errors. -*/ -void SdFile::writeln_P(PGM_P str) { - write_P(str); - println(); -} -#endif -//------------------------------------------------------------------------------ -/** - Check how many bytes can be written without blocking. - - \return The number of bytes that can be written without blocking. -*/ -int SdFile::availableForWrite() { - if (!isFile() || !(flags_ & O_WRITE)) { - return 0; - } - - // seek to end of file if append flag - if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { - if (!seekEnd()) { - return 0; - } - } - - if (vol_->isBusy()) { - return 0; - } - - if (flags_ & F_FILE_CLUSTER_ADDED) { - // new cluster added, trigger a non-blocking sync - sync(0); - flags_ &= ~F_FILE_CLUSTER_ADDED; - return 0; - } - - if (vol_->isCacheMirrorBlockDirty()) { - // cache mirror block is dirty, trigger a non-blocking sync - vol_->cacheMirrorBlockFlush(0); - return 0; - } - - flags_ |= F_FILE_NON_BLOCKING_WRITE; - - uint16_t blockOffset = curPosition_ & 0X1FF; - uint16_t n = 512 - blockOffset; - - return n; -} +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#include "SdFat.h" +#ifdef __AVR__ + #include +#endif +#include +//------------------------------------------------------------------------------ +// callback function for date/time +void (*SdFile::dateTime_)(uint16_t* date, uint16_t* time) = NULL; + +#if ALLOW_DEPRECATED_FUNCTIONS + // suppress cpplint warnings with NOLINT comment + void (*SdFile::oldDateTime_)(uint16_t& date, uint16_t& time) = NULL; // NOLINT +#endif // ALLOW_DEPRECATED_FUNCTIONS +//------------------------------------------------------------------------------ +// add a cluster to a file +uint8_t SdFile::addCluster() { + if (!vol_->allocContiguous(1, &curCluster_)) { + return false; + } + + // if first cluster of file link to directory entry + if (firstCluster_ == 0) { + firstCluster_ = curCluster_; + flags_ |= F_FILE_DIR_DIRTY; + } + flags_ |= F_FILE_CLUSTER_ADDED; + return true; +} +//------------------------------------------------------------------------------ +// Add a cluster to a directory file and zero the cluster. +// return with first block of cluster in the cache +uint8_t SdFile::addDirCluster(void) { + if (!addCluster()) { + return false; + } + + // zero data in cluster insure first cluster is in cache + uint32_t block = vol_->clusterStartBlock(curCluster_); + for (uint8_t i = vol_->blocksPerCluster_; i != 0; i--) { + if (!SdVolume::cacheZeroBlock(block + i - 1)) { + return false; + } + } + // Increase directory file size by cluster size + fileSize_ += 512UL << vol_->clusterSizeShift_; + return true; +} +//------------------------------------------------------------------------------ +// cache a file's directory entry +// return pointer to cached entry or null for failure +dir_t* SdFile::cacheDirEntry(uint8_t action) { + if (!SdVolume::cacheRawBlock(dirBlock_, action)) { + return NULL; + } + return SdVolume::cacheBuffer_.dir + dirIndex_; +} +//------------------------------------------------------------------------------ +/** + Close a file and force cached data and directory information + to be written to the storage device. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include no file is open or an I/O error. +*/ +uint8_t SdFile::close(void) { + if (!sync()) { + return false; + } + type_ = FAT_FILE_TYPE_CLOSED; + return true; +} +//------------------------------------------------------------------------------ +/** + Check for contiguous file and return its raw block range. + + \param[out] bgnBlock the first block address for the file. + \param[out] endBlock the last block address for the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include file is not contiguous, file has zero length + or an I/O error occurred. +*/ +uint8_t SdFile::contiguousRange(uint32_t* bgnBlock, uint32_t* endBlock) { + // error if no blocks + if (firstCluster_ == 0) { + return false; + } + + for (uint32_t c = firstCluster_; ; c++) { + uint32_t next; + if (!vol_->fatGet(c, &next)) { + return false; + } + + // check for contiguous + if (next != (c + 1)) { + // error if not end of chain + if (!vol_->isEOC(next)) { + return false; + } + *bgnBlock = vol_->clusterStartBlock(firstCluster_); + *endBlock = vol_->clusterStartBlock(c) + + vol_->blocksPerCluster_ - 1; + return true; + } + } +} +//------------------------------------------------------------------------------ +/** + Create and open a new contiguous file of a specified size. + + \note This function only supports short DOS 8.3 names. + See open() for more information. + + \param[in] dirFile The directory where the file will be created. + \param[in] fileName A valid DOS 8.3 file name. + \param[in] size The desired file size. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include \a fileName contains + an invalid DOS 8.3 file name, the FAT volume has not been initialized, + a file is already open, the file already exists, the root + directory is full or an I/O error. + +*/ +uint8_t SdFile::createContiguous(SdFile* dirFile, + const char* fileName, uint32_t size) { + // don't allow zero length file + if (size == 0) { + return false; + } + if (!open(dirFile, fileName, O_CREAT | O_EXCL | O_RDWR)) { + return false; + } + + // calculate number of clusters needed + uint32_t count = ((size - 1) >> (vol_->clusterSizeShift_ + 9)) + 1; + + // allocate clusters + if (!vol_->allocContiguous(count, &firstCluster_)) { + remove(); + return false; + } + fileSize_ = size; + + // insure sync() will update dir entry + flags_ |= F_FILE_DIR_DIRTY; + return sync(); +} +//------------------------------------------------------------------------------ +/** + Return a files directory entry + + \param[out] dir Location for return of the files directory entry. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::dirEntry(dir_t* dir) { + // make sure fields on SD are correct + if (!sync()) { + return false; + } + + // read entry + dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_READ); + if (!p) { + return false; + } + + // copy to caller's struct + memcpy(dir, p, sizeof(dir_t)); + return true; +} +//------------------------------------------------------------------------------ +/** + Format the name field of \a dir into the 13 byte array + \a name in standard 8.3 short name format. + + \param[in] dir The directory structure containing the name. + \param[out] name A 13 byte char array for the formatted name. +*/ +void SdFile::dirName(const dir_t& dir, char* name) { + uint8_t j = 0; + for (uint8_t i = 0; i < 11; i++) { + if (dir.name[i] == ' ') { + continue; + } + if (i == 8) { + name[j++] = '.'; + } + name[j++] = dir.name[i]; + } + name[j] = 0; +} +//------------------------------------------------------------------------------ +/** List directory contents to Serial. + + \param[in] flags The inclusive OR of + + LS_DATE - %Print file modification date + + LS_SIZE - %Print file size. + + LS_R - Recursive list of subdirectories. + + \param[in] indent Amount of space before file name. Used for recursive + list to indicate subdirectory level. +*/ +void SdFile::ls(uint8_t flags, uint8_t indent) { + dir_t* p; + + rewind(); + while ((p = readDirCache())) { + // done if past last used entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + + // skip deleted entry and entries for . and .. + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + + // only list subdirectories and files + if (!DIR_IS_FILE_OR_SUBDIR(p)) { + continue; + } + + // print any indent spaces + for (int8_t i = 0; i < indent; i++) { + Serial.print(' '); + } + + // print file name with possible blank fill + printDirName(*p, flags & (LS_DATE | LS_SIZE) ? 14 : 0); + + // print modify date/time if requested + if (flags & LS_DATE) { + printFatDate(p->lastWriteDate); + Serial.print(' '); + printFatTime(p->lastWriteTime); + } + // print size if requested + if (!DIR_IS_SUBDIR(p) && (flags & LS_SIZE)) { + Serial.print(' '); + Serial.print(p->fileSize); + } + Serial.println(); + + // list subdirectory content if requested + if ((flags & LS_R) && DIR_IS_SUBDIR(p)) { + uint16_t index = curPosition() / 32 - 1; + SdFile s; + if (s.open(this, index, O_READ)) { + s.ls(flags, indent + 2); + } + seekSet(32 * (index + 1)); + } + } +} +//------------------------------------------------------------------------------ +// format directory name field from a 8.3 name string +uint8_t SdFile::make83Name(const char* str, uint8_t* name) { + uint8_t c; + uint8_t n = 7; // max index for part before dot + uint8_t i = 0; + // blank fill name and extension + while (i < 11) { + name[i++] = ' '; + } + i = 0; + while ((c = *str++) != '\0') { + if (c == '.') { + if (n == 10) { + return false; // only one dot allowed + } + n = 10; // max index for full 8.3 name + i = 8; // place for extension + } else { + // illegal FAT characters + uint8_t b; + #if defined(__AVR__) + PGM_P p = PSTR("|<>^+=?/[];,*\"\\"); + while ((b = pgm_read_byte(p++))) if (b == c) { + return false; + } + #elif defined(__arm__) + const uint8_t valid[] = "|<>^+=?/[];,*\"\\"; + const uint8_t *p = valid; + while ((b = *p++)) if (b == c) { + return false; + } + #endif + // check size and only allow ASCII printable characters + if (i > n || c < 0X21 || c > 0X7E) { + return false; + } + // only upper case allowed in 8.3 names - convert lower to upper + name[i++] = c < 'a' || c > 'z' ? c : c + ('A' - 'a'); + } + } + // must have a file name, extension is optional + return name[0] != ' '; +} +//------------------------------------------------------------------------------ +/** Make a new directory. + + \param[in] dir An open SdFat instance for the directory that will containing + the new directory. + + \param[in] dirName A valid 8.3 DOS name for the new directory. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include this SdFile is already open, \a dir is not a + directory, \a dirName is invalid or already exists in \a dir. +*/ +uint8_t SdFile::makeDir(SdFile* dir, const char* dirName) { + dir_t d; + + // create a normal file + if (!open(dir, dirName, O_CREAT | O_EXCL | O_RDWR)) { + return false; + } + + // convert SdFile to directory + flags_ = O_READ; + type_ = FAT_FILE_TYPE_SUBDIR; + + // allocate and zero first cluster + if (!addDirCluster()) { + return false; + } + + // force entry to SD + if (!sync()) { + return false; + } + + // cache entry - should already be in cache due to sync() call + dir_t* p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!p) { + return false; + } + + // change directory entry attribute + p->attributes = DIR_ATT_DIRECTORY; + + // make entry for '.' + memcpy(&d, p, sizeof(d)); + for (uint8_t i = 1; i < 11; i++) { + d.name[i] = ' '; + } + d.name[0] = '.'; + + // cache block for '.' and '..' + uint32_t block = vol_->clusterStartBlock(firstCluster_); + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { + return false; + } + + // copy '.' to block + memcpy(&SdVolume::cacheBuffer_.dir[0], &d, sizeof(d)); + + // make entry for '..' + d.name[1] = '.'; + if (dir->isRoot()) { + d.firstClusterLow = 0; + d.firstClusterHigh = 0; + } else { + d.firstClusterLow = dir->firstCluster_ & 0XFFFF; + d.firstClusterHigh = dir->firstCluster_ >> 16; + } + // copy '..' to block + memcpy(&SdVolume::cacheBuffer_.dir[1], &d, sizeof(d)); + + // set position after '..' + curPosition_ = 2 * sizeof(d); + + // write first block + return SdVolume::cacheFlush(); +} +//------------------------------------------------------------------------------ +/** + Open a file or directory by name. + + \param[in] dirFile An open SdFat instance for the directory containing the + file to be opened. + + \param[in] fileName A valid 8.3 DOS name for a file to be opened. + + \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive + OR of flags from the following list + + O_READ - Open for reading. + + O_RDONLY - Same as O_READ. + + O_WRITE - Open for writing. + + O_WRONLY - Same as O_WRITE. + + O_RDWR - Open for reading and writing. + + O_APPEND - If set, the file offset shall be set to the end of the + file prior to each write. + + O_CREAT - If the file exists, this flag has no effect except as noted + under O_EXCL below. Otherwise, the file shall be created + + O_EXCL - If O_CREAT and O_EXCL are set, open() shall fail if the file exists. + + O_SYNC - Call sync() after each write. This flag should not be used with + write(uint8_t), write_P(PGM_P), writeln_P(PGM_P), or the Arduino Print class. + These functions do character at a time writes so sync() will be called + after each byte. + + O_TRUNC - If the file exists and is a regular file, and the file is + successfully opened and is not read only, its length shall be truncated to 0. + + \note Directory files must be opened read only. Write and truncation is + not allowed for directory files. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include this SdFile is already open, \a difFile is not + a directory, \a fileName is invalid, the file does not exist + or can't be opened in the access mode specified by oflag. +*/ +uint8_t SdFile::open(SdFile* dirFile, const char* fileName, uint8_t oflag) { + uint8_t dname[11]; + dir_t* p; + + // error if already open + if (isOpen()) { + return false; + } + + if (!make83Name(fileName, dname)) { + return false; + } + vol_ = dirFile->vol_; + dirFile->rewind(); + + // bool for empty entry found + uint8_t emptyFound = false; + + // search for file + while (dirFile->curPosition_ < dirFile->fileSize_) { + uint8_t index = 0XF & (dirFile->curPosition_ >> 5); + p = dirFile->readDirCache(); + if (p == NULL) { + return false; + } + + if (p->name[0] == DIR_NAME_FREE || p->name[0] == DIR_NAME_DELETED) { + // remember first empty slot + if (!emptyFound) { + emptyFound = true; + dirIndex_ = index; + dirBlock_ = SdVolume::cacheBlockNumber_; + } + // done if no entries follow + if (p->name[0] == DIR_NAME_FREE) { + break; + } + } else if (!memcmp(dname, p->name, 11)) { + // don't open existing file if O_CREAT and O_EXCL + if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { + return false; + } + + // open found file + return openCachedEntry(0XF & index, oflag); + } + } + // only create file if O_CREAT and O_WRITE + if ((oflag & (O_CREAT | O_WRITE)) != (O_CREAT | O_WRITE)) { + return false; + } + + // cache found slot or add cluster if end of file + if (emptyFound) { + p = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!p) { + return false; + } + } else { + if (dirFile->type_ == FAT_FILE_TYPE_ROOT16) { + return false; + } + + // add and zero cluster for dirFile - first cluster is in cache for write + if (!dirFile->addDirCluster()) { + return false; + } + + // use first entry in cluster + dirIndex_ = 0; + p = SdVolume::cacheBuffer_.dir; + } + // initialize as empty file + memset(p, 0, sizeof(dir_t)); + memcpy(p->name, dname, 11); + + // set timestamps + if (dateTime_) { + // call user function + dateTime_(&p->creationDate, &p->creationTime); + } else { + // use default date/time + p->creationDate = FAT_DEFAULT_DATE; + p->creationTime = FAT_DEFAULT_TIME; + } + p->lastAccessDate = p->creationDate; + p->lastWriteDate = p->creationDate; + p->lastWriteTime = p->creationTime; + + // force write of entry to SD + if (!SdVolume::cacheFlush()) { + return false; + } + + // open entry in cache + return openCachedEntry(dirIndex_, oflag); +} +//------------------------------------------------------------------------------ +/** + Open a file by index. + + \param[in] dirFile An open SdFat instance for the directory. + + \param[in] index The \a index of the directory entry for the file to be + opened. The value for \a index is (directory file position)/32. + + \param[in] oflag Values for \a oflag are constructed by a bitwise-inclusive + OR of flags O_READ, O_WRITE, O_TRUNC, and O_SYNC. + + See open() by fileName for definition of flags and return values. + +*/ +uint8_t SdFile::open(SdFile* dirFile, uint16_t index, uint8_t oflag) { + // error if already open + if (isOpen()) { + return false; + } + + // don't open existing file if O_CREAT and O_EXCL - user call error + if ((oflag & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)) { + return false; + } + + vol_ = dirFile->vol_; + + // seek to location of entry + if (!dirFile->seekSet(32 * index)) { + return false; + } + + // read entry into cache + dir_t* p = dirFile->readDirCache(); + if (p == NULL) { + return false; + } + + // error if empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_FREE || + p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + return false; + } + // open cached entry + return openCachedEntry(index & 0XF, oflag); +} +//------------------------------------------------------------------------------ +// open a cached directory entry. Assumes vol_ is initializes +uint8_t SdFile::openCachedEntry(uint8_t dirIndex, uint8_t oflag) { + // location of entry in cache + dir_t* p = SdVolume::cacheBuffer_.dir + dirIndex; + + // write or truncate is an error for a directory or read-only file + if (p->attributes & (DIR_ATT_READ_ONLY | DIR_ATT_DIRECTORY)) { + if (oflag & (O_WRITE | O_TRUNC)) { + return false; + } + } + // remember location of directory entry on SD + dirIndex_ = dirIndex; + dirBlock_ = SdVolume::cacheBlockNumber_; + + // copy first cluster number for directory fields + firstCluster_ = (uint32_t)p->firstClusterHigh << 16; + firstCluster_ |= p->firstClusterLow; + + // make sure it is a normal file or subdirectory + if (DIR_IS_FILE(p)) { + fileSize_ = p->fileSize; + type_ = FAT_FILE_TYPE_NORMAL; + } else if (DIR_IS_SUBDIR(p)) { + if (!vol_->chainSize(firstCluster_, &fileSize_)) { + return false; + } + type_ = FAT_FILE_TYPE_SUBDIR; + } else { + return false; + } + // save open flags for read/write + flags_ = oflag & (O_ACCMODE | O_SYNC | O_APPEND); + + // set to start of file + curCluster_ = 0; + curPosition_ = 0; + + // truncate file to zero length if requested + if (oflag & O_TRUNC) { + return truncate(0); + } + return true; +} +//------------------------------------------------------------------------------ +/** + Open a volume's root directory. + + \param[in] vol The FAT volume containing the root directory to be opened. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the FAT volume has not been initialized + or it a FAT12 volume. +*/ +uint8_t SdFile::openRoot(SdVolume* vol) { + // error if file is already open + if (isOpen()) { + return false; + } + + if (vol->fatType() == 16) { + type_ = FAT_FILE_TYPE_ROOT16; + firstCluster_ = 0; + fileSize_ = 32 * vol->rootDirEntryCount(); + } else if (vol->fatType() == 32) { + type_ = FAT_FILE_TYPE_ROOT32; + firstCluster_ = vol->rootDirStart(); + if (!vol->chainSize(firstCluster_, &fileSize_)) { + return false; + } + } else { + // volume is not initialized or FAT12 + return false; + } + vol_ = vol; + // read only + flags_ = O_READ; + + // set to start of file + curCluster_ = 0; + curPosition_ = 0; + + // root has no directory entry + dirBlock_ = 0; + dirIndex_ = 0; + return true; +} +//------------------------------------------------------------------------------ +/** %Print the name field of a directory entry in 8.3 format to Serial. + + \param[in] dir The directory structure containing the name. + \param[in] width Blank fill name if length is less than \a width. +*/ +void SdFile::printDirName(const dir_t& dir, uint8_t width) { + uint8_t w = 0; + for (uint8_t i = 0; i < 11; i++) { + if (dir.name[i] == ' ') { + continue; + } + if (i == 8) { + Serial.print('.'); + w++; + } + Serial.write(dir.name[i]); + w++; + } + if (DIR_IS_SUBDIR(&dir)) { + Serial.print('/'); + w++; + } + while (w < width) { + Serial.print(' '); + w++; + } +} +//------------------------------------------------------------------------------ +/** %Print a directory date field to Serial. + + Format is yyyy-mm-dd. + + \param[in] fatDate The date field from a directory entry. +*/ +void SdFile::printFatDate(uint16_t fatDate) { + Serial.print(FAT_YEAR(fatDate)); + Serial.print('-'); + printTwoDigits(FAT_MONTH(fatDate)); + Serial.print('-'); + printTwoDigits(FAT_DAY(fatDate)); +} +//------------------------------------------------------------------------------ +/** %Print a directory time field to Serial. + + Format is hh:mm:ss. + + \param[in] fatTime The time field from a directory entry. +*/ +void SdFile::printFatTime(uint16_t fatTime) { + printTwoDigits(FAT_HOUR(fatTime)); + Serial.print(':'); + printTwoDigits(FAT_MINUTE(fatTime)); + Serial.print(':'); + printTwoDigits(FAT_SECOND(fatTime)); +} +//------------------------------------------------------------------------------ +/** %Print a value as two digits to Serial. + + \param[in] v Value to be printed, 0 <= \a v <= 99 +*/ +void SdFile::printTwoDigits(uint8_t v) { + char str[3]; + str[0] = '0' + v / 10; + str[1] = '0' + v % 10; + str[2] = 0; + Serial.print(str); +} +//------------------------------------------------------------------------------ +/** + Read data from a file starting at the current position. + + \param[out] buf Pointer to the location that will receive the data. + + \param[in] nbyte Maximum number of bytes to read. + + \return For success read() returns the number of bytes read. + A value less than \a nbyte, including zero, will be returned + if end of file is reached. + If an error occurs, read() returns -1. Possible errors include + read() called before a file has been opened, corrupt file system + or an I/O error occurred. +*/ +int16_t SdFile::read(void* buf, uint16_t nbyte) { + uint8_t* dst = reinterpret_cast(buf); + + // error if not open or write only + if (!isOpen() || !(flags_ & O_READ)) { + return -1; + } + + // max bytes left in file + if (nbyte > (fileSize_ - curPosition_)) { + nbyte = fileSize_ - curPosition_; + } + + // amount left to read + uint16_t toRead = nbyte; + while (toRead > 0) { + uint32_t block; // raw device block number + uint16_t offset = curPosition_ & 0X1FF; // offset in block + if (type_ == FAT_FILE_TYPE_ROOT16) { + block = vol_->rootDirStart() + (curPosition_ >> 9); + } else { + uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); + if (offset == 0 && blockOfCluster == 0) { + // start of new cluster + if (curPosition_ == 0) { + // use first cluster in file + curCluster_ = firstCluster_; + } else { + // get next cluster from FAT + if (!vol_->fatGet(curCluster_, &curCluster_)) { + return -1; + } + } + } + block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; + } + uint16_t n = toRead; + + // amount to be read from current block + if (n > (512 - offset)) { + n = 512 - offset; + } + + // no buffering needed if n == 512 or user requests no buffering + if ((unbufferedRead() || n == 512) && + block != SdVolume::cacheBlockNumber_) { + if (!vol_->readData(block, offset, n, dst)) { + return -1; + } + dst += n; + } else { + // read block to cache and copy data to caller + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_READ)) { + return -1; + } + uint8_t* src = SdVolume::cacheBuffer_.data + offset; + uint8_t* end = src + n; + while (src != end) { + *dst++ = *src++; + } + } + curPosition_ += n; + toRead -= n; + } + return nbyte; +} +//------------------------------------------------------------------------------ +/** + Read the next directory entry from a directory file. + + \param[out] dir The dir_t struct that will receive the data. + + \return For success readDir() returns the number of bytes read. + A value of zero will be returned if end of file is reached. + If an error occurs, readDir() returns -1. Possible errors include + readDir() called before a directory has been opened, this is not + a directory file or an I/O error occurred. +*/ +int8_t SdFile::readDir(dir_t* dir) { + int8_t n; + // if not a directory file or miss-positioned return an error + if (!isDir() || (0X1F & curPosition_)) { + return -1; + } + + while ((n = read(dir, sizeof(dir_t))) == sizeof(dir_t)) { + // last entry if DIR_NAME_FREE + if (dir->name[0] == DIR_NAME_FREE) { + break; + } + // skip empty entries and entry for . and .. + if (dir->name[0] == DIR_NAME_DELETED || dir->name[0] == '.') { + continue; + } + // return if normal file or subdirectory + if (DIR_IS_FILE_OR_SUBDIR(dir)) { + return n; + } + } + // error, end of file, or past last entry + return n < 0 ? -1 : 0; +} +//------------------------------------------------------------------------------ +// Read next directory entry into the cache +// Assumes file is correctly positioned +dir_t* SdFile::readDirCache(void) { + // error if not directory + if (!isDir()) { + return NULL; + } + + // index of entry in cache + uint8_t i = (curPosition_ >> 5) & 0XF; + + // use read to locate and cache block + if (read() < 0) { + return NULL; + } + + // advance to next entry + curPosition_ += 31; + + // return pointer to entry + return (SdVolume::cacheBuffer_.dir + i); +} +//------------------------------------------------------------------------------ +/** + Remove a file. + + The directory entry and all data for the file are deleted. + + \note This function should not be used to delete the 8.3 version of a + file that has a long name. For example if a file has the long name + "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file read-only, is a directory, + or an I/O error occurred. +*/ +uint8_t SdFile::remove(void) { + // free any clusters - will fail if read-only or directory + if (!truncate(0)) { + return false; + } + + // cache directory entry + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + // mark entry deleted + d->name[0] = DIR_NAME_DELETED; + + // set this SdFile closed + type_ = FAT_FILE_TYPE_CLOSED; + + // write entry to SD + return SdVolume::cacheFlush(); +} +//------------------------------------------------------------------------------ +/** + Remove a file. + + The directory entry and all data for the file are deleted. + + \param[in] dirFile The directory that contains the file. + \param[in] fileName The name of the file to be removed. + + \note This function should not be used to delete the 8.3 version of a + file that has a long name. For example if a file has the long name + "New Text Document.txt" you should not delete the 8.3 name "NEWTEX~1.TXT". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file is a directory, is read only, + \a dirFile is not a directory, \a fileName is not found + or an I/O error occurred. +*/ +uint8_t SdFile::remove(SdFile* dirFile, const char* fileName) { + SdFile file; + if (!file.open(dirFile, fileName, O_WRITE)) { + return false; + } + return file.remove(); +} +//------------------------------------------------------------------------------ +/** Remove a directory file. + + The directory file will be removed only if it is empty and is not the + root directory. rmDir() follows DOS and Windows and ignores the + read-only attribute for the directory. + + \note This function should not be used to delete the 8.3 version of a + directory that has a long name. For example if a directory has the + long name "New folder" you should not delete the 8.3 name "NEWFOL~1". + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include the file is not a directory, is the root + directory, is not empty, or an I/O error occurred. +*/ +uint8_t SdFile::rmDir(void) { + // must be open subdirectory + if (!isSubDir()) { + return false; + } + + rewind(); + + // make sure directory is empty + while (curPosition_ < fileSize_) { + dir_t* p = readDirCache(); + if (p == NULL) { + return false; + } + // done if past last used entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + // skip empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + // error not empty + if (DIR_IS_FILE_OR_SUBDIR(p)) { + return false; + } + } + // convert empty directory to normal file for remove + type_ = FAT_FILE_TYPE_NORMAL; + flags_ |= O_WRITE; + return remove(); +} +//------------------------------------------------------------------------------ +/** Recursively delete a directory and all contained files. + + This is like the Unix/Linux 'rm -rf *' if called with the root directory + hence the name. + + Warning - This will remove all contents of the directory including + subdirectories. The directory will then be removed if it is not root. + The read-only attribute for files will be ignored. + + \note This function should not be used to delete the 8.3 version of + a directory that has a long name. See remove() and rmDir(). + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::rmRfStar(void) { + rewind(); + while (curPosition_ < fileSize_) { + SdFile f; + + // remember position + uint16_t index = curPosition_ / 32; + + dir_t* p = readDirCache(); + if (!p) { + return false; + } + + // done if past last entry + if (p->name[0] == DIR_NAME_FREE) { + break; + } + + // skip empty slot or '.' or '..' + if (p->name[0] == DIR_NAME_DELETED || p->name[0] == '.') { + continue; + } + + // skip if part of long file name or volume label in root + if (!DIR_IS_FILE_OR_SUBDIR(p)) { + continue; + } + + if (!f.open(this, index, O_READ)) { + return false; + } + if (f.isSubDir()) { + // recursively delete + if (!f.rmRfStar()) { + return false; + } + } else { + // ignore read-only + f.flags_ |= O_WRITE; + if (!f.remove()) { + return false; + } + } + // position to next entry if required + if (curPosition_ != (32u * (index + 1))) { + if (!seekSet(32u * (index + 1))) { + return false; + } + } + } + // don't try to delete root + if (isRoot()) { + return true; + } + return rmDir(); +} +//------------------------------------------------------------------------------ +/** + Sets a file's position. + + \param[in] pos The new position in bytes from the beginning of the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::seekSet(uint32_t pos) { + // error if file not open or seek past end of file + if (!isOpen() || pos > fileSize_) { + return false; + } + + if (type_ == FAT_FILE_TYPE_ROOT16) { + curPosition_ = pos; + return true; + } + if (pos == 0) { + // set position to start of file + curCluster_ = 0; + curPosition_ = 0; + return true; + } + // calculate cluster index for cur and new position + uint32_t nCur = (curPosition_ - 1) >> (vol_->clusterSizeShift_ + 9); + uint32_t nNew = (pos - 1) >> (vol_->clusterSizeShift_ + 9); + + if (nNew < nCur || curPosition_ == 0) { + // must follow chain from first cluster + curCluster_ = firstCluster_; + } else { + // advance from curPosition + nNew -= nCur; + } + while (nNew--) { + if (!vol_->fatGet(curCluster_, &curCluster_)) { + return false; + } + } + curPosition_ = pos; + return true; +} +//------------------------------------------------------------------------------ +/** + The sync() call causes all modified data and directory fields + to be written to the storage device. + + \param[in] blocking If the sync should block until fully complete. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include a call to sync() before a file has been + opened or an I/O error. +*/ +uint8_t SdFile::sync(uint8_t blocking) { + // only allow open files and directories + if (!isOpen()) { + return false; + } + + if (flags_ & F_FILE_DIR_DIRTY) { + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + // do not set filesize for dir files + if (!isDir()) { + d->fileSize = fileSize_; + } + + // update first cluster fields + d->firstClusterLow = firstCluster_ & 0XFFFF; + d->firstClusterHigh = firstCluster_ >> 16; + + // set modify time if user supplied a callback date/time function + if (dateTime_) { + dateTime_(&d->lastWriteDate, &d->lastWriteTime); + d->lastAccessDate = d->lastWriteDate; + } + // clear directory dirty + flags_ &= ~F_FILE_DIR_DIRTY; + } + + if (!blocking) { + flags_ &= ~F_FILE_NON_BLOCKING_WRITE; + } + + return SdVolume::cacheFlush(blocking); +} +//------------------------------------------------------------------------------ +/** + Set a file's timestamps in its directory entry. + + \param[in] flags Values for \a flags are constructed by a bitwise-inclusive + OR of flags from the following list + + T_ACCESS - Set the file's last access date. + + T_CREATE - Set the file's creation date and time. + + T_WRITE - Set the file's last write/modification date and time. + + \param[in] year Valid range 1980 - 2107 inclusive. + + \param[in] month Valid range 1 - 12 inclusive. + + \param[in] day Valid range 1 - 31 inclusive. + + \param[in] hour Valid range 0 - 23 inclusive. + + \param[in] minute Valid range 0 - 59 inclusive. + + \param[in] second Valid range 0 - 59 inclusive + + \note It is possible to set an invalid date since there is no check for + the number of days in a month. + + \note + Modify and access timestamps may be overwritten if a date time callback + function has been set by dateTimeCallback(). + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. +*/ +uint8_t SdFile::timestamp(uint8_t flags, uint16_t year, uint8_t month, + uint8_t day, uint8_t hour, uint8_t minute, uint8_t second) { + if (!isOpen() + || year < 1980 + || year > 2107 + || month < 1 + || month > 12 + || day < 1 + || day > 31 + || hour > 23 + || minute > 59 + || second > 59) { + return false; + } + dir_t* d = cacheDirEntry(SdVolume::CACHE_FOR_WRITE); + if (!d) { + return false; + } + + uint16_t dirDate = FAT_DATE(year, month, day); + uint16_t dirTime = FAT_TIME(hour, minute, second); + if (flags & T_ACCESS) { + d->lastAccessDate = dirDate; + } + if (flags & T_CREATE) { + d->creationDate = dirDate; + d->creationTime = dirTime; + // seems to be units of 1/100 second not 1/10 as Microsoft states + d->creationTimeTenths = second & 1 ? 100 : 0; + } + if (flags & T_WRITE) { + d->lastWriteDate = dirDate; + d->lastWriteTime = dirTime; + } + SdVolume::cacheSetDirty(); + return sync(); +} +//------------------------------------------------------------------------------ +/** + Truncate a file to a specified length. The current file position + will be maintained if it is less than or equal to \a length otherwise + it will be set to end of file. + + \param[in] length The desired length for the file. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. + Reasons for failure include file is read only, file is a directory, + \a length is greater than the current file size or an I/O error occurs. +*/ +uint8_t SdFile::truncate(uint32_t length) { + // error if not a normal file or read-only + if (!isFile() || !(flags_ & O_WRITE)) { + return false; + } + + // error if length is greater than current size + if (length > fileSize_) { + return false; + } + + // fileSize and length are zero - nothing to do + if (fileSize_ == 0) { + return true; + } + + // remember position for seek after truncation + uint32_t newPos = curPosition_ > length ? length : curPosition_; + + // position to last cluster in truncated file + if (!seekSet(length)) { + return false; + } + + if (length == 0) { + // free all clusters + if (!vol_->freeChain(firstCluster_)) { + return false; + } + firstCluster_ = 0; + } else { + uint32_t toFree; + if (!vol_->fatGet(curCluster_, &toFree)) { + return false; + } + + if (!vol_->isEOC(toFree)) { + // free extra clusters + if (!vol_->freeChain(toFree)) { + return false; + } + + // current cluster is end of chain + if (!vol_->fatPutEOC(curCluster_)) { + return false; + } + } + } + fileSize_ = length; + + // need to update directory entry + flags_ |= F_FILE_DIR_DIRTY; + + if (!sync()) { + return false; + } + + // set file to correct position + return seekSet(newPos); +} +//------------------------------------------------------------------------------ +/** + Write data to an open file. + + \note Data is moved to the cache but may not be written to the + storage device until sync() is called. + + \param[in] buf Pointer to the location of the data to be written. + + \param[in] nbyte Number of bytes to write. + + \return For success write() returns the number of bytes written, always + \a nbyte. If an error occurs, write() returns 0. Possible errors + include write() is called before a file has been opened, write is called + for a read-only file, device is full, a corrupt file system or an I/O error. + +*/ +size_t SdFile::write(const void* buf, uint16_t nbyte) { + // convert void* to uint8_t* - must be before goto statements + const uint8_t* src = reinterpret_cast(buf); + + // number of bytes left to write - must be before goto statements + uint16_t nToWrite = nbyte; + // if blocking writes should be used + uint8_t blocking = (flags_ & F_FILE_NON_BLOCKING_WRITE) == 0x00; + + // error if not a normal file or is read-only + if (!isFile() || !(flags_ & O_WRITE)) { + goto writeErrorReturn; + } + + // seek to end of file if append flag + if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { + if (!seekEnd()) { + goto writeErrorReturn; + } + } + + while (nToWrite > 0) { + uint8_t blockOfCluster = vol_->blockOfCluster(curPosition_); + uint16_t blockOffset = curPosition_ & 0X1FF; + if (blockOfCluster == 0 && blockOffset == 0) { + // start of new cluster + if (curCluster_ == 0) { + if (firstCluster_ == 0) { + // allocate first cluster of file + if (!addCluster()) { + goto writeErrorReturn; + } + } else { + curCluster_ = firstCluster_; + } + } else { + uint32_t next; + if (!vol_->fatGet(curCluster_, &next)) { + return false; + } + if (vol_->isEOC(next)) { + // add cluster if at end of chain + if (!addCluster()) { + goto writeErrorReturn; + } + } else { + curCluster_ = next; + } + } + } + // max space in block + uint16_t n = 512 - blockOffset; + + // lesser of space and amount to write + if (n > nToWrite) { + n = nToWrite; + } + + // block for data write + uint32_t block = vol_->clusterStartBlock(curCluster_) + blockOfCluster; + if (n == 512) { + // full block - don't need to use cache + // invalidate cache if block is in cache + if (SdVolume::cacheBlockNumber_ == block) { + SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; + } + if (!vol_->writeBlock(block, src, blocking)) { + goto writeErrorReturn; + } + src += 512; + } else { + if (blockOffset == 0 && curPosition_ >= fileSize_) { + // start of new block don't need to read into cache + if (!SdVolume::cacheFlush()) { + goto writeErrorReturn; + } + SdVolume::cacheBlockNumber_ = block; + SdVolume::cacheSetDirty(); + } else { + // rewrite part of block + if (!SdVolume::cacheRawBlock(block, SdVolume::CACHE_FOR_WRITE)) { + goto writeErrorReturn; + } + } + uint8_t* dst = SdVolume::cacheBuffer_.data + blockOffset; + uint8_t* end = dst + n; + while (dst != end) { + *dst++ = *src++; + } + } + nToWrite -= n; + curPosition_ += n; + } + if (curPosition_ > fileSize_) { + // update fileSize and insure sync will update dir entry + fileSize_ = curPosition_; + flags_ |= F_FILE_DIR_DIRTY; + } else if (dateTime_ && nbyte) { + // insure sync will update modified date and time + flags_ |= F_FILE_DIR_DIRTY; + } + + if (flags_ & O_SYNC) { + if (!sync()) { + goto writeErrorReturn; + } + } + return nbyte; + +writeErrorReturn: + // return for write error + //writeError = true; + setWriteError(); + return 0; +} +//------------------------------------------------------------------------------ +/** + Write a byte to a file. Required by the Arduino Print class. + + Use SdFile::writeError to check for errors. +*/ +size_t SdFile::write(uint8_t b) { + return write(&b, 1); +} +//------------------------------------------------------------------------------ +/** + Write a string to a file. Used by the Arduino Print class. + + Use SdFile::writeError to check for errors. +*/ +size_t SdFile::write(const char* str) { + return write(str, strlen(str)); +} +#ifdef __AVR__ +//------------------------------------------------------------------------------ +/** + Write a PROGMEM string to a file. + + Use SdFile::writeError to check for errors. +*/ +void SdFile::write_P(PGM_P str) { + for (uint8_t c; (c = pgm_read_byte(str)); str++) { + write(c); + } +} +//------------------------------------------------------------------------------ +/** + Write a PROGMEM string followed by CR/LF to a file. + + Use SdFile::writeError to check for errors. +*/ +void SdFile::writeln_P(PGM_P str) { + write_P(str); + println(); +} +#endif +//------------------------------------------------------------------------------ +/** + Check how many bytes can be written without blocking. + + \return The number of bytes that can be written without blocking. +*/ +int SdFile::availableForWrite() { + if (!isFile() || !(flags_ & O_WRITE)) { + return 0; + } + + // seek to end of file if append flag + if ((flags_ & O_APPEND) && curPosition_ != fileSize_) { + if (!seekEnd()) { + return 0; + } + } + + if (vol_->isBusy()) { + return 0; + } + + if (flags_ & F_FILE_CLUSTER_ADDED) { + // new cluster added, trigger a non-blocking sync + sync(0); + flags_ &= ~F_FILE_CLUSTER_ADDED; + return 0; + } + + if (vol_->isCacheMirrorBlockDirty()) { + // cache mirror block is dirty, trigger a non-blocking sync + vol_->cacheMirrorBlockFlush(0); + return 0; + } + + flags_ |= F_FILE_NON_BLOCKING_WRITE; + + uint16_t blockOffset = curPosition_ & 0X1FF; + uint16_t n = 512 - blockOffset; + + return n; +} diff --git a/megaavr/libraries/SD/src/utility/SdInfo.h b/megaavr/libraries/SD/src/utility/SdInfo.h index 6a0e087..e9c80db 100755 --- a/megaavr/libraries/SD/src/utility/SdInfo.h +++ b/megaavr/libraries/SD/src/utility/SdInfo.h @@ -1,232 +1,232 @@ -/* Arduino Sd2Card Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino Sd2Card Library - - This Library 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 Library 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 the Arduino Sd2Card Library. If not, see - . -*/ -#ifndef SdInfo_h -#define SdInfo_h -#include -// Based on the document: -// -// SD Specifications -// Part 1 -// Physical Layer -// Simplified Specification -// Version 2.00 -// September 25, 2006 -// -// www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf -//------------------------------------------------------------------------------ -// SD card commands -/** GO_IDLE_STATE - init card in spi mode if CS low */ -uint8_t const CMD0 = 0X00; -/** SEND_IF_COND - verify SD Memory Card interface operating condition.*/ -uint8_t const CMD8 = 0X08; -/** SEND_CSD - read the Card Specific Data (CSD register) */ -uint8_t const CMD9 = 0X09; -/** SEND_CID - read the card identification information (CID register) */ -uint8_t const CMD10 = 0X0A; -/** SEND_STATUS - read the card status register */ -uint8_t const CMD13 = 0X0D; -/** READ_BLOCK - read a single data block from the card */ -uint8_t const CMD17 = 0X11; -/** WRITE_BLOCK - write a single data block to the card */ -uint8_t const CMD24 = 0X18; -/** WRITE_MULTIPLE_BLOCK - write blocks of data until a STOP_TRANSMISSION */ -uint8_t const CMD25 = 0X19; -/** ERASE_WR_BLK_START - sets the address of the first block to be erased */ -uint8_t const CMD32 = 0X20; -/** ERASE_WR_BLK_END - sets the address of the last block of the continuous - range to be erased*/ -uint8_t const CMD33 = 0X21; -/** ERASE - erase all previously selected blocks */ -uint8_t const CMD38 = 0X26; -/** APP_CMD - escape for application specific command */ -uint8_t const CMD55 = 0X37; -/** READ_OCR - read the OCR register of a card */ -uint8_t const CMD58 = 0X3A; -/** SET_WR_BLK_ERASE_COUNT - Set the number of write blocks to be - pre-erased before writing */ -uint8_t const ACMD23 = 0X17; -/** SD_SEND_OP_COMD - Sends host capacity support information and - activates the card's initialization process */ -uint8_t const ACMD41 = 0X29; -//------------------------------------------------------------------------------ -/** status for card in the ready state */ -uint8_t const R1_READY_STATE = 0X00; -/** status for card in the idle state */ -uint8_t const R1_IDLE_STATE = 0X01; -/** status bit for illegal command */ -uint8_t const R1_ILLEGAL_COMMAND = 0X04; -/** start data token for read or write single block*/ -uint8_t const DATA_START_BLOCK = 0XFE; -/** stop token for write multiple blocks*/ -uint8_t const STOP_TRAN_TOKEN = 0XFD; -/** start data token for write multiple blocks*/ -uint8_t const WRITE_MULTIPLE_TOKEN = 0XFC; -/** mask for data response tokens after a write block operation */ -uint8_t const DATA_RES_MASK = 0X1F; -/** write data accepted token */ -uint8_t const DATA_RES_ACCEPTED = 0X05; -//------------------------------------------------------------------------------ -typedef struct CID { - // byte 0 - uint8_t mid; // Manufacturer ID - // byte 1-2 - char oid[2]; // OEM/Application ID - // byte 3-7 - char pnm[5]; // Product name - // byte 8 - unsigned prv_m : 4; // Product revision n.m - unsigned prv_n : 4; - // byte 9-12 - uint32_t psn; // Product serial number - // byte 13 - unsigned mdt_year_high : 4; // Manufacturing date - unsigned reserved : 4; - // byte 14 - unsigned mdt_month : 4; - unsigned mdt_year_low : 4; - // byte 15 - unsigned always1 : 1; - unsigned crc : 7; -} cid_t; -//------------------------------------------------------------------------------ -// CSD for version 1.00 cards -typedef struct CSDV1 { - // byte 0 - unsigned reserved1 : 6; - unsigned csd_ver : 2; - // byte 1 - uint8_t taac; - // byte 2 - uint8_t nsac; - // byte 3 - uint8_t tran_speed; - // byte 4 - uint8_t ccc_high; - // byte 5 - unsigned read_bl_len : 4; - unsigned ccc_low : 4; - // byte 6 - unsigned c_size_high : 2; - unsigned reserved2 : 2; - unsigned dsr_imp : 1; - unsigned read_blk_misalign : 1; - unsigned write_blk_misalign : 1; - unsigned read_bl_partial : 1; - // byte 7 - uint8_t c_size_mid; - // byte 8 - unsigned vdd_r_curr_max : 3; - unsigned vdd_r_curr_min : 3; - unsigned c_size_low : 2; - // byte 9 - unsigned c_size_mult_high : 2; - unsigned vdd_w_cur_max : 3; - unsigned vdd_w_curr_min : 3; - // byte 10 - unsigned sector_size_high : 6; - unsigned erase_blk_en : 1; - unsigned c_size_mult_low : 1; - // byte 11 - unsigned wp_grp_size : 7; - unsigned sector_size_low : 1; - // byte 12 - unsigned write_bl_len_high : 2; - unsigned r2w_factor : 3; - unsigned reserved3 : 2; - unsigned wp_grp_enable : 1; - // byte 13 - unsigned reserved4 : 5; - unsigned write_partial : 1; - unsigned write_bl_len_low : 2; - // byte 14 - unsigned reserved5: 2; - unsigned file_format : 2; - unsigned tmp_write_protect : 1; - unsigned perm_write_protect : 1; - unsigned copy : 1; - unsigned file_format_grp : 1; - // byte 15 - unsigned always1 : 1; - unsigned crc : 7; -} csd1_t; -//------------------------------------------------------------------------------ -// CSD for version 2.00 cards -typedef struct CSDV2 { - // byte 0 - unsigned reserved1 : 6; - unsigned csd_ver : 2; - // byte 1 - uint8_t taac; - // byte 2 - uint8_t nsac; - // byte 3 - uint8_t tran_speed; - // byte 4 - uint8_t ccc_high; - // byte 5 - unsigned read_bl_len : 4; - unsigned ccc_low : 4; - // byte 6 - unsigned reserved2 : 4; - unsigned dsr_imp : 1; - unsigned read_blk_misalign : 1; - unsigned write_blk_misalign : 1; - unsigned read_bl_partial : 1; - // byte 7 - unsigned reserved3 : 2; - unsigned c_size_high : 6; - // byte 8 - uint8_t c_size_mid; - // byte 9 - uint8_t c_size_low; - // byte 10 - unsigned sector_size_high : 6; - unsigned erase_blk_en : 1; - unsigned reserved4 : 1; - // byte 11 - unsigned wp_grp_size : 7; - unsigned sector_size_low : 1; - // byte 12 - unsigned write_bl_len_high : 2; - unsigned r2w_factor : 3; - unsigned reserved5 : 2; - unsigned wp_grp_enable : 1; - // byte 13 - unsigned reserved6 : 5; - unsigned write_partial : 1; - unsigned write_bl_len_low : 2; - // byte 14 - unsigned reserved7: 2; - unsigned file_format : 2; - unsigned tmp_write_protect : 1; - unsigned perm_write_protect : 1; - unsigned copy : 1; - unsigned file_format_grp : 1; - // byte 15 - unsigned always1 : 1; - unsigned crc : 7; -} csd2_t; -//------------------------------------------------------------------------------ -// union of old and new style CSD register -union csd_t { - csd1_t v1; - csd2_t v2; -}; -#endif // SdInfo_h +/* Arduino Sd2Card Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino Sd2Card Library + + This Library 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 Library 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 the Arduino Sd2Card Library. If not, see + . +*/ +#ifndef SdInfo_h +#define SdInfo_h +#include +// Based on the document: +// +// SD Specifications +// Part 1 +// Physical Layer +// Simplified Specification +// Version 2.00 +// September 25, 2006 +// +// www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf +//------------------------------------------------------------------------------ +// SD card commands +/** GO_IDLE_STATE - init card in spi mode if CS low */ +uint8_t const CMD0 = 0X00; +/** SEND_IF_COND - verify SD Memory Card interface operating condition.*/ +uint8_t const CMD8 = 0X08; +/** SEND_CSD - read the Card Specific Data (CSD register) */ +uint8_t const CMD9 = 0X09; +/** SEND_CID - read the card identification information (CID register) */ +uint8_t const CMD10 = 0X0A; +/** SEND_STATUS - read the card status register */ +uint8_t const CMD13 = 0X0D; +/** READ_BLOCK - read a single data block from the card */ +uint8_t const CMD17 = 0X11; +/** WRITE_BLOCK - write a single data block to the card */ +uint8_t const CMD24 = 0X18; +/** WRITE_MULTIPLE_BLOCK - write blocks of data until a STOP_TRANSMISSION */ +uint8_t const CMD25 = 0X19; +/** ERASE_WR_BLK_START - sets the address of the first block to be erased */ +uint8_t const CMD32 = 0X20; +/** ERASE_WR_BLK_END - sets the address of the last block of the continuous + range to be erased*/ +uint8_t const CMD33 = 0X21; +/** ERASE - erase all previously selected blocks */ +uint8_t const CMD38 = 0X26; +/** APP_CMD - escape for application specific command */ +uint8_t const CMD55 = 0X37; +/** READ_OCR - read the OCR register of a card */ +uint8_t const CMD58 = 0X3A; +/** SET_WR_BLK_ERASE_COUNT - Set the number of write blocks to be + pre-erased before writing */ +uint8_t const ACMD23 = 0X17; +/** SD_SEND_OP_COMD - Sends host capacity support information and + activates the card's initialization process */ +uint8_t const ACMD41 = 0X29; +//------------------------------------------------------------------------------ +/** status for card in the ready state */ +uint8_t const R1_READY_STATE = 0X00; +/** status for card in the idle state */ +uint8_t const R1_IDLE_STATE = 0X01; +/** status bit for illegal command */ +uint8_t const R1_ILLEGAL_COMMAND = 0X04; +/** start data token for read or write single block*/ +uint8_t const DATA_START_BLOCK = 0XFE; +/** stop token for write multiple blocks*/ +uint8_t const STOP_TRAN_TOKEN = 0XFD; +/** start data token for write multiple blocks*/ +uint8_t const WRITE_MULTIPLE_TOKEN = 0XFC; +/** mask for data response tokens after a write block operation */ +uint8_t const DATA_RES_MASK = 0X1F; +/** write data accepted token */ +uint8_t const DATA_RES_ACCEPTED = 0X05; +//------------------------------------------------------------------------------ +typedef struct CID { + // byte 0 + uint8_t mid; // Manufacturer ID + // byte 1-2 + char oid[2]; // OEM/Application ID + // byte 3-7 + char pnm[5]; // Product name + // byte 8 + unsigned prv_m : 4; // Product revision n.m + unsigned prv_n : 4; + // byte 9-12 + uint32_t psn; // Product serial number + // byte 13 + unsigned mdt_year_high : 4; // Manufacturing date + unsigned reserved : 4; + // byte 14 + unsigned mdt_month : 4; + unsigned mdt_year_low : 4; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} cid_t; +//------------------------------------------------------------------------------ +// CSD for version 1.00 cards +typedef struct CSDV1 { + // byte 0 + unsigned reserved1 : 6; + unsigned csd_ver : 2; + // byte 1 + uint8_t taac; + // byte 2 + uint8_t nsac; + // byte 3 + uint8_t tran_speed; + // byte 4 + uint8_t ccc_high; + // byte 5 + unsigned read_bl_len : 4; + unsigned ccc_low : 4; + // byte 6 + unsigned c_size_high : 2; + unsigned reserved2 : 2; + unsigned dsr_imp : 1; + unsigned read_blk_misalign : 1; + unsigned write_blk_misalign : 1; + unsigned read_bl_partial : 1; + // byte 7 + uint8_t c_size_mid; + // byte 8 + unsigned vdd_r_curr_max : 3; + unsigned vdd_r_curr_min : 3; + unsigned c_size_low : 2; + // byte 9 + unsigned c_size_mult_high : 2; + unsigned vdd_w_cur_max : 3; + unsigned vdd_w_curr_min : 3; + // byte 10 + unsigned sector_size_high : 6; + unsigned erase_blk_en : 1; + unsigned c_size_mult_low : 1; + // byte 11 + unsigned wp_grp_size : 7; + unsigned sector_size_low : 1; + // byte 12 + unsigned write_bl_len_high : 2; + unsigned r2w_factor : 3; + unsigned reserved3 : 2; + unsigned wp_grp_enable : 1; + // byte 13 + unsigned reserved4 : 5; + unsigned write_partial : 1; + unsigned write_bl_len_low : 2; + // byte 14 + unsigned reserved5: 2; + unsigned file_format : 2; + unsigned tmp_write_protect : 1; + unsigned perm_write_protect : 1; + unsigned copy : 1; + unsigned file_format_grp : 1; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} csd1_t; +//------------------------------------------------------------------------------ +// CSD for version 2.00 cards +typedef struct CSDV2 { + // byte 0 + unsigned reserved1 : 6; + unsigned csd_ver : 2; + // byte 1 + uint8_t taac; + // byte 2 + uint8_t nsac; + // byte 3 + uint8_t tran_speed; + // byte 4 + uint8_t ccc_high; + // byte 5 + unsigned read_bl_len : 4; + unsigned ccc_low : 4; + // byte 6 + unsigned reserved2 : 4; + unsigned dsr_imp : 1; + unsigned read_blk_misalign : 1; + unsigned write_blk_misalign : 1; + unsigned read_bl_partial : 1; + // byte 7 + unsigned reserved3 : 2; + unsigned c_size_high : 6; + // byte 8 + uint8_t c_size_mid; + // byte 9 + uint8_t c_size_low; + // byte 10 + unsigned sector_size_high : 6; + unsigned erase_blk_en : 1; + unsigned reserved4 : 1; + // byte 11 + unsigned wp_grp_size : 7; + unsigned sector_size_low : 1; + // byte 12 + unsigned write_bl_len_high : 2; + unsigned r2w_factor : 3; + unsigned reserved5 : 2; + unsigned wp_grp_enable : 1; + // byte 13 + unsigned reserved6 : 5; + unsigned write_partial : 1; + unsigned write_bl_len_low : 2; + // byte 14 + unsigned reserved7: 2; + unsigned file_format : 2; + unsigned tmp_write_protect : 1; + unsigned perm_write_protect : 1; + unsigned copy : 1; + unsigned file_format_grp : 1; + // byte 15 + unsigned always1 : 1; + unsigned crc : 7; +} csd2_t; +//------------------------------------------------------------------------------ +// union of old and new style CSD register +union csd_t { + csd1_t v1; + csd2_t v2; +}; +#endif // SdInfo_h diff --git a/megaavr/libraries/SD/src/utility/SdVolume.cpp b/megaavr/libraries/SD/src/utility/SdVolume.cpp index 60375c4..b8b6025 100755 --- a/megaavr/libraries/SD/src/utility/SdVolume.cpp +++ b/megaavr/libraries/SD/src/utility/SdVolume.cpp @@ -1,351 +1,351 @@ -/* Arduino SdFat Library - Copyright (C) 2009 by William Greiman - - This file is part of the Arduino SdFat Library - - This Library 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 Library 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 the Arduino SdFat Library. If not, see - . -*/ -#include "SdFat.h" -//------------------------------------------------------------------------------ -// raw block cache -// init cacheBlockNumber_to invalid SD block number -uint32_t SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; -cache_t SdVolume::cacheBuffer_; // 512 byte cache for Sd2Card -Sd2Card* SdVolume::sdCard_; // pointer to SD card object -uint8_t SdVolume::cacheDirty_ = 0; // cacheFlush() will write block if true -uint32_t SdVolume::cacheMirrorBlock_ = 0; // mirror block for second FAT -//------------------------------------------------------------------------------ -// find a contiguous group of clusters -uint8_t SdVolume::allocContiguous(uint32_t count, uint32_t* curCluster) { - // start of group - uint32_t bgnCluster; - - // flag to save place to start next search - uint8_t setStart; - - // set search start cluster - if (*curCluster) { - // try to make file contiguous - bgnCluster = *curCluster + 1; - - // don't save new start location - setStart = false; - } else { - // start at likely place for free cluster - bgnCluster = allocSearchStart_; - - // save next search start if one cluster - setStart = 1 == count; - } - // end of group - uint32_t endCluster = bgnCluster; - - // last cluster of FAT - uint32_t fatEnd = clusterCount_ + 1; - - // search the FAT for free clusters - for (uint32_t n = 0;; n++, endCluster++) { - // can't find space checked all clusters - if (n >= clusterCount_) { - return false; - } - - // past end - start from beginning of FAT - if (endCluster > fatEnd) { - bgnCluster = endCluster = 2; - } - uint32_t f; - if (!fatGet(endCluster, &f)) { - return false; - } - - if (f != 0) { - // cluster in use try next cluster as bgnCluster - bgnCluster = endCluster + 1; - } else if ((endCluster - bgnCluster + 1) == count) { - // done - found space - break; - } - } - // mark end of chain - if (!fatPutEOC(endCluster)) { - return false; - } - - // link clusters - while (endCluster > bgnCluster) { - if (!fatPut(endCluster - 1, endCluster)) { - return false; - } - endCluster--; - } - if (*curCluster != 0) { - // connect chains - if (!fatPut(*curCluster, bgnCluster)) { - return false; - } - } - // return first cluster number to caller - *curCluster = bgnCluster; - - // remember possible next free cluster - if (setStart) { - allocSearchStart_ = bgnCluster + 1; - } - - return true; -} -//------------------------------------------------------------------------------ -uint8_t SdVolume::cacheFlush(uint8_t blocking) { - if (cacheDirty_) { - if (!sdCard_->writeBlock(cacheBlockNumber_, cacheBuffer_.data, blocking)) { - return false; - } - - if (!blocking) { - return true; - } - - // mirror FAT tables - if (!cacheMirrorBlockFlush(blocking)) { - return false; - } - cacheDirty_ = 0; - } - return true; -} -//------------------------------------------------------------------------------ -uint8_t SdVolume::cacheMirrorBlockFlush(uint8_t blocking) { - if (cacheMirrorBlock_) { - if (!sdCard_->writeBlock(cacheMirrorBlock_, cacheBuffer_.data, blocking)) { - return false; - } - cacheMirrorBlock_ = 0; - } - return true; -} -//------------------------------------------------------------------------------ -uint8_t SdVolume::cacheRawBlock(uint32_t blockNumber, uint8_t action) { - if (cacheBlockNumber_ != blockNumber) { - if (!cacheFlush()) { - return false; - } - if (!sdCard_->readBlock(blockNumber, cacheBuffer_.data)) { - return false; - } - cacheBlockNumber_ = blockNumber; - } - cacheDirty_ |= action; - return true; -} -//------------------------------------------------------------------------------ -// cache a zero block for blockNumber -uint8_t SdVolume::cacheZeroBlock(uint32_t blockNumber) { - if (!cacheFlush()) { - return false; - } - - // loop take less flash than memset(cacheBuffer_.data, 0, 512); - for (uint16_t i = 0; i < 512; i++) { - cacheBuffer_.data[i] = 0; - } - cacheBlockNumber_ = blockNumber; - cacheSetDirty(); - return true; -} -//------------------------------------------------------------------------------ -// return the size in bytes of a cluster chain -uint8_t SdVolume::chainSize(uint32_t cluster, uint32_t* size) const { - uint32_t s = 0; - do { - if (!fatGet(cluster, &cluster)) { - return false; - } - s += 512UL << clusterSizeShift_; - } while (!isEOC(cluster)); - *size = s; - return true; -} -//------------------------------------------------------------------------------ -// Fetch a FAT entry -uint8_t SdVolume::fatGet(uint32_t cluster, uint32_t* value) const { - if (cluster > (clusterCount_ + 1)) { - return false; - } - uint32_t lba = fatStartBlock_; - lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; - if (lba != cacheBlockNumber_) { - if (!cacheRawBlock(lba, CACHE_FOR_READ)) { - return false; - } - } - if (fatType_ == 16) { - *value = cacheBuffer_.fat16[cluster & 0XFF]; - } else { - *value = cacheBuffer_.fat32[cluster & 0X7F] & FAT32MASK; - } - return true; -} -//------------------------------------------------------------------------------ -// Store a FAT entry -uint8_t SdVolume::fatPut(uint32_t cluster, uint32_t value) { - // error if reserved cluster - if (cluster < 2) { - return false; - } - - // error if not in FAT - if (cluster > (clusterCount_ + 1)) { - return false; - } - - // calculate block address for entry - uint32_t lba = fatStartBlock_; - lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; - - if (lba != cacheBlockNumber_) { - if (!cacheRawBlock(lba, CACHE_FOR_READ)) { - return false; - } - } - // store entry - if (fatType_ == 16) { - cacheBuffer_.fat16[cluster & 0XFF] = value; - } else { - cacheBuffer_.fat32[cluster & 0X7F] = value; - } - cacheSetDirty(); - - // mirror second FAT - if (fatCount_ > 1) { - cacheMirrorBlock_ = lba + blocksPerFat_; - } - return true; -} -//------------------------------------------------------------------------------ -// free a cluster chain -uint8_t SdVolume::freeChain(uint32_t cluster) { - // clear free cluster location - allocSearchStart_ = 2; - - do { - uint32_t next; - if (!fatGet(cluster, &next)) { - return false; - } - - // free cluster - if (!fatPut(cluster, 0)) { - return false; - } - - cluster = next; - } while (!isEOC(cluster)); - - return true; -} -//------------------------------------------------------------------------------ -/** - Initialize a FAT volume. - - \param[in] dev The SD card where the volume is located. - - \param[in] part The partition to be used. Legal values for \a part are - 1-4 to use the corresponding partition on a device formatted with - a MBR, Master Boot Record, or zero if the device is formatted as - a super floppy with the FAT boot sector in block zero. - - \return The value one, true, is returned for success and - the value zero, false, is returned for failure. Reasons for - failure include not finding a valid partition, not finding a valid - FAT file system in the specified partition or an I/O error. -*/ -uint8_t SdVolume::init(Sd2Card* dev, uint8_t part) { - uint32_t volumeStartBlock = 0; - sdCard_ = dev; - // if part == 0 assume super floppy with FAT boot sector in block zero - // if part > 0 assume mbr volume with partition table - if (part) { - if (part > 4) { - return false; - } - if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { - return false; - } - part_t* p = &cacheBuffer_.mbr.part[part - 1]; - if ((p->boot & 0X7F) != 0 || - p->totalSectors < 100 || - p->firstSector == 0) { - // not a valid partition - return false; - } - volumeStartBlock = p->firstSector; - } - if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { - return false; - } - bpb_t* bpb = &cacheBuffer_.fbs.bpb; - if (bpb->bytesPerSector != 512 || - bpb->fatCount == 0 || - bpb->reservedSectorCount == 0 || - bpb->sectorsPerCluster == 0) { - // not valid FAT volume - return false; - } - fatCount_ = bpb->fatCount; - blocksPerCluster_ = bpb->sectorsPerCluster; - - // determine shift that is same as multiply by blocksPerCluster_ - clusterSizeShift_ = 0; - while (blocksPerCluster_ != (1 << clusterSizeShift_)) { - // error if not power of 2 - if (clusterSizeShift_++ > 7) { - return false; - } - } - blocksPerFat_ = bpb->sectorsPerFat16 ? - bpb->sectorsPerFat16 : bpb->sectorsPerFat32; - - fatStartBlock_ = volumeStartBlock + bpb->reservedSectorCount; - - // count for FAT16 zero for FAT32 - rootDirEntryCount_ = bpb->rootDirEntryCount; - - // directory start for FAT16 dataStart for FAT32 - rootDirStart_ = fatStartBlock_ + bpb->fatCount * blocksPerFat_; - - // data start for FAT16 and FAT32 - dataStartBlock_ = rootDirStart_ + ((32 * bpb->rootDirEntryCount + 511) / 512); - - // total blocks for FAT16 or FAT32 - uint32_t totalBlocks = bpb->totalSectors16 ? - bpb->totalSectors16 : bpb->totalSectors32; - // total data blocks - clusterCount_ = totalBlocks - (dataStartBlock_ - volumeStartBlock); - - // divide by cluster size to get cluster count - clusterCount_ >>= clusterSizeShift_; - - // FAT type is determined by cluster count - if (clusterCount_ < 4085) { - fatType_ = 12; - } else if (clusterCount_ < 65525) { - fatType_ = 16; - } else { - rootDirStart_ = bpb->fat32RootCluster; - fatType_ = 32; - } - return true; -} +/* Arduino SdFat Library + Copyright (C) 2009 by William Greiman + + This file is part of the Arduino SdFat Library + + This Library 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 Library 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 the Arduino SdFat Library. If not, see + . +*/ +#include "SdFat.h" +//------------------------------------------------------------------------------ +// raw block cache +// init cacheBlockNumber_to invalid SD block number +uint32_t SdVolume::cacheBlockNumber_ = 0XFFFFFFFF; +cache_t SdVolume::cacheBuffer_; // 512 byte cache for Sd2Card +Sd2Card* SdVolume::sdCard_; // pointer to SD card object +uint8_t SdVolume::cacheDirty_ = 0; // cacheFlush() will write block if true +uint32_t SdVolume::cacheMirrorBlock_ = 0; // mirror block for second FAT +//------------------------------------------------------------------------------ +// find a contiguous group of clusters +uint8_t SdVolume::allocContiguous(uint32_t count, uint32_t* curCluster) { + // start of group + uint32_t bgnCluster; + + // flag to save place to start next search + uint8_t setStart; + + // set search start cluster + if (*curCluster) { + // try to make file contiguous + bgnCluster = *curCluster + 1; + + // don't save new start location + setStart = false; + } else { + // start at likely place for free cluster + bgnCluster = allocSearchStart_; + + // save next search start if one cluster + setStart = 1 == count; + } + // end of group + uint32_t endCluster = bgnCluster; + + // last cluster of FAT + uint32_t fatEnd = clusterCount_ + 1; + + // search the FAT for free clusters + for (uint32_t n = 0;; n++, endCluster++) { + // can't find space checked all clusters + if (n >= clusterCount_) { + return false; + } + + // past end - start from beginning of FAT + if (endCluster > fatEnd) { + bgnCluster = endCluster = 2; + } + uint32_t f; + if (!fatGet(endCluster, &f)) { + return false; + } + + if (f != 0) { + // cluster in use try next cluster as bgnCluster + bgnCluster = endCluster + 1; + } else if ((endCluster - bgnCluster + 1) == count) { + // done - found space + break; + } + } + // mark end of chain + if (!fatPutEOC(endCluster)) { + return false; + } + + // link clusters + while (endCluster > bgnCluster) { + if (!fatPut(endCluster - 1, endCluster)) { + return false; + } + endCluster--; + } + if (*curCluster != 0) { + // connect chains + if (!fatPut(*curCluster, bgnCluster)) { + return false; + } + } + // return first cluster number to caller + *curCluster = bgnCluster; + + // remember possible next free cluster + if (setStart) { + allocSearchStart_ = bgnCluster + 1; + } + + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheFlush(uint8_t blocking) { + if (cacheDirty_) { + if (!sdCard_->writeBlock(cacheBlockNumber_, cacheBuffer_.data, blocking)) { + return false; + } + + if (!blocking) { + return true; + } + + // mirror FAT tables + if (!cacheMirrorBlockFlush(blocking)) { + return false; + } + cacheDirty_ = 0; + } + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheMirrorBlockFlush(uint8_t blocking) { + if (cacheMirrorBlock_) { + if (!sdCard_->writeBlock(cacheMirrorBlock_, cacheBuffer_.data, blocking)) { + return false; + } + cacheMirrorBlock_ = 0; + } + return true; +} +//------------------------------------------------------------------------------ +uint8_t SdVolume::cacheRawBlock(uint32_t blockNumber, uint8_t action) { + if (cacheBlockNumber_ != blockNumber) { + if (!cacheFlush()) { + return false; + } + if (!sdCard_->readBlock(blockNumber, cacheBuffer_.data)) { + return false; + } + cacheBlockNumber_ = blockNumber; + } + cacheDirty_ |= action; + return true; +} +//------------------------------------------------------------------------------ +// cache a zero block for blockNumber +uint8_t SdVolume::cacheZeroBlock(uint32_t blockNumber) { + if (!cacheFlush()) { + return false; + } + + // loop take less flash than memset(cacheBuffer_.data, 0, 512); + for (uint16_t i = 0; i < 512; i++) { + cacheBuffer_.data[i] = 0; + } + cacheBlockNumber_ = blockNumber; + cacheSetDirty(); + return true; +} +//------------------------------------------------------------------------------ +// return the size in bytes of a cluster chain +uint8_t SdVolume::chainSize(uint32_t cluster, uint32_t* size) const { + uint32_t s = 0; + do { + if (!fatGet(cluster, &cluster)) { + return false; + } + s += 512UL << clusterSizeShift_; + } while (!isEOC(cluster)); + *size = s; + return true; +} +//------------------------------------------------------------------------------ +// Fetch a FAT entry +uint8_t SdVolume::fatGet(uint32_t cluster, uint32_t* value) const { + if (cluster > (clusterCount_ + 1)) { + return false; + } + uint32_t lba = fatStartBlock_; + lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; + if (lba != cacheBlockNumber_) { + if (!cacheRawBlock(lba, CACHE_FOR_READ)) { + return false; + } + } + if (fatType_ == 16) { + *value = cacheBuffer_.fat16[cluster & 0XFF]; + } else { + *value = cacheBuffer_.fat32[cluster & 0X7F] & FAT32MASK; + } + return true; +} +//------------------------------------------------------------------------------ +// Store a FAT entry +uint8_t SdVolume::fatPut(uint32_t cluster, uint32_t value) { + // error if reserved cluster + if (cluster < 2) { + return false; + } + + // error if not in FAT + if (cluster > (clusterCount_ + 1)) { + return false; + } + + // calculate block address for entry + uint32_t lba = fatStartBlock_; + lba += fatType_ == 16 ? cluster >> 8 : cluster >> 7; + + if (lba != cacheBlockNumber_) { + if (!cacheRawBlock(lba, CACHE_FOR_READ)) { + return false; + } + } + // store entry + if (fatType_ == 16) { + cacheBuffer_.fat16[cluster & 0XFF] = value; + } else { + cacheBuffer_.fat32[cluster & 0X7F] = value; + } + cacheSetDirty(); + + // mirror second FAT + if (fatCount_ > 1) { + cacheMirrorBlock_ = lba + blocksPerFat_; + } + return true; +} +//------------------------------------------------------------------------------ +// free a cluster chain +uint8_t SdVolume::freeChain(uint32_t cluster) { + // clear free cluster location + allocSearchStart_ = 2; + + do { + uint32_t next; + if (!fatGet(cluster, &next)) { + return false; + } + + // free cluster + if (!fatPut(cluster, 0)) { + return false; + } + + cluster = next; + } while (!isEOC(cluster)); + + return true; +} +//------------------------------------------------------------------------------ +/** + Initialize a FAT volume. + + \param[in] dev The SD card where the volume is located. + + \param[in] part The partition to be used. Legal values for \a part are + 1-4 to use the corresponding partition on a device formatted with + a MBR, Master Boot Record, or zero if the device is formatted as + a super floppy with the FAT boot sector in block zero. + + \return The value one, true, is returned for success and + the value zero, false, is returned for failure. Reasons for + failure include not finding a valid partition, not finding a valid + FAT file system in the specified partition or an I/O error. +*/ +uint8_t SdVolume::init(Sd2Card* dev, uint8_t part) { + uint32_t volumeStartBlock = 0; + sdCard_ = dev; + // if part == 0 assume super floppy with FAT boot sector in block zero + // if part > 0 assume mbr volume with partition table + if (part) { + if (part > 4) { + return false; + } + if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { + return false; + } + part_t* p = &cacheBuffer_.mbr.part[part - 1]; + if ((p->boot & 0X7F) != 0 || + p->totalSectors < 100 || + p->firstSector == 0) { + // not a valid partition + return false; + } + volumeStartBlock = p->firstSector; + } + if (!cacheRawBlock(volumeStartBlock, CACHE_FOR_READ)) { + return false; + } + bpb_t* bpb = &cacheBuffer_.fbs.bpb; + if (bpb->bytesPerSector != 512 || + bpb->fatCount == 0 || + bpb->reservedSectorCount == 0 || + bpb->sectorsPerCluster == 0) { + // not valid FAT volume + return false; + } + fatCount_ = bpb->fatCount; + blocksPerCluster_ = bpb->sectorsPerCluster; + + // determine shift that is same as multiply by blocksPerCluster_ + clusterSizeShift_ = 0; + while (blocksPerCluster_ != (1 << clusterSizeShift_)) { + // error if not power of 2 + if (clusterSizeShift_++ > 7) { + return false; + } + } + blocksPerFat_ = bpb->sectorsPerFat16 ? + bpb->sectorsPerFat16 : bpb->sectorsPerFat32; + + fatStartBlock_ = volumeStartBlock + bpb->reservedSectorCount; + + // count for FAT16 zero for FAT32 + rootDirEntryCount_ = bpb->rootDirEntryCount; + + // directory start for FAT16 dataStart for FAT32 + rootDirStart_ = fatStartBlock_ + bpb->fatCount * blocksPerFat_; + + // data start for FAT16 and FAT32 + dataStartBlock_ = rootDirStart_ + ((32 * bpb->rootDirEntryCount + 511) / 512); + + // total blocks for FAT16 or FAT32 + uint32_t totalBlocks = bpb->totalSectors16 ? + bpb->totalSectors16 : bpb->totalSectors32; + // total data blocks + clusterCount_ = totalBlocks - (dataStartBlock_ - volumeStartBlock); + + // divide by cluster size to get cluster count + clusterCount_ >>= clusterSizeShift_; + + // FAT type is determined by cluster count + if (clusterCount_ < 4085) { + fatType_ = 12; + } else if (clusterCount_ < 65525) { + fatType_ = 16; + } else { + rootDirStart_ = bpb->fat32RootCluster; + fatType_ = 32; + } + return true; +} From 5c58cb438698192309dabf4c3eec040bb6516565 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 10 Apr 2021 12:21:58 +0200 Subject: [PATCH 246/351] Improve initialization routine It's now slightly more efficient --- .../libraries/Comparator/src/Comparator.cpp | 36 +++++-------------- megaavr/libraries/Comparator/src/Comparator.h | 6 ++-- 2 files changed, 12 insertions(+), 30 deletions(-) diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index 6f5afdf..c179de1 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -32,10 +32,10 @@ void AnalogComparator::init() // Set DACREF AC.DACREF = dacref; - // Set hysteresis - AC.CTRLA = (AC.CTRLA & ~AC_HYSMODE_gm) | hysteresis; + // Set hysteresis and output pin state + AC.CTRLA = (AC.CTRLA & ~AC_HYSMODE_gm) | hysteresis | (output & AC_OUTEN_bm); - // Set inputs + // Clear input pins if(input_p == in_p::in0) PORTD.PIN2CTRL = PORT_ISC_INPUT_DISABLE_gc; else if(input_p == in_p::in1) @@ -50,33 +50,15 @@ void AnalogComparator::init() PORTD.PIN5CTRL = PORT_ISC_INPUT_DISABLE_gc; else if(input_n == in_n::in2) PORTD.PIN7CTRL = PORT_ISC_INPUT_DISABLE_gc; - AC.MUXCTRLA = (AC.MUXCTRLA & ~0x1B) | (input_p << 3) | input_n; - // Set output - if(output == out::enable) - { - AC.MUXCTRLA &= ~out::invert; - AC.CTRLA |= out::enable; - PORTA.DIRSET = PIN7_bm; - } - else if(output == out::invert /* || output == out::invert_enable */) - { - AC.MUXCTRLA |= out::invert; - AC.CTRLA |= out::enable; + // Set positive and negative pins, invert output if defined by the user + AC.MUXCTRLA = (AC.MUXCTRLA & ~0x1B) | (input_p << 3) | input_n | (output & AC_INVERT_bm); + + // Set output if enabled + if(output & AC_OUTEN_bm) PORTA.DIRSET = PIN7_bm; - } - else if(output == out::disable) - { - AC.MUXCTRLA &= ~out::invert; - AC.CTRLA &= ~out::enable; - PORTA.DIRCLR = PIN7_bm; - } - else if(output == out::disable_invert) - { - AC.MUXCTRLA |= out::invert; - AC.CTRLA &= ~out::enable; + else PORTA.DIRCLR = PIN7_bm; - } } void AnalogComparator::start(bool state) diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 30450a4..6b49165 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -8,10 +8,10 @@ namespace out enum output_t : uint8_t { disable = 0x00, - disable_invert = 0xC0, + disable_invert = 0x80, enable = 0x40, - invert = 0x80, - enable_invert = 0x80, + invert = 0xC0, + enable_invert = 0xC0, }; }; From 026ed36f7acd2d8ad1a0e738359b47f22744bc02 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 10 Apr 2021 20:40:44 +0200 Subject: [PATCH 247/351] Add info about memory-mapped flash --- README.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/README.md b/README.md index 7bc1106..64286bd 100644 --- a/README.md +++ b/README.md @@ -23,6 +23,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Fast IO](#fast-io) * [Pin macros](#pin-macros) * [Write to own flash](#write-to-own-flash) +* [Memory-mapped flash](#memory-mapped-flash) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -146,6 +147,13 @@ For more information on how it works and how you can use this in you own applica [Flash_put_get](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino) + [Flash_iterate](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino) for useful examples on how you can store strings, structs and variables to flash and retrieve then afterwards. +## Memory-mapped flash +Unlike classic AVRs, the flash memory on these parts is within the same address space as the main memory. This means that functions like `pgm_read_byte()` and `pgm_read_word()` is not needed to read directly from flash. Because of this, the compiler automatically puts any variable declared const into PROGMEM, and accesses it appropriately - you no longer need to explicitly declare them as PROGMEM! +This also includes quoted strings, which means that the string in `Serial.print("Hello World");` won't consume any RAM. This means that the `F()` macro is not needed when working with MegaCoreX. + +If you explicitly declare a variable PROGMEM, you must still use the `pgm_read_byte()/pgm_read_word()` functions, just like on "classic" AVRs. Do note that declaring things PROGMEM or using the `F()` macro works fine, but it is slower and consumes more flash than simply declaring something `const` or omitting the `F()` macro. + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. From 5be3f30fbd196bc9dee0ecc660a6f7d64b95024b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 10 Apr 2021 21:29:43 +0200 Subject: [PATCH 248/351] Remove PROGMEM attributes It's much more elegant to utilize the memory mapped flash instead --- .../Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino | 4 +--- .../Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino | 2 +- .../Read_write_without_buffer/Read_write_without_buffer.ino | 2 +- .../examples/Serial_read_write/Serial_read_write.ino | 2 +- megaavr/libraries/Optiboot_flasher/src/optiboot.cpp | 4 ++-- 5 files changed, 6 insertions(+), 8 deletions(-) diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino index d91793f..a87750b 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino @@ -25,7 +25,7 @@ uint8_t ram_buffer[SPM_PAGESIZE]; // Allocate two flash pages for storing data #define NUMBER_OF_PAGES 2 -const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) = {}; // Flash constructor Flash flash(flashSpace, sizeof(flashSpace), ram_buffer, sizeof(ram_buffer)); @@ -53,8 +53,6 @@ void write_data() void read_data() { - Serial.println("Read float from flash page 0: "); - // Fetch first flash page flash.fetch_page(0); diff --git a/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino index 9a1e723..927dc7f 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino @@ -33,7 +33,7 @@ uint8_t ram_buffer[SPM_PAGESIZE]; // Allocate two flash pages for storing data #define NUMBER_OF_PAGES 2 -const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) = {}; // Flash constructor Flash flash(flashSpace, sizeof(flashSpace), ram_buffer, sizeof(ram_buffer)); diff --git a/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino b/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino index c11bb98..54a8716 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Read_write_without_buffer/Read_write_without_buffer.ino @@ -25,7 +25,7 @@ // Allocate one flash pages for storing data #define NUMBER_OF_PAGES 2 -const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) PROGMEM = {}; +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__((aligned(SPM_PAGESIZE))) = {}; // Function for writing 16-bit integers to a flash page diff --git a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino index c963e5a..c2dc370 100644 --- a/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino +++ b/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino @@ -42,7 +42,7 @@ const char terminationChar = '@'; uint8_t ramBuffer[SPM_PAGESIZE]; // This array allocates the space you'll be able to write to -const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__ (( aligned(SPM_PAGESIZE) )) PROGMEM = { +const uint8_t flashSpace[SPM_PAGESIZE * NUMBER_OF_PAGES] __attribute__ (( aligned(SPM_PAGESIZE) )) = { "This some default content stored on page one" }; diff --git a/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp index 8ab2c3f..122b515 100755 --- a/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp +++ b/megaavr/libraries/Optiboot_flasher/src/optiboot.cpp @@ -62,7 +62,7 @@ void optiboot_page_erase(optiboot_addr_t address) */ void optiboot_page_fill(optiboot_addr_t address, uint8_t data) { - do_nvmctrl(address + MAPPED_PROGMEM_START, NVMCTRL_CMD_COPY_gc, data); + do_nvmctrl(address, NVMCTRL_CMD_COPY_gc, data); } @@ -124,7 +124,7 @@ void optiboot_read(const uint8_t allocated_flash_space[], uint8_t storage_array[ { for(uint16_t j = start_address; j < stop_address; j++) { - uint8_t read_character = pgm_read_byte(&allocated_flash_space[j + SPM_PAGESIZE * (page_number)]); + uint8_t read_character = allocated_flash_space[j + SPM_PAGESIZE * (page_number)]; storage_array[j - start_address] = read_character; } } From 866ab18e69e9418ab7c44756447413059420816c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 11 Apr 2021 21:50:22 +0200 Subject: [PATCH 249/351] Add keyword highlighting library The only way to get Arduino IDE to highlight relevant AVR keywords --- megaavr/libraries/MegaCoreX/keywords.txt | 4319 +++++++++++++++++ .../libraries/MegaCoreX/library.properties | 10 + .../libraries/MegaCoreX/src/AVR_keywords.h | 1 + 3 files changed, 4330 insertions(+) create mode 100644 megaavr/libraries/MegaCoreX/keywords.txt create mode 100644 megaavr/libraries/MegaCoreX/library.properties create mode 100644 megaavr/libraries/MegaCoreX/src/AVR_keywords.h diff --git a/megaavr/libraries/MegaCoreX/keywords.txt b/megaavr/libraries/MegaCoreX/keywords.txt new file mode 100644 index 0000000..b746e2b --- /dev/null +++ b/megaavr/libraries/MegaCoreX/keywords.txt @@ -0,0 +1,4319 @@ +# This file is a work in progress. The plan is to add (all/most) AVR specific words, so +# they get highlighted in the Arduino IDE when used +# More libraries will be added later + +# FUNCTIONS are color coded with KEYWORD2 +# MACROS WITH PARAMETERS are are color coded with KEYWORD3 RESERVED_WORD +# MACROS WITHOUT PARAMETERS are color coded with LITERAL2 RESERVED_WORD_2 + + + +#OTHER +megacorex LITERAL2 RESERVED_WORD_2 +MegaCoreX LITERAL2 RESERVED_WORD_2 +MEGACOREX LITERAL2 RESERVED_WORD_2 +__AVR_ATmega808__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega809__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega1608__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega1609__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega3208__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega3209__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega4808__ LITERAL2 RESERVED_WORD_2 +__AVR_ATmega4809__ LITERAL2 RESERVED_WORD_2 + +__ASM__ KEYWORD3 RESERVED_WORD +F_CPU LITERAL2 RESERVED_WORD_2 +main KEYWORD3 RESERVED_WORD +size_t LITERAL2 RESERVED_WORD_2 +_SFR_IO8 KEYWORD3 RESERVED_WORD +_SFR_IO16 KEYWORD3 RESERVED_WORD +_SFR_MEM8 KEYWORD3 RESERVED_WORD +_SFR_MEM16 KEYWORD3 RESERVED_WORD + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__util__atomic.html +ATOMIC_BLOCK KEYWORD3 RESERVED_WORD +NONATOMIC_BLOCK KEYWORD3 RESERVED_WORD +ATOMIC_RESTORESTATE LITERAL2 RESERVED_WORD_2 +ATOMIC_FORCEON LITERAL2 RESERVED_WORD_2 +NONATOMIC_RESTORESTATE LITERAL2 RESERVED_WORD_2 +NONATOMIC_FORCEOFF LITERAL2 RESERVED_WORD_2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__sfr.html +bit_is_set KEYWORD3 RESERVED_WORD +bit_is_clear KEYWORD3 RESERVED_WORD +_BV KEYWORD3 RESERVED_WORD +loop_until_bit_is_set KEYWORD3 RESERVED_WORD +loop_until_bit_is_clear KEYWORD3 RESERVED_WORD + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__util__delay.html +_delay_ms KEYWORD2 +_delay_us KEYWORD2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__interrupts.html +ISR KEYWORD3 RESERVED_WORD +SIGNAL KEYWORD3 RESERVED_WORD +EMPTY_INTERRUPT KEYWORD3 RESERVED_WORD +ISR_ALIAS KEYWORD3 RESERVED_WORD +reti KEYWORD3 RESERVED_WORD +cli KEYWORD3 RESERVED_WORD +sei KEYWORD3 RESERVED_WORD +BADISR_vect LITERAL2 RESERVED_WORD_2 +ISR_BLOCK LITERAL2 RESERVED_WORD_2 +ISR_NOBLOCK LITERAL2 RESERVED_WORD_2 +ISR_NAKED LITERAL2 RESERVED_WORD_2 +ISR_ALIASOF KEYWORD3 RESERVED_WORD + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__math.html +M_E LITERAL2 RESERVED_WORD_2 +M_LOG2E LITERAL2 RESERVED_WORD_2 +M_LOG10E LITERAL2 RESERVED_WORD_2 +M_LN2 LITERAL2 RESERVED_WORD_2 +M_LN10 LITERAL2 RESERVED_WORD_2 +M_PI LITERAL2 RESERVED_WORD_2 +M_PI_2 LITERAL2 RESERVED_WORD_2 +M_PI_4 LITERAL2 RESERVED_WORD_2 +M_1_PI LITERAL2 RESERVED_WORD_2 +M_2_PI LITERAL2 RESERVED_WORD_2 +M_2_SQRTPI LITERAL2 RESERVED_WORD_2 +M_SQRT2 LITERAL2 RESERVED_WORD_2 +M_SQRT1_2 LITERAL2 RESERVED_WORD_2 +NAN LITERAL2 RESERVED_WORD_2 +INFINITY LITERAL2 RESERVED_WORD_2 +cosf KEYWORD3 RESERVED_WORD +sinf KEYWORD3 RESERVED_WORD +tanf KEYWORD3 RESERVED_WORD +fabsf KEYWORD3 RESERVED_WORD +fmodf KEYWORD3 RESERVED_WORD +cbrtf KEYWORD3 RESERVED_WORD +cbrt KEYWORD2 +hypotf KEYWORD3 RESERVED_WORD +hypot KEYWORD2 +squaref KEYWORD3 RESERVED_WORD +square KEYWORD2 +floorf KEYWORD3 RESERVED_WORD +ceilf KEYWORD3 RESERVED_WORD +frexpf KEYWORD3 RESERVED_WORD +ldexpf KEYWORD3 RESERVED_WORD +expf KEYWORD3 RESERVED_WORD +coshf KEYWORD3 RESERVED_WORD +sinhf KEYWORD3 RESERVED_WORD +tanhf KEYWORD3 RESERVED_WORD +acosf KEYWORD3 RESERVED_WORD +asinf KEYWORD3 RESERVED_WORD +atanf KEYWORD3 RESERVED_WORD +atan2f KEYWORD3 RESERVED_WORD +logf KEYWORD3 RESERVED_WORD +log10f KEYWORD3 RESERVED_WORD +powf KEYWORD3 RESERVED_WORD +isnanf KEYWORD3 RESERVED_WORD +isnan KEYWORD2 +isinff KEYWORD3 RESERVED_WORD +isinf KEYWORD2 +isfinitef KEYWORD3 RESERVED_WORD +isfinite KEYWORD2 +copysign KEYWORD2 +copysignf KEYWORD3 RESERVED_WORD +signbitf KEYWORD3 RESERVED_WORD +signbit KEYWORD2 +fdimf KEYWORD3 RESERVED_WORD +fdim KEYWORD2 +fmaf KEYWORD3 RESERVED_WORD +fma KEYWORD2 +fmaxf KEYWORD3 RESERVED_WORD +fmax KEYWORD2 +fminf KEYWORD3 RESERVED_WORD +fmin KEYWORD2 +truncf KEYWORD3 RESERVED_WORD +trunc KEYWORD2 +roundf KEYWORD3 RESERVED_WORD +lroundf KEYWORD3 RESERVED_WORD +lround KEYWORD2 +lrintf KEYWORD3 RESERVED_WORD +lrint KEYWORD2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/power_8h.html +power_adc_disable KEYWORD2 +power_spi_disable KEYWORD2 +power_timer0_disable KEYWORD2 +power_timer1_disable KEYWORD2 +power_timer2_disable KEYWORD2 +power_timer3_disable KEYWORD2 +power_usart0_disable KEYWORD2 +power_usart1_disable KEYWORD2 +power_all_disable KEYWORD2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/sleep_8h.html +sleep_enable KEYWORD2 +sleep_disable KEYWORD2 +sleep_cpu KEYWORD2 +sleep_mode KEYWORD2 +sleep_bod_disable KEYWORD2 +_SLEEP_CONTROL_REG LITERAL2 RESERVED_WORD_2 +_SLEEP_ENABLE_MASK LITERAL2 RESERVED_WORD_2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__string.html +_FFS KEYWORD3 RESERVED_WORD +ffs KEYWORD2 +ffsl KEYWORD2 +ffsll KEYWORD2 +memccpy KEYWORD2 +memmem KEYWORD2 +memrchr KEYWORD2 +strcasecmp KEYWORD2 +strcasestr KEYWORD2 +strchrnul KEYWORD2 +strdup KEYWORD2 +strlcat KEYWORD2 +strlcpy KEYWORD2 +strnlen KEYWORD2 +strlwr KEYWORD2 +strncasecmp KEYWORD2 +strrev KEYWORD2 +strsep KEYWORD2 +strtok_r KEYWORD2 +strupr KEYWORD2 + + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__stdint.html +__USING_MINT8 LITERAL2 RESERVED_WORD_2 +__CONCATenate KEYWORD3 RESERVED_WORD +__CONCAT KEYWORD3 RESERVED_WORD +intptr_t LITERAL2 RESERVED_WORD_2 +uintptr_t LITERAL2 RESERVED_WORD_2 +int_least8_t LITERAL2 RESERVED_WORD_2 +uint_least8_t LITERAL2 RESERVED_WORD_2 +int_least16_t LITERAL2 RESERVED_WORD_2 +uint_least16_t LITERAL2 RESERVED_WORD_2 +int_least32_t LITERAL2 RESERVED_WORD_2 +uint_least32_t LITERAL2 RESERVED_WORD_2 +int_least64_t LITERAL2 RESERVED_WORD_2 +uint_least64_t LITERAL2 RESERVED_WORD_2 +int_fast8_t LITERAL2 RESERVED_WORD_2 +uint_fast8_t LITERAL2 RESERVED_WORD_2 +int_fast16_t LITERAL2 RESERVED_WORD_2 +uint_fast16_t LITERAL2 RESERVED_WORD_2 +int_fast32_t LITERAL2 RESERVED_WORD_2 +uint_fast32_t LITERAL2 RESERVED_WORD_2 +int_fast64_t LITERAL2 RESERVED_WORD_2 +uint_fast64_t LITERAL2 RESERVED_WORD_2 +intmax_t LITERAL2 RESERVED_WORD_2 +uintmax_t LITERAL2 RESERVED_WORD_2 +INT8_MAX LITERAL2 RESERVED_WORD_2 +INT8_MIN LITERAL2 RESERVED_WORD_2 +UINT8_MAX LITERAL2 RESERVED_WORD_2 +INT16_MAX LITERAL2 RESERVED_WORD_2 +INT16_MIN LITERAL2 RESERVED_WORD_2 +UINT16_MAX LITERAL2 RESERVED_WORD_2 +INT32_MAX LITERAL2 RESERVED_WORD_2 +INT32_MIN LITERAL2 RESERVED_WORD_2 +UINT32_MAX LITERAL2 RESERVED_WORD_2 +INT64_MAX LITERAL2 RESERVED_WORD_2 +INT64_MIN LITERAL2 RESERVED_WORD_2 +UINT64_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST8_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST8_MIN LITERAL2 RESERVED_WORD_2 +UINT_LEAST8_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST16_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST16_MIN LITERAL2 RESERVED_WORD_2 +UINT_LEAST16_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST32_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST32_MIN LITERAL2 RESERVED_WORD_2 +UINT_LEAST32_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST64_MAX LITERAL2 RESERVED_WORD_2 +INT_LEAST64_MIN LITERAL2 RESERVED_WORD_2 +UINT_LEAST64_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST8_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST8_MIN LITERAL2 RESERVED_WORD_2 +UINT_FAST8_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST16_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST16_MIN LITERAL2 RESERVED_WORD_2 +UINT_FAST16_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST32_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST32_MIN LITERAL2 RESERVED_WORD_2 +UINT_FAST32_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST64_MAX LITERAL2 RESERVED_WORD_2 +INT_FAST64_MIN LITERAL2 RESERVED_WORD_2 +UINT_FAST64_MAX LITERAL2 RESERVED_WORD_2 +INTPTR_MAX LITERAL2 RESERVED_WORD_2 +INTPTR_MIN LITERAL2 RESERVED_WORD_2 +UINTPTR_MAX LITERAL2 RESERVED_WORD_2 +INTMAX_MAX LITERAL2 RESERVED_WORD_2 +INTMAX_MIN LITERAL2 RESERVED_WORD_2 +UINTMAX_MAX LITERAL2 RESERVED_WORD_2 +PTRDIFF_MAX LITERAL2 RESERVED_WORD_2 +PTRDIFF_MIN LITERAL2 RESERVED_WORD_2 +SIG_ATOMIC_MAX LITERAL2 RESERVED_WORD_2 +SIG_ATOMIC_MIN LITERAL2 RESERVED_WORD_2 +SIZE_MAX LITERAL2 RESERVED_WORD_2 +WCHAR_MAX LITERAL2 RESERVED_WORD_2 +WCHAR_MIN LITERAL2 RESERVED_WORD_2 +WINT_MAX LITERAL2 RESERVED_WORD_2 +WINT_MIN LITERAL2 RESERVED_WORD_2 + + + +# - http://www.nongnu.org/avr-libc/user-manual/group__avr__watchdog.html +wdt_reset KEYWORD3 RESERVED_WORD +wdt_enable KEYWORD3 RESERVED_WORD +wdt_disable KEYWORD3 RESERVED_WORD +WDTO_15MS LITERAL2 RESERVED_WORD_2 +WDTO_30MS LITERAL2 RESERVED_WORD_2 +WDTO_60MS LITERAL2 RESERVED_WORD_2 +WDTO_120MS LITERAL2 RESERVED_WORD_2 +WDTO_250MS LITERAL2 RESERVED_WORD_2 +WDTO_500MS LITERAL2 RESERVED_WORD_2 +WDTO_1S LITERAL2 RESERVED_WORD_2 +WDTO_2S LITERAL2 RESERVED_WORD_2 +WDTO_4S LITERAL2 RESERVED_WORD_2 +WDTO_8S LITERAL2 RESERVED_WORD_2 + + + +# - definitions, interrupt & vectors +SPH LITERAL2 RESERVED_WORD_2 +SP15 KEYWORD3 RESERVED_WORD +SP14 KEYWORD3 RESERVED_WORD +SP13 KEYWORD3 RESERVED_WORD +SP12 KEYWORD3 RESERVED_WORD +SP11 KEYWORD3 RESERVED_WORD +SP10 KEYWORD3 RESERVED_WORD +SP9 KEYWORD3 RESERVED_WORD +SP8 KEYWORD3 RESERVED_WORD + + + +CCP LITERAL1 +SPH LITERAL1 +SPL LITERAL1 +SREG LITERAL1 +GPIOR0 LITERAL1 +GPIOR1 LITERAL1 +GPIOR2 LITERAL1 +GPIOR3 LITERAL1 +GPIO0 LITERAL1 +GPIO1 LITERAL1 +GPIO2 LITERAL1 +GPIO3 LITERAL1 + +register8_t LITERAL1 +register16_t LITERAL1 +register32_t LITERAL1 + +_WORDREGISTER KEYWORD3 RESERVED_WORD + + +CTRLA LITERAL1 +reserved_0x01 LITERAL1 +MUXCTRLA LITERAL1 +reserved_0x03 LITERAL1 +DACREF LITERAL1 +reserved_0x05 LITERAL1 +INTCTRL LITERAL1 +STATUS LITERAL1 +AC_t LITERAL1 + +AC_HYSMODE_OFF_gc KEYWORD3 RESERVED_WORD +AC_HYSMODE_10mV_gc KEYWORD3 RESERVED_WORD +AC_HYSMODE_25mV_gc KEYWORD3 RESERVED_WORD +AC_HYSMODE_50mV_gc KEYWORD3 RESERVED_WORD +AC_HYSMODE_t LITERAL1 + +AC_INTMODE_BOTHEDGE_gc KEYWORD3 RESERVED_WORD +AC_INTMODE_NEGEDGE_gc KEYWORD3 RESERVED_WORD +AC_INTMODE_POSEDGE_gc KEYWORD3 RESERVED_WORD +AC_INTMODE_t LITERAL1 + +AC_LPMODE_DIS_gc KEYWORD3 RESERVED_WORD +AC_LPMODE_EN_gc KEYWORD3 RESERVED_WORD +AC_LPMODE_t LITERAL1 + +AC_MUXNEG_PIN0_gc KEYWORD3 RESERVED_WORD +AC_MUXNEG_PIN1_gc KEYWORD3 RESERVED_WORD +AC_MUXNEG_PIN2_gc KEYWORD3 RESERVED_WORD +AC_MUXNEG_DACREF_gc KEYWORD3 RESERVED_WORD +AC_MUXNEG_t LITERAL1 + +AC_MUXPOS_PIN0_gc KEYWORD3 RESERVED_WORD +AC_MUXPOS_PIN1_gc KEYWORD3 RESERVED_WORD +AC_MUXPOS_PIN2_gc KEYWORD3 RESERVED_WORD +AC_MUXPOS_PIN3_gc KEYWORD3 RESERVED_WORD +AC_MUXPOS_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +CTRLC LITERAL1 +CTRLD LITERAL1 +CTRLE LITERAL1 +SAMPCTRL LITERAL1 +MUXPOS LITERAL1 +reserved_0x07 LITERAL1 +COMMAND LITERAL1 +EVCTRL LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +DBGCTRL LITERAL1 +TEMP LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +_WORDREGISTER(RES); KEYWORD3 RESERVED_WORD +_WORDREGISTER(WINLT); KEYWORD3 RESERVED_WORD +_WORDREGISTER(WINHT); KEYWORD3 RESERVED_WORD +CALIB LITERAL1 +reserved_0x17 LITERAL1 +ADC_t LITERAL1 + +ADC_ASDV_ASVOFF_gc KEYWORD3 RESERVED_WORD +ADC_ASDV_ASVON_gc KEYWORD3 RESERVED_WORD +ADC_ASDV_t LITERAL1 + +ADC_DUTYCYC_DUTY50_gc KEYWORD3 RESERVED_WORD +ADC_DUTYCYC_DUTY25_gc KEYWORD3 RESERVED_WORD +ADC_DUTYCYC_t LITERAL1 + +ADC_INITDLY_DLY0_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_DLY16_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_DLY32_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_DLY64_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_DLY128_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_DLY256_gc KEYWORD3 RESERVED_WORD +ADC_INITDLY_t LITERAL1 + +ADC_MUXPOS_AIN0_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN1_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_DACREF_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_TEMPSENSE_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_GND_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN2_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN3_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN4_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN5_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN6_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN7_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN8_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN9_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN10_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN11_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN12_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN13_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN14_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_AIN15_gc KEYWORD3 RESERVED_WORD +ADC_MUXPOS_t LITERAL1 + +ADC_PRESC_DIV2_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV4_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV8_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV16_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV32_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV64_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV128_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_DIV256_gc KEYWORD3 RESERVED_WORD +ADC_PRESC_t LITERAL1 + +ADC_REFSEL_INTREF_gc KEYWORD3 RESERVED_WORD +ADC_REFSEL_VDDREF_gc KEYWORD3 RESERVED_WORD +ADC_REFSEL_VREFA_gc KEYWORD3 RESERVED_WORD +ADC_REFSEL_t LITERAL1 + +ADC_RESSEL_10BIT_gc KEYWORD3 RESERVED_WORD +ADC_RESSEL_8BIT_gc KEYWORD3 RESERVED_WORD +ADC_RESSEL_t LITERAL1 + +ADC_SAMPNUM_ACC1_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC2_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC4_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC8_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC16_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC32_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_ACC64_gc KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_t LITERAL1 + +ADC_WINCM_NONE_gc KEYWORD3 RESERVED_WORD +ADC_WINCM_BELOW_gc KEYWORD3 RESERVED_WORD +ADC_WINCM_ABOVE_gc KEYWORD3 RESERVED_WORD +ADC_WINCM_INSIDE_gc KEYWORD3 RESERVED_WORD +ADC_WINCM_OUTSIDE_gc KEYWORD3 RESERVED_WORD +ADC_WINCM_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +reserved_0x02 LITERAL1 +reserved_0x03 LITERAL1 +reserved_0x04 LITERAL1 +reserved_0x05 LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +VLMCTRLA LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +STATUS LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +BOD_t LITERAL1 + +BOD_ACTIVE_DIS_gc KEYWORD3 RESERVED_WORD +BOD_ACTIVE_ENABLED_gc KEYWORD3 RESERVED_WORD +BOD_ACTIVE_SAMPLED_gc KEYWORD3 RESERVED_WORD +BOD_ACTIVE_ENWAKE_gc KEYWORD3 RESERVED_WORD +BOD_ACTIVE_t LITERAL1 + +BOD_LVL_BODLEVEL0_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL1_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL2_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL3_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL4_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL5_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL6_gc KEYWORD3 RESERVED_WORD +BOD_LVL_BODLEVEL7_gc KEYWORD3 RESERVED_WORD +BOD_LVL_t LITERAL1 + +BOD_SAMPFREQ_1KHZ_gc KEYWORD3 RESERVED_WORD +BOD_SAMPFREQ_125HZ_gc KEYWORD3 RESERVED_WORD +BOD_SAMPFREQ_t LITERAL1 + +BOD_SLEEP_DIS_gc KEYWORD3 RESERVED_WORD +BOD_SLEEP_ENABLED_gc KEYWORD3 RESERVED_WORD +BOD_SLEEP_SAMPLED_gc KEYWORD3 RESERVED_WORD +BOD_SLEEP_t LITERAL1 + +BOD_VLMCFG_BELOW_gc KEYWORD3 RESERVED_WORD +BOD_VLMCFG_ABOVE_gc KEYWORD3 RESERVED_WORD +BOD_VLMCFG_CROSS_gc KEYWORD3 RESERVED_WORD +BOD_VLMCFG_t LITERAL1 + +BOD_VLMLVL_5ABOVE_gc KEYWORD3 RESERVED_WORD +BOD_VLMLVL_15ABOVE_gc KEYWORD3 RESERVED_WORD +BOD_VLMLVL_25ABOVE_gc KEYWORD3 RESERVED_WORD +BOD_VLMLVL_t LITERAL1 + + +CTRLA LITERAL1 +SEQCTRL0 LITERAL1 +SEQCTRL1 LITERAL1 +reserved_0x03 LITERAL1 +reserved_0x04 LITERAL1 +INTCTRL0 LITERAL1 +reserved_0x06 LITERAL1 +INTFLAGS LITERAL1 +LUT0CTRLA LITERAL1 +LUT0CTRLB LITERAL1 +LUT0CTRLC LITERAL1 +TRUTH0 LITERAL1 +LUT1CTRLA LITERAL1 +LUT1CTRLB LITERAL1 +LUT1CTRLC LITERAL1 +TRUTH1 LITERAL1 +LUT2CTRLA LITERAL1 +LUT2CTRLB LITERAL1 +LUT2CTRLC LITERAL1 +TRUTH2 LITERAL1 +LUT3CTRLA LITERAL1 +LUT3CTRLB LITERAL1 +LUT3CTRLC LITERAL1 +TRUTH3 LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +reserved_0x20 LITERAL1 +reserved_0x21 LITERAL1 +reserved_0x22 LITERAL1 +reserved_0x23 LITERAL1 +reserved_0x24 LITERAL1 +reserved_0x25 LITERAL1 +reserved_0x26 LITERAL1 +reserved_0x27 LITERAL1 +reserved_0x28 LITERAL1 +reserved_0x29 LITERAL1 +reserved_0x2A LITERAL1 +reserved_0x2B LITERAL1 +reserved_0x2C LITERAL1 +reserved_0x2D LITERAL1 +reserved_0x2E LITERAL1 +reserved_0x2F LITERAL1 +reserved_0x30 LITERAL1 +reserved_0x31 LITERAL1 +reserved_0x32 LITERAL1 +reserved_0x33 LITERAL1 +reserved_0x34 LITERAL1 +reserved_0x35 LITERAL1 +reserved_0x36 LITERAL1 +reserved_0x37 LITERAL1 +reserved_0x38 LITERAL1 +reserved_0x39 LITERAL1 +reserved_0x3A LITERAL1 +reserved_0x3B LITERAL1 +reserved_0x3C LITERAL1 +reserved_0x3D LITERAL1 +reserved_0x3E LITERAL1 +reserved_0x3F LITERAL1 +CCL_t LITERAL1 + +CCL_CLKSRC_CLKPER_gc KEYWORD3 RESERVED_WORD +CCL_CLKSRC_IN2_gc KEYWORD3 RESERVED_WORD +CCL_CLKSRC_OSC20M_gc KEYWORD3 RESERVED_WORD +CCL_CLKSRC_OSCULP32K_gc KEYWORD3 RESERVED_WORD +CCL_CLKSRC_OSCULP1K_gc KEYWORD3 RESERVED_WORD +CCL_CLKSRC_t LITERAL1 + +CCL_EDGEDET_DIS_gc KEYWORD3 RESERVED_WORD +CCL_EDGEDET_EN_gc KEYWORD3 RESERVED_WORD +CCL_EDGEDET_t LITERAL1 + +CCL_FILTSEL_DISABLE_gc KEYWORD3 RESERVED_WORD +CCL_FILTSEL_SYNCH_gc KEYWORD3 RESERVED_WORD +CCL_FILTSEL_FILTER_gc KEYWORD3 RESERVED_WORD +CCL_FILTSEL_t LITERAL1 + +CCL_INSEL0_MASK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_FEEDBACK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_LINK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_EVENTA_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_EVENTB_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_IO_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_AC0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_USART0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_SPI0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_TCA0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_TCB0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL0_t LITERAL1 + +CCL_INSEL1_MASK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_FEEDBACK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_LINK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_EVENTA_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_EVENTB_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_IO_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_AC0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_USART1_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_SPI0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_TCA0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_TCB1_gc KEYWORD3 RESERVED_WORD +CCL_INSEL1_t LITERAL1 + +CCL_INSEL2_MASK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_FEEDBACK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_LINK_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_EVENTA_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_EVENTB_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_IO_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_AC0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_USART2_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_SPI0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_TCA0_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_TCB2_gc KEYWORD3 RESERVED_WORD +CCL_INSEL2_t LITERAL1 + +CCL_INTMODE0_INTDISABLE_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE0_RISING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE0_FALLING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE0_BOTH_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE0_t LITERAL1 + +CCL_INTMODE1_INTDISABLE_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE1_RISING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE1_FALLING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE1_BOTH_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE1_t LITERAL1 + +CCL_INTMODE2_INTDISABLE_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE2_RISING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE2_FALLING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE2_BOTH_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE2_t LITERAL1 + +CCL_INTMODE3_INTDISABLE_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE3_RISING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE3_FALLING_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE3_BOTH_gc KEYWORD3 RESERVED_WORD +CCL_INTMODE3_t LITERAL1 + +CCL_SEQSEL0_DISABLE_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_DFF_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_JK_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_LATCH_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_RS_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_t LITERAL1 + +CCL_SEQSEL1_DISABLE_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_DFF_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_JK_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_LATCH_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_RS_gc KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_t LITERAL1 + + +MCLKCTRLA LITERAL1 +MCLKCTRLB LITERAL1 +MCLKLOCK LITERAL1 +MCLKSTATUS LITERAL1 +reserved_0x04 LITERAL1 +reserved_0x05 LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +reserved_0x08 LITERAL1 +reserved_0x09 LITERAL1 +reserved_0x0A LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +OSC20MCTRLA LITERAL1 +OSC20MCALIBA LITERAL1 +OSC20MCALIBB LITERAL1 +reserved_0x13 LITERAL1 +reserved_0x14 LITERAL1 +reserved_0x15 LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +OSC32KCTRLA LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +XOSC32KCTRLA LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +CLKCTRL_t LITERAL1 + +CLKCTRL_CLKSEL_OSC20M_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL_OSCULP32K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL_XOSC32K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL_EXTCLK_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL_t LITERAL1 + +CLKCTRL_CSUT_1K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_16K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_32K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_64K_gc KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_t LITERAL1 + +CLKCTRL_PDIV_2X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_4X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_8X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_16X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_32X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_64X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_6X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_10X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_12X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_24X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_48X_gc KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_t LITERAL1 + + +CCP_SPM_gc KEYWORD3 RESERVED_WORD +CCP_IOREG_gc KEYWORD3 RESERVED_WORD +CCP_t LITERAL1 + + +CTRLA LITERAL1 +STATUS LITERAL1 +LVL0PRI LITERAL1 +LVL1VEC LITERAL1 +CPUINT_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +STATUS LITERAL1 +reserved_0x03 LITERAL1 +CRCSCAN_t LITERAL1 + +CRCSCAN_MODE_PRIORITY_gc KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_RESERVED_gc KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_BACKGROUND_gc KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_CONTINUOUS_gc KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_t LITERAL1 + +CRCSCAN_SRC_FLASH_gc KEYWORD3 RESERVED_WORD +CRCSCAN_SRC_APPLICATION_gc KEYWORD3 RESERVED_WORD +CRCSCAN_SRC_BOOT_gc KEYWORD3 RESERVED_WORD +CRCSCAN_SRC_t LITERAL1 + + +STROBE LITERAL1 +reserved_0x01 LITERAL1 +reserved_0x02 LITERAL1 +reserved_0x03 LITERAL1 +reserved_0x04 LITERAL1 +reserved_0x05 LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +reserved_0x08 LITERAL1 +reserved_0x09 LITERAL1 +reserved_0x0A LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +CHANNEL0 LITERAL1 +CHANNEL1 LITERAL1 +CHANNEL2 LITERAL1 +CHANNEL3 LITERAL1 +CHANNEL4 LITERAL1 +CHANNEL5 LITERAL1 +CHANNEL6 LITERAL1 +CHANNEL7 LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +USERCCLLUT0A LITERAL1 +USERCCLLUT0B LITERAL1 +USERCCLLUT1A LITERAL1 +USERCCLLUT1B LITERAL1 +USERCCLLUT2A LITERAL1 +USERCCLLUT2B LITERAL1 +USERCCLLUT3A LITERAL1 +USERCCLLUT3B LITERAL1 +USERADC0 LITERAL1 +USEREVOUTA LITERAL1 +USEREVOUTB LITERAL1 +USEREVOUTC LITERAL1 +USEREVOUTD LITERAL1 +USEREVOUTE LITERAL1 +USEREVOUTF LITERAL1 +USERUSART0 LITERAL1 +USERUSART1 LITERAL1 +USERUSART2 LITERAL1 +USERUSART3 LITERAL1 +USERTCA0 LITERAL1 +USERTCB0 LITERAL1 +USERTCB1 LITERAL1 +USERTCB2 LITERAL1 +USERTCB3 LITERAL1 +reserved_0x38 LITERAL1 +reserved_0x39 LITERAL1 +reserved_0x3A LITERAL1 +reserved_0x3B LITERAL1 +reserved_0x3C LITERAL1 +reserved_0x3D LITERAL1 +reserved_0x3E LITERAL1 +reserved_0x3F LITERAL1 +EVSYS_t LITERAL1 + +EVSYS_CHANNEL_OFF_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL0_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL1_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL2_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL3_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL4_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL5_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL6_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_CHANNEL7_gc KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_t LITERAL1 + +EVSYS_GENERATOR_OFF_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_UPDI_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_CCL_LUT0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_CCL_LUT1_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_CCL_LUT2_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_CCL_LUT3_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_AC0_OUT_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_ADC0_COMP_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN1_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN2_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN3_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN4_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN5_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN6_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT0_PIN7_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN1_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN2_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN3_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN4_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN5_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN6_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_PORT1_PIN7_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_OVF_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_USART0_XCK_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_USART1_XCK_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_USART2_XCK_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_USART3_XCK_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_SPI0_SCK_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_CMP_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_PIT0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCA0_OVF_LUNF_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCA0_HUNF_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCA0_CMP0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCA0_CMP1_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCA0_CMP2_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_PIT1_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_PIT2_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCB0_CMP0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCB1_CMP0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCB2_CMP0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_TCB3_CMP0_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_RTC_PIT3_gc KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_t LITERAL1 + +EVSYS_STROBE0_EV_STROBE_CH0_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH1_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH2_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH3_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH4_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH5_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH6_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_EV_STROBE_CH7_gc KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_t LITERAL1 + + +WDTCFG LITERAL1 +BODCFG LITERAL1 +OSCCFG LITERAL1 +reserved_0x03 LITERAL1 +reserved_0x04 LITERAL1 +SYSCFG0 LITERAL1 +SYSCFG1 LITERAL1 +APPEND LITERAL1 +BOOTEND LITERAL1 +FUSE_t LITERAL1 + + +ACTIVE_DIS_gc KEYWORD3 RESERVED_WORD +ACTIVE_ENABLED_gc KEYWORD3 RESERVED_WORD +ACTIVE_SAMPLED_gc KEYWORD3 RESERVED_WORD +ACTIVE_ENWAKE_gc KEYWORD3 RESERVED_WORD +ACTIVE_t LITERAL1 + +CRCSRC_FLASH_gc KEYWORD3 RESERVED_WORD +CRCSRC_BOOT_gc KEYWORD3 RESERVED_WORD +CRCSRC_BOOTAPP_gc KEYWORD3 RESERVED_WORD +CRCSRC_NOCRC_gc KEYWORD3 RESERVED_WORD +CRCSRC_t LITERAL1 + +FREQSEL_16MHZ_gc KEYWORD3 RESERVED_WORD +FREQSEL_20MHZ_gc KEYWORD3 RESERVED_WORD +FREQSEL_t LITERAL1 + +LVL_BODLEVEL0_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL1_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL2_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL3_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL4_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL5_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL6_gc KEYWORD3 RESERVED_WORD +LVL_BODLEVEL7_gc KEYWORD3 RESERVED_WORD +LVL_t LITERAL1 + +PERIOD_OFF_gc KEYWORD3 RESERVED_WORD +PERIOD_8CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_16CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_32CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_64CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_128CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_256CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_512CLK_gc KEYWORD3 RESERVED_WORD +PERIOD_1KCLK_gc KEYWORD3 RESERVED_WORD +PERIOD_2KCLK_gc KEYWORD3 RESERVED_WORD +PERIOD_4KCLK_gc KEYWORD3 RESERVED_WORD +PERIOD_8KCLK_gc KEYWORD3 RESERVED_WORD +PERIOD_t LITERAL1 + +RSTPINCFG_GPIO_gc KEYWORD3 RESERVED_WORD +RSTPINCFG_RST_gc KEYWORD3 RESERVED_WORD +RSTPINCFG_t LITERAL1 + +SAMPFREQ_1KHZ_gc KEYWORD3 RESERVED_WORD +SAMPFREQ_125HZ_gc KEYWORD3 RESERVED_WORD +SAMPFREQ_t LITERAL1 + +SLEEP_DIS_gc KEYWORD3 RESERVED_WORD +SLEEP_ENABLED_gc KEYWORD3 RESERVED_WORD +SLEEP_SAMPLED_gc KEYWORD3 RESERVED_WORD +SLEEP_t LITERAL1 + +SUT_0MS_gc KEYWORD3 RESERVED_WORD +SUT_1MS_gc KEYWORD3 RESERVED_WORD +SUT_2MS_gc KEYWORD3 RESERVED_WORD +SUT_4MS_gc KEYWORD3 RESERVED_WORD +SUT_8MS_gc KEYWORD3 RESERVED_WORD +SUT_16MS_gc KEYWORD3 RESERVED_WORD +SUT_32MS_gc KEYWORD3 RESERVED_WORD +SUT_64MS_gc KEYWORD3 RESERVED_WORD +SUT_t LITERAL1 + +WINDOW_OFF_gc KEYWORD3 RESERVED_WORD +WINDOW_8CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_16CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_32CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_64CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_128CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_256CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_512CLK_gc KEYWORD3 RESERVED_WORD +WINDOW_1KCLK_gc KEYWORD3 RESERVED_WORD +WINDOW_2KCLK_gc KEYWORD3 RESERVED_WORD +WINDOW_4KCLK_gc KEYWORD3 RESERVED_WORD +WINDOW_8KCLK_gc KEYWORD3 RESERVED_WORD +WINDOW_t LITERAL1 + + +LOCKBIT LITERAL1 +reserved_0x01 LITERAL1 +LOCKBIT_t LITERAL1 + +LB_RWLOCK_gc KEYWORD3 RESERVED_WORD +LB_NOLOCK_gc KEYWORD3 RESERVED_WORD +LB_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +STATUS LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +reserved_0x05 LITERAL1 +_WORDREGISTER(DATA); KEYWORD3 RESERVED_WORD +_WORDREGISTER(ADDR); KEYWORD3 RESERVED_WORD +reserved_0x0A LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +NVMCTRL_t LITERAL1 + +NVMCTRL_CMD_NONE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_PAGEWRITE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_PAGEERASE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_PAGEERASEWRITE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_PAGEBUFCLR_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_CHIPERASE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_EEERASE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_FUSEWRITE_gc KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_t LITERAL1 + + +DIR LITERAL1 +DIRSET LITERAL1 +DIRCLR LITERAL1 +DIRTGL LITERAL1 +OUT LITERAL1 +OUTSET LITERAL1 +OUTCLR LITERAL1 +OUTTGL LITERAL1 +IN LITERAL1 +INTFLAGS LITERAL1 +PORTCTRL LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +PIN0CTRL LITERAL1 +PIN1CTRL LITERAL1 +PIN2CTRL LITERAL1 +PIN3CTRL LITERAL1 +PIN4CTRL LITERAL1 +PIN5CTRL LITERAL1 +PIN6CTRL LITERAL1 +PIN7CTRL LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +PORT_t LITERAL1 + +PORT_ISC_INTDISABLE_gc KEYWORD3 RESERVED_WORD +PORT_ISC_BOTHEDGES_gc KEYWORD3 RESERVED_WORD +PORT_ISC_RISING_gc KEYWORD3 RESERVED_WORD +PORT_ISC_FALLING_gc KEYWORD3 RESERVED_WORD +PORT_ISC_INPUT_DISABLE_gc KEYWORD3 RESERVED_WORD +PORT_ISC_LEVEL_gc KEYWORD3 RESERVED_WORD +PORT_ISC_t LITERAL1 + + +EVSYSROUTEA LITERAL1 +CCLROUTEA LITERAL1 +USARTROUTEA LITERAL1 +TWISPIROUTEA LITERAL1 +TCAROUTEA LITERAL1 +TCBROUTEA LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +reserved_0x08 LITERAL1 +reserved_0x09 LITERAL1 +reserved_0x0A LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +PORTMUX_t LITERAL1 + +PORTMUX_SPI0_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_SPI0_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_SPI0_ALT2_gc KEYWORD3 RESERVED_WORD +PORTMUX_SPI0_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_SPI0_t LITERAL1 + +PORTMUX_TCA0_PORTA_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_PORTB_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_PORTC_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_PORTD_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_PORTE_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_PORTF_gc KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_t LITERAL1 + +PORTMUX_TWI0_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_ALT2_gc KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_t LITERAL1 + +PORTMUX_USART0_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART0_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART0_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART0_t LITERAL1 + +PORTMUX_USART1_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART1_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART1_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART1_t LITERAL1 + +PORTMUX_USART2_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART2_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART2_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART2_t LITERAL1 + +PORTMUX_USART3_DEFAULT_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART3_ALT1_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART3_NONE_gc KEYWORD3 RESERVED_WORD +PORTMUX_USART3_t LITERAL1 + + +RSTFR LITERAL1 +SWRR LITERAL1 +reserved_0x02 LITERAL1 +reserved_0x03 LITERAL1 +RSTCTRL_t LITERAL1 + + +CTRLA LITERAL1 +STATUS LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +TEMP LITERAL1 +DBGCTRL LITERAL1 +CALIB LITERAL1 +CLKSEL LITERAL1 +_WORDREGISTER(CNT); KEYWORD3 RESERVED_WORD +_WORDREGISTER(PER); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP); KEYWORD3 RESERVED_WORD +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +PITCTRLA LITERAL1 +PITSTATUS LITERAL1 +PITINTCTRL LITERAL1 +PITINTFLAGS LITERAL1 +reserved_0x14 LITERAL1 +PITDBGCTRL LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +RTC_t LITERAL1 + +RTC_CLKSEL_INT32K_gc KEYWORD3 RESERVED_WORD +RTC_CLKSEL_INT1K_gc KEYWORD3 RESERVED_WORD +RTC_CLKSEL_TOSC32K_gc KEYWORD3 RESERVED_WORD +RTC_CLKSEL_EXTCLK_gc KEYWORD3 RESERVED_WORD +RTC_CLKSEL_t LITERAL1 + +RTC_PERIOD_OFF_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC4_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC8_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC16_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC32_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC64_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC128_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC256_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC512_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC1024_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC2048_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC4096_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC8192_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC16384_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_CYC32768_gc KEYWORD3 RESERVED_WORD +RTC_PERIOD_t LITERAL1 + +RTC_PRESCALER_DIV1_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV2_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV4_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV8_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV16_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV32_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV64_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV128_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV256_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV512_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV1024_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV2048_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV4096_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV8192_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV16384_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_DIV32768_gc KEYWORD3 RESERVED_WORD +RTC_PRESCALER_t LITERAL1 + + +DEVICEID0 LITERAL1 +DEVICEID1 LITERAL1 +DEVICEID2 LITERAL1 +SERNUM0 LITERAL1 +SERNUM1 LITERAL1 +SERNUM2 LITERAL1 +SERNUM3 LITERAL1 +SERNUM4 LITERAL1 +SERNUM5 LITERAL1 +SERNUM6 LITERAL1 +SERNUM7 LITERAL1 +SERNUM8 LITERAL1 +SERNUM9 LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +reserved_0x10 LITERAL1 +reserved_0x11 LITERAL1 +reserved_0x12 LITERAL1 +reserved_0x13 LITERAL1 +OSCCAL32K LITERAL1 +reserved_0x15 LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +OSCCAL16M0 LITERAL1 +OSCCAL16M1 LITERAL1 +OSCCAL20M0 LITERAL1 +OSCCAL20M1 LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +TEMPSENSE0 LITERAL1 +TEMPSENSE1 LITERAL1 +OSC16ERR3V LITERAL1 +OSC16ERR5V LITERAL1 +OSC20ERR3V LITERAL1 +OSC20ERR5V LITERAL1 +reserved_0x26 LITERAL1 +reserved_0x27 LITERAL1 +reserved_0x28 LITERAL1 +reserved_0x29 LITERAL1 +reserved_0x2A LITERAL1 +reserved_0x2B LITERAL1 +reserved_0x2C LITERAL1 +reserved_0x2D LITERAL1 +reserved_0x2E LITERAL1 +CHECKSUM1 LITERAL1 +reserved_0x30 LITERAL1 +reserved_0x31 LITERAL1 +reserved_0x32 LITERAL1 +reserved_0x33 LITERAL1 +reserved_0x34 LITERAL1 +reserved_0x35 LITERAL1 +reserved_0x36 LITERAL1 +reserved_0x37 LITERAL1 +reserved_0x38 LITERAL1 +reserved_0x39 LITERAL1 +reserved_0x3A LITERAL1 +reserved_0x3B LITERAL1 +reserved_0x3C LITERAL1 +reserved_0x3D LITERAL1 +reserved_0x3E LITERAL1 +reserved_0x3F LITERAL1 +SIGROW_t LITERAL1 + + +CTRLA LITERAL1 +reserved_0x01 LITERAL1 +SLPCTRL_t LITERAL1 + +SLPCTRL_SMODE_IDLE_gc KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE_STDBY_gc KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE_PDOWN_gc KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE_t LITERAL1 +#define KEYWORD3 RESERVED_WORD +#define KEYWORD3 RESERVED_WORD +#define KEYWORD3 RESERVED_WORD + + +CTRLA LITERAL1 +CTRLB LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +DATA LITERAL1 +reserved_0x05 LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +SPI_t LITERAL1 + +SPI_MODE_0_gc KEYWORD3 RESERVED_WORD +SPI_MODE_1_gc KEYWORD3 RESERVED_WORD +SPI_MODE_2_gc KEYWORD3 RESERVED_WORD +SPI_MODE_3_gc KEYWORD3 RESERVED_WORD +SPI_MODE_t LITERAL1 + +SPI_PRESC_DIV4_gc KEYWORD3 RESERVED_WORD +SPI_PRESC_DIV16_gc KEYWORD3 RESERVED_WORD +SPI_PRESC_DIV64_gc KEYWORD3 RESERVED_WORD +SPI_PRESC_DIV128_gc KEYWORD3 RESERVED_WORD +SPI_PRESC_t LITERAL1 + + +reserved_0x00 LITERAL1 +REVID LITERAL1 +EXTBRK LITERAL1 +reserved_0x03 LITERAL1 +reserved_0x04 LITERAL1 +reserved_0x05 LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +reserved_0x08 LITERAL1 +reserved_0x09 LITERAL1 +reserved_0x0A LITERAL1 +reserved_0x0B LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +reserved_0x10 LITERAL1 +reserved_0x11 LITERAL1 +reserved_0x12 LITERAL1 +reserved_0x13 LITERAL1 +reserved_0x14 LITERAL1 +reserved_0x15 LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +OCDM LITERAL1 +OCDMS LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +SYSCFG_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +CTRLC LITERAL1 +CTRLD LITERAL1 +CTRLECLR LITERAL1 +CTRLESET LITERAL1 +CTRLFCLR LITERAL1 +CTRLFSET LITERAL1 +reserved_0x08 LITERAL1 +EVCTRL LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +DBGCTRL LITERAL1 +TEMP LITERAL1 +reserved_0x10 LITERAL1 +reserved_0x11 LITERAL1 +reserved_0x12 LITERAL1 +reserved_0x13 LITERAL1 +reserved_0x14 LITERAL1 +reserved_0x15 LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +_WORDREGISTER(CNT); KEYWORD3 RESERVED_WORD +reserved_0x22 LITERAL1 +reserved_0x23 LITERAL1 +reserved_0x24 LITERAL1 +reserved_0x25 LITERAL1 +_WORDREGISTER(PER); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP0); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP1); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP2); KEYWORD3 RESERVED_WORD +reserved_0x2E LITERAL1 +reserved_0x2F LITERAL1 +reserved_0x30 LITERAL1 +reserved_0x31 LITERAL1 +reserved_0x32 LITERAL1 +reserved_0x33 LITERAL1 +reserved_0x34 LITERAL1 +reserved_0x35 LITERAL1 +_WORDREGISTER(PERBUF); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP0BUF); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP1BUF); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CMP2BUF); KEYWORD3 RESERVED_WORD +reserved_0x3E LITERAL1 +reserved_0x3F LITERAL1 +TCA_SINGLE_t LITERAL1 + +CTRLA LITERAL1 +CTRLB LITERAL1 +CTRLC LITERAL1 +CTRLD LITERAL1 +CTRLECLR LITERAL1 +CTRLESET LITERAL1 +reserved_0x06 LITERAL1 +reserved_0x07 LITERAL1 +reserved_0x08 LITERAL1 +reserved_0x09 LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +reserved_0x0C LITERAL1 +reserved_0x0D LITERAL1 +DBGCTRL LITERAL1 +reserved_0x0F LITERAL1 +reserved_0x10 LITERAL1 +reserved_0x11 LITERAL1 +reserved_0x12 LITERAL1 +reserved_0x13 LITERAL1 +reserved_0x14 LITERAL1 +reserved_0x15 LITERAL1 +reserved_0x16 LITERAL1 +reserved_0x17 LITERAL1 +reserved_0x18 LITERAL1 +reserved_0x19 LITERAL1 +reserved_0x1A LITERAL1 +reserved_0x1B LITERAL1 +reserved_0x1C LITERAL1 +reserved_0x1D LITERAL1 +reserved_0x1E LITERAL1 +reserved_0x1F LITERAL1 +LCNT LITERAL1 +HCNT LITERAL1 +reserved_0x22 LITERAL1 +reserved_0x23 LITERAL1 +reserved_0x24 LITERAL1 +reserved_0x25 LITERAL1 +LPER LITERAL1 +HPER LITERAL1 +LCMP0 LITERAL1 +HCMP0 LITERAL1 +LCMP1 LITERAL1 +HCMP1 LITERAL1 +LCMP2 LITERAL1 +HCMP2 LITERAL1 +reserved_0x2E LITERAL1 +reserved_0x2F LITERAL1 +reserved_0x30 LITERAL1 +reserved_0x31 LITERAL1 +reserved_0x32 LITERAL1 +reserved_0x33 LITERAL1 +reserved_0x34 LITERAL1 +reserved_0x35 LITERAL1 +reserved_0x36 LITERAL1 +reserved_0x37 LITERAL1 +reserved_0x38 LITERAL1 +reserved_0x39 LITERAL1 +reserved_0x3A LITERAL1 +reserved_0x3B LITERAL1 +reserved_0x3C LITERAL1 +reserved_0x3D LITERAL1 +reserved_0x3E LITERAL1 +reserved_0x3F LITERAL1 +TCA_SPLIT_t LITERAL1 + +TCA_SINGLE_t KEYWORD3 RESERVED_WORD +TCA_SPLIT_t KEYWORD3 RESERVED_WORD +TCA_t LITERAL1 + +TCA_SINGLE_CLKSEL_DIV1_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV2_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV4_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV8_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV16_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV64_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV256_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_DIV1024_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_t LITERAL1 + +TCA_SINGLE_CMD_NONE_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_UPDATE_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_RESTART_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_RESET_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_t LITERAL1 + +TCA_SINGLE_DIR_UP_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_DIR_DOWN_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_DIR_t LITERAL1 + +TCA_SINGLE_EVACT_POSEDGE_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_ANYEDGE_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_HIGHLVL_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_UPDOWN_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_t LITERAL1 + +TCA_SINGLE_WGMODE_NORMAL_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_FRQ_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_SINGLESLOPE_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_DSTOP_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_DSBOTH_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_DSBOTTOM_gc KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_t LITERAL1 + +TCA_SPLIT_CLKSEL_DIV1_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV2_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV4_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV8_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV16_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV64_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV256_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_DIV1024_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_t LITERAL1 + +TCA_SPLIT_CMD_NONE_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD_UPDATE_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD_RESTART_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD_RESET_gc KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +reserved_0x02 LITERAL1 +reserved_0x03 LITERAL1 +EVCTRL LITERAL1 +INTCTRL LITERAL1 +INTFLAGS LITERAL1 +STATUS LITERAL1 +DBGCTRL LITERAL1 +TEMP LITERAL1 +_WORDREGISTER(CNT); KEYWORD3 RESERVED_WORD +_WORDREGISTER(CCMP); KEYWORD3 RESERVED_WORD +reserved_0x0E LITERAL1 +reserved_0x0F LITERAL1 +TCB_t LITERAL1 + +TCB_CLKSEL_CLKDIV1_gc KEYWORD3 RESERVED_WORD +TCB_CLKSEL_CLKDIV2_gc KEYWORD3 RESERVED_WORD +TCB_CLKSEL_CLKTCA_gc KEYWORD3 RESERVED_WORD +TCB_CLKSEL_t LITERAL1 + +TCB_CNTMODE_INT_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_TIMEOUT_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_CAPT_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_FRQ_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_PW_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_FRQPW_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_SINGLE_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_PWM8_gc KEYWORD3 RESERVED_WORD +TCB_CNTMODE_t LITERAL1 + + +CTRLA LITERAL1 +DUALCTRL LITERAL1 +DBGCTRL LITERAL1 +MCTRLA LITERAL1 +MCTRLB LITERAL1 +MSTATUS LITERAL1 +MBAUD LITERAL1 +MADDR LITERAL1 +MDATA LITERAL1 +SCTRLA LITERAL1 +SCTRLB LITERAL1 +SSTATUS LITERAL1 +SADDR LITERAL1 +SDATA LITERAL1 +SADDRMASK LITERAL1 +reserved_0x0F LITERAL1 +TWI_t LITERAL1 + +TWI_ACKACT_ACK_gc KEYWORD3 RESERVED_WORD +TWI_ACKACT_NACK_gc KEYWORD3 RESERVED_WORD +TWI_ACKACT_t LITERAL1 + +TWI_AP_STOP_gc KEYWORD3 RESERVED_WORD +TWI_AP_ADR_gc KEYWORD3 RESERVED_WORD +TWI_AP_t LITERAL1 + +TWI_BUSSTATE_UNKNOWN_gc KEYWORD3 RESERVED_WORD +TWI_BUSSTATE_IDLE_gc KEYWORD3 RESERVED_WORD +TWI_BUSSTATE_OWNER_gc KEYWORD3 RESERVED_WORD +TWI_BUSSTATE_BUSY_gc KEYWORD3 RESERVED_WORD +TWI_BUSSTATE_t LITERAL1 + +TWI_MCMD_NOACT_gc KEYWORD3 RESERVED_WORD +TWI_MCMD_REPSTART_gc KEYWORD3 RESERVED_WORD +TWI_MCMD_RECVTRANS_gc KEYWORD3 RESERVED_WORD +TWI_MCMD_STOP_gc KEYWORD3 RESERVED_WORD +TWI_MCMD_t LITERAL1 + +TWI_SCMD_NOACT_gc KEYWORD3 RESERVED_WORD +TWI_SCMD_COMPTRANS_gc KEYWORD3 RESERVED_WORD +TWI_SCMD_RESPONSE_gc KEYWORD3 RESERVED_WORD +TWI_SCMD_t LITERAL1 + +TWI_SDAHOLD_OFF_gc KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_50NS_gc KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_300NS_gc KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_500NS_gc KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_t LITERAL1 + +TWI_SDASETUP_4CYC_gc KEYWORD3 RESERVED_WORD +TWI_SDASETUP_8CYC_gc KEYWORD3 RESERVED_WORD +TWI_SDASETUP_t LITERAL1 + +TWI_TIMEOUT_DISABLED_gc KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_50US_gc KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_100US_gc KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_200US_gc KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_t LITERAL1 + + +RXDATAL LITERAL1 +RXDATAH LITERAL1 +TXDATAL LITERAL1 +TXDATAH LITERAL1 +STATUS LITERAL1 +CTRLA LITERAL1 +CTRLB LITERAL1 +CTRLC LITERAL1 +_WORDREGISTER(BAUD); KEYWORD3 RESERVED_WORD +CTRLD LITERAL1 +DBGCTRL LITERAL1 +EVCTRL LITERAL1 +TXPLCTRL LITERAL1 +RXPLCTRL LITERAL1 +reserved_0x0F LITERAL1 +USART_t LITERAL1 + +USART_ABW_WDW0_gc KEYWORD3 RESERVED_WORD +USART_ABW_WDW1_gc KEYWORD3 RESERVED_WORD +USART_ABW_WDW2_gc KEYWORD3 RESERVED_WORD +USART_ABW_WDW3_gc KEYWORD3 RESERVED_WORD +USART_ABW_t LITERAL1 + +USART_CHSIZE_5BIT_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_6BIT_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_7BIT_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_8BIT_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_9BITL_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_9BITH_gc KEYWORD3 RESERVED_WORD +USART_CHSIZE_t LITERAL1 + +USART_CMODE_ASYNCHRONOUS_gc KEYWORD3 RESERVED_WORD +USART_CMODE_SYNCHRONOUS_gc KEYWORD3 RESERVED_WORD +USART_CMODE_IRCOM_gc KEYWORD3 RESERVED_WORD +USART_CMODE_MSPI_gc KEYWORD3 RESERVED_WORD +USART_CMODE_t LITERAL1 + +USART_PMODE_DISABLED_gc KEYWORD3 RESERVED_WORD +USART_PMODE_EVEN_gc KEYWORD3 RESERVED_WORD +USART_PMODE_ODD_gc KEYWORD3 RESERVED_WORD +USART_PMODE_t LITERAL1 + +USART_RS485_OFF_gc KEYWORD3 RESERVED_WORD +USART_RS485_EXT_gc KEYWORD3 RESERVED_WORD +USART_RS485_INT_gc KEYWORD3 RESERVED_WORD +USART_RS485_t LITERAL1 + +USART_RXMODE_NORMAL_gc KEYWORD3 RESERVED_WORD +USART_RXMODE_CLK2X_gc KEYWORD3 RESERVED_WORD +USART_RXMODE_GENAUTO_gc KEYWORD3 RESERVED_WORD +USART_RXMODE_LINAUTO_gc KEYWORD3 RESERVED_WORD +USART_RXMODE_t LITERAL1 + +USART_SBMODE_1BIT_gc KEYWORD3 RESERVED_WORD +USART_SBMODE_2BIT_gc KEYWORD3 RESERVED_WORD +USART_SBMODE_t LITERAL1 + + +USERROW0 LITERAL1 +USERROW1 LITERAL1 +USERROW2 LITERAL1 +USERROW3 LITERAL1 +USERROW4 LITERAL1 +USERROW5 LITERAL1 +USERROW6 LITERAL1 +USERROW7 LITERAL1 +USERROW8 LITERAL1 +USERROW9 LITERAL1 +USERROW10 LITERAL1 +USERROW11 LITERAL1 +USERROW12 LITERAL1 +USERROW13 LITERAL1 +USERROW14 LITERAL1 +USERROW15 LITERAL1 +USERROW16 LITERAL1 +USERROW17 LITERAL1 +USERROW18 LITERAL1 +USERROW19 LITERAL1 +USERROW20 LITERAL1 +USERROW21 LITERAL1 +USERROW22 LITERAL1 +USERROW23 LITERAL1 +USERROW24 LITERAL1 +USERROW25 LITERAL1 +USERROW26 LITERAL1 +USERROW27 LITERAL1 +USERROW28 LITERAL1 +USERROW29 LITERAL1 +USERROW30 LITERAL1 +USERROW31 LITERAL1 +USERROW32 LITERAL1 +USERROW33 LITERAL1 +USERROW34 LITERAL1 +USERROW35 LITERAL1 +USERROW36 LITERAL1 +USERROW37 LITERAL1 +USERROW38 LITERAL1 +USERROW39 LITERAL1 +USERROW40 LITERAL1 +USERROW41 LITERAL1 +USERROW42 LITERAL1 +USERROW43 LITERAL1 +USERROW44 LITERAL1 +USERROW45 LITERAL1 +USERROW46 LITERAL1 +USERROW47 LITERAL1 +USERROW48 LITERAL1 +USERROW49 LITERAL1 +USERROW50 LITERAL1 +USERROW51 LITERAL1 +USERROW52 LITERAL1 +USERROW53 LITERAL1 +USERROW54 LITERAL1 +USERROW55 LITERAL1 +USERROW56 LITERAL1 +USERROW57 LITERAL1 +USERROW58 LITERAL1 +USERROW59 LITERAL1 +USERROW60 LITERAL1 +USERROW61 LITERAL1 +USERROW62 LITERAL1 +USERROW63 LITERAL1 +USERROW_t LITERAL1 + + +DIR LITERAL1 +OUT LITERAL1 +IN LITERAL1 +INTFLAGS LITERAL1 +VPORT_t LITERAL1 + + +CTRLA LITERAL1 +CTRLB LITERAL1 +VREF_t LITERAL1 + +VREF_AC0REFSEL_0V55_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_1V1_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_2V5_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_4V34_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_1V5_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_AVDD_gc KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_t LITERAL1 + +VREF_ADC0REFSEL_0V55_gc KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_1V1_gc KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_2V5_gc KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_4V34_gc KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_1V5_gc KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_t LITERAL1 + + +CTRLA LITERAL1 +STATUS LITERAL1 +WDT_t LITERAL1 + +WDT_PERIOD_OFF_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_8CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_16CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_32CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_64CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_128CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_256CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_512CLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_1KCLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_2KCLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_4KCLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_8KCLK_gc KEYWORD3 RESERVED_WORD +WDT_PERIOD_t LITERAL1 + +WDT_WINDOW_OFF_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_8CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_16CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_32CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_64CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_128CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_256CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_512CLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_1KCLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_2KCLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_4KCLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_8KCLK_gc KEYWORD3 RESERVED_WORD +WDT_WINDOW_t LITERAL1 + +VPORTA KEYWORD2 +VPORTB KEYWORD2 +VPORTC KEYWORD2 +VPORTD KEYWORD2 +VPORTE KEYWORD2 +VPORTF KEYWORD2 +RSTCTRL KEYWORD2 +SLPCTRL KEYWORD2 +CLKCTRL KEYWORD2 +BOD KEYWORD2 +VREF KEYWORD2 +WDT KEYWORD2 +CPUINT KEYWORD2 +CRCSCAN KEYWORD2 +RTC KEYWORD2 +EVSYS KEYWORD2 +CCL KEYWORD2 +PORTA KEYWORD2 +PORTB KEYWORD2 +PORTC KEYWORD2 +PORTD KEYWORD2 +PORTE KEYWORD2 +PORTF KEYWORD2 +PORTMUX KEYWORD2 +ADC0 KEYWORD2 +AC0 KEYWORD2 +USART0 KEYWORD2 +USART1 KEYWORD2 +USART2 KEYWORD2 +USART3 KEYWORD2 +TWI0 KEYWORD2 +SPI0 KEYWORD2 +TCA0 KEYWORD2 +TCB0 KEYWORD2 +TCB1 KEYWORD2 +TCB2 KEYWORD2 +TCB3 KEYWORD2 +SYSCFG KEYWORD2 +NVMCTRL KEYWORD2 +SIGROW KEYWORD2 +FUSE KEYWORD2 +LOCKBIT KEYWORD2 +USERROW KEYWORD2 + + +VPORTA_DIR LITERAL1 +VPORTA_OUT LITERAL1 +VPORTA_IN LITERAL1 +VPORTA_INTFLAGS LITERAL1 + +VPORTB_DIR LITERAL1 +VPORTB_OUT LITERAL1 +VPORTB_IN LITERAL1 +VPORTB_INTFLAGS LITERAL1 + +VPORTC_DIR LITERAL1 +VPORTC_OUT LITERAL1 +VPORTC_IN LITERAL1 +VPORTC_INTFLAGS LITERAL1 + +VPORTD_DIR LITERAL1 +VPORTD_OUT LITERAL1 +VPORTD_IN LITERAL1 +VPORTD_INTFLAGS LITERAL1 + +VPORTE_DIR LITERAL1 +VPORTE_OUT LITERAL1 +VPORTE_IN LITERAL1 +VPORTE_INTFLAGS LITERAL1 + +VPORTF_DIR LITERAL1 +VPORTF_OUT LITERAL1 +VPORTF_IN LITERAL1 +VPORTF_INTFLAGS LITERAL1 + +GPIO_GPIOR0 LITERAL1 +GPIO_GPIOR1 LITERAL1 +GPIO_GPIOR2 LITERAL1 +GPIO_GPIOR3 LITERAL1 + +GPIO_GPIO0 LITERAL1 +GPIO_GPIO1 LITERAL1 +GPIO_GPIO2 LITERAL1 +GPIO_GPIO3 LITERAL1 + +CPU_CCP LITERAL1 +CPU_SPL LITERAL1 +CPU_SPH LITERAL1 +CPU_SREG LITERAL1 + +RSTCTRL_RSTFR LITERAL1 +RSTCTRL_SWRR LITERAL1 + +SLPCTRL_CTRLA LITERAL1 + +CLKCTRL_MCLKCTRLA LITERAL1 +CLKCTRL_MCLKCTRLB LITERAL1 +CLKCTRL_MCLKLOCK LITERAL1 +CLKCTRL_MCLKSTATUS LITERAL1 +CLKCTRL_OSC20MCTRLA LITERAL1 +CLKCTRL_OSC20MCALIBA LITERAL1 +CLKCTRL_OSC20MCALIBB LITERAL1 +CLKCTRL_OSC32KCTRLA LITERAL1 +CLKCTRL_XOSC32KCTRLA LITERAL1 + +BOD_CTRLA LITERAL1 +BOD_CTRLB LITERAL1 +BOD_VLMCTRLA LITERAL1 +BOD_INTCTRL LITERAL1 +BOD_INTFLAGS LITERAL1 +BOD_STATUS LITERAL1 + +VREF_CTRLA LITERAL1 +VREF_CTRLB LITERAL1 + +WDT_CTRLA LITERAL1 +WDT_STATUS LITERAL1 + +CPUINT_CTRLA LITERAL1 +CPUINT_STATUS LITERAL1 +CPUINT_LVL0PRI LITERAL1 +CPUINT_LVL1VEC LITERAL1 + +CRCSCAN_CTRLA LITERAL1 +CRCSCAN_CTRLB LITERAL1 +CRCSCAN_STATUS LITERAL1 + +RTC_CTRLA LITERAL1 +RTC_STATUS LITERAL1 +RTC_INTCTRL LITERAL1 +RTC_INTFLAGS LITERAL1 +RTC_TEMP LITERAL1 +RTC_DBGCTRL LITERAL1 +RTC_CALIB LITERAL1 +RTC_CLKSEL LITERAL1 +RTC_CNT LITERAL1 +RTC_CNTL LITERAL1 +RTC_CNTH LITERAL1 +RTC_PER LITERAL1 +RTC_PERL LITERAL1 +RTC_PERH LITERAL1 +RTC_CMP LITERAL1 +RTC_CMPL LITERAL1 +RTC_CMPH LITERAL1 +RTC_PITCTRLA LITERAL1 +RTC_PITSTATUS LITERAL1 +RTC_PITINTCTRL LITERAL1 +RTC_PITINTFLAGS LITERAL1 +RTC_PITDBGCTRL LITERAL1 + +EVSYS_STROBE LITERAL1 +EVSYS_CHANNEL0 LITERAL1 +EVSYS_CHANNEL1 LITERAL1 +EVSYS_CHANNEL2 LITERAL1 +EVSYS_CHANNEL3 LITERAL1 +EVSYS_CHANNEL4 LITERAL1 +EVSYS_CHANNEL5 LITERAL1 +EVSYS_CHANNEL6 LITERAL1 +EVSYS_CHANNEL7 LITERAL1 +EVSYS_USERCCLLUT0A LITERAL1 +EVSYS_USERCCLLUT0B LITERAL1 +EVSYS_USERCCLLUT1A LITERAL1 +EVSYS_USERCCLLUT1B LITERAL1 +EVSYS_USERCCLLUT2A LITERAL1 +EVSYS_USERCCLLUT2B LITERAL1 +EVSYS_USERCCLLUT3A LITERAL1 +EVSYS_USERCCLLUT3B LITERAL1 +EVSYS_USERADC0 LITERAL1 +EVSYS_USEREVOUTA LITERAL1 +EVSYS_USEREVOUTB LITERAL1 +EVSYS_USEREVOUTC LITERAL1 +EVSYS_USEREVOUTD LITERAL1 +EVSYS_USEREVOUTE LITERAL1 +EVSYS_USEREVOUTF LITERAL1 +EVSYS_USERUSART0 LITERAL1 +EVSYS_USERUSART1 LITERAL1 +EVSYS_USERUSART2 LITERAL1 +EVSYS_USERUSART3 LITERAL1 +EVSYS_USERTCA0 LITERAL1 +EVSYS_USERTCB0 LITERAL1 +EVSYS_USERTCB1 LITERAL1 +EVSYS_USERTCB2 LITERAL1 +EVSYS_USERTCB3 LITERAL1 + +CCL_CTRLA LITERAL1 +CCL_SEQCTRL0 LITERAL1 +CCL_SEQCTRL1 LITERAL1 +CCL_INTCTRL0 LITERAL1 +CCL_INTFLAGS LITERAL1 +CCL_LUT0CTRLA LITERAL1 +CCL_LUT0CTRLB LITERAL1 +CCL_LUT0CTRLC LITERAL1 +CCL_TRUTH0 LITERAL1 +CCL_LUT1CTRLA LITERAL1 +CCL_LUT1CTRLB LITERAL1 +CCL_LUT1CTRLC LITERAL1 +CCL_TRUTH1 LITERAL1 +CCL_LUT2CTRLA LITERAL1 +CCL_LUT2CTRLB LITERAL1 +CCL_LUT2CTRLC LITERAL1 +CCL_TRUTH2 LITERAL1 +CCL_LUT3CTRLA LITERAL1 +CCL_LUT3CTRLB LITERAL1 +CCL_LUT3CTRLC LITERAL1 +CCL_TRUTH3 LITERAL1 + +PORTA_DIR LITERAL1 +PORTA_DIRSET LITERAL1 +PORTA_DIRCLR LITERAL1 +PORTA_DIRTGL LITERAL1 +PORTA_OUT LITERAL1 +PORTA_OUTSET LITERAL1 +PORTA_OUTCLR LITERAL1 +PORTA_OUTTGL LITERAL1 +PORTA_IN LITERAL1 +PORTA_INTFLAGS LITERAL1 +PORTA_PORTCTRL LITERAL1 +PORTA_PIN0CTRL LITERAL1 +PORTA_PIN1CTRL LITERAL1 +PORTA_PIN2CTRL LITERAL1 +PORTA_PIN3CTRL LITERAL1 +PORTA_PIN4CTRL LITERAL1 +PORTA_PIN5CTRL LITERAL1 +PORTA_PIN6CTRL LITERAL1 +PORTA_PIN7CTRL LITERAL1 + +PORTB_DIR LITERAL1 +PORTB_DIRSET LITERAL1 +PORTB_DIRCLR LITERAL1 +PORTB_DIRTGL LITERAL1 +PORTB_OUT LITERAL1 +PORTB_OUTSET LITERAL1 +PORTB_OUTCLR LITERAL1 +PORTB_OUTTGL LITERAL1 +PORTB_IN LITERAL1 +PORTB_INTFLAGS LITERAL1 +PORTB_PORTCTRL LITERAL1 +PORTB_PIN0CTRL LITERAL1 +PORTB_PIN1CTRL LITERAL1 +PORTB_PIN2CTRL LITERAL1 +PORTB_PIN3CTRL LITERAL1 +PORTB_PIN4CTRL LITERAL1 +PORTB_PIN5CTRL LITERAL1 +PORTB_PIN6CTRL LITERAL1 +PORTB_PIN7CTRL LITERAL1 + +PORTC_DIR LITERAL1 +PORTC_DIRSET LITERAL1 +PORTC_DIRCLR LITERAL1 +PORTC_DIRTGL LITERAL1 +PORTC_OUT LITERAL1 +PORTC_OUTSET LITERAL1 +PORTC_OUTCLR LITERAL1 +PORTC_OUTTGL LITERAL1 +PORTC_IN LITERAL1 +PORTC_INTFLAGS LITERAL1 +PORTC_PORTCTRL LITERAL1 +PORTC_PIN0CTRL LITERAL1 +PORTC_PIN1CTRL LITERAL1 +PORTC_PIN2CTRL LITERAL1 +PORTC_PIN3CTRL LITERAL1 +PORTC_PIN4CTRL LITERAL1 +PORTC_PIN5CTRL LITERAL1 +PORTC_PIN6CTRL LITERAL1 +PORTC_PIN7CTRL LITERAL1 + +PORTD_DIR LITERAL1 +PORTD_DIRSET LITERAL1 +PORTD_DIRCLR LITERAL1 +PORTD_DIRTGL LITERAL1 +PORTD_OUT LITERAL1 +PORTD_OUTSET LITERAL1 +PORTD_OUTCLR LITERAL1 +PORTD_OUTTGL LITERAL1 +PORTD_IN LITERAL1 +PORTD_INTFLAGS LITERAL1 +PORTD_PORTCTRL LITERAL1 +PORTD_PIN0CTRL LITERAL1 +PORTD_PIN1CTRL LITERAL1 +PORTD_PIN2CTRL LITERAL1 +PORTD_PIN3CTRL LITERAL1 +PORTD_PIN4CTRL LITERAL1 +PORTD_PIN5CTRL LITERAL1 +PORTD_PIN6CTRL LITERAL1 +PORTD_PIN7CTRL LITERAL1 + +PORTE_DIR LITERAL1 +PORTE_DIRSET LITERAL1 +PORTE_DIRCLR LITERAL1 +PORTE_DIRTGL LITERAL1 +PORTE_OUT LITERAL1 +PORTE_OUTSET LITERAL1 +PORTE_OUTCLR LITERAL1 +PORTE_OUTTGL LITERAL1 +PORTE_IN LITERAL1 +PORTE_INTFLAGS LITERAL1 +PORTE_PORTCTRL LITERAL1 +PORTE_PIN0CTRL LITERAL1 +PORTE_PIN1CTRL LITERAL1 +PORTE_PIN2CTRL LITERAL1 +PORTE_PIN3CTRL LITERAL1 +PORTE_PIN4CTRL LITERAL1 +PORTE_PIN5CTRL LITERAL1 +PORTE_PIN6CTRL LITERAL1 +PORTE_PIN7CTRL LITERAL1 + +PORTF_DIR LITERAL1 +PORTF_DIRSET LITERAL1 +PORTF_DIRCLR LITERAL1 +PORTF_DIRTGL LITERAL1 +PORTF_OUT LITERAL1 +PORTF_OUTSET LITERAL1 +PORTF_OUTCLR LITERAL1 +PORTF_OUTTGL LITERAL1 +PORTF_IN LITERAL1 +PORTF_INTFLAGS LITERAL1 +PORTF_PORTCTRL LITERAL1 +PORTF_PIN0CTRL LITERAL1 +PORTF_PIN1CTRL LITERAL1 +PORTF_PIN2CTRL LITERAL1 +PORTF_PIN3CTRL LITERAL1 +PORTF_PIN4CTRL LITERAL1 +PORTF_PIN5CTRL LITERAL1 +PORTF_PIN6CTRL LITERAL1 +PORTF_PIN7CTRL LITERAL1 + +PORTMUX_EVSYSROUTEA LITERAL1 +PORTMUX_CCLROUTEA LITERAL1 +PORTMUX_USARTROUTEA LITERAL1 +PORTMUX_TWISPIROUTEA LITERAL1 +PORTMUX_TCAROUTEA LITERAL1 +PORTMUX_TCBROUTEA LITERAL1 + +ADC0_CTRLA LITERAL1 +ADC0_CTRLB LITERAL1 +ADC0_CTRLC LITERAL1 +ADC0_CTRLD LITERAL1 +ADC0_CTRLE LITERAL1 +ADC0_SAMPCTRL LITERAL1 +ADC0_MUXPOS LITERAL1 +ADC0_COMMAND LITERAL1 +ADC0_EVCTRL LITERAL1 +ADC0_INTCTRL LITERAL1 +ADC0_INTFLAGS LITERAL1 +ADC0_DBGCTRL LITERAL1 +ADC0_TEMP LITERAL1 +ADC0_RES LITERAL1 +ADC0_RESL LITERAL1 +ADC0_RESH LITERAL1 +ADC0_WINLT LITERAL1 +ADC0_WINLTL LITERAL1 +ADC0_WINLTH LITERAL1 +ADC0_WINHT LITERAL1 +ADC0_WINHTL LITERAL1 +ADC0_WINHTH LITERAL1 +ADC0_CALIB LITERAL1 + +AC0_CTRLA LITERAL1 +AC0_MUXCTRLA LITERAL1 +AC0_DACREF LITERAL1 +AC0_INTCTRL LITERAL1 +AC0_STATUS LITERAL1 + +USART0_RXDATAL LITERAL1 +USART0_RXDATAH LITERAL1 +USART0_TXDATAL LITERAL1 +USART0_TXDATAH LITERAL1 +USART0_STATUS LITERAL1 +USART0_CTRLA LITERAL1 +USART0_CTRLB LITERAL1 +USART0_CTRLC LITERAL1 +USART0_BAUD LITERAL1 +USART0_BAUDL LITERAL1 +USART0_BAUDH LITERAL1 +USART0_CTRLD LITERAL1 +USART0_DBGCTRL LITERAL1 +USART0_EVCTRL LITERAL1 +USART0_TXPLCTRL LITERAL1 +USART0_RXPLCTRL LITERAL1 + +USART1_RXDATAL LITERAL1 +USART1_RXDATAH LITERAL1 +USART1_TXDATAL LITERAL1 +USART1_TXDATAH LITERAL1 +USART1_STATUS LITERAL1 +USART1_CTRLA LITERAL1 +USART1_CTRLB LITERAL1 +USART1_CTRLC LITERAL1 +USART1_BAUD LITERAL1 +USART1_BAUDL LITERAL1 +USART1_BAUDH LITERAL1 +USART1_CTRLD LITERAL1 +USART1_DBGCTRL LITERAL1 +USART1_EVCTRL LITERAL1 +USART1_TXPLCTRL LITERAL1 +USART1_RXPLCTRL LITERAL1 + +USART2_RXDATAL LITERAL1 +USART2_RXDATAH LITERAL1 +USART2_TXDATAL LITERAL1 +USART2_TXDATAH LITERAL1 +USART2_STATUS LITERAL1 +USART2_CTRLA LITERAL1 +USART2_CTRLB LITERAL1 +USART2_CTRLC LITERAL1 +USART2_BAUD LITERAL1 +USART2_BAUDL LITERAL1 +USART2_BAUDH LITERAL1 +USART2_CTRLD LITERAL1 +USART2_DBGCTRL LITERAL1 +USART2_EVCTRL LITERAL1 +USART2_TXPLCTRL LITERAL1 +USART2_RXPLCTRL LITERAL1 + +USART3_RXDATAL LITERAL1 +USART3_RXDATAH LITERAL1 +USART3_TXDATAL LITERAL1 +USART3_TXDATAH LITERAL1 +USART3_STATUS LITERAL1 +USART3_CTRLA LITERAL1 +USART3_CTRLB LITERAL1 +USART3_CTRLC LITERAL1 +USART3_BAUD LITERAL1 +USART3_BAUDL LITERAL1 +USART3_BAUDH LITERAL1 +USART3_CTRLD LITERAL1 +USART3_DBGCTRL LITERAL1 +USART3_EVCTRL LITERAL1 +USART3_TXPLCTRL LITERAL1 +USART3_RXPLCTRL LITERAL1 + +TWI0_CTRLA LITERAL1 +TWI0_DUALCTRL LITERAL1 +TWI0_DBGCTRL LITERAL1 +TWI0_MCTRLA LITERAL1 +TWI0_MCTRLB LITERAL1 +TWI0_MSTATUS LITERAL1 +TWI0_MBAUD LITERAL1 +TWI0_MADDR LITERAL1 +TWI0_MDATA LITERAL1 +TWI0_SCTRLA LITERAL1 +TWI0_SCTRLB LITERAL1 +TWI0_SSTATUS LITERAL1 +TWI0_SADDR LITERAL1 +TWI0_SDATA LITERAL1 +TWI0_SADDRMASK LITERAL1 + +SPI0_CTRLA LITERAL1 +SPI0_CTRLB LITERAL1 +SPI0_INTCTRL LITERAL1 +SPI0_INTFLAGS LITERAL1 +SPI0_DATA LITERAL1 + +TCA0_SINGLE_CTRLA LITERAL1 +TCA0_SINGLE_CTRLB LITERAL1 +TCA0_SINGLE_CTRLC LITERAL1 +TCA0_SINGLE_CTRLD LITERAL1 +TCA0_SINGLE_CTRLECLR LITERAL1 +TCA0_SINGLE_CTRLESET LITERAL1 +TCA0_SINGLE_CTRLFCLR LITERAL1 +TCA0_SINGLE_CTRLFSET LITERAL1 +TCA0_SINGLE_EVCTRL LITERAL1 +TCA0_SINGLE_INTCTRL LITERAL1 +TCA0_SINGLE_INTFLAGS LITERAL1 +TCA0_SINGLE_DBGCTRL LITERAL1 +TCA0_SINGLE_TEMP LITERAL1 +TCA0_SINGLE_CNT LITERAL1 +TCA0_SINGLE_PER LITERAL1 +TCA0_SINGLE_CMP0 LITERAL1 +TCA0_SINGLE_CMP1 LITERAL1 +TCA0_SINGLE_CMP2 LITERAL1 +TCA0_SINGLE_PERBUF LITERAL1 +TCA0_SINGLE_CMP0BUF LITERAL1 +TCA0_SINGLE_CMP1BUF LITERAL1 +TCA0_SINGLE_CMP2BUF LITERAL1 +TCA0_SPLIT_CTRLA LITERAL1 +TCA0_SPLIT_CTRLB LITERAL1 +TCA0_SPLIT_CTRLC LITERAL1 +TCA0_SPLIT_CTRLD LITERAL1 +TCA0_SPLIT_CTRLECLR LITERAL1 +TCA0_SPLIT_CTRLESET LITERAL1 +TCA0_SPLIT_INTCTRL LITERAL1 +TCA0_SPLIT_INTFLAGS LITERAL1 +TCA0_SPLIT_DBGCTRL LITERAL1 +TCA0_SPLIT_LCNT LITERAL1 +TCA0_SPLIT_HCNT LITERAL1 +TCA0_SPLIT_LPER LITERAL1 +TCA0_SPLIT_HPER LITERAL1 +TCA0_SPLIT_LCMP0 LITERAL1 +TCA0_SPLIT_HCMP0 LITERAL1 +TCA0_SPLIT_LCMP1 LITERAL1 +TCA0_SPLIT_HCMP1 LITERAL1 +TCA0_SPLIT_LCMP2 LITERAL1 +TCA0_SPLIT_HCMP2 LITERAL1 + +TCB0_CTRLA LITERAL1 +TCB0_CTRLB LITERAL1 +TCB0_EVCTRL LITERAL1 +TCB0_INTCTRL LITERAL1 +TCB0_INTFLAGS LITERAL1 +TCB0_STATUS LITERAL1 +TCB0_DBGCTRL LITERAL1 +TCB0_TEMP LITERAL1 +TCB0_CNT LITERAL1 +TCB0_CNTL LITERAL1 +TCB0_CNTH LITERAL1 +TCB0_CCMP LITERAL1 +TCB0_CCMPL LITERAL1 +TCB0_CCMPH LITERAL1 + +TCB1_CTRLA LITERAL1 +TCB1_CTRLB LITERAL1 +TCB1_EVCTRL LITERAL1 +TCB1_INTCTRL LITERAL1 +TCB1_INTFLAGS LITERAL1 +TCB1_STATUS LITERAL1 +TCB1_DBGCTRL LITERAL1 +TCB1_TEMP LITERAL1 +TCB1_CNT LITERAL1 +TCB1_CNTL LITERAL1 +TCB1_CNTH LITERAL1 +TCB1_CCMP LITERAL1 +TCB1_CCMPL LITERAL1 +TCB1_CCMPH LITERAL1 + +TCB2_CTRLA LITERAL1 +TCB2_CTRLB LITERAL1 +TCB2_EVCTRL LITERAL1 +TCB2_INTCTRL LITERAL1 +TCB2_INTFLAGS LITERAL1 +TCB2_STATUS LITERAL1 +TCB2_DBGCTRL LITERAL1 +TCB2_TEMP LITERAL1 +TCB2_CNT LITERAL1 +TCB2_CNTL LITERAL1 +TCB2_CNTH LITERAL1 +TCB2_CCMP LITERAL1 +TCB2_CCMPL LITERAL1 +TCB2_CCMPH LITERAL1 + +TCB3_CTRLA LITERAL1 +TCB3_CTRLB LITERAL1 +TCB3_EVCTRL LITERAL1 +TCB3_INTCTRL LITERAL1 +TCB3_INTFLAGS LITERAL1 +TCB3_STATUS LITERAL1 +TCB3_DBGCTRL LITERAL1 +TCB3_TEMP LITERAL1 +TCB3_CNT LITERAL1 +TCB3_CNTL LITERAL1 +TCB3_CNTH LITERAL1 +TCB3_CCMP LITERAL1 +TCB3_CCMPL LITERAL1 +TCB3_CCMPH LITERAL1 + +SYSCFG_REVID LITERAL1 +SYSCFG_EXTBRK LITERAL1 +SYSCFG_OCDM LITERAL1 +SYSCFG_OCDMS LITERAL1 + +NVMCTRL_CTRLA LITERAL1 +NVMCTRL_CTRLB LITERAL1 +NVMCTRL_STATUS LITERAL1 +NVMCTRL_INTCTRL LITERAL1 +NVMCTRL_INTFLAGS LITERAL1 +NVMCTRL_DATA LITERAL1 +NVMCTRL_DATAL LITERAL1 +NVMCTRL_DATAH LITERAL1 +NVMCTRL_ADDR LITERAL1 +NVMCTRL_ADDRL LITERAL1 +NVMCTRL_ADDRH LITERAL1 + +SIGROW_DEVICEID0 LITERAL1 +SIGROW_DEVICEID1 LITERAL1 +SIGROW_DEVICEID2 LITERAL1 +SIGROW_SERNUM0 LITERAL1 +SIGROW_SERNUM1 LITERAL1 +SIGROW_SERNUM2 LITERAL1 +SIGROW_SERNUM3 LITERAL1 +SIGROW_SERNUM4 LITERAL1 +SIGROW_SERNUM5 LITERAL1 +SIGROW_SERNUM6 LITERAL1 +SIGROW_SERNUM7 LITERAL1 +SIGROW_SERNUM8 LITERAL1 +SIGROW_SERNUM9 LITERAL1 +SIGROW_OSCCAL32K LITERAL1 +SIGROW_OSCCAL16M0 LITERAL1 +SIGROW_OSCCAL16M1 LITERAL1 +SIGROW_OSCCAL20M0 LITERAL1 +SIGROW_OSCCAL20M1 LITERAL1 +SIGROW_TEMPSENSE0 LITERAL1 +SIGROW_TEMPSENSE1 LITERAL1 +SIGROW_OSC16ERR3V LITERAL1 +SIGROW_OSC16ERR5V LITERAL1 +SIGROW_OSC20ERR3V LITERAL1 +SIGROW_OSC20ERR5V LITERAL1 +SIGROW_CHECKSUM1 LITERAL1 + +FUSE_WDTCFG LITERAL1 +FUSE_BODCFG LITERAL1 +FUSE_OSCCFG LITERAL1 +FUSE_SYSCFG0 LITERAL1 +FUSE_SYSCFG1 LITERAL1 +FUSE_APPEND LITERAL1 +FUSE_BOOTEND LITERAL1 + +LOCKBIT_LOCKBIT LITERAL1 + +USERROW_USERROW0 LITERAL1 +USERROW_USERROW1 LITERAL1 +USERROW_USERROW2 LITERAL1 +USERROW_USERROW3 LITERAL1 +USERROW_USERROW4 LITERAL1 +USERROW_USERROW5 LITERAL1 +USERROW_USERROW6 LITERAL1 +USERROW_USERROW7 LITERAL1 +USERROW_USERROW8 LITERAL1 +USERROW_USERROW9 LITERAL1 +USERROW_USERROW10 LITERAL1 +USERROW_USERROW11 LITERAL1 +USERROW_USERROW12 LITERAL1 +USERROW_USERROW13 LITERAL1 +USERROW_USERROW14 LITERAL1 +USERROW_USERROW15 LITERAL1 +USERROW_USERROW16 LITERAL1 +USERROW_USERROW17 LITERAL1 +USERROW_USERROW18 LITERAL1 +USERROW_USERROW19 LITERAL1 +USERROW_USERROW20 LITERAL1 +USERROW_USERROW21 LITERAL1 +USERROW_USERROW22 LITERAL1 +USERROW_USERROW23 LITERAL1 +USERROW_USERROW24 LITERAL1 +USERROW_USERROW25 LITERAL1 +USERROW_USERROW26 LITERAL1 +USERROW_USERROW27 LITERAL1 +USERROW_USERROW28 LITERAL1 +USERROW_USERROW29 LITERAL1 +USERROW_USERROW30 LITERAL1 +USERROW_USERROW31 LITERAL1 +USERROW_USERROW32 LITERAL1 +USERROW_USERROW33 LITERAL1 +USERROW_USERROW34 LITERAL1 +USERROW_USERROW35 LITERAL1 +USERROW_USERROW36 LITERAL1 +USERROW_USERROW37 LITERAL1 +USERROW_USERROW38 LITERAL1 +USERROW_USERROW39 LITERAL1 +USERROW_USERROW40 LITERAL1 +USERROW_USERROW41 LITERAL1 +USERROW_USERROW42 LITERAL1 +USERROW_USERROW43 LITERAL1 +USERROW_USERROW44 LITERAL1 +USERROW_USERROW45 LITERAL1 +USERROW_USERROW46 LITERAL1 +USERROW_USERROW47 LITERAL1 +USERROW_USERROW48 LITERAL1 +USERROW_USERROW49 LITERAL1 +USERROW_USERROW50 LITERAL1 +USERROW_USERROW51 LITERAL1 +USERROW_USERROW52 LITERAL1 +USERROW_USERROW53 LITERAL1 +USERROW_USERROW54 LITERAL1 +USERROW_USERROW55 LITERAL1 +USERROW_USERROW56 LITERAL1 +USERROW_USERROW57 LITERAL1 +USERROW_USERROW58 LITERAL1 +USERROW_USERROW59 LITERAL1 +USERROW_USERROW60 LITERAL1 +USERROW_USERROW61 LITERAL1 +USERROW_USERROW62 LITERAL1 +USERROW_USERROW63 LITERAL1 + + +AC_ENABLE_bm KEYWORD3 RESERVED_WORD +AC_ENABLE_bp KEYWORD3 RESERVED_WORD +AC_HYSMODE_gm KEYWORD3 RESERVED_WORD +AC_HYSMODE_gp KEYWORD3 RESERVED_WORD +AC_HYSMODE0_bm KEYWORD3 RESERVED_WORD +AC_HYSMODE0_bp KEYWORD3 RESERVED_WORD +AC_HYSMODE1_bm KEYWORD3 RESERVED_WORD +AC_HYSMODE1_bp KEYWORD3 RESERVED_WORD +AC_LPMODE_bm KEYWORD3 RESERVED_WORD +AC_LPMODE_bp KEYWORD3 RESERVED_WORD +AC_INTMODE_gm KEYWORD3 RESERVED_WORD +AC_INTMODE_gp KEYWORD3 RESERVED_WORD +AC_INTMODE0_bm KEYWORD3 RESERVED_WORD +AC_INTMODE0_bp KEYWORD3 RESERVED_WORD +AC_INTMODE1_bm KEYWORD3 RESERVED_WORD +AC_INTMODE1_bp KEYWORD3 RESERVED_WORD +AC_OUTEN_bm KEYWORD3 RESERVED_WORD +AC_OUTEN_bp KEYWORD3 RESERVED_WORD +AC_RUNSTDBY_bm KEYWORD3 RESERVED_WORD +AC_RUNSTDBY_bp KEYWORD3 RESERVED_WORD + +AC_MUXNEG_gm KEYWORD3 RESERVED_WORD +AC_MUXNEG_gp KEYWORD3 RESERVED_WORD +AC_MUXNEG0_bm KEYWORD3 RESERVED_WORD +AC_MUXNEG0_bp KEYWORD3 RESERVED_WORD +AC_MUXNEG1_bm KEYWORD3 RESERVED_WORD +AC_MUXNEG1_bp KEYWORD3 RESERVED_WORD +AC_MUXPOS_gm KEYWORD3 RESERVED_WORD +AC_MUXPOS_gp KEYWORD3 RESERVED_WORD +AC_MUXPOS0_bm KEYWORD3 RESERVED_WORD +AC_MUXPOS0_bp KEYWORD3 RESERVED_WORD +AC_MUXPOS1_bm KEYWORD3 RESERVED_WORD +AC_MUXPOS1_bp KEYWORD3 RESERVED_WORD +AC_INVERT_bm KEYWORD3 RESERVED_WORD +AC_INVERT_bp KEYWORD3 RESERVED_WORD + +AC_DATA_gm KEYWORD3 RESERVED_WORD +AC_DATA_gp KEYWORD3 RESERVED_WORD +AC_DATA0_bm KEYWORD3 RESERVED_WORD +AC_DATA0_bp KEYWORD3 RESERVED_WORD +AC_DATA1_bm KEYWORD3 RESERVED_WORD +AC_DATA1_bp KEYWORD3 RESERVED_WORD +AC_DATA2_bm KEYWORD3 RESERVED_WORD +AC_DATA2_bp KEYWORD3 RESERVED_WORD +AC_DATA3_bm KEYWORD3 RESERVED_WORD +AC_DATA3_bp KEYWORD3 RESERVED_WORD +AC_DATA4_bm KEYWORD3 RESERVED_WORD +AC_DATA4_bp KEYWORD3 RESERVED_WORD +AC_DATA5_bm KEYWORD3 RESERVED_WORD +AC_DATA5_bp KEYWORD3 RESERVED_WORD +AC_DATA6_bm KEYWORD3 RESERVED_WORD +AC_DATA6_bp KEYWORD3 RESERVED_WORD +AC_DATA7_bm KEYWORD3 RESERVED_WORD +AC_DATA7_bp KEYWORD3 RESERVED_WORD + +AC_CMP_bm KEYWORD3 RESERVED_WORD +AC_CMP_bp KEYWORD3 RESERVED_WORD + + +AC_STATE_bm KEYWORD3 RESERVED_WORD +AC_STATE_bp KEYWORD3 RESERVED_WORD + + +ADC_ENABLE_bm KEYWORD3 RESERVED_WORD +ADC_ENABLE_bp KEYWORD3 RESERVED_WORD +ADC_FREERUN_bm KEYWORD3 RESERVED_WORD +ADC_FREERUN_bp KEYWORD3 RESERVED_WORD +ADC_RESSEL_bm KEYWORD3 RESERVED_WORD +ADC_RESSEL_bp KEYWORD3 RESERVED_WORD +ADC_RUNSTBY_bm KEYWORD3 RESERVED_WORD +ADC_RUNSTBY_bp KEYWORD3 RESERVED_WORD + +ADC_SAMPNUM_gm KEYWORD3 RESERVED_WORD +ADC_SAMPNUM_gp KEYWORD3 RESERVED_WORD +ADC_SAMPNUM0_bm KEYWORD3 RESERVED_WORD +ADC_SAMPNUM0_bp KEYWORD3 RESERVED_WORD +ADC_SAMPNUM1_bm KEYWORD3 RESERVED_WORD +ADC_SAMPNUM1_bp KEYWORD3 RESERVED_WORD +ADC_SAMPNUM2_bm KEYWORD3 RESERVED_WORD +ADC_SAMPNUM2_bp KEYWORD3 RESERVED_WORD + +ADC_PRESC_gm KEYWORD3 RESERVED_WORD +ADC_PRESC_gp KEYWORD3 RESERVED_WORD +ADC_PRESC0_bm KEYWORD3 RESERVED_WORD +ADC_PRESC0_bp KEYWORD3 RESERVED_WORD +ADC_PRESC1_bm KEYWORD3 RESERVED_WORD +ADC_PRESC1_bp KEYWORD3 RESERVED_WORD +ADC_PRESC2_bm KEYWORD3 RESERVED_WORD +ADC_PRESC2_bp KEYWORD3 RESERVED_WORD +ADC_REFSEL_gm KEYWORD3 RESERVED_WORD +ADC_REFSEL_gp KEYWORD3 RESERVED_WORD +ADC_REFSEL0_bm KEYWORD3 RESERVED_WORD +ADC_REFSEL0_bp KEYWORD3 RESERVED_WORD +ADC_REFSEL1_bm KEYWORD3 RESERVED_WORD +ADC_REFSEL1_bp KEYWORD3 RESERVED_WORD +ADC_SAMPCAP_bm KEYWORD3 RESERVED_WORD +ADC_SAMPCAP_bp KEYWORD3 RESERVED_WORD + +ADC_SAMPDLY_gm KEYWORD3 RESERVED_WORD +ADC_SAMPDLY_gp KEYWORD3 RESERVED_WORD +ADC_SAMPDLY0_bm KEYWORD3 RESERVED_WORD +ADC_SAMPDLY0_bp KEYWORD3 RESERVED_WORD +ADC_SAMPDLY1_bm KEYWORD3 RESERVED_WORD +ADC_SAMPDLY1_bp KEYWORD3 RESERVED_WORD +ADC_SAMPDLY2_bm KEYWORD3 RESERVED_WORD +ADC_SAMPDLY2_bp KEYWORD3 RESERVED_WORD +ADC_SAMPDLY3_bm KEYWORD3 RESERVED_WORD +ADC_SAMPDLY3_bp KEYWORD3 RESERVED_WORD +ADC_ASDV_bm KEYWORD3 RESERVED_WORD +ADC_ASDV_bp KEYWORD3 RESERVED_WORD +ADC_INITDLY_gm KEYWORD3 RESERVED_WORD +ADC_INITDLY_gp KEYWORD3 RESERVED_WORD +ADC_INITDLY0_bm KEYWORD3 RESERVED_WORD +ADC_INITDLY0_bp KEYWORD3 RESERVED_WORD +ADC_INITDLY1_bm KEYWORD3 RESERVED_WORD +ADC_INITDLY1_bp KEYWORD3 RESERVED_WORD +ADC_INITDLY2_bm KEYWORD3 RESERVED_WORD +ADC_INITDLY2_bp KEYWORD3 RESERVED_WORD + +ADC_WINCM_gm KEYWORD3 RESERVED_WORD +ADC_WINCM_gp KEYWORD3 RESERVED_WORD +ADC_WINCM0_bm KEYWORD3 RESERVED_WORD +ADC_WINCM0_bp KEYWORD3 RESERVED_WORD +ADC_WINCM1_bm KEYWORD3 RESERVED_WORD +ADC_WINCM1_bp KEYWORD3 RESERVED_WORD +ADC_WINCM2_bm KEYWORD3 RESERVED_WORD +ADC_WINCM2_bp KEYWORD3 RESERVED_WORD + +ADC_SAMPLEN_gm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN_gp KEYWORD3 RESERVED_WORD +ADC_SAMPLEN0_bm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN0_bp KEYWORD3 RESERVED_WORD +ADC_SAMPLEN1_bm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN1_bp KEYWORD3 RESERVED_WORD +ADC_SAMPLEN2_bm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN2_bp KEYWORD3 RESERVED_WORD +ADC_SAMPLEN3_bm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN3_bp KEYWORD3 RESERVED_WORD +ADC_SAMPLEN4_bm KEYWORD3 RESERVED_WORD +ADC_SAMPLEN4_bp KEYWORD3 RESERVED_WORD + +ADC_MUXPOS_gm KEYWORD3 RESERVED_WORD +ADC_MUXPOS_gp KEYWORD3 RESERVED_WORD +ADC_MUXPOS0_bm KEYWORD3 RESERVED_WORD +ADC_MUXPOS0_bp KEYWORD3 RESERVED_WORD +ADC_MUXPOS1_bm KEYWORD3 RESERVED_WORD +ADC_MUXPOS1_bp KEYWORD3 RESERVED_WORD +ADC_MUXPOS2_bm KEYWORD3 RESERVED_WORD +ADC_MUXPOS2_bp KEYWORD3 RESERVED_WORD +ADC_MUXPOS3_bm KEYWORD3 RESERVED_WORD +ADC_MUXPOS3_bp KEYWORD3 RESERVED_WORD +ADC_MUXPOS4_bm KEYWORD3 RESERVED_WORD +ADC_MUXPOS4_bp KEYWORD3 RESERVED_WORD + +ADC_STCONV_bm KEYWORD3 RESERVED_WORD +ADC_STCONV_bp KEYWORD3 RESERVED_WORD + +ADC_STARTEI_bm KEYWORD3 RESERVED_WORD +ADC_STARTEI_bp KEYWORD3 RESERVED_WORD + +ADC_RESRDY_bm KEYWORD3 RESERVED_WORD +ADC_RESRDY_bp KEYWORD3 RESERVED_WORD +ADC_WCMP_bm KEYWORD3 RESERVED_WORD +ADC_WCMP_bp KEYWORD3 RESERVED_WORD + + + + +ADC_DBGRUN_bm KEYWORD3 RESERVED_WORD +ADC_DBGRUN_bp KEYWORD3 RESERVED_WORD + +ADC_TEMP_gm KEYWORD3 RESERVED_WORD +ADC_TEMP_gp KEYWORD3 RESERVED_WORD +ADC_TEMP0_bm KEYWORD3 RESERVED_WORD +ADC_TEMP0_bp KEYWORD3 RESERVED_WORD +ADC_TEMP1_bm KEYWORD3 RESERVED_WORD +ADC_TEMP1_bp KEYWORD3 RESERVED_WORD +ADC_TEMP2_bm KEYWORD3 RESERVED_WORD +ADC_TEMP2_bp KEYWORD3 RESERVED_WORD +ADC_TEMP3_bm KEYWORD3 RESERVED_WORD +ADC_TEMP3_bp KEYWORD3 RESERVED_WORD +ADC_TEMP4_bm KEYWORD3 RESERVED_WORD +ADC_TEMP4_bp KEYWORD3 RESERVED_WORD +ADC_TEMP5_bm KEYWORD3 RESERVED_WORD +ADC_TEMP5_bp KEYWORD3 RESERVED_WORD +ADC_TEMP6_bm KEYWORD3 RESERVED_WORD +ADC_TEMP6_bp KEYWORD3 RESERVED_WORD +ADC_TEMP7_bm KEYWORD3 RESERVED_WORD +ADC_TEMP7_bp KEYWORD3 RESERVED_WORD + +ADC_DUTYCYC_bm KEYWORD3 RESERVED_WORD +ADC_DUTYCYC_bp KEYWORD3 RESERVED_WORD + + +BOD_SLEEP_gm KEYWORD3 RESERVED_WORD +BOD_SLEEP_gp KEYWORD3 RESERVED_WORD +BOD_SLEEP0_bm KEYWORD3 RESERVED_WORD +BOD_SLEEP0_bp KEYWORD3 RESERVED_WORD +BOD_SLEEP1_bm KEYWORD3 RESERVED_WORD +BOD_SLEEP1_bp KEYWORD3 RESERVED_WORD +BOD_ACTIVE_gm KEYWORD3 RESERVED_WORD +BOD_ACTIVE_gp KEYWORD3 RESERVED_WORD +BOD_ACTIVE0_bm KEYWORD3 RESERVED_WORD +BOD_ACTIVE0_bp KEYWORD3 RESERVED_WORD +BOD_ACTIVE1_bm KEYWORD3 RESERVED_WORD +BOD_ACTIVE1_bp KEYWORD3 RESERVED_WORD +BOD_SAMPFREQ_bm KEYWORD3 RESERVED_WORD +BOD_SAMPFREQ_bp KEYWORD3 RESERVED_WORD + +BOD_LVL_gm KEYWORD3 RESERVED_WORD +BOD_LVL_gp KEYWORD3 RESERVED_WORD +BOD_LVL0_bm KEYWORD3 RESERVED_WORD +BOD_LVL0_bp KEYWORD3 RESERVED_WORD +BOD_LVL1_bm KEYWORD3 RESERVED_WORD +BOD_LVL1_bp KEYWORD3 RESERVED_WORD +BOD_LVL2_bm KEYWORD3 RESERVED_WORD +BOD_LVL2_bp KEYWORD3 RESERVED_WORD + +BOD_VLMLVL_gm KEYWORD3 RESERVED_WORD +BOD_VLMLVL_gp KEYWORD3 RESERVED_WORD +BOD_VLMLVL0_bm KEYWORD3 RESERVED_WORD +BOD_VLMLVL0_bp KEYWORD3 RESERVED_WORD +BOD_VLMLVL1_bm KEYWORD3 RESERVED_WORD +BOD_VLMLVL1_bp KEYWORD3 RESERVED_WORD + +BOD_VLMIE_bm KEYWORD3 RESERVED_WORD +BOD_VLMIE_bp KEYWORD3 RESERVED_WORD +BOD_VLMCFG_gm KEYWORD3 RESERVED_WORD +BOD_VLMCFG_gp KEYWORD3 RESERVED_WORD +BOD_VLMCFG0_bm KEYWORD3 RESERVED_WORD +BOD_VLMCFG0_bp KEYWORD3 RESERVED_WORD +BOD_VLMCFG1_bm KEYWORD3 RESERVED_WORD +BOD_VLMCFG1_bp KEYWORD3 RESERVED_WORD + +BOD_VLMIF_bm KEYWORD3 RESERVED_WORD +BOD_VLMIF_bp KEYWORD3 RESERVED_WORD + +BOD_VLMS_bm KEYWORD3 RESERVED_WORD +BOD_VLMS_bp KEYWORD3 RESERVED_WORD + + +CCL_ENABLE_bm KEYWORD3 RESERVED_WORD +CCL_ENABLE_bp KEYWORD3 RESERVED_WORD +CCL_RUNSTDBY_bm KEYWORD3 RESERVED_WORD +CCL_RUNSTDBY_bp KEYWORD3 RESERVED_WORD + +CCL_SEQSEL0_gm KEYWORD3 RESERVED_WORD +CCL_SEQSEL0_gp KEYWORD3 RESERVED_WORD +CCL_SEQSEL00_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL00_bp KEYWORD3 RESERVED_WORD +CCL_SEQSEL01_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL01_bp KEYWORD3 RESERVED_WORD +CCL_SEQSEL02_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL02_bp KEYWORD3 RESERVED_WORD + +CCL_SEQSEL1_gm KEYWORD3 RESERVED_WORD +CCL_SEQSEL1_gp KEYWORD3 RESERVED_WORD +CCL_SEQSEL10_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL10_bp KEYWORD3 RESERVED_WORD +CCL_SEQSEL11_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL11_bp KEYWORD3 RESERVED_WORD +CCL_SEQSEL12_bm KEYWORD3 RESERVED_WORD +CCL_SEQSEL12_bp KEYWORD3 RESERVED_WORD + +CCL_INTMODE0_gm KEYWORD3 RESERVED_WORD +CCL_INTMODE0_gp KEYWORD3 RESERVED_WORD +CCL_INTMODE00_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE00_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE01_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE01_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE1_gm KEYWORD3 RESERVED_WORD +CCL_INTMODE1_gp KEYWORD3 RESERVED_WORD +CCL_INTMODE10_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE10_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE11_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE11_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE2_gm KEYWORD3 RESERVED_WORD +CCL_INTMODE2_gp KEYWORD3 RESERVED_WORD +CCL_INTMODE20_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE20_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE21_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE21_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE3_gm KEYWORD3 RESERVED_WORD +CCL_INTMODE3_gp KEYWORD3 RESERVED_WORD +CCL_INTMODE30_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE30_bp KEYWORD3 RESERVED_WORD +CCL_INTMODE31_bm KEYWORD3 RESERVED_WORD +CCL_INTMODE31_bp KEYWORD3 RESERVED_WORD + +CCL_INT_gm KEYWORD3 RESERVED_WORD +CCL_INT_gp KEYWORD3 RESERVED_WORD +CCL_INT0_bm KEYWORD3 RESERVED_WORD +CCL_INT0_bp KEYWORD3 RESERVED_WORD +CCL_INT1_bm KEYWORD3 RESERVED_WORD +CCL_INT1_bp KEYWORD3 RESERVED_WORD +CCL_INT2_bm KEYWORD3 RESERVED_WORD +CCL_INT2_bp KEYWORD3 RESERVED_WORD +CCL_INT3_bm KEYWORD3 RESERVED_WORD +CCL_INT3_bp KEYWORD3 RESERVED_WORD + + +CCL_CLKSRC_gm KEYWORD3 RESERVED_WORD +CCL_CLKSRC_gp KEYWORD3 RESERVED_WORD +CCL_CLKSRC0_bm KEYWORD3 RESERVED_WORD +CCL_CLKSRC0_bp KEYWORD3 RESERVED_WORD +CCL_CLKSRC1_bm KEYWORD3 RESERVED_WORD +CCL_CLKSRC1_bp KEYWORD3 RESERVED_WORD +CCL_CLKSRC2_bm KEYWORD3 RESERVED_WORD +CCL_CLKSRC2_bp KEYWORD3 RESERVED_WORD +CCL_FILTSEL_gm KEYWORD3 RESERVED_WORD +CCL_FILTSEL_gp KEYWORD3 RESERVED_WORD +CCL_FILTSEL0_bm KEYWORD3 RESERVED_WORD +CCL_FILTSEL0_bp KEYWORD3 RESERVED_WORD +CCL_FILTSEL1_bm KEYWORD3 RESERVED_WORD +CCL_FILTSEL1_bp KEYWORD3 RESERVED_WORD +CCL_OUTEN_bm KEYWORD3 RESERVED_WORD +CCL_OUTEN_bp KEYWORD3 RESERVED_WORD +CCL_EDGEDET_bm KEYWORD3 RESERVED_WORD +CCL_EDGEDET_bp KEYWORD3 RESERVED_WORD + +CCL_INSEL0_gm KEYWORD3 RESERVED_WORD +CCL_INSEL0_gp KEYWORD3 RESERVED_WORD +CCL_INSEL00_bm KEYWORD3 RESERVED_WORD +CCL_INSEL00_bp KEYWORD3 RESERVED_WORD +CCL_INSEL01_bm KEYWORD3 RESERVED_WORD +CCL_INSEL01_bp KEYWORD3 RESERVED_WORD +CCL_INSEL02_bm KEYWORD3 RESERVED_WORD +CCL_INSEL02_bp KEYWORD3 RESERVED_WORD +CCL_INSEL03_bm KEYWORD3 RESERVED_WORD +CCL_INSEL03_bp KEYWORD3 RESERVED_WORD +CCL_INSEL1_gm KEYWORD3 RESERVED_WORD +CCL_INSEL1_gp KEYWORD3 RESERVED_WORD +CCL_INSEL10_bm KEYWORD3 RESERVED_WORD +CCL_INSEL10_bp KEYWORD3 RESERVED_WORD +CCL_INSEL11_bm KEYWORD3 RESERVED_WORD +CCL_INSEL11_bp KEYWORD3 RESERVED_WORD +CCL_INSEL12_bm KEYWORD3 RESERVED_WORD +CCL_INSEL12_bp KEYWORD3 RESERVED_WORD +CCL_INSEL13_bm KEYWORD3 RESERVED_WORD +CCL_INSEL13_bp KEYWORD3 RESERVED_WORD + +CCL_INSEL2_gm KEYWORD3 RESERVED_WORD +CCL_INSEL2_gp KEYWORD3 RESERVED_WORD +CCL_INSEL20_bm KEYWORD3 RESERVED_WORD +CCL_INSEL20_bp KEYWORD3 RESERVED_WORD +CCL_INSEL21_bm KEYWORD3 RESERVED_WORD +CCL_INSEL21_bp KEYWORD3 RESERVED_WORD +CCL_INSEL22_bm KEYWORD3 RESERVED_WORD +CCL_INSEL22_bp KEYWORD3 RESERVED_WORD +CCL_INSEL23_bm KEYWORD3 RESERVED_WORD +CCL_INSEL23_bp KEYWORD3 RESERVED_WORD + + +CLKCTRL_CLKSEL_gm KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL_gp KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL0_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL0_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL1_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CLKSEL1_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CLKOUT_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CLKOUT_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_PEN_bm KEYWORD3 RESERVED_WORD +CLKCTRL_PEN_bp KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_gm KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV_gp KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV0_bm KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV0_bp KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV1_bm KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV1_bp KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV2_bm KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV2_bp KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV3_bm KEYWORD3 RESERVED_WORD +CLKCTRL_PDIV3_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_LOCKEN_bm KEYWORD3 RESERVED_WORD +CLKCTRL_LOCKEN_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_SOSC_bm KEYWORD3 RESERVED_WORD +CLKCTRL_SOSC_bp KEYWORD3 RESERVED_WORD +CLKCTRL_OSC20MS_bm KEYWORD3 RESERVED_WORD +CLKCTRL_OSC20MS_bp KEYWORD3 RESERVED_WORD +CLKCTRL_OSC32KS_bm KEYWORD3 RESERVED_WORD +CLKCTRL_OSC32KS_bp KEYWORD3 RESERVED_WORD +CLKCTRL_XOSC32KS_bm KEYWORD3 RESERVED_WORD +CLKCTRL_XOSC32KS_bp KEYWORD3 RESERVED_WORD +CLKCTRL_EXTS_bm KEYWORD3 RESERVED_WORD +CLKCTRL_EXTS_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_RUNSTDBY_bm KEYWORD3 RESERVED_WORD +CLKCTRL_RUNSTDBY_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_CAL20M_gm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M_gp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M0_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M0_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M1_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M1_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M2_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M2_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M3_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M3_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M4_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M4_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M5_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M5_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M6_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CAL20M6_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_TEMPCAL20M_gm KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M_gp KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M0_bm KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M0_bp KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M1_bm KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M1_bp KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M2_bm KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M2_bp KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M3_bm KEYWORD3 RESERVED_WORD +CLKCTRL_TEMPCAL20M3_bp KEYWORD3 RESERVED_WORD +CLKCTRL_LOCK_bm KEYWORD3 RESERVED_WORD +CLKCTRL_LOCK_bp KEYWORD3 RESERVED_WORD + + + +CLKCTRL_ENABLE_bm KEYWORD3 RESERVED_WORD +CLKCTRL_ENABLE_bp KEYWORD3 RESERVED_WORD + +CLKCTRL_SEL_bm KEYWORD3 RESERVED_WORD +CLKCTRL_SEL_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_gm KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT_gp KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT0_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT0_bp KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT1_bm KEYWORD3 RESERVED_WORD +CLKCTRL_CSUT1_bp KEYWORD3 RESERVED_WORD + + +CPU_CCP_gm KEYWORD3 RESERVED_WORD +CPU_CCP_gp KEYWORD3 RESERVED_WORD +CPU_CCP0_bm KEYWORD3 RESERVED_WORD +CPU_CCP0_bp KEYWORD3 RESERVED_WORD +CPU_CCP1_bm KEYWORD3 RESERVED_WORD +CPU_CCP1_bp KEYWORD3 RESERVED_WORD +CPU_CCP2_bm KEYWORD3 RESERVED_WORD +CPU_CCP2_bp KEYWORD3 RESERVED_WORD +CPU_CCP3_bm KEYWORD3 RESERVED_WORD +CPU_CCP3_bp KEYWORD3 RESERVED_WORD +CPU_CCP4_bm KEYWORD3 RESERVED_WORD +CPU_CCP4_bp KEYWORD3 RESERVED_WORD +CPU_CCP5_bm KEYWORD3 RESERVED_WORD +CPU_CCP5_bp KEYWORD3 RESERVED_WORD +CPU_CCP6_bm KEYWORD3 RESERVED_WORD +CPU_CCP6_bp KEYWORD3 RESERVED_WORD +CPU_CCP7_bm KEYWORD3 RESERVED_WORD +CPU_CCP7_bp KEYWORD3 RESERVED_WORD + +CPU_C_bm KEYWORD3 RESERVED_WORD +CPU_C_bp KEYWORD3 RESERVED_WORD +CPU_Z_bm KEYWORD3 RESERVED_WORD +CPU_Z_bp KEYWORD3 RESERVED_WORD +CPU_N_bm KEYWORD3 RESERVED_WORD +CPU_N_bp KEYWORD3 RESERVED_WORD +CPU_V_bm KEYWORD3 RESERVED_WORD +CPU_V_bp KEYWORD3 RESERVED_WORD +CPU_S_bm KEYWORD3 RESERVED_WORD +CPU_S_bp KEYWORD3 RESERVED_WORD +CPU_H_bm KEYWORD3 RESERVED_WORD +CPU_H_bp KEYWORD3 RESERVED_WORD +CPU_T_bm KEYWORD3 RESERVED_WORD +CPU_T_bp KEYWORD3 RESERVED_WORD +CPU_I_bm KEYWORD3 RESERVED_WORD +CPU_I_bp KEYWORD3 RESERVED_WORD + + +CPUINT_LVL0RR_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0RR_bp KEYWORD3 RESERVED_WORD +CPUINT_CVT_bm KEYWORD3 RESERVED_WORD +CPUINT_CVT_bp KEYWORD3 RESERVED_WORD +CPUINT_IVSEL_bm KEYWORD3 RESERVED_WORD +CPUINT_IVSEL_bp KEYWORD3 RESERVED_WORD + +CPUINT_LVL0EX_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0EX_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1EX_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1EX_bp KEYWORD3 RESERVED_WORD +CPUINT_NMIEX_bm KEYWORD3 RESERVED_WORD +CPUINT_NMIEX_bp KEYWORD3 RESERVED_WORD + +CPUINT_LVL0PRI_gm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI_gp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI0_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI0_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI1_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI1_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI2_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI2_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI3_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI3_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI4_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI4_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI5_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI5_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI6_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI6_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI7_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL0PRI7_bp KEYWORD3 RESERVED_WORD + +CPUINT_LVL1VEC_gm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC_gp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC0_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC0_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC1_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC1_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC2_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC2_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC3_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC3_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC4_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC4_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC5_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC5_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC6_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC6_bp KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC7_bm KEYWORD3 RESERVED_WORD +CPUINT_LVL1VEC7_bp KEYWORD3 RESERVED_WORD + + +CRCSCAN_ENABLE_bm KEYWORD3 RESERVED_WORD +CRCSCAN_ENABLE_bp KEYWORD3 RESERVED_WORD +CRCSCAN_NMIEN_bm KEYWORD3 RESERVED_WORD +CRCSCAN_NMIEN_bp KEYWORD3 RESERVED_WORD +CRCSCAN_RESET_bm KEYWORD3 RESERVED_WORD +CRCSCAN_RESET_bp KEYWORD3 RESERVED_WORD + +CRCSCAN_SRC_gm KEYWORD3 RESERVED_WORD +CRCSCAN_SRC_gp KEYWORD3 RESERVED_WORD +CRCSCAN_SRC0_bm KEYWORD3 RESERVED_WORD +CRCSCAN_SRC0_bp KEYWORD3 RESERVED_WORD +CRCSCAN_SRC1_bm KEYWORD3 RESERVED_WORD +CRCSCAN_SRC1_bp KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_gm KEYWORD3 RESERVED_WORD +CRCSCAN_MODE_gp KEYWORD3 RESERVED_WORD +CRCSCAN_MODE0_bm KEYWORD3 RESERVED_WORD +CRCSCAN_MODE0_bp KEYWORD3 RESERVED_WORD +CRCSCAN_MODE1_bm KEYWORD3 RESERVED_WORD +CRCSCAN_MODE1_bp KEYWORD3 RESERVED_WORD + +CRCSCAN_BUSY_bm KEYWORD3 RESERVED_WORD +CRCSCAN_BUSY_bp KEYWORD3 RESERVED_WORD +CRCSCAN_OK_bm KEYWORD3 RESERVED_WORD +CRCSCAN_OK_bp KEYWORD3 RESERVED_WORD + + +EVSYS_STROBE0_gm KEYWORD3 RESERVED_WORD +EVSYS_STROBE0_gp KEYWORD3 RESERVED_WORD +EVSYS_STROBE00_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE00_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE01_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE01_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE02_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE02_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE03_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE03_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE04_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE04_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE05_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE05_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE06_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE06_bp KEYWORD3 RESERVED_WORD +EVSYS_STROBE07_bm KEYWORD3 RESERVED_WORD +EVSYS_STROBE07_bp KEYWORD3 RESERVED_WORD + +EVSYS_GENERATOR_gm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR_gp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR0_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR0_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR1_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR1_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR2_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR2_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR3_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR3_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR4_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR4_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR5_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR5_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR6_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR6_bp KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR7_bm KEYWORD3 RESERVED_WORD +EVSYS_GENERATOR7_bp KEYWORD3 RESERVED_WORD + + +EVSYS_CHANNEL_gm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL_gp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL0_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL0_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL1_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL1_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL2_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL2_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL3_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL3_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL4_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL4_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL5_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL5_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL6_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL6_bp KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL7_bm KEYWORD3 RESERVED_WORD +EVSYS_CHANNEL7_bp KEYWORD3 RESERVED_WORD + + +FUSE_PERIOD_gm KEYWORD3 RESERVED_WORD +FUSE_PERIOD_gp KEYWORD3 RESERVED_WORD +FUSE_PERIOD0_bm KEYWORD3 RESERVED_WORD +FUSE_PERIOD0_bp KEYWORD3 RESERVED_WORD +FUSE_PERIOD1_bm KEYWORD3 RESERVED_WORD +FUSE_PERIOD1_bp KEYWORD3 RESERVED_WORD +FUSE_PERIOD2_bm KEYWORD3 RESERVED_WORD +FUSE_PERIOD2_bp KEYWORD3 RESERVED_WORD +FUSE_PERIOD3_bm KEYWORD3 RESERVED_WORD +FUSE_PERIOD3_bp KEYWORD3 RESERVED_WORD +FUSE_WINDOW_gm KEYWORD3 RESERVED_WORD +FUSE_WINDOW_gp KEYWORD3 RESERVED_WORD +FUSE_WINDOW0_bm KEYWORD3 RESERVED_WORD +FUSE_WINDOW0_bp KEYWORD3 RESERVED_WORD +FUSE_WINDOW1_bm KEYWORD3 RESERVED_WORD +FUSE_WINDOW1_bp KEYWORD3 RESERVED_WORD +FUSE_WINDOW2_bm KEYWORD3 RESERVED_WORD +FUSE_WINDOW2_bp KEYWORD3 RESERVED_WORD +FUSE_WINDOW3_bm KEYWORD3 RESERVED_WORD +FUSE_WINDOW3_bp KEYWORD3 RESERVED_WORD + +FUSE_SLEEP_gm KEYWORD3 RESERVED_WORD +FUSE_SLEEP_gp KEYWORD3 RESERVED_WORD +FUSE_SLEEP0_bm KEYWORD3 RESERVED_WORD +FUSE_SLEEP0_bp KEYWORD3 RESERVED_WORD +FUSE_SLEEP1_bm KEYWORD3 RESERVED_WORD +FUSE_SLEEP1_bp KEYWORD3 RESERVED_WORD +FUSE_ACTIVE_gm KEYWORD3 RESERVED_WORD +FUSE_ACTIVE_gp KEYWORD3 RESERVED_WORD +FUSE_ACTIVE0_bm KEYWORD3 RESERVED_WORD +FUSE_ACTIVE0_bp KEYWORD3 RESERVED_WORD +FUSE_ACTIVE1_bm KEYWORD3 RESERVED_WORD +FUSE_ACTIVE1_bp KEYWORD3 RESERVED_WORD +FUSE_SAMPFREQ_bm KEYWORD3 RESERVED_WORD +FUSE_SAMPFREQ_bp KEYWORD3 RESERVED_WORD +FUSE_LVL_gm KEYWORD3 RESERVED_WORD +FUSE_LVL_gp KEYWORD3 RESERVED_WORD +FUSE_LVL0_bm KEYWORD3 RESERVED_WORD +FUSE_LVL0_bp KEYWORD3 RESERVED_WORD +FUSE_LVL1_bm KEYWORD3 RESERVED_WORD +FUSE_LVL1_bp KEYWORD3 RESERVED_WORD +FUSE_LVL2_bm KEYWORD3 RESERVED_WORD +FUSE_LVL2_bp KEYWORD3 RESERVED_WORD + +FUSE_FREQSEL_gm KEYWORD3 RESERVED_WORD +FUSE_FREQSEL_gp KEYWORD3 RESERVED_WORD +FUSE_FREQSEL0_bm KEYWORD3 RESERVED_WORD +FUSE_FREQSEL0_bp KEYWORD3 RESERVED_WORD +FUSE_FREQSEL1_bm KEYWORD3 RESERVED_WORD +FUSE_FREQSEL1_bp KEYWORD3 RESERVED_WORD +FUSE_OSCLOCK_bm KEYWORD3 RESERVED_WORD +FUSE_OSCLOCK_bp KEYWORD3 RESERVED_WORD + +FUSE_EESAVE_bm KEYWORD3 RESERVED_WORD +FUSE_EESAVE_bp KEYWORD3 RESERVED_WORD +FUSE_RSTPINCFG_bm KEYWORD3 RESERVED_WORD +FUSE_RSTPINCFG_bp KEYWORD3 RESERVED_WORD +FUSE_CRCSRC_gm KEYWORD3 RESERVED_WORD +FUSE_CRCSRC_gp KEYWORD3 RESERVED_WORD +FUSE_CRCSRC0_bm KEYWORD3 RESERVED_WORD +FUSE_CRCSRC0_bp KEYWORD3 RESERVED_WORD +FUSE_CRCSRC1_bm KEYWORD3 RESERVED_WORD +FUSE_CRCSRC1_bp KEYWORD3 RESERVED_WORD + +FUSE_SUT_gm KEYWORD3 RESERVED_WORD +FUSE_SUT_gp KEYWORD3 RESERVED_WORD +FUSE_SUT0_bm KEYWORD3 RESERVED_WORD +FUSE_SUT0_bp KEYWORD3 RESERVED_WORD +FUSE_SUT1_bm KEYWORD3 RESERVED_WORD +FUSE_SUT1_bp KEYWORD3 RESERVED_WORD +FUSE_SUT2_bm KEYWORD3 RESERVED_WORD +FUSE_SUT2_bp KEYWORD3 RESERVED_WORD + + +LOCKBIT_LB_gm KEYWORD3 RESERVED_WORD +LOCKBIT_LB_gp KEYWORD3 RESERVED_WORD +LOCKBIT_LB0_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB0_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB1_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB1_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB2_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB2_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB3_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB3_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB4_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB4_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB5_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB5_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB6_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB6_bp KEYWORD3 RESERVED_WORD +LOCKBIT_LB7_bm KEYWORD3 RESERVED_WORD +LOCKBIT_LB7_bp KEYWORD3 RESERVED_WORD + + +NVMCTRL_CMD_gm KEYWORD3 RESERVED_WORD +NVMCTRL_CMD_gp KEYWORD3 RESERVED_WORD +NVMCTRL_CMD0_bm KEYWORD3 RESERVED_WORD +NVMCTRL_CMD0_bp KEYWORD3 RESERVED_WORD +NVMCTRL_CMD1_bm KEYWORD3 RESERVED_WORD +NVMCTRL_CMD1_bp KEYWORD3 RESERVED_WORD +NVMCTRL_CMD2_bm KEYWORD3 RESERVED_WORD +NVMCTRL_CMD2_bp KEYWORD3 RESERVED_WORD + +NVMCTRL_APCWP_bm KEYWORD3 RESERVED_WORD +NVMCTRL_APCWP_bp KEYWORD3 RESERVED_WORD +NVMCTRL_BOOTLOCK_bm KEYWORD3 RESERVED_WORD +NVMCTRL_BOOTLOCK_bp KEYWORD3 RESERVED_WORD + +NVMCTRL_FBUSY_bm KEYWORD3 RESERVED_WORD +NVMCTRL_FBUSY_bp KEYWORD3 RESERVED_WORD +NVMCTRL_EEBUSY_bm KEYWORD3 RESERVED_WORD +NVMCTRL_EEBUSY_bp KEYWORD3 RESERVED_WORD +NVMCTRL_WRERROR_bm KEYWORD3 RESERVED_WORD +NVMCTRL_WRERROR_bp KEYWORD3 RESERVED_WORD + +NVMCTRL_EEREADY_bm KEYWORD3 RESERVED_WORD +NVMCTRL_EEREADY_bp KEYWORD3 RESERVED_WORD + +PORT_INT_gm KEYWORD3 RESERVED_WORD +PORT_INT_gp KEYWORD3 RESERVED_WORD +PORT_INT0_bm KEYWORD3 RESERVED_WORD +PORT_INT0_bp KEYWORD3 RESERVED_WORD +PORT_INT1_bm KEYWORD3 RESERVED_WORD +PORT_INT1_bp KEYWORD3 RESERVED_WORD +PORT_INT2_bm KEYWORD3 RESERVED_WORD +PORT_INT2_bp KEYWORD3 RESERVED_WORD +PORT_INT3_bm KEYWORD3 RESERVED_WORD +PORT_INT3_bp KEYWORD3 RESERVED_WORD +PORT_INT4_bm KEYWORD3 RESERVED_WORD +PORT_INT4_bp KEYWORD3 RESERVED_WORD +PORT_INT5_bm KEYWORD3 RESERVED_WORD +PORT_INT5_bp KEYWORD3 RESERVED_WORD +PORT_INT6_bm KEYWORD3 RESERVED_WORD +PORT_INT6_bp KEYWORD3 RESERVED_WORD +PORT_INT7_bm KEYWORD3 RESERVED_WORD +PORT_INT7_bp KEYWORD3 RESERVED_WORD + +PORT_SRL_bm KEYWORD3 RESERVED_WORD +PORT_SRL_bp KEYWORD3 RESERVED_WORD + +PORT_ISC_gm KEYWORD3 RESERVED_WORD +PORT_ISC_gp KEYWORD3 RESERVED_WORD +PORT_ISC0_bm KEYWORD3 RESERVED_WORD +PORT_ISC0_bp KEYWORD3 RESERVED_WORD +PORT_ISC1_bm KEYWORD3 RESERVED_WORD +PORT_ISC1_bp KEYWORD3 RESERVED_WORD +PORT_ISC2_bm KEYWORD3 RESERVED_WORD +PORT_ISC2_bp KEYWORD3 RESERVED_WORD +PORT_PULLUPEN_bm KEYWORD3 RESERVED_WORD +PORT_PULLUPEN_bp KEYWORD3 RESERVED_WORD +PORT_INVEN_bm KEYWORD3 RESERVED_WORD +PORT_INVEN_bp KEYWORD3 RESERVED_WORD + +PORTMUX_EVOUT0_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT0_bp KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT1_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT1_bp KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT2_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT2_bp KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT3_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT3_bp KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT4_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT4_bp KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT5_bm KEYWORD3 RESERVED_WORD +PORTMUX_EVOUT5_bp KEYWORD3 RESERVED_WORD + +PORTMUX_LUT0_bm KEYWORD3 RESERVED_WORD +PORTMUX_LUT0_bp KEYWORD3 RESERVED_WORD +PORTMUX_LUT1_bm KEYWORD3 RESERVED_WORD +PORTMUX_LUT1_bp KEYWORD3 RESERVED_WORD +PORTMUX_LUT2_bm KEYWORD3 RESERVED_WORD +PORTMUX_LUT2_bp KEYWORD3 RESERVED_WORD +PORTMUX_LUT3_bm KEYWORD3 RESERVED_WORD +PORTMUX_LUT3_bp KEYWORD3 RESERVED_WORD + +PORTMUX_USART0_gm KEYWORD3 RESERVED_WORD +PORTMUX_USART0_gp KEYWORD3 RESERVED_WORD +PORTMUX_USART00_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART00_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART01_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART01_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART1_gm KEYWORD3 RESERVED_WORD +PORTMUX_USART1_gp KEYWORD3 RESERVED_WORD +PORTMUX_USART10_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART10_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART11_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART11_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART2_gm KEYWORD3 RESERVED_WORD +PORTMUX_USART2_gp KEYWORD3 RESERVED_WORD +PORTMUX_USART20_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART20_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART21_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART21_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART3_gm KEYWORD3 RESERVED_WORD +PORTMUX_USART3_gp KEYWORD3 RESERVED_WORD +PORTMUX_USART30_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART30_bp KEYWORD3 RESERVED_WORD +PORTMUX_USART31_bm KEYWORD3 RESERVED_WORD +PORTMUX_USART31_bp KEYWORD3 RESERVED_WORD + +PORTMUX_SPI0_gm KEYWORD3 RESERVED_WORD +PORTMUX_SPI0_gp KEYWORD3 RESERVED_WORD +PORTMUX_SPI00_bm KEYWORD3 RESERVED_WORD +PORTMUX_SPI00_bp KEYWORD3 RESERVED_WORD +PORTMUX_SPI01_bm KEYWORD3 RESERVED_WORD +PORTMUX_SPI01_bp KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_gm KEYWORD3 RESERVED_WORD +PORTMUX_TWI0_gp KEYWORD3 RESERVED_WORD +PORTMUX_TWI00_bm KEYWORD3 RESERVED_WORD +PORTMUX_TWI00_bp KEYWORD3 RESERVED_WORD +PORTMUX_TWI01_bm KEYWORD3 RESERVED_WORD +PORTMUX_TWI01_bp KEYWORD3 RESERVED_WORD + +PORTMUX_TCA0_gm KEYWORD3 RESERVED_WORD +PORTMUX_TCA0_gp KEYWORD3 RESERVED_WORD +PORTMUX_TCA00_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCA00_bp KEYWORD3 RESERVED_WORD +PORTMUX_TCA01_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCA01_bp KEYWORD3 RESERVED_WORD +PORTMUX_TCA02_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCA02_bp KEYWORD3 RESERVED_WORD + +PORTMUX_TCB0_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCB0_bp KEYWORD3 RESERVED_WORD +PORTMUX_TCB1_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCB1_bp KEYWORD3 RESERVED_WORD +PORTMUX_TCB2_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCB2_bp KEYWORD3 RESERVED_WORD +PORTMUX_TCB3_bm KEYWORD3 RESERVED_WORD +PORTMUX_TCB3_bp KEYWORD3 RESERVED_WORD + + +RSTCTRL_PORF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_PORF_bp KEYWORD3 RESERVED_WORD +RSTCTRL_BORF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_BORF_bp KEYWORD3 RESERVED_WORD +RSTCTRL_EXTRF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_EXTRF_bp KEYWORD3 RESERVED_WORD +RSTCTRL_WDRF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_WDRF_bp KEYWORD3 RESERVED_WORD +RSTCTRL_SWRF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_SWRF_bp KEYWORD3 RESERVED_WORD +RSTCTRL_UPDIRF_bm KEYWORD3 RESERVED_WORD +RSTCTRL_UPDIRF_bp KEYWORD3 RESERVED_WORD + +RSTCTRL_SWRE_bm KEYWORD3 RESERVED_WORD +RSTCTRL_SWRE_bp KEYWORD3 RESERVED_WORD + + +RTC_RTCEN_bm KEYWORD3 RESERVED_WORD +RTC_RTCEN_bp KEYWORD3 RESERVED_WORD +RTC_PRESCALER_gm KEYWORD3 RESERVED_WORD +RTC_PRESCALER_gp KEYWORD3 RESERVED_WORD +RTC_PRESCALER0_bm KEYWORD3 RESERVED_WORD +RTC_PRESCALER0_bp KEYWORD3 RESERVED_WORD +RTC_PRESCALER1_bm KEYWORD3 RESERVED_WORD +RTC_PRESCALER1_bp KEYWORD3 RESERVED_WORD +RTC_PRESCALER2_bm KEYWORD3 RESERVED_WORD +RTC_PRESCALER2_bp KEYWORD3 RESERVED_WORD +RTC_PRESCALER3_bm KEYWORD3 RESERVED_WORD +RTC_PRESCALER3_bp KEYWORD3 RESERVED_WORD +RTC_RUNSTDBY_bm KEYWORD3 RESERVED_WORD +RTC_RUNSTDBY_bp KEYWORD3 RESERVED_WORD + +RTC_CTRLABUSY_bm KEYWORD3 RESERVED_WORD +RTC_CTRLABUSY_bp KEYWORD3 RESERVED_WORD +RTC_CNTBUSY_bm KEYWORD3 RESERVED_WORD +RTC_CNTBUSY_bp KEYWORD3 RESERVED_WORD +RTC_PERBUSY_bm KEYWORD3 RESERVED_WORD +RTC_PERBUSY_bp KEYWORD3 RESERVED_WORD +RTC_CMPBUSY_bm KEYWORD3 RESERVED_WORD +RTC_CMPBUSY_bp KEYWORD3 RESERVED_WORD + +RTC_OVF_bm KEYWORD3 RESERVED_WORD +RTC_OVF_bp KEYWORD3 RESERVED_WORD +RTC_CMP_bm KEYWORD3 RESERVED_WORD +RTC_CMP_bp KEYWORD3 RESERVED_WORD + + + + +RTC_DBGRUN_bm KEYWORD3 RESERVED_WORD +RTC_DBGRUN_bp KEYWORD3 RESERVED_WORD + +RTC_ERROR_gm KEYWORD3 RESERVED_WORD +RTC_ERROR_gp KEYWORD3 RESERVED_WORD +RTC_ERROR0_bm KEYWORD3 RESERVED_WORD +RTC_ERROR0_bp KEYWORD3 RESERVED_WORD +RTC_ERROR1_bm KEYWORD3 RESERVED_WORD +RTC_ERROR1_bp KEYWORD3 RESERVED_WORD +RTC_ERROR2_bm KEYWORD3 RESERVED_WORD +RTC_ERROR2_bp KEYWORD3 RESERVED_WORD +RTC_ERROR3_bm KEYWORD3 RESERVED_WORD +RTC_ERROR3_bp KEYWORD3 RESERVED_WORD +RTC_ERROR4_bm KEYWORD3 RESERVED_WORD +RTC_ERROR4_bp KEYWORD3 RESERVED_WORD +RTC_ERROR5_bm KEYWORD3 RESERVED_WORD +RTC_ERROR5_bp KEYWORD3 RESERVED_WORD +RTC_ERROR6_bm KEYWORD3 RESERVED_WORD +RTC_ERROR6_bp KEYWORD3 RESERVED_WORD +RTC_SIGN_bm KEYWORD3 RESERVED_WORD +RTC_SIGN_bp KEYWORD3 RESERVED_WORD + +RTC_CLKSEL_gm KEYWORD3 RESERVED_WORD +RTC_CLKSEL_gp KEYWORD3 RESERVED_WORD +RTC_CLKSEL0_bm KEYWORD3 RESERVED_WORD +RTC_CLKSEL0_bp KEYWORD3 RESERVED_WORD +RTC_CLKSEL1_bm KEYWORD3 RESERVED_WORD +RTC_CLKSEL1_bp KEYWORD3 RESERVED_WORD + +RTC_PITEN_bm KEYWORD3 RESERVED_WORD +RTC_PITEN_bp KEYWORD3 RESERVED_WORD +RTC_PERIOD_gm KEYWORD3 RESERVED_WORD +RTC_PERIOD_gp KEYWORD3 RESERVED_WORD +RTC_PERIOD0_bm KEYWORD3 RESERVED_WORD +RTC_PERIOD0_bp KEYWORD3 RESERVED_WORD +RTC_PERIOD1_bm KEYWORD3 RESERVED_WORD +RTC_PERIOD1_bp KEYWORD3 RESERVED_WORD +RTC_PERIOD2_bm KEYWORD3 RESERVED_WORD +RTC_PERIOD2_bp KEYWORD3 RESERVED_WORD +RTC_PERIOD3_bm KEYWORD3 RESERVED_WORD +RTC_PERIOD3_bp KEYWORD3 RESERVED_WORD + +RTC_CTRLBUSY_bm KEYWORD3 RESERVED_WORD +RTC_CTRLBUSY_bp KEYWORD3 RESERVED_WORD + +RTC_PI_bm KEYWORD3 RESERVED_WORD +RTC_PI_bp KEYWORD3 RESERVED_WORD + + +SLPCTRL_SEN_bm KEYWORD3 RESERVED_WORD +SLPCTRL_SEN_bp KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE_gm KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE_gp KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE0_bm KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE0_bp KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE1_bm KEYWORD3 RESERVED_WORD +SLPCTRL_SMODE1_bp KEYWORD3 RESERVED_WORD + + +SPI_ENABLE_bm KEYWORD3 RESERVED_WORD +SPI_ENABLE_bp KEYWORD3 RESERVED_WORD +SPI_PRESC_gm KEYWORD3 RESERVED_WORD +SPI_PRESC_gp KEYWORD3 RESERVED_WORD +SPI_PRESC0_bm KEYWORD3 RESERVED_WORD +SPI_PRESC0_bp KEYWORD3 RESERVED_WORD +SPI_PRESC1_bm KEYWORD3 RESERVED_WORD +SPI_PRESC1_bp KEYWORD3 RESERVED_WORD +SPI_CLK2X_bm KEYWORD3 RESERVED_WORD +SPI_CLK2X_bp KEYWORD3 RESERVED_WORD +SPI_MASTER_bm KEYWORD3 RESERVED_WORD +SPI_MASTER_bp KEYWORD3 RESERVED_WORD +SPI_DORD_bm KEYWORD3 RESERVED_WORD +SPI_DORD_bp KEYWORD3 RESERVED_WORD + +SPI_MODE_gm KEYWORD3 RESERVED_WORD +SPI_MODE_gp KEYWORD3 RESERVED_WORD +SPI_MODE0_bm KEYWORD3 RESERVED_WORD +SPI_MODE0_bp KEYWORD3 RESERVED_WORD +SPI_MODE1_bm KEYWORD3 RESERVED_WORD +SPI_MODE1_bp KEYWORD3 RESERVED_WORD +SPI_SSD_bm KEYWORD3 RESERVED_WORD +SPI_SSD_bp KEYWORD3 RESERVED_WORD +SPI_BUFWR_bm KEYWORD3 RESERVED_WORD +SPI_BUFWR_bp KEYWORD3 RESERVED_WORD +SPI_BUFEN_bm KEYWORD3 RESERVED_WORD +SPI_BUFEN_bp KEYWORD3 RESERVED_WORD + +SPI_IE_bm KEYWORD3 RESERVED_WORD +SPI_IE_bp KEYWORD3 RESERVED_WORD +SPI_SSIE_bm KEYWORD3 RESERVED_WORD +SPI_SSIE_bp KEYWORD3 RESERVED_WORD +SPI_DREIE_bm KEYWORD3 RESERVED_WORD +SPI_DREIE_bp KEYWORD3 RESERVED_WORD +SPI_TXCIE_bm KEYWORD3 RESERVED_WORD +SPI_TXCIE_bp KEYWORD3 RESERVED_WORD +SPI_RXCIE_bm KEYWORD3 RESERVED_WORD +SPI_RXCIE_bp KEYWORD3 RESERVED_WORD + +SPI_BUFOVF_bm KEYWORD3 RESERVED_WORD +SPI_BUFOVF_bp KEYWORD3 RESERVED_WORD +SPI_SSIF_bm KEYWORD3 RESERVED_WORD +SPI_SSIF_bp KEYWORD3 RESERVED_WORD +SPI_DREIF_bm KEYWORD3 RESERVED_WORD +SPI_DREIF_bp KEYWORD3 RESERVED_WORD +SPI_TXCIF_bm KEYWORD3 RESERVED_WORD +SPI_TXCIF_bp KEYWORD3 RESERVED_WORD +SPI_WRCOL_bm KEYWORD3 RESERVED_WORD +SPI_WRCOL_bp KEYWORD3 RESERVED_WORD +SPI_RXCIF_bm KEYWORD3 RESERVED_WORD +SPI_RXCIF_bp KEYWORD3 RESERVED_WORD +SPI_IF_bm KEYWORD3 RESERVED_WORD +SPI_IF_bp KEYWORD3 RESERVED_WORD + + +SYSCFG_ENEXTBRK_bm KEYWORD3 RESERVED_WORD +SYSCFG_ENEXTBRK_bp KEYWORD3 RESERVED_WORD + +SYSCFG_OCDMR_bm KEYWORD3 RESERVED_WORD +SYSCFG_OCDMR_bp KEYWORD3 RESERVED_WORD + + +TCA_SINGLE_ENABLE_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_ENABLE_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_gm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL_gp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL0_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL0_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL1_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL1_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL2_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CLKSEL2_bp KEYWORD3 RESERVED_WORD + +TCA_SINGLE_WGMODE_gm KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE_gp KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE0_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE0_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE1_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE1_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE2_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_WGMODE2_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_ALUPD_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_ALUPD_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0EN_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0EN_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1EN_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1EN_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2EN_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2EN_bp KEYWORD3 RESERVED_WORD + +TCA_SINGLE_CMP0OV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0OV_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1OV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1OV_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2OV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2OV_bp KEYWORD3 RESERVED_WORD + +TCA_SINGLE_SPLITM_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_SPLITM_bp KEYWORD3 RESERVED_WORD + +TCA_SINGLE_DIR_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_DIR_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_LUPD_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_LUPD_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_gm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD_gp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD0_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD0_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD1_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMD1_bp KEYWORD3 RESERVED_WORD + + + + + +TCA_SINGLE_PERBV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_PERBV_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0BV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0BV_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1BV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1BV_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2BV_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2BV_bp KEYWORD3 RESERVED_WORD + + + + + + +TCA_SINGLE_CNTEI_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CNTEI_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_gm KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT_gp KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT0_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT0_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT1_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_EVACT1_bp KEYWORD3 RESERVED_WORD + +TCA_SINGLE_OVF_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_OVF_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP0_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP1_bp KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_CMP2_bp KEYWORD3 RESERVED_WORD + + + + + + +TCA_SINGLE_DBGRUN_bm KEYWORD3 RESERVED_WORD +TCA_SINGLE_DBGRUN_bp KEYWORD3 RESERVED_WORD + +TCA_SPLIT_ENABLE_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_ENABLE_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_gm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL_gp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL0_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL0_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL1_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL1_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL2_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CLKSEL2_bp KEYWORD3 RESERVED_WORD + +TCA_SPLIT_LCMP0EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP0EN_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1EN_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2EN_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP0EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP0EN_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP1EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP1EN_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP2EN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP2EN_bp KEYWORD3 RESERVED_WORD + +TCA_SPLIT_LCMP0OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP0OV_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1OV_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2OV_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP0OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP0OV_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP1OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP1OV_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP2OV_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HCMP2OV_bp KEYWORD3 RESERVED_WORD + +TCA_SPLIT_SPLITM_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_SPLITM_bp KEYWORD3 RESERVED_WORD + +TCA_SPLIT_CMD_gm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD_gp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD0_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD0_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD1_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_CMD1_bp KEYWORD3 RESERVED_WORD + + + +TCA_SPLIT_LUNF_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LUNF_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_HUNF_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_HUNF_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP0_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP0_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP1_bp KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_LCMP2_bp KEYWORD3 RESERVED_WORD + + + + + + + +TCA_SPLIT_DBGRUN_bm KEYWORD3 RESERVED_WORD +TCA_SPLIT_DBGRUN_bp KEYWORD3 RESERVED_WORD + + +TCB_ENABLE_bm KEYWORD3 RESERVED_WORD +TCB_ENABLE_bp KEYWORD3 RESERVED_WORD +TCB_CLKSEL_gm KEYWORD3 RESERVED_WORD +TCB_CLKSEL_gp KEYWORD3 RESERVED_WORD +TCB_CLKSEL0_bm KEYWORD3 RESERVED_WORD +TCB_CLKSEL0_bp KEYWORD3 RESERVED_WORD +TCB_CLKSEL1_bm KEYWORD3 RESERVED_WORD +TCB_CLKSEL1_bp KEYWORD3 RESERVED_WORD +TCB_SYNCUPD_bm KEYWORD3 RESERVED_WORD +TCB_SYNCUPD_bp KEYWORD3 RESERVED_WORD +TCB_RUNSTDBY_bm KEYWORD3 RESERVED_WORD +TCB_RUNSTDBY_bp KEYWORD3 RESERVED_WORD + +TCB_CNTMODE_gm KEYWORD3 RESERVED_WORD +TCB_CNTMODE_gp KEYWORD3 RESERVED_WORD +TCB_CNTMODE0_bm KEYWORD3 RESERVED_WORD +TCB_CNTMODE0_bp KEYWORD3 RESERVED_WORD +TCB_CNTMODE1_bm KEYWORD3 RESERVED_WORD +TCB_CNTMODE1_bp KEYWORD3 RESERVED_WORD +TCB_CNTMODE2_bm KEYWORD3 RESERVED_WORD +TCB_CNTMODE2_bp KEYWORD3 RESERVED_WORD +TCB_CCMPEN_bm KEYWORD3 RESERVED_WORD +TCB_CCMPEN_bp KEYWORD3 RESERVED_WORD +TCB_CCMPINIT_bm KEYWORD3 RESERVED_WORD +TCB_CCMPINIT_bp KEYWORD3 RESERVED_WORD +TCB_ASYNC_bm KEYWORD3 RESERVED_WORD +TCB_ASYNC_bp KEYWORD3 RESERVED_WORD + +TCB_CAPTEI_bm KEYWORD3 RESERVED_WORD +TCB_CAPTEI_bp KEYWORD3 RESERVED_WORD +TCB_EDGE_bm KEYWORD3 RESERVED_WORD +TCB_EDGE_bp KEYWORD3 RESERVED_WORD +TCB_FILTER_bm KEYWORD3 RESERVED_WORD +TCB_FILTER_bp KEYWORD3 RESERVED_WORD + +TCB_CAPT_bm KEYWORD3 RESERVED_WORD +TCB_CAPT_bp KEYWORD3 RESERVED_WORD + + + +TCB_RUN_bm KEYWORD3 RESERVED_WORD +TCB_RUN_bp KEYWORD3 RESERVED_WORD + +TCB_DBGRUN_bm KEYWORD3 RESERVED_WORD +TCB_DBGRUN_bp KEYWORD3 RESERVED_WORD + + +TWI_FMPEN_bm KEYWORD3 RESERVED_WORD +TWI_FMPEN_bp KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_gm KEYWORD3 RESERVED_WORD +TWI_SDAHOLD_gp KEYWORD3 RESERVED_WORD +TWI_SDAHOLD0_bm KEYWORD3 RESERVED_WORD +TWI_SDAHOLD0_bp KEYWORD3 RESERVED_WORD +TWI_SDAHOLD1_bm KEYWORD3 RESERVED_WORD +TWI_SDAHOLD1_bp KEYWORD3 RESERVED_WORD +TWI_SDASETUP_bm KEYWORD3 RESERVED_WORD +TWI_SDASETUP_bp KEYWORD3 RESERVED_WORD + +TWI_ENABLE_bm KEYWORD3 RESERVED_WORD +TWI_ENABLE_bp KEYWORD3 RESERVED_WORD + + + +TWI_DBGRUN_bm KEYWORD3 RESERVED_WORD +TWI_DBGRUN_bp KEYWORD3 RESERVED_WORD + + +TWI_SMEN_bm KEYWORD3 RESERVED_WORD +TWI_SMEN_bp KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_gm KEYWORD3 RESERVED_WORD +TWI_TIMEOUT_gp KEYWORD3 RESERVED_WORD +TWI_TIMEOUT0_bm KEYWORD3 RESERVED_WORD +TWI_TIMEOUT0_bp KEYWORD3 RESERVED_WORD +TWI_TIMEOUT1_bm KEYWORD3 RESERVED_WORD +TWI_TIMEOUT1_bp KEYWORD3 RESERVED_WORD +TWI_QCEN_bm KEYWORD3 RESERVED_WORD +TWI_QCEN_bp KEYWORD3 RESERVED_WORD +TWI_WIEN_bm KEYWORD3 RESERVED_WORD +TWI_WIEN_bp KEYWORD3 RESERVED_WORD +TWI_RIEN_bm KEYWORD3 RESERVED_WORD +TWI_RIEN_bp KEYWORD3 RESERVED_WORD + +TWI_MCMD_gm KEYWORD3 RESERVED_WORD +TWI_MCMD_gp KEYWORD3 RESERVED_WORD +TWI_MCMD0_bm KEYWORD3 RESERVED_WORD +TWI_MCMD0_bp KEYWORD3 RESERVED_WORD +TWI_MCMD1_bm KEYWORD3 RESERVED_WORD +TWI_MCMD1_bp KEYWORD3 RESERVED_WORD +TWI_ACKACT_bm KEYWORD3 RESERVED_WORD +TWI_ACKACT_bp KEYWORD3 RESERVED_WORD +TWI_FLUSH_bm KEYWORD3 RESERVED_WORD +TWI_FLUSH_bp KEYWORD3 RESERVED_WORD + +TWI_BUSSTATE_gm KEYWORD3 RESERVED_WORD +TWI_BUSSTATE_gp KEYWORD3 RESERVED_WORD +TWI_BUSSTATE0_bm KEYWORD3 RESERVED_WORD +TWI_BUSSTATE0_bp KEYWORD3 RESERVED_WORD +TWI_BUSSTATE1_bm KEYWORD3 RESERVED_WORD +TWI_BUSSTATE1_bp KEYWORD3 RESERVED_WORD +TWI_BUSERR_bm KEYWORD3 RESERVED_WORD +TWI_BUSERR_bp KEYWORD3 RESERVED_WORD +TWI_ARBLOST_bm KEYWORD3 RESERVED_WORD +TWI_ARBLOST_bp KEYWORD3 RESERVED_WORD +TWI_RXACK_bm KEYWORD3 RESERVED_WORD +TWI_RXACK_bp KEYWORD3 RESERVED_WORD +TWI_CLKHOLD_bm KEYWORD3 RESERVED_WORD +TWI_CLKHOLD_bp KEYWORD3 RESERVED_WORD +TWI_WIF_bm KEYWORD3 RESERVED_WORD +TWI_WIF_bp KEYWORD3 RESERVED_WORD +TWI_RIF_bm KEYWORD3 RESERVED_WORD +TWI_RIF_bp KEYWORD3 RESERVED_WORD + + + +TWI_PMEN_bm KEYWORD3 RESERVED_WORD +TWI_PMEN_bp KEYWORD3 RESERVED_WORD +TWI_PIEN_bm KEYWORD3 RESERVED_WORD +TWI_PIEN_bp KEYWORD3 RESERVED_WORD +TWI_APIEN_bm KEYWORD3 RESERVED_WORD +TWI_APIEN_bp KEYWORD3 RESERVED_WORD +TWI_DIEN_bm KEYWORD3 RESERVED_WORD +TWI_DIEN_bp KEYWORD3 RESERVED_WORD + +TWI_SCMD_gm KEYWORD3 RESERVED_WORD +TWI_SCMD_gp KEYWORD3 RESERVED_WORD +TWI_SCMD0_bm KEYWORD3 RESERVED_WORD +TWI_SCMD0_bp KEYWORD3 RESERVED_WORD +TWI_SCMD1_bm KEYWORD3 RESERVED_WORD +TWI_SCMD1_bp KEYWORD3 RESERVED_WORD + + +TWI_AP_bm KEYWORD3 RESERVED_WORD +TWI_AP_bp KEYWORD3 RESERVED_WORD +TWI_DIR_bm KEYWORD3 RESERVED_WORD +TWI_DIR_bp KEYWORD3 RESERVED_WORD + +TWI_COLL_bm KEYWORD3 RESERVED_WORD +TWI_COLL_bp KEYWORD3 RESERVED_WORD + + +TWI_APIF_bm KEYWORD3 RESERVED_WORD +TWI_APIF_bp KEYWORD3 RESERVED_WORD +TWI_DIF_bm KEYWORD3 RESERVED_WORD +TWI_DIF_bp KEYWORD3 RESERVED_WORD + +TWI_ADDREN_bm KEYWORD3 RESERVED_WORD +TWI_ADDREN_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK_gm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK_gp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK0_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK0_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK1_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK1_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK2_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK2_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK3_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK3_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK4_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK4_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK5_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK5_bp KEYWORD3 RESERVED_WORD +TWI_ADDRMASK6_bm KEYWORD3 RESERVED_WORD +TWI_ADDRMASK6_bp KEYWORD3 RESERVED_WORD + + +USART_DATA_gm KEYWORD3 RESERVED_WORD +USART_DATA_gp KEYWORD3 RESERVED_WORD +USART_DATA0_bm KEYWORD3 RESERVED_WORD +USART_DATA0_bp KEYWORD3 RESERVED_WORD +USART_DATA1_bm KEYWORD3 RESERVED_WORD +USART_DATA1_bp KEYWORD3 RESERVED_WORD +USART_DATA2_bm KEYWORD3 RESERVED_WORD +USART_DATA2_bp KEYWORD3 RESERVED_WORD +USART_DATA3_bm KEYWORD3 RESERVED_WORD +USART_DATA3_bp KEYWORD3 RESERVED_WORD +USART_DATA4_bm KEYWORD3 RESERVED_WORD +USART_DATA4_bp KEYWORD3 RESERVED_WORD +USART_DATA5_bm KEYWORD3 RESERVED_WORD +USART_DATA5_bp KEYWORD3 RESERVED_WORD +USART_DATA6_bm KEYWORD3 RESERVED_WORD +USART_DATA6_bp KEYWORD3 RESERVED_WORD +USART_DATA7_bm KEYWORD3 RESERVED_WORD +USART_DATA7_bp KEYWORD3 RESERVED_WORD + +USART_DATA8_bm KEYWORD3 RESERVED_WORD +USART_DATA8_bp KEYWORD3 RESERVED_WORD +USART_PERR_bm KEYWORD3 RESERVED_WORD +USART_PERR_bp KEYWORD3 RESERVED_WORD +USART_FERR_bm KEYWORD3 RESERVED_WORD +USART_FERR_bp KEYWORD3 RESERVED_WORD +USART_BUFOVF_bm KEYWORD3 RESERVED_WORD +USART_BUFOVF_bp KEYWORD3 RESERVED_WORD +USART_RXCIF_bm KEYWORD3 RESERVED_WORD +USART_RXCIF_bp KEYWORD3 RESERVED_WORD + + + + + +USART_WFB_bm KEYWORD3 RESERVED_WORD +USART_WFB_bp KEYWORD3 RESERVED_WORD +USART_BDF_bm KEYWORD3 RESERVED_WORD +USART_BDF_bp KEYWORD3 RESERVED_WORD +USART_ISFIF_bm KEYWORD3 RESERVED_WORD +USART_ISFIF_bp KEYWORD3 RESERVED_WORD +USART_RXSIF_bm KEYWORD3 RESERVED_WORD +USART_RXSIF_bp KEYWORD3 RESERVED_WORD +USART_DREIF_bm KEYWORD3 RESERVED_WORD +USART_DREIF_bp KEYWORD3 RESERVED_WORD +USART_TXCIF_bm KEYWORD3 RESERVED_WORD +USART_TXCIF_bp KEYWORD3 RESERVED_WORD + + +USART_RS485_gm KEYWORD3 RESERVED_WORD +USART_RS485_gp KEYWORD3 RESERVED_WORD +USART_RS4850_bm KEYWORD3 RESERVED_WORD +USART_RS4850_bp KEYWORD3 RESERVED_WORD +USART_RS4851_bm KEYWORD3 RESERVED_WORD +USART_RS4851_bp KEYWORD3 RESERVED_WORD +USART_ABEIE_bm KEYWORD3 RESERVED_WORD +USART_ABEIE_bp KEYWORD3 RESERVED_WORD +USART_LBME_bm KEYWORD3 RESERVED_WORD +USART_LBME_bp KEYWORD3 RESERVED_WORD +USART_RXSIE_bm KEYWORD3 RESERVED_WORD +USART_RXSIE_bp KEYWORD3 RESERVED_WORD +USART_DREIE_bm KEYWORD3 RESERVED_WORD +USART_DREIE_bp KEYWORD3 RESERVED_WORD +USART_TXCIE_bm KEYWORD3 RESERVED_WORD +USART_TXCIE_bp KEYWORD3 RESERVED_WORD +USART_RXCIE_bm KEYWORD3 RESERVED_WORD +USART_RXCIE_bp KEYWORD3 RESERVED_WORD + +USART_MPCM_bm KEYWORD3 RESERVED_WORD +USART_MPCM_bp KEYWORD3 RESERVED_WORD +USART_RXMODE_gm KEYWORD3 RESERVED_WORD +USART_RXMODE_gp KEYWORD3 RESERVED_WORD +USART_RXMODE0_bm KEYWORD3 RESERVED_WORD +USART_RXMODE0_bp KEYWORD3 RESERVED_WORD +USART_RXMODE1_bm KEYWORD3 RESERVED_WORD +USART_RXMODE1_bp KEYWORD3 RESERVED_WORD +USART_ODME_bm KEYWORD3 RESERVED_WORD +USART_ODME_bp KEYWORD3 RESERVED_WORD +USART_SFDEN_bm KEYWORD3 RESERVED_WORD +USART_SFDEN_bp KEYWORD3 RESERVED_WORD +USART_TXEN_bm KEYWORD3 RESERVED_WORD +USART_TXEN_bp KEYWORD3 RESERVED_WORD +USART_RXEN_bm KEYWORD3 RESERVED_WORD +USART_RXEN_bp KEYWORD3 RESERVED_WORD + +USART_UCPHA_bm KEYWORD3 RESERVED_WORD +USART_UCPHA_bp KEYWORD3 RESERVED_WORD +USART_UDORD_bm KEYWORD3 RESERVED_WORD +USART_UDORD_bp KEYWORD3 RESERVED_WORD +USART_CHSIZE_gm KEYWORD3 RESERVED_WORD +USART_CHSIZE_gp KEYWORD3 RESERVED_WORD +USART_CHSIZE0_bm KEYWORD3 RESERVED_WORD +USART_CHSIZE0_bp KEYWORD3 RESERVED_WORD +USART_CHSIZE1_bm KEYWORD3 RESERVED_WORD +USART_CHSIZE1_bp KEYWORD3 RESERVED_WORD +USART_CHSIZE2_bm KEYWORD3 RESERVED_WORD +USART_CHSIZE2_bp KEYWORD3 RESERVED_WORD +USART_SBMODE_bm KEYWORD3 RESERVED_WORD +USART_SBMODE_bp KEYWORD3 RESERVED_WORD +USART_PMODE_gm KEYWORD3 RESERVED_WORD +USART_PMODE_gp KEYWORD3 RESERVED_WORD +USART_PMODE0_bm KEYWORD3 RESERVED_WORD +USART_PMODE0_bp KEYWORD3 RESERVED_WORD +USART_PMODE1_bm KEYWORD3 RESERVED_WORD +USART_PMODE1_bp KEYWORD3 RESERVED_WORD +USART_CMODE_gm KEYWORD3 RESERVED_WORD +USART_CMODE_gp KEYWORD3 RESERVED_WORD +USART_CMODE0_bm KEYWORD3 RESERVED_WORD +USART_CMODE0_bp KEYWORD3 RESERVED_WORD +USART_CMODE1_bm KEYWORD3 RESERVED_WORD +USART_CMODE1_bp KEYWORD3 RESERVED_WORD + +USART_ABW_gm KEYWORD3 RESERVED_WORD +USART_ABW_gp KEYWORD3 RESERVED_WORD +USART_ABW0_bm KEYWORD3 RESERVED_WORD +USART_ABW0_bp KEYWORD3 RESERVED_WORD +USART_ABW1_bm KEYWORD3 RESERVED_WORD +USART_ABW1_bp KEYWORD3 RESERVED_WORD + +USART_DBGRUN_bm KEYWORD3 RESERVED_WORD +USART_DBGRUN_bp KEYWORD3 RESERVED_WORD +USART_ABMBP_bm KEYWORD3 RESERVED_WORD +USART_ABMBP_bp KEYWORD3 RESERVED_WORD + +USART_IREI_bm KEYWORD3 RESERVED_WORD +USART_IREI_bp KEYWORD3 RESERVED_WORD + +USART_TXPL_gm KEYWORD3 RESERVED_WORD +USART_TXPL_gp KEYWORD3 RESERVED_WORD +USART_TXPL0_bm KEYWORD3 RESERVED_WORD +USART_TXPL0_bp KEYWORD3 RESERVED_WORD +USART_TXPL1_bm KEYWORD3 RESERVED_WORD +USART_TXPL1_bp KEYWORD3 RESERVED_WORD +USART_TXPL2_bm KEYWORD3 RESERVED_WORD +USART_TXPL2_bp KEYWORD3 RESERVED_WORD +USART_TXPL3_bm KEYWORD3 RESERVED_WORD +USART_TXPL3_bp KEYWORD3 RESERVED_WORD +USART_TXPL4_bm KEYWORD3 RESERVED_WORD +USART_TXPL4_bp KEYWORD3 RESERVED_WORD +USART_TXPL5_bm KEYWORD3 RESERVED_WORD +USART_TXPL5_bp KEYWORD3 RESERVED_WORD +USART_TXPL6_bm KEYWORD3 RESERVED_WORD +USART_TXPL6_bp KEYWORD3 RESERVED_WORD +USART_TXPL7_bm KEYWORD3 RESERVED_WORD +USART_TXPL7_bp KEYWORD3 RESERVED_WORD + +USART_RXPL_gm KEYWORD3 RESERVED_WORD +USART_RXPL_gp KEYWORD3 RESERVED_WORD +USART_RXPL0_bm KEYWORD3 RESERVED_WORD +USART_RXPL0_bp KEYWORD3 RESERVED_WORD +USART_RXPL1_bm KEYWORD3 RESERVED_WORD +USART_RXPL1_bp KEYWORD3 RESERVED_WORD +USART_RXPL2_bm KEYWORD3 RESERVED_WORD +USART_RXPL2_bp KEYWORD3 RESERVED_WORD +USART_RXPL3_bm KEYWORD3 RESERVED_WORD +USART_RXPL3_bp KEYWORD3 RESERVED_WORD +USART_RXPL4_bm KEYWORD3 RESERVED_WORD +USART_RXPL4_bp KEYWORD3 RESERVED_WORD +USART_RXPL5_bm KEYWORD3 RESERVED_WORD +USART_RXPL5_bp KEYWORD3 RESERVED_WORD +USART_RXPL6_bm KEYWORD3 RESERVED_WORD +USART_RXPL6_bp KEYWORD3 RESERVED_WORD + + +VPORT_INT_gm KEYWORD3 RESERVED_WORD +VPORT_INT_gp KEYWORD3 RESERVED_WORD +VPORT_INT0_bm KEYWORD3 RESERVED_WORD +VPORT_INT0_bp KEYWORD3 RESERVED_WORD +VPORT_INT1_bm KEYWORD3 RESERVED_WORD +VPORT_INT1_bp KEYWORD3 RESERVED_WORD +VPORT_INT2_bm KEYWORD3 RESERVED_WORD +VPORT_INT2_bp KEYWORD3 RESERVED_WORD +VPORT_INT3_bm KEYWORD3 RESERVED_WORD +VPORT_INT3_bp KEYWORD3 RESERVED_WORD +VPORT_INT4_bm KEYWORD3 RESERVED_WORD +VPORT_INT4_bp KEYWORD3 RESERVED_WORD +VPORT_INT5_bm KEYWORD3 RESERVED_WORD +VPORT_INT5_bp KEYWORD3 RESERVED_WORD +VPORT_INT6_bm KEYWORD3 RESERVED_WORD +VPORT_INT6_bp KEYWORD3 RESERVED_WORD +VPORT_INT7_bm KEYWORD3 RESERVED_WORD +VPORT_INT7_bp KEYWORD3 RESERVED_WORD + + +VREF_AC0REFSEL_gm KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL_gp KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL0_bm KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL0_bp KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL1_bm KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL1_bp KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL2_bm KEYWORD3 RESERVED_WORD +VREF_AC0REFSEL2_bp KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_gm KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL_gp KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL0_bm KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL0_bp KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL1_bm KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL1_bp KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL2_bm KEYWORD3 RESERVED_WORD +VREF_ADC0REFSEL2_bp KEYWORD3 RESERVED_WORD + +VREF_AC0REFEN_bm KEYWORD3 RESERVED_WORD +VREF_AC0REFEN_bp KEYWORD3 RESERVED_WORD +VREF_ADC0REFEN_bm KEYWORD3 RESERVED_WORD +VREF_ADC0REFEN_bp KEYWORD3 RESERVED_WORD + + +WDT_PERIOD_gm KEYWORD3 RESERVED_WORD +WDT_PERIOD_gp KEYWORD3 RESERVED_WORD +WDT_PERIOD0_bm KEYWORD3 RESERVED_WORD +WDT_PERIOD0_bp KEYWORD3 RESERVED_WORD +WDT_PERIOD1_bm KEYWORD3 RESERVED_WORD +WDT_PERIOD1_bp KEYWORD3 RESERVED_WORD +WDT_PERIOD2_bm KEYWORD3 RESERVED_WORD +WDT_PERIOD2_bp KEYWORD3 RESERVED_WORD +WDT_PERIOD3_bm KEYWORD3 RESERVED_WORD +WDT_PERIOD3_bp KEYWORD3 RESERVED_WORD +WDT_WINDOW_gm KEYWORD3 RESERVED_WORD +WDT_WINDOW_gp KEYWORD3 RESERVED_WORD +WDT_WINDOW0_bm KEYWORD3 RESERVED_WORD +WDT_WINDOW0_bp KEYWORD3 RESERVED_WORD +WDT_WINDOW1_bm KEYWORD3 RESERVED_WORD +WDT_WINDOW1_bp KEYWORD3 RESERVED_WORD +WDT_WINDOW2_bm KEYWORD3 RESERVED_WORD +WDT_WINDOW2_bp KEYWORD3 RESERVED_WORD +WDT_WINDOW3_bm KEYWORD3 RESERVED_WORD +WDT_WINDOW3_bp KEYWORD3 RESERVED_WORD + +WDT_SYNCBUSY_bm KEYWORD3 RESERVED_WORD +WDT_SYNCBUSY_bp KEYWORD3 RESERVED_WORD +WDT_LOCK_bm KEYWORD3 RESERVED_WORD +WDT_LOCK_bp KEYWORD3 RESERVED_WORD +PIN0_bm KEYWORD3 RESERVED_WORD +PIN0_bp KEYWORD3 RESERVED_WORD +PIN1_bm KEYWORD3 RESERVED_WORD +PIN1_bp KEYWORD3 RESERVED_WORD +PIN2_bm KEYWORD3 RESERVED_WORD +PIN2_bp KEYWORD3 RESERVED_WORD +PIN3_bm KEYWORD3 RESERVED_WORD +PIN3_bp KEYWORD3 RESERVED_WORD +PIN4_bm KEYWORD3 RESERVED_WORD +PIN4_bp KEYWORD3 RESERVED_WORD +PIN5_bm KEYWORD3 RESERVED_WORD +PIN5_bp KEYWORD3 RESERVED_WORD +PIN6_bm KEYWORD3 RESERVED_WORD +PIN6_bp KEYWORD3 RESERVED_WORD +PIN7_bm KEYWORD3 RESERVED_WORD +PIN7_bp KEYWORD3 RESERVED_WORD + + + +CRCSCAN_NMI_vect_num LITERAL1 +CRCSCAN_NMI_vect LITERAL1 + +BOD_VLM_vect_num LITERAL1 +BOD_VLM_vect LITERAL1 + +RTC_CNT_vect_num LITERAL1 +RTC_CNT_vect LITERAL1 +RTC_PIT_vect_num LITERAL1 +RTC_PIT_vect LITERAL1 + +CCL_CCL_vect_num LITERAL1 +CCL_CCL_vect LITERAL1 + +PORTA_PORT_vect_num LITERAL1 +PORTA_PORT_vect LITERAL1 + +TCA0_LUNF_vect_num LITERAL1 +TCA0_LUNF_vect LITERAL1 +TCA0_OVF_vect_num LITERAL1 +TCA0_OVF_vect LITERAL1 +TCA0_HUNF_vect_num LITERAL1 +TCA0_HUNF_vect LITERAL1 +TCA0_LCMP0_vect_num LITERAL1 +TCA0_LCMP0_vect LITERAL1 +TCA0_CMP0_vect_num LITERAL1 +TCA0_CMP0_vect LITERAL1 +TCA0_CMP1_vect_num LITERAL1 +TCA0_CMP1_vect LITERAL1 +TCA0_LCMP1_vect_num LITERAL1 +TCA0_LCMP1_vect LITERAL1 +TCA0_LCMP2_vect_num LITERAL1 +TCA0_LCMP2_vect LITERAL1 +TCA0_CMP2_vect_num LITERAL1 +TCA0_CMP2_vect LITERAL1 + +TCB0_INT_vect_num LITERAL1 +TCB0_INT_vect LITERAL1 + +TCB1_INT_vect_num LITERAL1 +TCB1_INT_vect LITERAL1 + +TWI0_TWIS_vect_num LITERAL1 +TWI0_TWIS_vect LITERAL1 +TWI0_TWIM_vect_num LITERAL1 +TWI0_TWIM_vect LITERAL1 + +SPI0_INT_vect_num LITERAL1 +SPI0_INT_vect LITERAL1 + +USART0_RXC_vect_num LITERAL1 +USART0_RXC_vect LITERAL1 +USART0_DRE_vect_num LITERAL1 +USART0_DRE_vect LITERAL1 +USART0_TXC_vect_num LITERAL1 +USART0_TXC_vect LITERAL1 + +PORTD_PORT_vect_num LITERAL1 +PORTD_PORT_vect LITERAL1 + +AC0_AC_vect_num LITERAL1 +AC0_AC_vect LITERAL1 + +ADC0_RESRDY_vect_num LITERAL1 +ADC0_RESRDY_vect LITERAL1 +ADC0_WCOMP_vect_num LITERAL1 +ADC0_WCOMP_vect LITERAL1 + +PORTC_PORT_vect_num LITERAL1 +PORTC_PORT_vect LITERAL1 + +TCB2_INT_vect_num LITERAL1 +TCB2_INT_vect LITERAL1 + +USART1_RXC_vect_num LITERAL1 +USART1_RXC_vect LITERAL1 +USART1_DRE_vect_num LITERAL1 +USART1_DRE_vect LITERAL1 +USART1_TXC_vect_num LITERAL1 +USART1_TXC_vect LITERAL1 + +PORTF_PORT_vect_num LITERAL1 +PORTF_PORT_vect LITERAL1 + +NVMCTRL_EE_vect_num LITERAL1 +NVMCTRL_EE_vect LITERAL1 + +USART2_RXC_vect_num LITERAL1 +USART2_RXC_vect LITERAL1 +USART2_DRE_vect_num LITERAL1 +USART2_DRE_vect LITERAL1 +USART2_TXC_vect_num LITERAL1 +USART2_TXC_vect LITERAL1 + +PORTB_PORT_vect_num LITERAL1 +PORTB_PORT_vect LITERAL1 + +PORTE_PORT_vect_num LITERAL1 +PORTE_PORT_vect LITERAL1 + +TCB3_INT_vect_num LITERAL1 +TCB3_INT_vect LITERAL1 + +USART3_RXC_vect_num LITERAL1 +USART3_RXC_vect LITERAL1 +USART3_DRE_vect_num LITERAL1 +USART3_DRE_vect LITERAL1 +USART3_TXC_vect_num LITERAL1 +USART3_TXC_vect LITERAL1 +_VECTOR_SIZE LITERAL1 +_VECTORS_SIZE LITERAL1 + +DATAMEM_START LITERAL1 +DATAMEM_SIZE LITERAL1 +DATAMEM_START LITERAL1 +DATAMEM_SIZE LITERAL1 +DATAMEM_END LITERAL1 +EEPROM_START LITERAL1 +EEPROM_SIZE LITERAL1 +EEPROM_PAGE_SIZE LITERAL1 +EEPROM_START LITERAL1 +EEPROM_SIZE LITERAL1 +EEPROM_PAGE_SIZE LITERAL1 +EEPROM_END LITERAL1 + +MAPPED_EEPROM_START LITERAL1 +MAPPED_EEPROM_SIZE LITERAL1 +MAPPED_EEPROM_PAGE_SIZE LITERAL1 +MAPPED_EEPROM_END LITERAL1 +FUSES_START LITERAL1 +FUSES_SIZE LITERAL1 +FUSES_PAGE_SIZE LITERAL1 +FUSES_START LITERAL1 +FUSES_SIZE LITERAL1 +FUSES_PAGE_SIZE LITERAL1 +FUSES_END LITERAL1 +INTERNAL_SRAM_START LITERAL1 +INTERNAL_SRAM_SIZE LITERAL1 +INTERNAL_SRAM_PAGE_SIZE LITERAL1 +INTERNAL_SRAM_START LITERAL1 +INTERNAL_SRAM_SIZE LITERAL1 +INTERNAL_SRAM_PAGE_SIZE LITERAL1 +INTERNAL_SRAM_END LITERAL1 +IO_START LITERAL1 +IO_SIZE LITERAL1 +IO_PAGE_SIZE LITERAL1 +IO_START LITERAL1 +IO_SIZE LITERAL1 +IO_PAGE_SIZE LITERAL1 +IO_END LITERAL1 +LOCKBITS_START LITERAL1 +LOCKBITS_SIZE LITERAL1 +LOCKBITS_PAGE_SIZE LITERAL1 +LOCKBITS_START LITERAL1 +LOCKBITS_SIZE LITERAL1 +LOCKBITS_PAGE_SIZE LITERAL1 +LOCKBITS_END LITERAL1 +MAPPED_PROGMEM_START LITERAL1 +MAPPED_PROGMEM_SIZE LITERAL1 +MAPPED_PROGMEM_PAGE_SIZE LITERAL1 +MAPPED_PROGMEM_START LITERAL1 +MAPPED_PROGMEM_SIZE LITERAL1 +MAPPED_PROGMEM_PAGE_SIZE LITERAL1 +MAPPED_PROGMEM_END LITERAL1 +PROD_SIGNATURES_START LITERAL1 +PROD_SIGNATURES_SIZE LITERAL1 +PROD_SIGNATURES_PAGE_SIZE LITERAL1 +PROD_SIGNATURES_START LITERAL1 +PROD_SIGNATURES_SIZE LITERAL1 +PROD_SIGNATURES_PAGE_SIZE LITERAL1 +PROD_SIGNATURES_END LITERAL1 +SIGNATURES_START LITERAL1 +SIGNATURES_SIZE LITERAL1 +SIGNATURES_PAGE_SIZE LITERAL1 +SIGNATURES_START LITERAL1 +SIGNATURES_SIZE LITERAL1 +SIGNATURES_PAGE_SIZE LITERAL1 +SIGNATURES_END LITERAL1 +USER_SIGNATURES_START LITERAL1 +USER_SIGNATURES_SIZE LITERAL1 +USER_SIGNATURES_PAGE_SIZE LITERAL1 +USER_SIGNATURES_START LITERAL1 +USER_SIGNATURES_SIZE LITERAL1 +USER_SIGNATURES_PAGE_SIZE LITERAL1 +USER_SIGNATURES_END LITERAL1 +PROGMEM_START LITERAL1 +PROGMEM_SIZE LITERAL1 +PROGMEM_START LITERAL1 +PROGMEM_SIZE LITERAL1 +PROGMEM_END LITERAL1 +PROGMEM_START LITERAL1 +PROGMEM_SIZE LITERAL1 +PROGMEM_PAGE_SIZE LITERAL1 +PROGMEM_START LITERAL1 +PROGMEM_SIZE LITERAL1 +PROGMEM_PAGE_SIZE LITERAL1 +PROGMEM_END LITERAL1 +FLASHSTART LITERAL1 +FLASHEND LITERAL1 +RAMSTART LITERAL1 +RAMSIZE LITERAL1 +RAMEND LITERAL1 +E2END LITERAL1 +E2PAGESIZE LITERAL1 + +FUSE_MEMORY_SIZE LITERAL1 + +FUSE_PERIOD0 LITERAL1 +FUSE_PERIOD1 LITERAL1 +FUSE_PERIOD2 LITERAL1 +FUSE_PERIOD3 LITERAL1 +FUSE_WINDOW0 LITERAL1 +FUSE_WINDOW1 LITERAL1 +FUSE_WINDOW2 LITERAL1 +FUSE_WINDOW3 LITERAL1 +FUSE0_DEFAULT LITERAL1 +FUSE_WDTCFG_DEFAULT LITERAL1 + +FUSE_SLEEP0 LITERAL1 +FUSE_SLEEP1 LITERAL1 +FUSE_ACTIVE0 LITERAL1 +FUSE_ACTIVE1 LITERAL1 +FUSE_SAMPFREQ LITERAL1 +FUSE_LVL0 LITERAL1 +FUSE_LVL1 LITERAL1 +FUSE_LVL2 LITERAL1 +FUSE1_DEFAULT LITERAL1 +FUSE_BODCFG_DEFAULT LITERAL1 + +FUSE_FREQSEL0 LITERAL1 +FUSE_FREQSEL1 LITERAL1 +FUSE_OSCLOCK LITERAL1 +FUSE2_DEFAULT LITERAL1 +FUSE_OSCCFG_DEFAULT LITERAL1 + +FUSE_EESAVE LITERAL1 +FUSE_RSTPINCFG LITERAL1 +FUSE_CRCSRC0 LITERAL1 +FUSE_CRCSRC1 LITERAL1 +FUSE5_DEFAULT LITERAL1 +FUSE_SYSCFG0_DEFAULT LITERAL1 + +FUSE_SUT0 LITERAL1 +FUSE_SUT1 LITERAL1 +FUSE_SUT2 LITERAL1 +FUSE6_DEFAULT LITERAL1 +FUSE_SYSCFG1_DEFAULT LITERAL1 + +FUSE7_DEFAULT LITERAL1 +FUSE_APPEND_DEFAULT LITERAL1 + +FUSE8_DEFAULT LITERAL1 +FUSE_BOOTEND_DEFAULT LITERAL1 + +__LOCK_BITS_EXIST LITERAL1 + +SIGNATURE_0 LITERAL1 +SIGNATURE_1 LITERAL1 +SIGNATURE_2 LITERAL1 diff --git a/megaavr/libraries/MegaCoreX/library.properties b/megaavr/libraries/MegaCoreX/library.properties new file mode 100644 index 0000000..6afd7cf --- /dev/null +++ b/megaavr/libraries/MegaCoreX/library.properties @@ -0,0 +1,10 @@ +name=Keyword highlighter +version=0.1 +author=MCUdude +maintainer=MCUdude +sentence=Highlights relevant AVR keywords in the Arduino IDE +paragraph= +category=Other +url=https://github.com/MCUdude/MegaCoreX +architectures=megaavr +types=Arduino diff --git a/megaavr/libraries/MegaCoreX/src/AVR_keywords.h b/megaavr/libraries/MegaCoreX/src/AVR_keywords.h new file mode 100644 index 0000000..f3d5868 --- /dev/null +++ b/megaavr/libraries/MegaCoreX/src/AVR_keywords.h @@ -0,0 +1 @@ +// This file causes the Arduino IDE to see AVR_keywords as a valid library From 31a3042c2159fa1e687fb597564f752790f84acd Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 19 Apr 2021 22:41:54 +0200 Subject: [PATCH 250/351] Create README.md --- megaavr/libraries/Optiboot_flasher/README.md | 197 +++++++++++++++++++ 1 file changed, 197 insertions(+) create mode 100644 megaavr/libraries/Optiboot_flasher/README.md diff --git a/megaavr/libraries/Optiboot_flasher/README.md b/megaavr/libraries/Optiboot_flasher/README.md new file mode 100644 index 0000000..9db0f22 --- /dev/null +++ b/megaavr/libraries/Optiboot_flasher/README.md @@ -0,0 +1,197 @@ +# Optiboot Flash +Two libraries are used to interface with the "write-to-flash" functionality the Optiboot bootloader has. Flash.h/cpp is a high-level library that makes it easy to store strings, variables, structs, etc. to the flash memory and easily retrieve them. optiboot.h/cpp is a low-level read/write library that does the actual reading and writing to flash. If your application needs more storage than the EEPROM can offer, Flash is the library for you. If you're very memory constrained and want to do the heavy lifting yourself, optiboot is the library for you. See the examples of how you can interface with these two libraries. + + +## Flash() +Class constructor for interfacing with the "write-to-flash" functionality. +For arguments has to be present. A reference to the allocated flash space array, the size of the allocated space, a RAM buffer, and its size. + +##### Usage: +```c++ +// Create object 'flash' with flash_space_array and ram_buffer +Flash flash(flash_space_array, sizeof(flash_space_array), ram_buffer, sizeof(ram_buffer)); +``` + + +## Flash[] +Operator overloaded object. This lets you use the object itself to access the RAM buffer. + +##### Usage: +```cpp +uint8_t data = flash[0x00]; // Read data from address 0x00 in the buffer +flash[0x00] = data; // Write the contents of 'data' to address 0x00 +``` + + +## check_writable() +Checks if a bootloader that has "write-to-flash" functionality is present + +##### Usage: +```cpp +bool valid_bootloader = flash.check_writable(); +``` + +##### Returns: +`bool` valid bootloader present + + +## clear_buffer() +Clears the RAM buffer. Sets all values to 0x00 if no parameter is present + +##### Usage: +```cpp +flash.clear_buffer(); // Write all zeros to the RAM buffer +flash.clear:buffer(0xff); // Write all 0xff's to the RAM buffer +``` + +##### Returns: +`void` + + +## read_buffer() +**Alternative to `flash[]`**. Reads a byte from the RAM buffer. + +##### Usage: +```cpp +uint8_t data = flash.read_buffer(0x00); // Read data from place 0x00 in the buffer +uint8_t data = flash.read_buffer(0x40); // Read data from place 0x40 +``` + +##### Returns: +`uint8_t` data in buffer place *N* + + +## write_buffer() +**Alternative to `flash[]`**. Writes a byte to the RAM buffer + +##### Usage: +```cpp +flash.write_buffer(0x00, 'H'); // Write character 'H' to buffer place 0x00 +``` + +##### Returns: +`void` + + +## buffer_size() +Returns the size of the allocated RAM buffer in bytes + +##### Usage: +```cpp +uint16_t allocated_buffer = flash.buffer_size(); +``` + +##### Returns: +`uint16_t` buffer size in bytes + + +## write_page() +Writes the RAM buffer to flash + +##### Usage: +```cpp +flash.write_page(1); // Write buffer to flash page 1 +``` + +##### Returns: +`void` + + +## fetch_page() +Fetches a flash page and stores it in the RAM buffer + +##### Usage: +```cpp +flash.fetch_page(1); // Fetch flash page 1 +``` + +##### Returns: +`void` + + +## fetch_data() +Fetches a given amount of data from flash. Note that the start and stop address is relative to the start of the flash space array. +This means that The span can't be larger than the size of the RAM buffer. + +##### Usage: +```cpp +flash.fetch_data(128, 192); // Read 64 bytes of data from beginning of flash page one (128 bytes flash page size) +``` + +##### Returns: +`void` + + +## put() +Write any data type or object to flash + +##### Usage: +```cpp +float f = 123.456f; +char text[13] = "Hello World!"; +flash.put(0x00, f); // Store float value to flash, starting from address 0 +flash.put(sizeof(float), text); // Store text after the float variable +``` + + +## get() +Read any data type or object from flash + +##### Usage: +```cpp +float f; +char text[13]; +flash.get(0x00, f); // Fetch float variable from flash address 0 and store it to variable f +flash.getsizeof(float), text); // Fetch text after the float variable +``` + + +Optiboot +====== + +## optiboot_check_writable() +Checks if a bootloader that has "write-to-flash" functionality is present + +##### Usage: +```cpp +bool valid_bootloader = optiboot_check_writable(); +``` + +##### Returns: +`bool` valid bootloader present + + +## optiboot_read() +Reads data from the flash memory into a buffer + +##### Usage: +```cpp +optiboot_read(flash_space_array, ram_buffer, page_number, page_start_address, page_stop_address); +``` + +##### Returns: +`void` + + +## optiboot_readPage() +Reads an entire flash page into a buffer + +##### Usage: +```cpp +optiboot_readPage(flash_space_array, ram_buffer, page_number); +``` + +##### Returns: +`void` + + +## optiboot_writePage() +Writes data to a flash page + +##### Usage: +```cpp +optiboot_writePage(flash_space_array, ram_buffer, page_number); +``` + +##### Returns: +`void` From 5ba7807c84c4b4c807c712671f524e4861cf8fb2 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 21 Apr 2021 18:17:10 +0200 Subject: [PATCH 251/351] Fix analog pin macro issue Closes #121 --- megaavr/variants/40pin-standard/pins_arduino.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index dbe0a0d..b57f0d5 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -70,7 +70,7 @@ #define ANALOG_INPUT_OFFSET 14 #define LED_BUILTIN PIN_PA7 #define EXTERNAL_NUM_INTERRUPTS 47 -#define digitalPinToAnalogInput(p) ((p < NUM_ANALOG_INPUTS) ? (p) : ((p) >= PIN_PD0 && (p) <= PIN_PE3) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= PIN_PF2 && (p) <= PIN_PF5) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) +#define digitalPinToAnalogInput(p) ((p < 14) ? (p) : ((p) >= PIN_PD0 && (p) <= PIN_PE3) ? ((p) - ANALOG_INPUT_OFFSET) : ((p) >= PIN_PF2 && (p) <= PIN_PF5) ? ((p) - 2 - ANALOG_INPUT_OFFSET) : NOT_A_PIN) #define digitalOrAnalogPinToDigital(p) ((p <= 11) ? ((p) + ANALOG_INPUT_OFFSET) : ((p) <= 15) ? ((p) + ANALOG_INPUT_OFFSET + 2) : (((p) >= 26 && (p) <= 31)) ? (p) : NOT_A_PIN) // Timer to use for millis/micros From 3703799ad0282883686ab1ed189e328b6bf350a2 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 26 Apr 2021 22:03:09 +0200 Subject: [PATCH 252/351] Add MEGACOREX macros --- megaavr/variants/28pin-standard/pins_arduino.h | 3 +++ megaavr/variants/32pin-standard/pins_arduino.h | 3 +++ megaavr/variants/40pin-standard/pins_arduino.h | 3 +++ megaavr/variants/48pin-standard/pins_arduino.h | 3 +++ megaavr/variants/nano-every/pins_arduino.h | 3 +++ megaavr/variants/uno-wifi/pins_arduino.h | 3 +++ 6 files changed, 18 insertions(+) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index f10f4ac..e66f077 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -18,6 +18,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define MEGACOREX_DEFAULT_28PIN_PINOUT #define __AVR_ATmegax08__ diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 5bda929..77b71cd 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -18,6 +18,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define MEGACOREX_DEFAULT_32PIN_PINOUT #define __AVR_ATmegax08__ diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index b57f0d5..5d7a334 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -20,6 +20,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define MEGACOREX_DEFAULT_40PIN_PINOUT #define __AVR_ATmegax09__ diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 963f462..1edb899 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -23,6 +23,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define MEGACOREX_DEFAULT_48PIN_PINOUT #define __AVR_ATmegax09__ diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index c384bf5..d44b278 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -26,6 +26,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define NANO_EVERY_PINOUT #define NONA4809_PINOUT #define __AVR_ATmegax09__ diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index d5daeef..e32ffbc 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -27,6 +27,9 @@ #include #include "timers.h" +#define MEGACOREX +#define MCUDUDE_MEGACOREX + #define UNO_WIFI_REV2_PINOUT #define UNO2018_PINOUT #define __AVR_ATmegax09__ From 2ced9a16668662e871f24454acc04ccc5c422ed9 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 10 May 2021 14:46:46 +0200 Subject: [PATCH 253/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 79e3746..7d537ca 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.6 +version=1.0.8 # AVR compile variables # --------------------- From 6ce1f59d7eede202fd573269bc0bbd8179852a18 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 23 May 2021 21:32:31 +0200 Subject: [PATCH 254/351] Fix bug in analogWrite when accessing 16 bit registe See https://github.com/arduino/ArduinoCore-megaavr/pull/94 for details --- megaavr/cores/coreX-corefiles/wiring_analog.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 7a9ce57..2d3674a 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -126,6 +126,8 @@ void analogWrite(uint8_t pin, int val) uint8_t *timer_cmp_out; TCB_t *timer_B; + uint8_t savedSREG; + /* Find out Port and Pin to correctly handle port mux, and timer. */ switch (digital_pin_timer) { @@ -143,7 +145,10 @@ void analogWrite(uint8_t pin, int val) } /* Configure duty cycle for correct compare channel */ - (*timer_cmp_out) = val; + savedSREG = SREG; + cli(); + (*timer_cmp_out) = (val); // non-atomic 16-bit write operation + SREG = savedSREG; /* Enable output on pin */ TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + bit_pos)); @@ -158,8 +163,12 @@ void analogWrite(uint8_t pin, int val) //assert (((TIMERB0 - TIMERB3) == 2)); timer_B = ((TCB_t *)&TCB0 + (digital_pin_timer - TIMERB0)); - /* set duty cycle */ - timer_B->CCMPH = val; + // (16-bit read/write operation are non-atomic and use a temporary register) + savedSREG = SREG; + cli(); + timer_B->CCMPL = timer_B->CCMPL; // Copy CCMPL into temporary register + timer_B->CCMPH = val; // Set CCMPH value + copy temporary register content into CCMPL + SREG = savedSREG; /* Enable Timer Output */ timer_B->CTRLB |= (TCB_CCMPEN_bm); From cd2a1fde7b868c623973f193b36cbb8dcd35247e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 21 Jun 2021 18:34:51 +0200 Subject: [PATCH 255/351] Update to C++17 --- megaavr/cores/coreX-corefiles/new.cpp | 15 +++++++++++++++ megaavr/cores/coreX-corefiles/new.h | 6 ++++++ megaavr/platform.txt | 2 +- 3 files changed, 22 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/new.cpp b/megaavr/cores/coreX-corefiles/new.cpp index a265fd6..26403f1 100644 --- a/megaavr/cores/coreX-corefiles/new.cpp +++ b/megaavr/cores/coreX-corefiles/new.cpp @@ -37,3 +37,18 @@ void operator delete[](void *ptr) { free(ptr); } + +// C++14 introduces additional delete operators +#if __cplusplus >= 201402L + +void operator delete(void * ptr, size_t) +{ + ::operator delete(ptr); +} + +void operator delete[](void * ptr, size_t) +{ + ::operator delete(ptr); +} + +#endif // End language is C++14 or greater diff --git a/megaavr/cores/coreX-corefiles/new.h b/megaavr/cores/coreX-corefiles/new.h index d1fc852..66b9619 100644 --- a/megaavr/cores/coreX-corefiles/new.h +++ b/megaavr/cores/coreX-corefiles/new.h @@ -26,4 +26,10 @@ void * operator new[](size_t size); void operator delete(void* ptr); void operator delete[](void* ptr); +// C++14 introduces additional delete operators +#if __cplusplus >= 201402L +void operator delete(void * ptr, size_t); +void operator delete[](void * ptr, size_t); +#endif // end language is C++14 or greater + #endif diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 7d537ca..9e56c13 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -25,7 +25,7 @@ compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin - compiler.c.elf.cmd=avr-gcc compiler.S.flags=-c -g -x assembler-with-cpp -flto -MMD compiler.cpp.cmd=avr-g++ -compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++11 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -Wno-error=narrowing -MMD -flto +compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++17 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -Wno-error=narrowing -MMD -flto compiler.ar.cmd=avr-gcc-ar compiler.ar.flags=rcs compiler.objcopy.cmd=avr-objcopy From 9bc4b614798635f9b17670ee7adf13f1035dcfe7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 22 Jun 2021 18:50:57 +0200 Subject: [PATCH 256/351] Update Travis CI badge --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 64286bd..3886626 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,5 @@ # MegaCoreX -[![Build Status](https://travis-ci.org/MCUdude/MegaCoreX.svg?branch=master)](https://travis-ci.org/MCUdude/MegaCoreX) +[![Build Status](https://travis-ci.com/MCUdude/MegaCoreX.svg?branch=master)](https://travis-ci.com/MCUdude/MegaCoreX) An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. Its largest variant, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis. @@ -211,7 +211,7 @@ The megaAVR-0 microcontrollers are equipped with four independent configurable l ### Analog Comparator (AC) The megaAVR-0 microcontrollers are equipped with an analog comparator. It compares the voltage levels on two inputs and gives a digital output based on this comparison. The megAVR chip has four positive AC pins and three negative. There's also a configurable internal voltage reference that can be used on the negative comparator pin instead of an external voltage. -Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. +Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Comparator) for more information, library reference and examples. ### Event System (EVSYS) The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. Give the [Event library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Event) a try! Here you'll find documentation and useful library examples. From 6b6d3a8d747fd529f71220b1970f85c9e7a90af1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 22 Jun 2021 20:52:30 +0200 Subject: [PATCH 257/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 9e56c13..bab0837 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.8 +version=1.0.9 # AVR compile variables # --------------------- From ea46dbe9e017f80f90ee78696d2366f4d57ae29e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 20 Jul 2021 12:37:21 +0200 Subject: [PATCH 258/351] Initial support for Nano 4808 Also known as the Thinary Nano Every. #125 related --- PlatformIO.md | 32 +- README.md | 13 + megaavr/boards.txt | 8 + megaavr/variants/nano-4808/pins_arduino.h | 367 ++++++++++++++++++++++ 4 files changed, 404 insertions(+), 16 deletions(-) create mode 100644 megaavr/variants/nano-4808/pins_arduino.h diff --git a/PlatformIO.md b/PlatformIO.md index 03af516..cf6e09a 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -1,20 +1,20 @@ # PlatformIO -[PlatformIO](https://platformio.org) is an open source ecosystem for embedded development. +[PlatformIO](https://platformio.org) is an open source ecosystem for embedded development. It has a built-in library manager and is Arduino compatible. It supports most operating systems; Windows, MacOS, Linux 32 and 64-bit, ARM and X86. And best of all, MegaCoreX is supported! * [What is PlatformIO?](http://docs.platformio.org/en/latest/what-is-platformio.html) * [PlatformIO IDE](https://platformio.org/platformio-ide) * Getting started with [PlatformIO IDE](https://docs.platformio.org/en/latest/integration/ide/visualstudio.html) or [PlatformIO command line interface](https://docs.platformio.org/en/latest/core/index.html) -* [Advanced functionality](https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html) +* [Advanced functionality](https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html) * [Project Examples](https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html#examples) -## MegaCoreX + PlatformIO +## MegaCoreX + PlatformIO MegaCoreX and PlatformIO goes great together. You can do serial uploads and upload using a dedicated UPDI programmer, but you can also let PlatformIO calulate the fuses and load the correct bootloader file, just like Arduino IDE does! -PlatformIO uses the information provided in platformio.ini to calculate what fuse bits and what bootloader file to load. -Simply provide enough information and run the following commands: +PlatformIO uses the information provided in platformio.ini to calculate what fuse bits and what bootloader file to load. +Simply provide enough information and run the following commands: ```ini ; Only set fuses @@ -24,8 +24,8 @@ pio run -t bootloader -e fuses_bootloader ; (where "fuses_bootloader" can be replace with a different environment to match your build configuration) ``` -You can find a platformio.ini template you can use when creating a project for a MegaCoreX compatible device below. -The most common functionality is available in this template. As you can see, the templated is divided into multiple environments. +You can find a platformio.ini template you can use when creating a project for a MegaCoreX compatible device below. +The most common functionality is available in this template. As you can see, the templated is divided into multiple environments. * The default build environment are defined under *[platformio]*. * All parameters that are common for all environments are defined under *[env]*. @@ -72,11 +72,11 @@ board_build.variant = 48pin-standard ; Unflag build flags build_unflags = -; Extra build flags +; Extra build flags build_flags = ; Monitor port is auto detected. Override here -;monitor_port = +;monitor_port = ; Serial monitor baud rate monitor_speed = 9600 @@ -131,7 +131,7 @@ The table below shows what board name should be used for each target ### `board_build.f_cpu` -Specifies the clock frequency in [Hz]. +Specifies the clock frequency in [Hz]. Used to determine what oscillator option to choose. A capital *L* has to be added to the end of the frequency number. Below is a table with supported clocks for MegaCoreX. Defaults to 16 MHz internal if not specified. @@ -153,7 +153,7 @@ Below is a table with supported clocks for MegaCoreX. Defaults to 16 MHz interna ### `board_hardware.oscillator` -Spefices to use the internal or an external oscillator. +Spefices to use the internal or an external oscillator. | Oscillator option | |----------------------| @@ -206,13 +206,13 @@ Specifies what functionality the reset pin should have. Note that the option `re ### `board_build.variant` -Holds the current pinout in use. +Holds the current pinout in use. See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. | Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | |----------------------------|------------------------------------|----------------------------|----------------------------| | `48pin-standard` (default) | `40pin-standard` (must be defined) | `32pin-standard` (default) | `28pin-standard` (default) | -| `nano-every` | | | | +| `nano-every` | | `nano-4808` | | | `uno-wifi` | | | | @@ -259,11 +259,11 @@ Programmer used for uploading. ### `upload_flags` -Used to pass extra flags to Avrdude when uploading using a programmer. -Typical parameters are `-PUSB` and `-v`. +Used to pass extra flags to Avrdude when uploading using a programmer. +Typical parameters are `-PUSB` and `-v`. **Note that every flag has to be on its own line, and they have to be indented with two spaces:** ```ini -upload_flags = +upload_flags = -PUSB -v ``` diff --git a/README.md b/README.md index 3886626..4f72277 100644 --- a/README.md +++ b/README.md @@ -40,6 +40,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Getting your hardware working](#getting-your-hardware-working) - [Arduino Uno WiFi Rev2](#arduino-uno-wifi-rev2) - [Arduino Nano Every](#arduino-nano-every) + - [Nano 4808](#nano-4808) - [Curiosity Nano](#curiosity-nano) - [AVR-IOT-WG](#avr-iot-wg) - [4809 Xplained Pro](#atmega4809-xplained-pro) @@ -325,28 +326,40 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he [The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: + ### Arduino Nano Every [The Arduino Nano Every](https://store.arduino.cc/arduino-nano-every) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the *only* supported pinout is *Nano Every*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano Every does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. For more information about this board please see the product page and its schematic. Click to enlarge: + +### Nano 4808 +The Nano 4808, also known as the Thinary Nano 4808 a third party Arduino compatible board with the Nano form factor. It uses an ATmega4808 and the *only* supported pinout is *Nano 4808*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano 4808 does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. + +Click to enlarge: + + + ### Curiosity Nano [The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: + ### ATmega4809 Xplained Pro [The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: + diff --git a/megaavr/boards.txt b/megaavr/boards.txt index da611d0..a5e0d81 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -282,9 +282,17 @@ menu.bootloader=Bootloader # Pinouts 4808.menu.pinout.32pin_standard=32 pin standard 4808.menu.pinout.32pin_standard.build.variant=32pin-standard + 4808.menu.pinout.28pin_standard=28 pin standard 4808.menu.pinout.28pin_standard.build.variant=28pin-standard +4808.menu.pinout.nano_4808=Nano 4808 +4808.menu.pinout.nano_4808.build.variant=nano-4808 +4808.menu.pinout.nano_4808.upload.tool=avrdude_nanoevery +4808.menu.pinout.nano_4808.upload.use_1200bps_touch=true +4808.menu.pinout.nano_4808.upload.protocol=jtag2updi +4808.menu.pinout.nano_4808.program.extra_params=-P{serial.port} -e + # Reset pin 4808.menu.resetpin.reset=Reset 4808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h new file mode 100644 index 0000000..166e207 --- /dev/null +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -0,0 +1,367 @@ +/* + pins_arduino.h - Pin definition functions for Arduino + Part of Arduino - http://www.arduino.cc/ + + Copyright (c) 2007 David A. Mellis + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General + Public License along with this library; if not, write to the + Free Software Foundation, Inc., 59 Temple Place, Suite 330, + Boston, MA 02111-1307 USA +*/ + +#ifndef Pins_Arduino_h +#define Pins_Arduino_h + +#include +#include "timers.h" + +#define MEGACOREX +#define MCUDUDE_MEGACOREX + +#define NANO_4808_PINOUT +#define NONA4808_PINOUT +#define __AVR_ATmegax08__ + +// Arduino pin macros +#define PIN_PF0 0 +#define PIN_PF1 1 +#define PIN_PA0 2 +#define PIN_PA1 3 +#define PIN_PA2 4 +#define PIN_PA3 5 +#define PIN_PA4 6 +#define PIN_PA5 7 +#define PIN_PA6 8 +#define PIN_PA7 9 +#define PIN_PC3 10 +#define PIN_PC0 11 +#define PIN_PC1 12 +#define PIN_PC2 13 +#define PIN_PD0 14 +#define PIN_PD1 15 +#define PIN_PD2 16 +#define PIN_PD3 17 +#define PIN_PF2 18 +#define PIN_PF3 19 +#define PIN_PF4 20 +#define PIN_PF5 21 +#define PIN_PD4 22 +#define PIN_PD5 23 +#define PIN_PD6 24 +#define PIN_PD7 25 +#define PIN_PF6 26 + +#define PINS_COUNT 27 +#define NUM_DIGITAL_PINS PINS_COUNT +#define NUM_ANALOG_INPUTS 12 +#define NUM_RESERVED_PINS 0 +#define NUM_INTERNALLY_USED_PINS 0 +#define NUM_I2C_PINS 2 +#define NUM_SPI_PINS 3 +#define NUM_TOTAL_FREE_PINS PINS_COUNT +#define NUM_TOTAL_PINS PINS_COUNT +#define ANALOG_INPUT_OFFSET 14 +#define LED_BUILTIN PIN_PC2 +#define EXTERNAL_NUM_INTERRUPTS 47 +#define digitalPinToAnalogInput(p) (((p) < 8) ? (p) : ((p) >= 14 && (p) >= 25) ? (p) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) + +// Timer to use for millis/micros +#if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) +#define MILLIS_USE_TIMERB2 // Use TCB2 if nothing else if defined +#endif + +// PWM pins +#if defined(MILLIS_USE_TIMERB0) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) +#elif defined(MILLIS_USE_TIMERB1) + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) +#else // default to MILLIS_USE_TIMERB2 + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) +#endif + +// Timer pin mapping +#define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] +#define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 +#define TCB1_PINS 0x00 // TCB1 output on PA3 instead of PF5 +#define TCB2_PINS 0x00 // TCB2 output on PC0 instead of PB4 + +// SPI 0 +// Pinswapped by default +// Pinswap 2 not available +#define SPI_INTERFACES_COUNT 1 +#define SPI_MUX PORTMUX_SPI0_ALT1_gc +#define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_DEFAULT_gc +#define PIN_SPI_MISO PIN_PC1 +#define PIN_SPI_SCK PIN_PC2 +#define PIN_SPI_MOSI PIN_PC0 +#define PIN_SPI_SS PIN_PC3 +#define PIN_SPI_MISO_PINSWAP_1 PIN_PA5 +#define PIN_SPI_SCK_PINSWAP_1 PIN_PA6 +#define PIN_SPI_MOSI_PINSWAP_1 PIN_PA4 +#define PIN_SPI_SS_PINSWAP_1 PIN_PA7 +static const uint8_t SS = PIN_SPI_SS; +static const uint8_t MOSI = PIN_SPI_MOSI; +static const uint8_t MISO = PIN_SPI_MISO; +static const uint8_t SCK = PIN_SPI_SCK; + +// TWI 0 +// No pinswap enabled by default +#define TWI_MUX PORTMUX_TWI0_DEFAULT_gc +#define TWI_MUX_PINSWAP PORTMUX_TWI0_ALT2_gc +#define PIN_WIRE_SDA PIN_PA2 +#define PIN_WIRE_SCL PIN_PA3 +#define PIN_WIRE_SDA_PINSWAP_1 PIN_PC2 +#define PIN_WIRE_SCL_PINSWAP_1 PIN_PC3 +static const uint8_t SDA = PIN_WIRE_SDA; +static const uint8_t SCL = PIN_WIRE_SCL; + +// USART 0 +// No pinswap enabled by default +#define HWSERIAL0 &USART2 +#define HWSERIAL0_DRE_VECTOR USART2_DRE_vect +#define HWSERIAL0_DRE_VECTOR_NUM USART2_DRE_vect_num +#define HWSERIAL0_RXC_VECTOR USART2_RXC_vect +#define HWSERIAL0_MUX PORTMUX_USART2_DEFAULT_gc +#define HWSERIAL0_MUX_PINSWAP_1 PORTMUX_USART2_ALT1_gc +#define PIN_HWSERIAL0_TX PIN_PF0 +#define PIN_HWSERIAL0_RX PIN_PF1 +#define PIN_HWSERIAL0_XCK PIN_PF2 +#define PIN_HWSERIAL0_XDIR PIN_PF3 +#define PIN_HWSERIAL0_TX_PINSWAP_1 PIN_PF4 +#define PIN_HWSERIAL0_RX_PINSWAP_1 PIN_PF5 +#define PIN_HWSERIAL0_XCK_PINSWAP_1 PIN_PF6 + +// USART1 +// No pinswap available +#define HWSERIAL1 &USART1 +#define HWSERIAL1_DRE_VECTOR USART1_DRE_vect +#define HWSERIAL1_DRE_VECTOR_NUM USART1_DRE_vect_num +#define HWSERIAL1_RXC_VECTOR USART1_RXC_vect +#define HWSERIAL1_MUX PORTMUX_USART1_DEFAULT_gc +#define HWSERIAL1_MUX_PINSWAP_1 PORTMUX_USART1_DEFAULT_gc +#define PIN_HWSERIAL1_TX PIN_PC0 +#define PIN_HWSERIAL1_RX PIN_PC1 +#define PIN_HWSERIAL1_XCK PIN_PC2 +#define PIN_HWSERIAL1_XDIR PIN_PC3 +#define PIN_HWSERIAL1_TX_PINSWAP_1 PIN_HWSERIAL1_TX +#define PIN_HWSERIAL1_RX_PINSWAP_1 PIN_HWSERIAL1_RX + +// USART 2 +// No pinswap enabled by default +#define HWSERIAL2 &USART0 +#define HWSERIAL2_DRE_VECTOR USART0_DRE_vect +#define HWSERIAL2_DRE_VECTOR_NUM USART0_DRE_vect_num +#define HWSERIAL2_RXC_VECTOR USART0_RXC_vect +#define HWSERIAL2_MUX PORTMUX_USART0_DEFAULT_gc +#define HWSERIAL2_MUX_PINSWAP_1 PORTMUX_USART0_ALT1_gc +#define PIN_HWSERIAL2_TX PIN_PA0 +#define PIN_HWSERIAL2_RX PIN_PA1 +#define PIN_HWSERIAL2_XCK PIN_PA2 +#define PIN_HWSERIAL2_XDIR PIN_PA3 +#define PIN_HWSERIAL2_TX_PINSWAP_1 PIN_PA4 +#define PIN_HWSERIAL2_RX_PINSWAP_1 PIN_PA5 +#define PIN_HWSERIAL2_XCK_PINSWAP_1 PIN_PA6 +#define PIN_HWSERIAL2_XDIR_PINSWAP_1 PIN_PA7 + +// Analog pins +#define PIN_A0 PIN_PD0 +#define PIN_A1 PIN_PD1 +#define PIN_A2 PIN_PD2 +#define PIN_A3 PIN_PD3 +#define PIN_A4 PIN_PF2 +#define PIN_A5 PIN_PF3 +#define PIN_A6 PIN_PF4 +#define PIN_A7 PIN_PF5 +#define PIN_A8 PIN_PD4 +#define PIN_A9 PIN_PD5 +#define PIN_A10 PIN_PD6 +#define PIN_A11 PIN_PD7 +static const uint8_t A0 = PIN_A0; +static const uint8_t A1 = PIN_A1; +static const uint8_t A2 = PIN_A2; +static const uint8_t A3 = PIN_A3; +static const uint8_t A4 = PIN_A4; +static const uint8_t A5 = PIN_A5; +static const uint8_t A6 = PIN_A6; +static const uint8_t A7 = PIN_A7; +static const uint8_t A8 = PIN_A8; +static const uint8_t A9 = PIN_A9; +static const uint8_t A10 = PIN_A10; +static const uint8_t A11 = PIN_A11; + +#ifdef ARDUINO_MAIN + +const uint8_t digital_pin_to_port[] = { + PF, // 0 PF0/USART2_Tx/TOSC1 + PF, // 1 PF1/USART2_Rx/TOSC2 + PA, // 2 PA0/USART0_Tx/CLKIN + PA, // 3 PA1/USART0_Rx + PA, // 4 PA2/SDA + PA, // 5 PA3/SCL + PA, // 6 PA4/MOSI + PA, // 7 PA5/MISO + PA, // 8 PA6/SCK + PA, // 9 PA7/SS/CLKOUT/LED_BUILTIN + PC, // 10 PC3 + PC, // 11 PC0/USART1_Tx + PC, // 12 PC1/USART1_Rx + PC, // 13 PC2 + PD, // 14 PD0/AIN0 + PD, // 15 PD1/AIN1 + PD, // 16 PD2/AIN2 + PD, // 17 PD3/AIN3 + PF, // 18 PF2/AIN12 + PF, // 19 PF3/AIN13 + PF, // 20 PF4/AIN14/TCB0 PWM + PF, // 21 PF5/AIN15/TCB1 PWM + PD, // 22 PD4/AIN4 + PD, // 23 PD5/AIN5 + PD, // 24 PD6/AIN6 + PD, // 25 PD7/AIN7/AREF + PF // 26 PF6 RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_position[] = { + PIN0_bp, // 0 PF0/USART2_Tx/TOSC1 + PIN1_bp, // 1 PF1/USART2_Rx/TOSC2 + PIN0_bp, // 2 PA0/USART0_Tx/CLKIN + PIN1_bp, // 3 PA1/USART0_Rx + PIN2_bp, // 4 PA2/SDA + PIN3_bp, // 5 PA3/SCL + PIN4_bp, // 6 PA4/MOSI + PIN5_bp, // 7 PA5/MISO + PIN6_bp, // 8 PA6/SCK + PIN7_bp, // 9 PA7/SS/CLKOUT/LED_BUILTIN + PIN3_bp, // 10 PC3 + PIN0_bp, // 11 PC0/USART1_Tx + PIN1_bp, // 12 PC1/USART1_Rx + PIN2_bp, // 13 PC2 + PIN0_bp, // 14 PD0/AIN0 + PIN1_bp, // 15 PD1/AIN1 + PIN2_bp, // 16 PD2/AIN2 + PIN3_bp, // 17 PD3/AIN3 + PIN2_bp, // 18 PF2/AIN12 + PIN3_bp, // 19 PF3/AIN13 + PIN4_bp, // 20 PF4/AIN14/TCB0 PWM + PIN5_bp, // 21 PF5/AIN15/TCB1 PWM + PIN4_bp, // 22 PD4/AIN4 + PIN5_bp, // 23 PD5/AIN5 + PIN6_bp, // 24 PD6/AIN6 + PIN7_bp, // 25 PD7/AIN7/AREF + PIN6_bp // 26 PF6 RESET +}; + +/* Use this for accessing PINnCTRL register */ +const uint8_t digital_pin_to_bit_mask[] = { + PIN0_bm, // 0 PF0/USART2_Tx/TOSC1 + PIN1_bm, // 1 PF1/USART2_Rx/TOSC2 + PIN0_bm, // 2 PA0/USART0_Tx/CLKIN + PIN1_bm, // 3 PA1/USART0_Rx + PIN2_bm, // 4 PA2/SDA + PIN3_bm, // 5 PA3/SCL + PIN4_bm, // 6 PA4/MOSI + PIN5_bm, // 7 PA5/MISO + PIN6_bm, // 8 PA6/SCK + PIN7_bm, // 9 PA7/SS/CLKOUT/LED_BUILTIN + PIN3_bm, // 10 PC3 + PIN0_bm, // 11 PC0/USART1_Tx + PIN1_bm, // 12 PC1/USART1_Rx + PIN2_bm, // 13 PC2 + PIN0_bm, // 14 PD0/AIN0 + PIN1_bm, // 15 PD1/AIN1 + PIN2_bm, // 16 PD2/AIN2 + PIN3_bm, // 17 PD3/AIN3 + PIN3_bm, // 18 PF3/AIN13 + PIN4_bm, // 19 PF4/AIN14/TCB0 PWM + PIN5_bm, // 20 PF5/AIN15/TCB1 PWM + PIN4_bm, // 21 PD4/AIN4 + PIN5_bm, // 22 PD5/AIN5 + PIN6_bm, // 23 PD6/AIN6 + PIN7_bm, // 24 PD7/AIN7/AREF + PIN2_bm, // 25 PF2/AIN12 + PIN6_bm // 26 PF6 RESET +}; + +const uint8_t digital_pin_to_timer[] = { + NOT_ON_TIMER, // 0 PF0/USART2_Tx/TOSC1 + NOT_ON_TIMER, // 1 PF1/USART2_Rx/TOSC2 + NOT_ON_TIMER, // 2 PA0/USART0_Tx/CLKIN + NOT_ON_TIMER, // 3 PA1/USART0_Rx +#if !defined(MILLIS_USE_TIMERB0) + TIMERB0, // 4 PA2/SDA +#else + NOT_ON_TIMER, // 4 PA2/SDA +#endif +#if !defined(MILLIS_USE_TIMERB1) + TIMERB1, // 5 PA3/SCL +#else + NOT_ON_TIMER, // 5 PA3/SCL +#endif + NOT_ON_TIMER, // 6 PA4/MOSI + NOT_ON_TIMER, // 7 PA5/MISO + NOT_ON_TIMER, // 8 PA6/SCK + NOT_ON_TIMER, // 9 PA7/SS/CLKOUT/LED_BUILTIN + NOT_ON_TIMER, // 10 PC3 +#if !defined(MILLIS_USE_TIMERB2) + TIMERB2, // 11 PC0/USART1_Tx +#else + NOT_ON_TIMER, // 11 PC0/USART1_Tx +#endif + NOT_ON_TIMER, // 12 PC1/USART1_Rx + NOT_ON_TIMER, // 13 PC2 + TIMERA0, // 14 PD0/AIN0 + TIMERA0, // 15 PD1/AIN1 + TIMERA0, // 16 PD2/AIN2 + TIMERA0, // 17 PD3/AIN3 + TIMERA0, // 18 PD4/AIN4 + NOT_ON_TIMER, // 19 PF2/AIN12 + NOT_ON_TIMER, // 20 PF3/AIN13 + NOT_ON_TIMER, // 21 PF4/AIN14 + NOT_ON_TIMER, // 22 PF5/AIN15 + TIMERA0, // 23 PD5/AIN5 + NOT_ON_TIMER, // 24 PD6/AIN6 + NOT_ON_TIMER, // 25 PD7/AIN7/AREF + NOT_ON_TIMER // 26 PF6 RESET +}; + +#endif + +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_USBVIRTUAL Serial + +void initVariant() __attribute__((weak)); +void initVariant() { } + +#endif From 7683567af9dd5aca164b1d00269f25653f3657bd Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 21 Jul 2021 08:15:03 +0200 Subject: [PATCH 259/351] Fix typo in timer pin mapping --- megaavr/variants/nano-4808/pins_arduino.h | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index 166e207..2a02555 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -329,11 +329,11 @@ const uint8_t digital_pin_to_timer[] = { TIMERA0, // 15 PD1/AIN1 TIMERA0, // 16 PD2/AIN2 TIMERA0, // 17 PD3/AIN3 - TIMERA0, // 18 PD4/AIN4 - NOT_ON_TIMER, // 19 PF2/AIN12 - NOT_ON_TIMER, // 20 PF3/AIN13 - NOT_ON_TIMER, // 21 PF4/AIN14 - NOT_ON_TIMER, // 22 PF5/AIN15 + NOT_ON_TIMER, // 18 PF2/AIN12 + NOT_ON_TIMER, // 19 PF3/AIN13 + NOT_ON_TIMER, // 20 PF4/AIN14 + NOT_ON_TIMER, // 21 PF5/AIN15 + TIMERA0, // 22 PD4/AIN4 TIMERA0, // 23 PD5/AIN5 NOT_ON_TIMER, // 24 PD6/AIN6 NOT_ON_TIMER, // 25 PD7/AIN7/AREF From f0d0edbd9b940e41cab9b670baff96214a2a21ee Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 21 Jul 2021 11:37:31 +0200 Subject: [PATCH 260/351] Fix pin mapping issue Caused some pin numbers to be ofset by one. #125 related --- megaavr/variants/nano-4808/pins_arduino.h | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index 2a02555..0636e5a 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -287,14 +287,14 @@ const uint8_t digital_pin_to_bit_mask[] = { PIN1_bm, // 15 PD1/AIN1 PIN2_bm, // 16 PD2/AIN2 PIN3_bm, // 17 PD3/AIN3 - PIN3_bm, // 18 PF3/AIN13 - PIN4_bm, // 19 PF4/AIN14/TCB0 PWM - PIN5_bm, // 20 PF5/AIN15/TCB1 PWM - PIN4_bm, // 21 PD4/AIN4 - PIN5_bm, // 22 PD5/AIN5 - PIN6_bm, // 23 PD6/AIN6 - PIN7_bm, // 24 PD7/AIN7/AREF - PIN2_bm, // 25 PF2/AIN12 + PIN2_bm, // 18 PF2/AIN12 + PIN3_bm, // 19 PF3/AIN13 + PIN4_bm, // 20 PF4/AIN14/TCB0 PWM + PIN5_bm, // 21 PF5/AIN15/TCB1 PWM + PIN4_bm, // 22 PD4/AIN4 + PIN5_bm, // 23 PD5/AIN5 + PIN6_bm, // 24 PD6/AIN6 + PIN7_bm, // 25 PD7/AIN7/AREF PIN6_bm // 26 PF6 RESET }; From 40afdd797505eab1d7e5a04ef5f95ef8369a08f6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 21 Jul 2021 11:47:44 +0200 Subject: [PATCH 261/351] Update Nano 4808 description --- README.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/README.md b/README.md index 4f72277..f23bcaa 100644 --- a/README.md +++ b/README.md @@ -337,8 +337,7 @@ Click to enlarge: ### Nano 4808 -The Nano 4808, also known as the Thinary Nano 4808 a third party Arduino compatible board with the Nano form factor. It uses an ATmega4808 and the *only* supported pinout is *Nano 4808*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano 4808 does not support a bootloader, so select *No bootloader* in the tools menu. Burning bootloader or upload using programmer will not work either. However, all fuses are set every time you upload our program. - +The Nano 4808, also known as the Thinary Nano 4808 a third-party Arduino compatible board with the Nano form factor. It uses an ATmega4808 and the *only* supported pinout is *Nano 4808*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. The Nano 4808 does not support a bootloader, so select *No bootloader* in the tools menu. The on-board JTAG2UPDI programmer is known to be difficult to enter programming mode when printing to the serial monitor. If you're having upload issues, connect a dedicated UPDI programmer to the UPDI pin, select it in the programmers menu and upload using the programmer. Click to enlarge: From 358e102c5afd74ca2ae212ec707cd4ffa5322ebc Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 21 Jul 2021 11:49:19 +0200 Subject: [PATCH 262/351] Rename mEDBG and nEDBG programmers --- megaavr/programmers.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index 2305629..beb2180 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -1,18 +1,18 @@ -medbg.name=Atmel mEDBG (ATmega32u4) +medbg.name=Atmel mEDBG/microUPDI medbg.communication=usb medbg.protocol=xplainedmini_updi medbg.program.protocol=xplainedmini_updi medbg.program.tool=avrdude medbg.program.extra_params=-Pusb -nedbg.name=Atmel nEDBG (ATSAMD21E18) +nedbg.name=Atmel nEDBG/Curiosity Nano nedbg.communication=usb nedbg.protocol=curiosity_updi nedbg.program.protocol=curiosity_updi nedbg.program.tool=avrdude nedbg.program.extra_params=-Pusb -edbg.name=Atmel EDBG (AT32UC3A4256) +edbg.name=Atmel EDBG edbg.communication=usb edbg.protocol=xplainedpro_updi edbg.program.protocol=xplainedpro_updi From aa802ba0efe7fb7e07a1e0e1bb447b2543edcfb0 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 21 Aug 2021 23:38:51 +0200 Subject: [PATCH 263/351] Update Event library --- megaavr/libraries/Event/README.md | 126 +++++- .../Read_event_settings.ino | 6 +- .../examples/Simple_event/Simple_event.ino | 4 +- megaavr/libraries/Event/keywords.txt | 9 +- megaavr/libraries/Event/src/Event.cpp | 362 +++++++++++++++++- megaavr/libraries/Event/src/Event.h | 50 ++- 6 files changed, 511 insertions(+), 46 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index e9110d1..cc8ff32 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -1,6 +1,6 @@ # Event -A library for interfacing with the built-in Event system on the megaAVR-0 series MCUs. -Developed by [MCUdude](https://github.com/MCUdude/). +A library for interfacing with the built-in Event system on the megaAVR-0 series MCUs. +Developed by [MCUdude](https://github.com/MCUdude/). **From the datasheet:** > The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. @@ -9,7 +9,7 @@ More information about the Event system and how it works can be found in the [Mi ### Level vs. Pulse events -There are two types of events - a "pulse" interrupt, which lasts for the duration of a single clock cycle (either `CLK_PER` or a relevant (slower) clock - for example, the USART XCK generator provides a pulse event which lasts one XCK period, whuich is far slower than CLK_PER), or a "level" interrupt which lasts for the duration of some condition. +There are two types of events - a "pulse" interrupt, which lasts for the duration of a single clock cycle (either `CLK_PER` or a relevant (slower) clock - for example, the USART XCK generator provides a pulse event which lasts one XCK period, whuich is far slower than CLK_PER), or a "level" interrupt which lasts for the duration of some condition. Often for a given even generator or user only one or the other makes sense. Less often, for some reason or another, you may need a level event, but all you have is a pulse event - or the other way around. A [CCL module (Logic.h)](../Logic/README.md) event between the two at the cost of the logic module and one event channel. In the case of timer WO (PWM) channels, the CCL already has level inputs. @@ -24,10 +24,10 @@ At first glance, nore than half of the users and generators seem, at best, odd - ## Event -Class for interfacing with the built-in Event system. Each event generator channel has its own object. +Class for interfacing with the built-in Event system. Each event generator channel has its own object. Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make sure you use the right channel for the task. -In short terms: +In short terms: * `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels * `genN::rtc_div512`, `genN::rtc_div256`, `genN::rtc_div128` and `genN::rtc_div64` are only available on even numbered channels * PIN PA0..7 and PB0..5 can only be used as event generators on channel 0 and 1 @@ -44,17 +44,53 @@ uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channe ``` -## get_user_channel() -Function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also, note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. -An event generator can have multiple event users, but an event user can only have one event generator. +## get_channel() +Static function that returns the object associated with the passed channel number. Useful if you need to get the correct Event object based on an integer number. ### Usage ```c++ -uint8_t connected_to = Event::get_user_channel(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to +// Create a reference to the object get_channel() returns, which in this case will be the Event2 object +// myEvent can be futher used as a regular object +Event& myEvent = Event::get_channel(2); + +// Simple check to compare two objects +if(&myEvent == &Event2) +{ + // myEvent and Event2 is the same thing! +} ``` -## set_generator() +## get_generator_channel() +Static function that returns the object used for a particular event generator. Useful to figure out which channel or object a generator is connected to. +Returns a reference to the `Event_empty` object if the generator is not connected to any channel. + +### Usage +```c++ +// Set ccl0_out as event generator for channel 2 +Event2.set_generator(gen::ccl0_out); + +// Now we want to get the channel/object connected to the ccl0_out generator +// Create a reference to the object get_generator_channel() returns. +Event& myEvent = Event::get_generator_channel(gen::ccl0_out); + +// myEvent is now a reference to Event2! +``` + + +## get_generator() +Function to get the generator used for a particular channel. + +### Usage +```c++ +uint8_t generator_used = Event0.get_generator(); +if(generator_used == gen::ccl0_out) { + Serial.println("We're using gen::ccl0_out as generator"); +} +``` + + +## set_generator(gen::generator_t) Function to assign an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. ### Usage @@ -95,15 +131,45 @@ Below is a table with all possible generators for each channel. | `gen::tcb3_capt` | | | | | | | | | -## get_generator() -Function to get the generator used for a particular channel. +## set_generator(uint8_t pin_number) +Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [set_generator_pin()](#set_generator_pin) instead.** ### Usage ```c++ -uint8_t generator_used = Event0.get_generator(); -if(generator_used == gen::ccl0_out) { - Serial.println("We're using gen::ccl0_out as generator"); -} +Event0.set_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 +Event1.set_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an event generator for channel 1 +``` + + +## set_generator_pin(uint8_t pin_number) +Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` if the pin can't be assigned to a channel. + +### Usage +```c++ +// We're using PIN_PE2 as event generator, and the library finds a suited object +Event& myEvent = Event::set_generator_pin(PIN_PE2); + +// The myEvent object can be used directly +myEvent.start(); +``` + + +## get_user_channel_number() +Static function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also, note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. +An event generator can have multiple event users, but an event user can only have one event generator. + +### Usage +```c++ +uint8_t connected_to = Event::get_user_channel_number(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to +``` + + +## get_user_channel() +Static function that returns the Event channel object a particular user is connected to. Returns a referece to the `Event_empty` object if not connected to any event channel. + +### Usage +```c++ +Event& myEvent = Event::get_user_channel(user::ccl0_event_a); ``` @@ -118,7 +184,7 @@ Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user ``` ### User table -Below is a table with all possible event users. +Below is a table with all possible event users. Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` | Event users | Notes | @@ -152,6 +218,28 @@ Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is | `user::tcb3` | | +## set_user_pin(uint8_t pin_number) +Function to set an Arduino pin as an event user. Note that only some pins can be used for this. See table below for more details + +### Usage +```c++ +Event0.set_user_pin(PIN_PA2); +``` + +### Arduino pin table +| Event pin users | Notes | +|-----------------|----------------------------------------------------------------------------------------------------------| +| PIN_PA2 | | +| PIN_PA7 | Pin swapped variant of PIN_PA2. Cannot be used in combination with PIN_PA2 | +| PIN_PB2 | Only available on ATmegaX809 | +| PIN_PC2 | | +| PIN_PC7 | Pin swapped variant of PIN_PC2. Cannot be used in combination with PIN_PC2. Only available on ATmegaX809 | +| PIN_PD2 | | +| PIN_PD7 | Pin swapped variant of PIN_PD2. Cannot be used in combination with PIN_PD2 | +| PIN_PE2 | Only available on ATmegaX809 | +| PIN_PF2 | Not available on 28-pin parts | + + ## clear_user() Function to detach a user from a channel. Note that you don't need to know what channel to detach from, simply use `Event::clear_user()`. @@ -162,8 +250,8 @@ Event::clear_user(user::evouta); // Remove the user::evouta from whatever event ## soft_event() -Creates a single software event - users connected to that channel will react to it in the same way as they would to one caused by the generator the channel is connected to. -Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! +Creates a single software event - users connected to that channel will react to it in the same way as they would to one caused by the generator the channel is connected to. +Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! The software events will invert the channel, and so will trigger something regardless of whether it needs a the event channel to go high or low. ### Usage diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 9d23543..92dd49f 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -7,9 +7,9 @@ | Developed in 2021 by MCUdude | | https://github.com/MCUdude/ | | | -| In this example, we demonstrate the possibilities of reading out what | -| event channel we're working with, what generator is used, and which | -| channel an event user has been connected to. | +| In this example, we demonstrate the possibilities of reading out | +| which event channel we're working with, which generator is used, and | +| whichchannel an event user has been connected to. | | | | See Microchip's application note AN2451 for more information. | |***********************************************************************/ diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index 1a2d8a3..77aa0eb 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -7,7 +7,7 @@ | Developed in 2021 by MCUdude | | https://github.com/MCUdude/ | | | -| In this example we use pin PA7 as an event generator, and pin PC2 and | +| In this example we use pin PE0 as an event generator, and pin PC2 and | | PD2 as event users. In practice, pin PC2 and PD2 will follow | | PE0's state. | | | @@ -20,7 +20,7 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event4.set_generator(gen0::pin_pa7); // Set pin PA7 as event generator + Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet Event4.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index cacc12b..c6a2391 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -11,10 +11,15 @@ # Methods and Functions (KEYWORD2) ####################################### get_channel_number KEYWORD2 -get_user_channel KEYWORD2 -set_generator KEYWORD2 +get_channel KEYWORD2 +get_generator_channel KEYWORD2 get_generator KEYWORD2 +set_generator KEYWORD2 +set_generator_pin KEYWORD2 +get_user_channel_number KEYWORD2 +get_user_channel KEYWORD2 set_user KEYWORD2 +set_user_pin KEYWORD2 clear_user KEYWORD2 soft_event KEYWORD2 start KEYWORD2 diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 4163099..dd34e53 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -3,6 +3,7 @@ // Pre-defined objects #if defined(EVSYS_CHANNEL0) Event Event0(0, EVSYS_CHANNEL0); + Event Event_empty(255, EVSYS_CHANNEL0); #endif #if defined(EVSYS_CHANNEL1) Event Event1(1, EVSYS_CHANNEL1); @@ -57,18 +58,125 @@ uint8_t Event::get_channel_number() /** - * @brief Returns the Event channel number a particular user is connected to + * @brief Returns the object associated with the passed channel number * - * @param event_user The event user to check - * @return int8_t Event channel number. Returns -1 if not connected to any event channel + * @param ch_number Channel number + * @return Event& Event object associated with the channel number. + * Returns the Event_empty object if invalid channel number */ -int8_t Event::get_user_channel(user::user_t event_user) +Event& Event::get_channel(uint8_t ch_number) { - // Figure out what user register to read from to based on the passed parameter - volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + #if defined(EVSYS_CHANNEL0) + if(Event0.channel_number == ch_number) + return Event0; + #endif + #if defined(EVSYS_CHANNEL1) + if(Event1.channel_number == ch_number) + return Event1; + #endif + #if defined(EVSYS_CHANNEL2) + if(Event2.channel_number == ch_number) + return Event2; + #endif + #if defined(EVSYS_CHANNEL3) + if(Event3.channel_number == ch_number) + return Event3; + #endif + #if defined(EVSYS_CHANNEL4) + if(Event4.channel_number == ch_number) + return Event4; + #endif + #if defined(EVSYS_CHANNEL5) + if(Event5.channel_number == ch_number) + return Event5; + #endif + #if defined(EVSYS_CHANNEL6) + if(Event6.channel_number == ch_number) + return Event6; + #endif + #if defined(EVSYS_CHANNEL7) + if(Event7.channel_number == ch_number) + return Event7; + #endif + #if defined(EVSYS_CHANNEL8) + if(Event8.channel_number == ch_number) + return Event8; + #endif + #if defined(EVSYS_CHANNEL9) + if(Event9.channel_number == ch_number) + return Event9; + #endif - // Return what channel the user is connected to - return *user_register - 1; + #if defined(EVSYS_CHANNEL0) + else + return Event_empty; + #endif +} + +/** + * @brief Returns the event channel object used for a particular event generator + * + * @param generator Event generator + * @return Event& Event channel object used with this event generator + */ +Event& Event::get_generator_channel(uint8_t generator) +{ + #if defined(EVSYS_CHANNEL0) + if(Event0.generator_type == generator) + return Event0; + #endif + #if defined(EVSYS_CHANNEL1) + if(Event1.generator_type == generator) + return Event1; + #endif + #if defined(EVSYS_CHANNEL2) + if(Event2.generator_type == generator) + return Event2; + #endif + #if defined(EVSYS_CHANNEL3) + if(Event3.generator_type == generator) + return Event3; + #endif + #if defined(EVSYS_CHANNEL4) + if(Event4.generator_type == generator) + return Event4; + #endif + #if defined(EVSYS_CHANNEL5) + if(Event5.generator_type == generator) + return Event5; + #endif + #if defined(EVSYS_CHANNEL6) + if(Event6.generator_type == generator) + return Event6; + #endif + #if defined(EVSYS_CHANNEL7) + if(Event7.generator_type == generator) + return Event7; + #endif + #if defined(EVSYS_CHANNEL8) + if(Event8.generator_type == generator) + return Event8; + #endif + #if defined(EVSYS_CHANNEL9) + if(Event9.generator_type == generator) + return Event9; + #endif + + #if defined(EVSYS_CHANNEL0) + else + return Event_empty; + #endif +} + + +/** + * @brief Returns the generator type a particular channel has + * + * @return uint8_t Generator type. Returns 0 if no generator is used + */ +uint8_t Event::get_generator() +{ + return generator_type; } @@ -79,21 +187,184 @@ int8_t Event::get_user_channel(user::user_t event_user) * Use gen:: for functionality present on all event channels. * Use genN:: for functionality present on channel N. */ -void Event::set_generator(uint8_t event_generator) +void Event::set_generator(gen::generator_t event_generator) { // Store event generator setting for use in start() and stop() - generator_type = event_generator; + generator_type = (uint8_t)event_generator; } /** - * @brief Returns the generator type a particular channel has + * @brief Function that lets you use an Arduino pin as event generator. + * Note that you'll have to manually keep track of which event channel + * objects to use to make sure the passed Arduino pin is supported. + * A different approach is to use Event::set_generator_pin(), which + * automatically picks the correct event channel for you. * - * @return uint8_t Generator type. Returns 0 if no generator is used + * @param pin_number Arduino pin number to use as event generator */ -uint8_t Event::get_generator() +void Event::set_generator(uint8_t pin_number) { - return generator_type; + uint8_t port = digitalPinToPort(pin_number); + uint8_t port_pin = digitalPinToBitPosition(pin_number); + + // Store event generator setting for use in start() and stop() + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) + generator_type = 0x40 | (port & 0x01) << 3 | port_pin; + else + generator_type = gen::disable; +} + +/** + * @brief Static member function that sets an Arduino pin number as event + * generator and returns the object it has select as event channel. + * It will always try to select the lowest channel number as possible. + * + * @param pin_number Arduino pin number to use as event generator + * @return Event& Event channel object used as the event channel. Returns the + * Event_empty object if passed Arduino pin is invalid or no event + * channel is available + */ +Event& Event::set_generator_pin(uint8_t pin_number) +{ + uint8_t port = digitalPinToPort(pin_number); + uint8_t port_pin = digitalPinToBitPosition(pin_number); + + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) + { + uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; + if(port == PA || port == PB) + { + if(Event0.generator_type == gen::disable) + { + Event0.generator_type = gen; + return Event0; + } + else if(Event1.generator_type == gen::disable) + { + Event1.generator_type = gen; + return Event1; + } + } + else if(port == PC || port == PD) + { + if(Event2.generator_type == gen::disable) + { + Event2.generator_type = gen; + return Event2; + } + else if(Event3.generator_type == gen::disable) + { + Event3.generator_type = gen; + return Event3; + } + } + else if(port == PE || port == PF) + { + if(Event4.generator_type == gen::disable) + { + Event4.generator_type = gen; + return Event4; + } + else if(Event5.generator_type == gen::disable) + { + Event5.generator_type = gen; + return Event5; + } + } + #if defined(Dx_64_PINS) + else if(port == PG) + { + if(Event6.generator_type == gen::disable) + { + Event6.generator_type = gen; + return Event6; + } + else if(Event7.generator_type == gen::disable) + { + Event7.generator_type = gen; + return Event7; + } + } + #endif + } + return Event_empty; +} + + +/** + * @brief Returns the Event channel number a particular user is connected to + * + * @param event_user The event user to check + * @return int8_t Event channel number. + * Returns -1 if not connected to any event channel + */ +int8_t Event::get_user_channel_number(user::user_t event_user) +{ + // Figure out what user register to read from to based on the passed parameter + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; + + // Return which channel the user is connected to + return *user_register - 1; +} + + +/** + * @brief Returns the Event channel object a particular user is connected to + * + * @param event_user The event user to check + * @return Event& Event channel object. Returns the Event_empty object if the + * user is not connected to any event channel + */ +Event& Event::get_user_channel(user::user_t event_user) +{ + int8_t ch_number = get_user_channel_number(event_user); + + #if defined(EVSYS_CHANNEL0) + if(Event0.channel_number == ch_number) + return Event0; + #endif + #if defined(EVSYS_CHANNEL1) + if(Event1.channel_number == ch_number) + return Event1; + #endif + #if defined(EVSYS_CHANNEL2) + if(Event2.channel_number == ch_number) + return Event2; + #endif + #if defined(EVSYS_CHANNEL3) + if(Event3.channel_number == ch_number) + return Event3; + #endif + #if defined(EVSYS_CHANNEL4) + if(Event4.channel_number == ch_number) + return Event4; + #endif + #if defined(EVSYS_CHANNEL5) + if(Event5.channel_number == ch_number) + return Event5; + #endif + #if defined(EVSYS_CHANNEL6) + if(Event6.channel_number == ch_number) + return Event6; + #endif + #if defined(EVSYS_CHANNEL7) + if(Event7.channel_number == ch_number) + return Event7; + #endif + #if defined(EVSYS_CHANNEL8) + if(Event8.channel_number == ch_number) + return Event8; + #endif + #if defined(EVSYS_CHANNEL9) + if(Event9.channel_number == ch_number) + return Event9; + #endif + + #if defined(EVSYS_CHANNEL0) + else + return Event_empty; + #endif } @@ -124,6 +395,69 @@ void Event::set_user(user::user_t event_user) } } +/** + * @brief Sets an Arduino pin as a user for a particular event channel + * + * @param pin_number The Arduino pin number to use as a channel user + * @return uint8_t Event channel user enum + (for instance user::evouta_pin_pa2 pin PIN_PA2 is passed) + * Returns -1 if invalid pin is passed + */ +int8_t Event::set_user_pin(uint8_t pin_number) +{ + uint8_t port = digitalPinToPort(pin_number); + uint8_t port_pin = digitalPinToBitPosition(pin_number); + + int8_t event_user = -1; + + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) + { + if(port == PA) + { + if(port_pin == 2) + event_user = user::evouta_pin_pa2; + else if(port_pin == 7) + event_user = user::evouta_pin_pa7; + } + #if defined(__AVR_ATmegax09__) + else if(port == PB) + { + if(port_pin == 2) + event_user = user::evoutb_pin_pb2; + } + #endif + else if(port == PC) + { + if(port_pin == 2) + event_user = user::evoutc_pin_pc2; + #if defined(__AVR_ATmegax09__) + else if(port_pin == 7) + event_user = user::evoutc_pin_pc7; + #endif + } + else if(port == PD) + { + if(port_pin == 2) + event_user = user::evoutd_pin_pd2; + else if(port_pin == 7) + event_user = user::evoutd_pin_pd7; + } + #if defined(__AVR_ATmegax09__) + else if(port == PE) + { + if(port_pin == 2) + event_user = user::evoute_pin_pe2; + } + #endif + else if(port == PF) + { + if(port_pin == 2) + event_user = user::evoutf_pin_pf2; + } + set_user((user::user_t)event_user); + } + return event_user; +} /** * @brief Clears/removed a user from a particular event channel if set diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 2d643ec..988e5c1 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -114,7 +114,7 @@ namespace gen pin_pb2 = 0x4A, pin_pb3 = 0x4B, pin_pb4 = 0x4C, - pin_pb5 = 0x4F, + pin_pb5 = 0x4D, #endif #if defined(Dx_64_PINS) pin_pb6 = 0x4E, @@ -150,7 +150,7 @@ namespace gen pin_pb2 = 0x4A, pin_pb3 = 0x4B, pin_pb4 = 0x4C, - pin_pb5 = 0x4F, + pin_pb5 = 0x4D, #endif #if defined(Dx_64_PINS) pin_pb6 = 0x4E, @@ -187,7 +187,7 @@ namespace gen pin_pd2 = 0x4A, pin_pd3 = 0x4B, pin_pd4 = 0x4C, - pin_pd5 = 0x4F, + pin_pd5 = 0x4D, pin_pd6 = 0x4E, pin_pd7 = 0x4F, }; @@ -221,7 +221,7 @@ namespace gen pin_pd2 = 0x4A, pin_pd3 = 0x4B, pin_pd4 = 0x4C, - pin_pd5 = 0x4F, + pin_pd5 = 0x4D, pin_pd6 = 0x4E, pin_pd7 = 0x4F, }; @@ -612,10 +612,48 @@ class Event public: Event(uint8_t channel_num, volatile uint8_t &channel_addr); uint8_t get_channel_number(); - static int8_t get_user_channel(user::user_t event_user); - void set_generator(uint8_t generator); + static Event& get_channel(uint8_t channel_number); + static Event& get_generator_channel(uint8_t generator); uint8_t get_generator(); + void set_generator(gen::generator_t generator); + void set_generator(uint8_t pin_number); + static Event& set_generator_pin(uint8_t pin_number); + + #if defined(EVSYS_CHANNEL0) + void set_generator(gen0::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL1) + void set_generator(gen1::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL2) + void set_generator(gen2::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL3) + void set_generator(gen3::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL4) + void set_generator(gen4::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL5) + void set_generator(gen5::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL6) + void set_generator(gen6::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL7) + void set_generator(gen7::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL8) + void set_generator(gen8::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + #if defined(EVSYS_CHANNEL9) + void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif + + static int8_t get_user_channel_number(user::user_t event_user); + static Event& get_user_channel(user::user_t event_user); void set_user(user::user_t event_user); + int8_t set_user_pin(uint8_t pin_number); static void clear_user(user::user_t event_user); void soft_event(); void start(bool state = true); From fe237a250607cb6814954ff7976a3942d24a4eb3 Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 24 Aug 2021 20:42:11 +0200 Subject: [PATCH 264/351] Add function declarations --- megaavr/libraries/Event/README.md | 84 +++++++++++++++++++++++++++++-- 1 file changed, 81 insertions(+), 3 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index cc8ff32..ea70275 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -25,7 +25,7 @@ At first glance, nore than half of the users and generators seem, at best, odd - ## Event Class for interfacing with the built-in Event system. Each event generator channel has its own object. -Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Note that channels have different functionality, so make sure you use the right channel for the task. +Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Refer to static functions by using `Event::`. Note that different channels have different functionality, so make sure you use the right channel for the task. In short terms: * `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels @@ -38,6 +38,11 @@ In short terms: ## get_channel_number() Function to get the current channel number. Useful if the channel object has been passed to a function as reference. +### Declaration +``` c++ +uint8_t get_channel_number(); +``` + ### Usage ``` c++ uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channel_number will return 0 @@ -47,6 +52,11 @@ uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channe ## get_channel() Static function that returns the object associated with the passed channel number. Useful if you need to get the correct Event object based on an integer number. +### Declaration +``` c++ +static Event& get_channel(uint8_t channel_number); +``` + ### Usage ```c++ // Create a reference to the object get_channel() returns, which in this case will be the Event2 object @@ -65,6 +75,11 @@ if(&myEvent == &Event2) Static function that returns the object used for a particular event generator. Useful to figure out which channel or object a generator is connected to. Returns a reference to the `Event_empty` object if the generator is not connected to any channel. +### Declaration +``` c++ +static Event& get_generator_channel(uint8_t generator); +``` + ### Usage ```c++ // Set ccl0_out as event generator for channel 2 @@ -81,6 +96,11 @@ Event& myEvent = Event::get_generator_channel(gen::ccl0_out); ## get_generator() Function to get the generator used for a particular channel. +### Declaration +``` c++ +uint8_t get_generator(); +``` + ### Usage ```c++ uint8_t generator_used = Event0.get_generator(); @@ -93,6 +113,14 @@ if(generator_used == gen::ccl0_out) { ## set_generator(gen::generator_t) Function to assign an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. +### Declaration +``` c++ +void set_generator(gen::generator_t generator); +void set_generator(gen0::generator_t generator); +//... +void set_generator(gen7::generator_t generator); +``` + ### Usage ```c++ Event0.set_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 @@ -134,6 +162,11 @@ Below is a table with all possible generators for each channel. ## set_generator(uint8_t pin_number) Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [set_generator_pin()](#set_generator_pin) instead.** +### Declaration +``` c++ +void set_generator(uint8_t pin_number); +``` + ### Usage ```c++ Event0.set_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 @@ -141,9 +174,14 @@ Event1.set_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an even ``` -## set_generator_pin(uint8_t pin_number) +## set_generator_pin() Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` if the pin can't be assigned to a channel. +### Declaration +``` c++ +static Event& set_generator_pin(uint8_t pin_number); +``` + ### Usage ```c++ // We're using PIN_PE2 as event generator, and the library finds a suited object @@ -158,15 +196,25 @@ myEvent.start(); Static function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also, note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. An event generator can have multiple event users, but an event user can only have one event generator. +### Declaration +``` c++ +static int8_t get_user_channel_number(user::user_t event_user); +``` + ### Usage ```c++ -uint8_t connected_to = Event::get_user_channel_number(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to +int8_t connected_to = Event::get_user_channel_number(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to ``` ## get_user_channel() Static function that returns the Event channel object a particular user is connected to. Returns a referece to the `Event_empty` object if not connected to any event channel. +### Declaration +``` c++ +static Event& get_user_channel(user::user_t event_user); +``` + ### Usage ```c++ Event& myEvent = Event::get_user_channel(user::ccl0_event_a); @@ -176,6 +224,11 @@ Event& myEvent = Event::get_user_channel(user::ccl0_event_a); ## set_user() Function to connect an event user to an event generator. Note that a generator can have multiple users. +### Declaration +``` c++ +void set_user(user::user_t event_user); +``` + ### Usage ```c++ Event0.set_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 @@ -221,6 +274,11 @@ Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is ## set_user_pin(uint8_t pin_number) Function to set an Arduino pin as an event user. Note that only some pins can be used for this. See table below for more details +### Declaration +``` c++ +int8_t set_user_pin(uint8_t pin_number); +``` + ### Usage ```c++ Event0.set_user_pin(PIN_PA2); @@ -243,6 +301,11 @@ Event0.set_user_pin(PIN_PA2); ## clear_user() Function to detach a user from a channel. Note that you don't need to know what channel to detach from, simply use `Event::clear_user()`. +### Declaration +``` c++ +static void clear_user(user::user_t event_user); +``` + ### Usage ```c++ Event::clear_user(user::evouta); // Remove the user::evouta from whatever event channel it is connected to @@ -254,6 +317,11 @@ Creates a single software event - users connected to that channel will react to Great if you have to force trigger something. Note that a software event only lasts a single system clock cycle, so it's rather fast! The software events will invert the channel, and so will trigger something regardless of whether it needs a the event channel to go high or low. +### Declaration +``` c++ +void soft_event(); +``` + ### Usage ```c++ Event0.soft_event(); // Create a single software event on Event0 @@ -263,6 +331,11 @@ Event0.soft_event(); // Create a single software event on Event0 ## start() Starts an event generator channel by writing the generator selected by `set_generator()` function. +### Declaration +``` c++ +void start(bool state = true); +``` + ### Usage ```c++ Event0.start(); // Starts the Event0 generator channel @@ -272,6 +345,11 @@ Event0.start(); // Starts the Event0 generator channel ## stop() Stops an event generator channel. The `Eventn` object retains memory of what generator it was previously set to. +### Declaration +``` c++ +void stop(); +``` + ### Usage ```c++ Event0.stop(); // Stops the Event0 generator channel From 1337691a7e624e74620a112d157bb4262e440129 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Sep 2021 21:11:31 +0200 Subject: [PATCH 265/351] Fix analogRead issue for 32-pin parts Closes #128 --- megaavr/cores/coreX-corefiles/wiring_analog.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 2d3674a..5305d72 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -54,7 +54,7 @@ void analogReference(uint8_t mode) int analogRead(uint8_t pin) { pin = digitalPinToAnalogInput(pin); - if (pin > NUM_ANALOG_INPUTS) + if (pin > 15) return NOT_A_PIN; #if defined(ADC0) From 702154ee56a85aa47b3e9528a6ee26d2be5bb14d Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Sep 2021 19:24:03 +0200 Subject: [PATCH 266/351] Add more info about the Event_empty object --- megaavr/libraries/Event/README.md | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index ea70275..6ce60db 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -26,6 +26,8 @@ At first glance, nore than half of the users and generators seem, at best, odd - ## Event Class for interfacing with the built-in Event system. Each event generator channel has its own object. Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Refer to static functions by using `Event::`. Note that different channels have different functionality, so make sure you use the right channel for the task. +`Event_empty` is an object that's used to indicate if an event user isn't connected to an event channel and the user program requests an object. + In short terms: * `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels @@ -36,7 +38,7 @@ In short terms: ## get_channel_number() -Function to get the current channel number. Useful if the channel object has been passed to a function as reference. +Function to get the current channel number. Useful if the channel object has been passed to a function as reference. The `Event_empty` object has channel number 255. ### Declaration ``` c++ @@ -175,7 +177,7 @@ Event1.set_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an even ## set_generator_pin() -Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` if the pin can't be assigned to a channel. +Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` (generator number 255) if the pin can't be assigned to a channel. ### Declaration ``` c++ From 1d9de4f9881742d49d2b8a75b1700efeac5162c0 Mon Sep 17 00:00:00 2001 From: Pan Ziyue Date: Sun, 24 Oct 2021 13:10:47 +0800 Subject: [PATCH 267/351] added fuse configurations for Nano Every --- megaavr/platform.txt | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index bab0837..93480f2 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -143,6 +143,16 @@ tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} -e {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude_nanoevery.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse2="-Ufuse2:w:{bootloader.OSCCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse4="-Ufuse4:w:{bootloader.TCD0CFG}:m" +tools.avrdude_nanoevery.bootloader.fuse5="-Ufuse5:w:{bootloader.SYSCFG0}:m" +tools.avrdude_nanoevery.bootloader.fuse6="-Ufuse6:w:{bootloader.SYSCFG1}:m" +tools.avrdude_nanoevery.bootloader.fuse7="-Ufuse7:w:{bootloader.APPEND}:m" +tools.avrdude_nanoevery.bootloader.fuse8="-Ufuse8:w:{bootloader.BOOTEND}:m" +tools.avrdude_nanoevery.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" + tools.avrdude.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" tools.avrdude.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" tools.avrdude.bootloader.fuse2="-Ufuse2:w:{bootloader.OSCCFG}:m" From 4b920a4006af545962437f36e37254f41fc128d1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 27 Oct 2021 21:52:14 +0200 Subject: [PATCH 268/351] Update Event library Minor formatting and typo fixes. Rename set_generator and set_generator_pin to assign_generator and assign_generator_pin. #126 related --- megaavr/libraries/Event/README.md | 36 ++++++------ .../Read_event_settings.ino | 4 +- .../Route_logic_pins/Route_logic_pins.ino | 20 +++---- .../examples/Simple_event/Simple_event.ino | 2 +- megaavr/libraries/Event/keywords.txt | 6 +- megaavr/libraries/Event/src/Event.cpp | 58 ++++++++++++------- megaavr/libraries/Event/src/Event.h | 31 +++++----- 7 files changed, 88 insertions(+), 69 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 6ce60db..5c06fbb 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -85,7 +85,7 @@ static Event& get_generator_channel(uint8_t generator); ### Usage ```c++ // Set ccl0_out as event generator for channel 2 -Event2.set_generator(gen::ccl0_out); +Event2.assign_generator(gen::ccl0_out); // Now we want to get the channel/object connected to the ccl0_out generator // Create a reference to the object get_generator_channel() returns. @@ -112,21 +112,21 @@ if(generator_used == gen::ccl0_out) { ``` -## set_generator(gen::generator_t) +## assign_generator(gen::generator_t) Function to assign an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. ### Declaration ``` c++ -void set_generator(gen::generator_t generator); -void set_generator(gen0::generator_t generator); +void assign_generator(gen::generator_t generator); +void assign_generator(gen0::generator_t generator); //... -void set_generator(gen7::generator_t generator); +void assign_generator(gen7::generator_t generator); ``` ### Usage ```c++ -Event0.set_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 -Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 +Event0.assign_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 +Event2.assign_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 ``` ### Generator table @@ -161,33 +161,33 @@ Below is a table with all possible generators for each channel. | `gen::tcb3_capt` | | | | | | | | | -## set_generator(uint8_t pin_number) -Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [set_generator_pin()](#set_generator_pin) instead.** +## assign_generator(uint8_t pin_number) +Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [assign_generator_pin()](#assign_generator_pin) instead.** ### Declaration ``` c++ -void set_generator(uint8_t pin_number); +void assign_generator(uint8_t pin_number); ``` ### Usage ```c++ -Event0.set_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 -Event1.set_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an event generator for channel 1 +Event0.assign_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 +Event1.assign_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an event generator for channel 1 ``` -## set_generator_pin() -Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` (generator number 255) if the pin can't be assigned to a channel. +## assign_generator_pin() +Static function that sets an Arduino pin as the event generator. Unlike assign_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` (generator number 255) if the pin can't be assigned to a channel. ### Declaration ``` c++ -static Event& set_generator_pin(uint8_t pin_number); +static Event& assign_generator_pin(uint8_t pin_number); ``` ### Usage ```c++ // We're using PIN_PE2 as event generator, and the library finds a suited object -Event& myEvent = Event::set_generator_pin(PIN_PE2); +Event& myEvent = Event::assign_generator_pin(PIN_PE2); // The myEvent object can be used directly myEvent.start(); @@ -233,7 +233,7 @@ void set_user(user::user_t event_user); ### Usage ```c++ -Event0.set_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 +Event0.assign_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 Event0.set_user(user::evoutc); // Set EVOUTC (pin PC2) as event user Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user ``` @@ -331,7 +331,7 @@ Event0.soft_event(); // Create a single software event on Event0 ## start() -Starts an event generator channel by writing the generator selected by `set_generator()` function. +Starts an event generator channel by writing the generator selected by the `assign_generator()` function. ### Declaration ``` c++ diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 92dd49f..6ea7d46 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -34,8 +34,8 @@ void setup() { Serial2.begin(9600); // Initialize hardware serial port - Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator - Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator + Event1.assign_generator(gen0::pin_pa3); // Set pin PA3 as event generator + Event2.assign_generator(gen2::pin_pc3); // Set pin PC3 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet Event1.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user diff --git a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino index fce8b84..43df811 100644 --- a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino +++ b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino @@ -35,18 +35,18 @@ void setup() { // Initialize Event channel 2 and 3 - Event2.set_generator(gen2::pin_pc0); // Set pin PC0 as event generator - Event3.set_generator(gen3::pin_pc1); // Set pin PC1 as event generator - Event2.set_user(user::ccl0_event_a); // Set CCL0 (Logic0) event A as user - Event3.set_user(user::ccl0_event_b); // Set CCL0 (Logic0) event B as user + Event2.assign_generator(gen2::pin_pc0); // Set pin PC0 as event generator + Event3.assign_generator(gen3::pin_pc1); // Set pin PC1 as event generator + Event2.set_user(user::ccl0_event_a); // Set CCL0 (Logic0) event A as user + Event3.set_user(user::ccl0_event_b); // Set CCL0 (Logic0) event B as user // Initialize logic block 0 - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::event_a; // Connect input 0 to ccl0_event_a (PC0 through Event2) - Logic0.input1 = in::event_b; // Connect input 0 to ccl0_event_b (PC1 through Event3) - Logic0.input2 = in::input; // Set PA2 as input - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.truth = 0x80; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = in::event_a; // Connect input 0 to ccl0_event_a (PC0 through Event2) + Logic0.input1 = in::event_b; // Connect input 0 to ccl0_event_b (PC1 through Event3) + Logic0.input2 = in::input; // Set PA2 as input + Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) + Logic0.truth = 0x80; // Set truth table Logic0.init(); // Start event channels and the logic hardware diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index 77aa0eb..c41d42f 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -20,7 +20,7 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator + Event4.assign_generator(gen4::pin_pe0); // Set pin PE0 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet Event4.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index c6a2391..47c68c4 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -1,5 +1,5 @@ ####################################### -# Syntax Coloring Map For Wire +# Syntax Coloring Map For Event ####################################### ####################################### @@ -14,8 +14,8 @@ get_channel_number KEYWORD2 get_channel KEYWORD2 get_generator_channel KEYWORD2 get_generator KEYWORD2 -set_generator KEYWORD2 -set_generator_pin KEYWORD2 +assign_generator KEYWORD2 +assign_generator_pin KEYWORD2 get_user_channel_number KEYWORD2 get_user_channel KEYWORD2 set_user KEYWORD2 diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index dd34e53..60f5f89 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -113,6 +113,7 @@ Event& Event::get_channel(uint8_t ch_number) #endif } + /** * @brief Returns the event channel object used for a particular event generator * @@ -187,7 +188,7 @@ uint8_t Event::get_generator() * Use gen:: for functionality present on all event channels. * Use genN:: for functionality present on channel N. */ -void Event::set_generator(gen::generator_t event_generator) +void Event::assign_generator(gen::generator_t event_generator) { // Store event generator setting for use in start() and stop() generator_type = (uint8_t)event_generator; @@ -198,12 +199,12 @@ void Event::set_generator(gen::generator_t event_generator) * @brief Function that lets you use an Arduino pin as event generator. * Note that you'll have to manually keep track of which event channel * objects to use to make sure the passed Arduino pin is supported. - * A different approach is to use Event::set_generator_pin(), which + * A different approach is to use Event::assign_generator_pin(), which * automatically picks the correct event channel for you. * * @param pin_number Arduino pin number to use as event generator */ -void Event::set_generator(uint8_t pin_number) +void Event::assign_generator(uint8_t pin_number) { uint8_t port = digitalPinToPort(pin_number); uint8_t port_pin = digitalPinToBitPosition(pin_number); @@ -215,32 +216,31 @@ void Event::set_generator(uint8_t pin_number) generator_type = gen::disable; } + /** - * @brief Static member function that sets an Arduino pin number as event + * @brief Static member function that sets a port pin as event * generator and returns the object it has select as event channel. * It will always try to select the lowest channel number as possible. * - * @param pin_number Arduino pin number to use as event generator + * @param port Port to use as event generator + * @param port_pin Pin number on port to use as event generator * @return Event& Event channel object used as the event channel. Returns the * Event_empty object if passed Arduino pin is invalid or no event * channel is available */ -Event& Event::set_generator_pin(uint8_t pin_number) +Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { - uint8_t port = digitalPinToPort(pin_number); - uint8_t port_pin = digitalPinToBitPosition(pin_number); - if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; if(port == PA || port == PB) { - if(Event0.generator_type == gen::disable) + if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } - else if(Event1.generator_type == gen::disable) + else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; @@ -248,12 +248,12 @@ Event& Event::set_generator_pin(uint8_t pin_number) } else if(port == PC || port == PD) { - if(Event2.generator_type == gen::disable) + if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } - else if(Event3.generator_type == gen::disable) + else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; @@ -261,12 +261,12 @@ Event& Event::set_generator_pin(uint8_t pin_number) } else if(port == PE || port == PF) { - if(Event4.generator_type == gen::disable) + if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } - else if(Event5.generator_type == gen::disable) + else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) { Event5.generator_type = gen; return Event5; @@ -275,12 +275,12 @@ Event& Event::set_generator_pin(uint8_t pin_number) #if defined(Dx_64_PINS) else if(port == PG) { - if(Event6.generator_type == gen::disable) + if(Event6.generator_type == gen::disable || Event6.generator_type == gen) { Event6.generator_type = gen; return Event6; } - else if(Event7.generator_type == gen::disable) + else if(Event7.generator_type == gen::disable || Event7.generator_type == gen) { Event7.generator_type = gen; return Event7; @@ -292,6 +292,24 @@ Event& Event::set_generator_pin(uint8_t pin_number) } +/** + * @brief Static member function that sets an Arduino pin as event + * generator and returns the object it has select as event channel. + * It will always try to select the lowest channel number as possible. + * + * @param pin_number Arduino pin number to use as event generator + * @return Event& Event channel object used as the event channel. Returns the + * Event_empty object if passed Arduino pin is invalid or no event + * channel is available + */ +Event& Event::assign_generator_pin(uint8_t pin_number) +{ + uint8_t port = digitalPinToPort(pin_number); + uint8_t port_pin = digitalPinToBitPosition(pin_number); + return Event::assign_generator_pin(port, port_pin); +} + + /** * @brief Returns the Event channel number a particular user is connected to * @@ -383,7 +401,7 @@ void Event::set_user(user::user_t event_user) *user_register = channel_number + 1; // Set PORTMUX pin swap for EVOUT if selected as channel generator - if (event_user & 0x80) + if(event_user & 0x80) { #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); @@ -474,7 +492,7 @@ void Event::clear_user(user::user_t event_user) *user_register = 0x00; // Clear PORTMUX pin swap for EVOUT if selected as channel generator - if (event_user & 0x80) + if(event_user & 0x80) { #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); @@ -521,7 +539,7 @@ void Event::soft_event() */ void Event::start(bool state) { - if (state) + if(state) { // Write event generator setting to EVSYS_CHANNELn register channel_address = generator_type; diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 988e5c1..781e452 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -81,7 +81,7 @@ namespace gen mvio_ok = 0x05, opamp0_ready = 0x34, opamp1_ready = 0x35, -#if defined (OPAMP2) +#if defined(OPAMP2) opamp2_ready = 0x36, #endif #endif // defined(__AVR_DB__) @@ -460,7 +460,7 @@ namespace user #if !defined(Dx_28_PINS) evoutf_pin_pf2 = 0x13, #endif -#if defined (Dx_64_PINS) +#if defined(Dx_64_PINS) evoutg_pin_pg2 = 0x14, #endif usart0_irda = 0x15, @@ -615,39 +615,40 @@ class Event static Event& get_channel(uint8_t channel_number); static Event& get_generator_channel(uint8_t generator); uint8_t get_generator(); - void set_generator(gen::generator_t generator); - void set_generator(uint8_t pin_number); - static Event& set_generator_pin(uint8_t pin_number); + void assign_generator(gen::generator_t generator); + void assign_generator(uint8_t pin_number); + static Event& assign_generator_pin(uint8_t port, uint8_t port_pin); + static Event& assign_generator_pin(uint8_t pin_number); #if defined(EVSYS_CHANNEL0) - void set_generator(gen0::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen0::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL1) - void set_generator(gen1::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen1::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL2) - void set_generator(gen2::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen2::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL3) - void set_generator(gen3::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen3::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL4) - void set_generator(gen4::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen4::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL5) - void set_generator(gen5::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen5::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL6) - void set_generator(gen6::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen6::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL7) - void set_generator(gen7::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen7::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL8) - void set_generator(gen8::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen8::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL9) - void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } + void assign_generator(gen9::generator_t generator) { assign_generator((gen::generator_t)generator); } #endif static int8_t get_user_channel_number(user::user_t event_user); From 40be2383aaba019b24e2bb5fef7875c97bc94729 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 4 Dec 2021 13:33:32 +0100 Subject: [PATCH 269/351] Add GCC printf formatting checks --- megaavr/cores/coreX-corefiles/api/Print.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/Print.h b/megaavr/cores/coreX-corefiles/api/Print.h index b771739..f1498ef 100644 --- a/megaavr/cores/coreX-corefiles/api/Print.h +++ b/megaavr/cores/coreX-corefiles/api/Print.h @@ -82,7 +82,7 @@ class Print size_t println(const Printable&); size_t println(void); - int16_t printf(const char *format, ...); + int16_t printf(const char *format, ...) __attribute__ ((format (printf, 2, 3))); int16_t printf(const __FlashStringHelper *format, ...); virtual void flush() { /* Empty implementation for backward compatibility */ } From 4b8e8380b1fdfa217ed4665128580f754fbc92ec Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Dec 2021 20:35:50 +0100 Subject: [PATCH 270/351] Rename non-static assign_generator functions to set_generator --- .../Read_event_settings.ino | 4 ++-- .../Route_logic_pins/Route_logic_pins.ino | 4 ++-- .../examples/Simple_event/Simple_event.ino | 2 +- megaavr/libraries/Event/keywords.txt | 1 + megaavr/libraries/Event/src/Event.cpp | 4 ++-- megaavr/libraries/Event/src/Event.h | 24 +++++++++---------- 6 files changed, 20 insertions(+), 19 deletions(-) diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 6ea7d46..92dd49f 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -34,8 +34,8 @@ void setup() { Serial2.begin(9600); // Initialize hardware serial port - Event1.assign_generator(gen0::pin_pa3); // Set pin PA3 as event generator - Event2.assign_generator(gen2::pin_pc3); // Set pin PC3 as event generator + Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator + Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet Event1.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user diff --git a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino index 43df811..88623a5 100644 --- a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino +++ b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino @@ -35,8 +35,8 @@ void setup() { // Initialize Event channel 2 and 3 - Event2.assign_generator(gen2::pin_pc0); // Set pin PC0 as event generator - Event3.assign_generator(gen3::pin_pc1); // Set pin PC1 as event generator + Event2.set_generator(gen2::pin_pc0); // Set pin PC0 as event generator + Event3.set_generator(gen3::pin_pc1); // Set pin PC1 as event generator Event2.set_user(user::ccl0_event_a); // Set CCL0 (Logic0) event A as user Event3.set_user(user::ccl0_event_b); // Set CCL0 (Logic0) event B as user diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index c41d42f..77aa0eb 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -20,7 +20,7 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event4.assign_generator(gen4::pin_pe0); // Set pin PE0 as event generator + Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet Event4.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index 47c68c4..0fc5097 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -14,6 +14,7 @@ get_channel_number KEYWORD2 get_channel KEYWORD2 get_generator_channel KEYWORD2 get_generator KEYWORD2 +set_generator KEYWORD2 assign_generator KEYWORD2 assign_generator_pin KEYWORD2 get_user_channel_number KEYWORD2 diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 60f5f89..263c25a 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -188,7 +188,7 @@ uint8_t Event::get_generator() * Use gen:: for functionality present on all event channels. * Use genN:: for functionality present on channel N. */ -void Event::assign_generator(gen::generator_t event_generator) +void Event::set_generator(gen::generator_t event_generator) { // Store event generator setting for use in start() and stop() generator_type = (uint8_t)event_generator; @@ -204,7 +204,7 @@ void Event::assign_generator(gen::generator_t event_generator) * * @param pin_number Arduino pin number to use as event generator */ -void Event::assign_generator(uint8_t pin_number) +void Event::set_generator(uint8_t pin_number) { uint8_t port = digitalPinToPort(pin_number); uint8_t port_pin = digitalPinToBitPosition(pin_number); diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 781e452..27d224b 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -615,40 +615,40 @@ class Event static Event& get_channel(uint8_t channel_number); static Event& get_generator_channel(uint8_t generator); uint8_t get_generator(); - void assign_generator(gen::generator_t generator); - void assign_generator(uint8_t pin_number); + void set_generator(gen::generator_t generator); + void set_generator(uint8_t pin_number); static Event& assign_generator_pin(uint8_t port, uint8_t port_pin); static Event& assign_generator_pin(uint8_t pin_number); #if defined(EVSYS_CHANNEL0) - void assign_generator(gen0::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen0::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL1) - void assign_generator(gen1::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen1::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL2) - void assign_generator(gen2::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen2::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL3) - void assign_generator(gen3::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen3::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL4) - void assign_generator(gen4::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen4::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL5) - void assign_generator(gen5::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen5::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL6) - void assign_generator(gen6::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen6::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL7) - void assign_generator(gen7::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen7::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL8) - void assign_generator(gen8::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen8::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL9) - void assign_generator(gen9::generator_t generator) { assign_generator((gen::generator_t)generator); } + void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } #endif static int8_t get_user_channel_number(user::user_t event_user); From 7ac9dc19c4167ae0d88389b74e9d9f91daf046b6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Dec 2021 23:03:16 +0100 Subject: [PATCH 271/351] Update Event library Update README and add long_soft_event() --- megaavr/libraries/Event/README.md | 74 +++++++++++++++++---------- megaavr/libraries/Event/keywords.txt | 1 + megaavr/libraries/Event/src/Event.cpp | 71 ++++++++++++++++++++++--- megaavr/libraries/Event/src/Event.h | 1 + 4 files changed, 114 insertions(+), 33 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 5c06fbb..a07f817 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -5,6 +5,11 @@ Developed by [MCUdude](https://github.com/MCUdude/). **From the datasheet:** > The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. + +## Overview +The event system allows routing of signals from event "generators" (outputs on various peripherals) through an event "channel", which one or more "event users" can be connected. When an event signal coming from the generator is is "active" or "high", the users connected to the same channel as the generator will perform certain specified actions depending on the peripheral. Generators are often the sorts of things that generate an interrupt if that is enabled - but some things can generate constant level events (such as following the state of a pin). +The event users can do a wide variety of things. The ADC can kick off a staged measurement. Type A and B timers can count them, and type B timers can measure their duration or time between them with input capture. USARTs can even use them as their RX input! This is nice and all - but what really makes the Event system reach it's potential is CCL (configurable custom logic) which can use events as inputs, in addiion to having access to several more internal sourcesof "event-like" signals - and being event generators in their own right. + More information about the Event system and how it works can be found in the [Microchip Application Note AN2451](http://ww1.microchip.com/downloads/en/AppNotes/DS00002451B.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). @@ -14,19 +19,19 @@ Often for a given even generator or user only one or the other makes sense. Less ### Synchronization +>Events can be either synchronous or asynchronous to the peripheral clock. Each Event System channel has two subchannels: one asynchronous and one synchronous. +>The asynchronous subchannel is identical to the event output from the generator. If the event generator generates a signal asynchronous to the peripheral clock, the signal on the asynchronous subchannel will be asynchronous. If the event generator generates a signal synchronous to the peripheral clock, the signal on the asynchronous subchannel +>will also be synchronous. +>The synchronous subchannel is identical to the event output from the generator, if the event generator generates a signal synchronous to the peripheral clock. If the event generator generates a signal asynchronous to the peripheral clock, this signal is first synchronized before being routed onto the synchronous subchannel. Depending on when the event occurs, synchronization will delay the it by two to three clock cycles. The Event System automatically perform this synchronization if an asynchronous generator is selected for an event channel. + The event system, under the hood, is asynchronous - it can react faster than the system clock (often a lot faster). The fact that it is asynchronous usually doesn't matter, but it is one of the things one should keep in mind when using these features, because every so often it does. -### Some of these events are *weird* -At first glance, nore than half of the users and generators seem, at best, odd - and a good few of them might appear entirely useless. Most of the event system can only truly be understood when considering the full range of generators and users - particularly the CCL. One of the tragedies of a datasheet is that it - generally - lacks a "why". Behind every mysterious event, there is a use case that seems obscure to most people - but within some sub-field, it's common and essential. There are also times when something may seem surprising until you're more familiar with the event and logic systems in general. - - - ## Event -Class for interfacing with the built-in Event system. Each event generator channel has its own object. -Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Refer to static functions by using `Event::`. Note that different channels have different functionality, so make sure you use the right channel for the task. -`Event_empty` is an object that's used to indicate if an event user isn't connected to an event channel and the user program requests an object. +Class for interfacing with the Event system (EVSYS). Each event channel has its own object. +Use the predefined objects `Event0`, `Event1`, `Event2`, `Event3`, `Event4`, `Event5`, `Event6` or `Event7`. Refer to static functions by using `Event::`. Additionally, there is an `Event_empty` that is returned whenever you call a method that returns an Event reference, but it can't fulfil your request. +Note that different channels have different functionality, so make sure you use the right channel for the task. In short terms: @@ -52,7 +57,7 @@ uint8_t this_channel = Event0.get_channel_number(); // In this case, get_channe ## get_channel() -Static function that returns the object associated with the passed channel number. Useful if you need to get the correct Event object based on an integer number. +Static function that returns the event object of that number. Useful if you need to get the correct Event object based on an integer number. ### Declaration ``` c++ @@ -85,7 +90,7 @@ static Event& get_generator_channel(uint8_t generator); ### Usage ```c++ // Set ccl0_out as event generator for channel 2 -Event2.assign_generator(gen::ccl0_out); +Event2.set_generator(gen::ccl0_out); // Now we want to get the channel/object connected to the ccl0_out generator // Create a reference to the object get_generator_channel() returns. @@ -112,21 +117,21 @@ if(generator_used == gen::ccl0_out) { ``` -## assign_generator(gen::generator_t) -Function to assign an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. +## set_generator(gen::generator_t) +Function to connect an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. ### Declaration ``` c++ -void assign_generator(gen::generator_t generator); -void assign_generator(gen0::generator_t generator); +void set_generator(gen::generator_t generator); +void set_generator(gen0::generator_t generator); //... -void assign_generator(gen7::generator_t generator); +void set_generator(gen7::generator_t generator); ``` ### Usage ```c++ -Event0.assign_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 -Event2.assign_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 +Event0.set_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 +Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 ``` ### Generator table @@ -161,23 +166,23 @@ Below is a table with all possible generators for each channel. | `gen::tcb3_capt` | | | | | | | | | -## assign_generator(uint8_t pin_number) +## set_generator(uint8_t pin_number) Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [assign_generator_pin()](#assign_generator_pin) instead.** ### Declaration ``` c++ -void assign_generator(uint8_t pin_number); +void set_generator(uint8_t pin_number); ``` ### Usage ```c++ -Event0.assign_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 -Event1.assign_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an event generator for channel 1 +Event0.set_generator(PIN_PA0); // Will work. PA0 can be used as an event generator for channel 0 +Event1.set_generator(PIN_PC3); // WILL NOT WORK! PORTC cannot be used as an event generator for channel 1 ``` ## assign_generator_pin() -Static function that sets an Arduino pin as the event generator. Unlike assign_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` (generator number 255) if the pin can't be assigned to a channel. +Static function that sets an Arduino pin as the event generator. Unlike set_generator(uint8_t pin_number), this function will return the object the generator has been assigned to. It will always try to use the lowest possible channel number as possible, and will return a reference to the object `Event_empty` (generator number 255) if the pin can't be assigned to a channel. ### Declaration ``` c++ @@ -195,8 +200,9 @@ myEvent.start(); ## get_user_channel_number() -Static function to get what event channel a user is connected to. Returns -1 if not connected to any channel. Note that we use `user::` as prefix when we refer to event users. Also, note that we don't have to specify an object to determine what channel the user is connected to. if you're not sure, use `Event::get_user_channel`. -An event generator can have multiple event users, but an event user can only have one event generator. +Static function to get what event channel a user is connected to. Returns -1 if not connected to any channel. +Note that we use `user::` as prefix when we refer to event users. Since this is a static function you don't have to specify an object to determine what channel the user is connected to. An event channel, and hence an event generator, can have as many event users are you want - but an event user can only have one event generator. +You cannot get a list or count of all users connected to a generator except by iterating over the list. ### Declaration ``` c++ @@ -210,7 +216,7 @@ int8_t connected_to = Event::get_user_channel_number(user::ccl0_event_a); // Ret ## get_user_channel() -Static function that returns the Event channel object a particular user is connected to. Returns a referece to the `Event_empty` object if not connected to any event channel. +Static function that returns the Event channel object a particular user is connected to. unlike get_user_channel_number()`, this returns a reference to an Event object, and returns a referece to the `Event_empty` object if not connected to any event channel. ### Declaration ``` c++ @@ -233,7 +239,7 @@ void set_user(user::user_t event_user); ### Usage ```c++ -Event0.assign_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 +Event0.set_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 Event0.set_user(user::evoutc); // Set EVOUTC (pin PC2) as event user Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user ``` @@ -330,8 +336,22 @@ Event0.soft_event(); // Create a single software event on Event0 ``` +### long_soft_event() +`soft_event()` is only one system clock long, and might be difficult to catch in a real-life application. This function does the same thing as `soft_event()` but has a programmable interval for how long the soft event will last. + +The event lengths that are available are 2, 4, 6, 10 and 16 system clocks. (Any number less than 4 will give 2 clock-long pulse, only 4 will give a 4 clock long one. Anything between 4 and 10 will give 6, exactly 10 will give 10, and anything larger will give 16). + +#### Usage +```c++ +Event0.long_soft_event(4); // Will invert the state of the event channel for 4 system clock cycles (200ns at 20 MHz) +Event0.long_soft_event(10); // Will invert the state of the event channel for 10 system clock cycles (500ns at 20 MHz) + +``` +Don't forget that this is an invert, not a "high" or "low". It should be entirely possible for the event that normally drives it to occur resulting in the state changing during that pulse, depending on it's configuration. Note also that the overhead of long_soft_event is typically several times the length of the pulse due to calculating the bitmask to write; it's longer with higher numbered channels. + + ## start() -Starts an event generator channel by writing the generator selected by the `assign_generator()` function. +Starts an event generator channel by writing the generator selected by the `set_generator()` function. ### Declaration ``` c++ diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index 0fc5097..95525a3 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -23,6 +23,7 @@ set_user KEYWORD2 set_user_pin KEYWORD2 clear_user KEYWORD2 soft_event KEYWORD2 +long_soft_event KEYWORD2 start KEYWORD2 stop KEYWORD2 diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 263c25a..7e9788b 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -413,6 +413,7 @@ void Event::set_user(user::user_t event_user) } } + /** * @brief Sets an Arduino pin as a user for a particular event channel * @@ -437,7 +438,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) else if(port_pin == 7) event_user = user::evouta_pin_pa7; } - #if defined(__AVR_ATmegax09__) + #if defined(PIN_PB2) else if(port == PB) { if(port_pin == 2) @@ -448,7 +449,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) { if(port_pin == 2) event_user = user::evoutc_pin_pc2; - #if defined(__AVR_ATmegax09__) + #if defined(PIN_PC7) else if(port_pin == 7) event_user = user::evoutc_pin_pc7; #endif @@ -460,7 +461,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) else if(port_pin == 7) event_user = user::evoutd_pin_pd7; } - #if defined(__AVR_ATmegax09__) + #if defined(PIN_PE2) else if(port == PE) { if(port_pin == 2) @@ -477,6 +478,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) return event_user; } + /** * @brief Clears/removed a user from a particular event channel if set * @@ -516,15 +518,17 @@ void Event::soft_event() // megaAVR 0-series EVSYS.STROBE = (1 << channel_number); #elif defined(EVSYS_ASYNCCH0) - // TODO: tinyAVR 0/1-series + // tinyAVR 0/1-series #else + // tinyAVR 2-series and AVR-Dx // We expect there to be an EVSYS.SWEVENTA channel plus an - // EVSYS.SWEVENTB if it has more than 8 event channels. + // EVSYS.SWEVENTB it it has more than 8 event channels. #if defined(EVSYS_SWEVENTB) if(channel_number < 8) EVSYS.SWEVENTA = (1 << channel_number); else - EVSYS.SWEVENTB = (1 << (channel_number - 8)); + EVSYS.SWEVENTB = channel_number - 7; + } #else EVSYS.SWEVENTA = (1 << channel_number); #endif @@ -532,6 +536,61 @@ void Event::soft_event() } +void Event::long_soft_event(uint8_t length) +{ + uint8_t channel = channel_number; + uint16_t strobeaddr; + #if defined(EVSYS_STROBE) + strobeaddr = (uint16_t) &EVSYS_STROBE; + #elif defined(EVSYS_SWEVENTB) + if(channel > 7) + { + channel -= 8; + strobeaddr = (uint16_t) &EVSYS_SWEVENTB; + } + else + strobeaddr = (uint16_t) &EVSYS_SWEVENTA; + #elif defined(EVSYS_SWEVENTA) + strobeaddr = (uint16_t) &EVSYS_SWEVENTA; + #else + #error "Don't know the strobe register!" + #endif + channel = (1 << channel); + __asm__ __volatile__ ( + "in r0, 0x3F" "\n\t" // Save SREG + "cli" "\n\t" // Interrupts off + "cpi %1, 4" "\n\t" + "brcs long_soft2" "\n\t" // Less than 4 -> 2 + "breq long_soft4" "\n\t" // Equal to 4 -> 4 + "cpi %1, 10" "\n\t" // Compare with 8 + "brcs long_soft6" "\n\t" // Less than 10 (but more than 4) -> 6 + "breq long_soft10""\n\t" // Equal to 10 -> 10 + "st Z, %0" "\n\t" // Otherwise they get 16. + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "long_soft10:" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "long_soft6:" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "long_soft4:" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "long_soft2:" "\n\t" + "st Z, %0" "\n\t" + "st Z, %0" "\n\t" + "out 0x3f, r0" "\n" // Restore SREG, reenable interrupts + ::"r"((uint8_t) channel),"d"((uint8_t) length),"z" ((uint16_t) strobeaddr)); +} + + + /** * @brief Starts the event generator for a particular event channel * diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 27d224b..59c2818 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -657,6 +657,7 @@ class Event int8_t set_user_pin(uint8_t pin_number); static void clear_user(user::user_t event_user); void soft_event(); + void long_soft_event(uint8_t length); void start(bool state = true); void stop(); From f56b67dbc155a5bf9547df8108f9fab59a7da7a5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 8 Dec 2021 00:18:28 +0100 Subject: [PATCH 272/351] Make get_generator_channel work for Arduino pins as well --- megaavr/libraries/Event/README.md | 3 +- megaavr/libraries/Event/src/Event.cpp | 66 ++++++++++++++++++++++++++- megaavr/libraries/Event/src/Event.h | 13 +++++- 3 files changed, 79 insertions(+), 3 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index a07f817..3638401 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -84,7 +84,8 @@ Returns a reference to the `Event_empty` object if the generator is not connecte ### Declaration ``` c++ -static Event& get_generator_channel(uint8_t generator); +static Event& get_generator_channel(gen::generator_t generator); // For all other generators (gen, gen0...gen7) +static Event& get_generator_channel(uint8_t generator); // For Arduino pins ``` ### Usage diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 7e9788b..9740807 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -120,7 +120,7 @@ Event& Event::get_channel(uint8_t ch_number) * @param generator Event generator * @return Event& Event channel object used with this event generator */ -Event& Event::get_generator_channel(uint8_t generator) +Event& Event::get_generator_channel(gen::generator_t generator) { #if defined(EVSYS_CHANNEL0) if(Event0.generator_type == generator) @@ -170,6 +170,70 @@ Event& Event::get_generator_channel(uint8_t generator) } +/** + * @brief Returns the event channel object used for a particular event generator Arduino pin + * + * @param generator_pin Event generator Arduino pin number + * @return Event& Event channel object used with this event generator + */ +Event& Event::get_generator_channel(uint8_t generator_pin) +{ + uint8_t port = digitalPinToPort(generator_pin); + uint8_t port_pin = digitalPinToBitPosition(generator_pin); + + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) + { + uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; + if(port == PA || port == PB) + { + #if defined(EVSYS_CHANNEL0) + if(Event0.generator_type == gen) + return Event0; + #endif + #if defined(EVSYS_CHANNEL1) + else if(Event1.generator_type == gen) + return Event1; + #endif + } + else if(port == PC || port == PD) + { + #if defined(EVSYS_CHANNEL2) + if(Event2.generator_type == gen) + return Event2; + #endif + #if defined(EVSYS_CHANNEL3) + else if(Event3.generator_type == gen) + return Event3; + #endif + } + else if(port == PE || port == PF) + { + #if defined(EVSYS_CHANNEL4) + if(Event4.generator_type == gen) + return Event4; + #endif + #if defined(EVSYS_CHANNEL5) + else if(Event5.generator_type == gen) + return Event5; + #endif + } + #if defined(Dx_64_PINS) + else if(port == PG) + { + if(Event6.generator_type == gen) + return Event6; + else if(Event7.generator_type == gen) + return Event7; + } + #endif + } + + #if defined(EVSYS_CHANNEL0) + return Event_empty; + #endif +} + + /** * @brief Returns the generator type a particular channel has * diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 59c2818..804a144 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -613,7 +613,8 @@ class Event Event(uint8_t channel_num, volatile uint8_t &channel_addr); uint8_t get_channel_number(); static Event& get_channel(uint8_t channel_number); - static Event& get_generator_channel(uint8_t generator); + static Event& get_generator_channel(gen::generator_t generator); + static Event& get_generator_channel(uint8_t generator_pin); uint8_t get_generator(); void set_generator(gen::generator_t generator); void set_generator(uint8_t pin_number); @@ -621,33 +622,43 @@ class Event static Event& assign_generator_pin(uint8_t pin_number); #if defined(EVSYS_CHANNEL0) + void get_generator_channel(gen0::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen0::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL1) + void get_generator_channel(gen1::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen1::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL2) + void get_generator_channel(gen2::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen2::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL3) + void get_generator_channel(gen3::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen3::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL4) + void get_generator_channel(gen4::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen4::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL5) + void get_generator_channel(gen5::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen5::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL6) + void get_generator_channel(gen6::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen6::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL7) + void get_generator_channel(gen7::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen7::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL8) + void get_generator_channel(gen8::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen8::generator_t generator) { set_generator((gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL9) + void get_generator_channel(gen9::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } #endif From 2b7c95110658dbdb7c01b38f623bc306f1d4d2bf Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 8 Dec 2021 00:18:43 +0100 Subject: [PATCH 273/351] Update examples --- .../Read_event_settings.ino | 16 +++++++--- .../examples/Simple_event/Simple_event.ino | 32 ++++++++++++++----- 2 files changed, 36 insertions(+), 12 deletions(-) diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 92dd49f..8cdeedd 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -9,7 +9,7 @@ | | | In this example, we demonstrate the possibilities of reading out | | which event channel we're working with, which generator is used, and | -| whichchannel an event user has been connected to. | +| which channel an event user has been connected to. | | | | See Microchip's application note AN2451 for more information. | |***********************************************************************/ @@ -27,23 +27,26 @@ void print_event_info(Event& my_event) void print_user_info(user::user_t my_user) { // Event::get_user_channel() returns -1 if the user isn't connected to any event generator - Serial2.printf("User 0x%02x is connected to event channel no. %d\n\n", my_user, Event::get_user_channel(my_user)); + Serial2.printf("User 0x%02x is connected to event channel no. %d\n\n", my_user, Event::get_user_channel_number(my_user)); } void setup() { Serial2.begin(9600); // Initialize hardware serial port - Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator - Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator + Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator for event channel 1 + Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator for event channel 2 + Event& myEvent = Event::assign_generator_pin(PIN_PA2); // Set pin PA2 as event generator for an available channel // For more information about EVOUT, see the PORTMUX section in the datasheet Event1.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user Event2.set_user(user::evouta_pin_pa2); // Set EVOUTA as event user + myEvent.set_user_pin(PIN_PD2); // Set pin PD2 (EVOUTD) as event user // Start event channels Event1.start(); Event2.start(); + myEvent.start(); } void loop() @@ -56,5 +59,10 @@ void loop() print_event_info(Event2); print_user_info(user::evouta_pin_pa2); + // Print info about myEvent and its user + Event& myEvent = Event::get_generator_channel(PIN_PA2); + print_event_info(myEvent); + print_user_info(user::evoutd_pin_pd2); + delay(5000); } diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index 77aa0eb..900b752 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -7,9 +7,12 @@ | Developed in 2021 by MCUdude | | https://github.com/MCUdude/ | | | -| In this example we use pin PE0 as an event generator, and pin PC2 and | -| PD2 as event users. In practice, pin PC2 and PD2 will follow | -| PE0's state. | +| In this example we look at two different ways of setting up a simple | +| Event generator ans user. In the first example use pin PA0 as an | +| event generator, and pin PC2 and PD2 as event users. In practice, | +| pin PC2 and PD2 will follow PA0's state. | +| In the other example we just provide "Arduino pins" as generator and | +| user, and let the library take care of the rest. | | | | See Microchip's application note AN2451 for more information. | |***********************************************************************/ @@ -20,14 +23,27 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event4.set_generator(gen4::pin_pe0); // Set pin PE0 as event generator + Event0.set_generator(gen0::pin_pa0); // Set pin PA0 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet - Event4.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user - Event4.set_user(user::evoutd_pin_pd2); // Set EVOUTF as event user + Event0.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user + Event0.set_user(user::evoutd_pin_pd2); // Set EVOUTD as event user - // Start the event channel - Event4.start(); + // Start event channel + Event0.start(); + + + + // A different approach is to let the library itself take care of which Event channel to use: + + // Assign generator to an available channel + Event& myEvent = Event::assign_generator_pin(PIN_PA1); + + // Connect a user, in this case an Arduino pin, to the myEvent channel + myEvent.set_user_pin(PIN_PA2); + + // Start event channel + myEvent.start(); } void loop() From bd5cc79898780917296548662aa5318c91652b64 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 9 Dec 2021 21:59:19 +0100 Subject: [PATCH 274/351] Add assign_generator() function --- megaavr/libraries/Event/README.md | 16 ++++ megaavr/libraries/Event/src/Event.cpp | 103 ++++++++++++++++++++++++++ megaavr/libraries/Event/src/Event.h | 1 + 3 files changed, 120 insertions(+) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 3638401..25aa3e8 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -167,6 +167,22 @@ Below is a table with all possible generators for each channel. | `gen::tcb3_capt` | | | | | | | | | +### assign_generator(gen::generator_t) +Static function that connects an event generator to a channel. What's different compared to `set_generator()` is that this function returns a reference to the channel object the generator has been assigned to. In other words, you don't need to keep track of the exact channel number, it just assigns an available channel. +Note that this function only accepts generators that are present on all channels (gen::). It will return a reference to the `Event_empty` object if no channel is available. + +### Declaration +``` c++ +static Event& assign_generator(gen::generator_t event_generator); +``` + +### Usage +```c++ +Event& myEvent = Event::assign_generator(gen::ac0_out); // Assign the AC0 out generator to a channel +myEvent.start(); +``` + + ## set_generator(uint8_t pin_number) Function that sets an Arduino pin as the event generator. Note that you will have to make sure a particular pin can be used as an event generator for the selected channel/object. **If this sounds like a hassle, use [assign_generator_pin()](#assign_generator_pin) instead.** diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 9740807..fbb1f3f 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -374,6 +374,109 @@ Event& Event::assign_generator_pin(uint8_t pin_number) } +/** + * @brief Static member function that takes a gen:: generator as a parameter and + * finds an available channel for it. Starts with the highest possible channel + * number, 7, and iterate down to 0 + * + * @param event_generator generator to assign to an event channel + * @return Event& Reference to the event object the generator has been assigned to. + * Returns the Event_empty object if no generator has been assigned to a channel + */ +Event& Event::assign_generator(gen::generator_t event_generator) +{ + // Check if generator is already in use + Event& channel = Event::get_generator_channel(event_generator); + if(channel.get_channel_number() != 255) + return channel; + + else + { + #if defined(EVSYS_CHANNEL9) + if(Event9.get_generator() == gen::disable) + { + Event9.set_generator(event_generator); + return Event9; + } + else + #endif + #if defined(EVSYS_CHANNEL8) + if(Event8.get_generator() == gen::disable) + { + Event8.set_generator(event_generator); + return Event8; + } + else + #endif + #if defined(EVSYS_CHANNEL7) + if(Event7.get_generator() == gen::disable) + { + Event7.set_generator(event_generator); + return Event7; + } + else + #endif + #if defined(EVSYS_CHANNEL6) + if(Event6.get_generator() == gen::disable) + { + Event6.set_generator(event_generator); + return Event6; + } + else + #endif + #if defined(EVSYS_CHANNEL5) + if(Event5.get_generator() == gen::disable) + { + Event5.set_generator(event_generator); + return Event5; + } + else + #endif + #if defined(EVSYS_CHANNEL4) + if(Event4.get_generator() == gen::disable) + { + Event4.set_generator(event_generator); + return Event4; + } + else + #endif + #if defined(EVSYS_CHANNEL3) + if(Event3.get_generator() == gen::disable) + { + Event3.set_generator(event_generator); + return Event3; + } + else + #endif + #if defined(EVSYS_CHANNEL2) + if(Event2.get_generator() == gen::disable) + { + Event2.set_generator(event_generator); + return Event2; + } + else + #endif + #if defined(EVSYS_CHANNEL1) + if(Event1.get_generator() == gen::disable) + { + Event1.set_generator(event_generator); + return Event1; + } + else + #endif + #if defined(EVSYS_CHANNEL0) + if(Event0.get_generator() == gen::disable) + { + Event0.set_generator(event_generator); + return Event0; + } + else + #endif + return channel; // if we're on this branch, we know chan is Event_empty + } +} + + /** * @brief Returns the Event channel number a particular user is connected to * diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 804a144..cc7b0c2 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -617,6 +617,7 @@ class Event static Event& get_generator_channel(uint8_t generator_pin); uint8_t get_generator(); void set_generator(gen::generator_t generator); + static Event& assign_generator(gen::generator_t event_generator); void set_generator(uint8_t pin_number); static Event& assign_generator_pin(uint8_t port, uint8_t port_pin); static Event& assign_generator_pin(uint8_t pin_number); From e65d200e5b37e089939cadc427d398ffb4f11a3b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 9 Dec 2021 22:15:25 +0100 Subject: [PATCH 275/351] Add missing user aliases --- megaavr/libraries/Event/README.md | 58 ++++++++++++++--------------- megaavr/libraries/Event/src/Event.h | 5 +++ 2 files changed, 34 insertions(+), 29 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 25aa3e8..6f97b26 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -265,35 +265,35 @@ Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user Below is a table with all possible event users. Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` -| Event users | Notes | -|------------------------|-----------------------------------------------------------------------| -| `user::ccl0_event_a` | | -| `user::ccl0_event_b` | | -| `user::ccl1_event_a` | | -| `user::ccl1_event_b` | | -| `user::ccl2_event_a` | | -| `user::ccl2_event_b` | | -| `user::ccl3_event_a` | | -| `user::ccl3_event_b` | | -| `user::adc0_start` | | -| `user::evouta_pin_pa2` | | -| `user::evouta_pin_pa7` | Pin swapped variant of `evouta_pin_pa2` | -| `user::evoutb_pin_pb2` | Only available on ATmegaX809 | -| `user::evoutc_pin_pc2` | | -| `user::evoutc_pin_pc7` | Pin swapped variant of `evoutc_pin_pc2`. Only available on ATmegaX809 | -| `user::evoutd_pin_pd2` | | -| `user::evoutd_pin_pd7` | Pin swapped variant of `evoutd_pin_pd2` | -| `user::evoute_pin_pe2` | Only available on ATmegaX809 | -| `user::evoutf_pin_pf2` | Not available on 28-pin parts | -| `user::usart0_irda` | | -| `user::usart1_irda` | | -| `user::usart2_irda` | | -| `user::usart3_irda` | | -| `user::tca0` | | -| `user::tcb0` | | -| `user::tcb1` | | -| `user::tcb2` | | -| `user::tcb3` | | +| Event users | Notes | +|-----------------------------------|-----------------------------------------------------------------------| +| `user::ccl0_event_a` | | +| `user::ccl0_event_b` | | +| `user::ccl1_event_a` | | +| `user::ccl1_event_b` | | +| `user::ccl2_event_a` | | +| `user::ccl2_event_b` | | +| `user::ccl3_event_a` | | +| `user::ccl3_event_b` | | +| `user::adc0_start` | | +| `user::evouta_pin_pa2` | | +| `user::evouta_pin_pa7` | Pin swapped variant of `evouta_pin_pa2` | +| `user::evoutb_pin_pb2` | Only available on ATmegaX809 | +| `user::evoutc_pin_pc2` | | +| `user::evoutc_pin_pc7` | Pin swapped variant of `evoutc_pin_pc2`. Only available on ATmegaX809 | +| `user::evoutd_pin_pd2` | | +| `user::evoutd_pin_pd7` | Pin swapped variant of `evoutd_pin_pd2` | +| `user::evoute_pin_pe2` | Only available on ATmegaX809 | +| `user::evoutf_pin_pf2` | Not available on 28-pin parts | +| `user::usart0_irda` | | +| `user::usart1_irda` | | +| `user::usart2_irda` | | +| `user::usart3_irda` | | +| `user::tca0` or `user::tca0_capt` | | +| `user::tcb0` or `user::tcb0_capt` | | +| `user::tcb1` or `user::tcb1_capt` | | +| `user::tcb2` or `user::tcb2_capt` | | +| `user::tcb3` or `user::tcb3_capt` | | ## set_user_pin(uint8_t pin_number) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index cc7b0c2..02cdb75 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -418,11 +418,16 @@ namespace user usart3_irda = 0x12, #endif tca0 = 0x13, + tca0_capt = 0x13, tcb0 = 0x14, + tcb0_capt = 0x14, tcb1 = 0x15, + tcb1_capt = 0x15, tcb2 = 0x16, + tcb2_capt = 0x16, #if defined(TCB3) tcb3 = 0x17, + tcb3_capt = 0x17, #endif // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX evouta_pin_pa7 = 0x89, From 03a8fac14a78676253ef86e6c9065c555fe1491f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Dec 2021 00:32:10 +0100 Subject: [PATCH 276/351] Update enums Now the formatting is slightly different, and tiny0/1/2 are also supported --- megaavr/libraries/Event/src/Event.h | 1330 +++++++++++++++++++-------- 1 file changed, 967 insertions(+), 363 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 02cdb75..7974833 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -3,12 +3,10 @@ #include - +#if defined(MEGACOREX) || defined(DXCORE) // Features present on all generator channels -namespace gen -{ - enum generator_t : uint8_t - { +namespace gen { + enum generator_t : uint8_t { disable = 0x00, off = 0x00, updi_synch = 0x01, @@ -19,6 +17,12 @@ namespace gen ccl2_out = 0x12, ccl3_out = 0x13, ac0_out = 0x20, +#if defined(AC1) + ac1_out = 0x21, +#endif +#if defined(AC2) + ac2_out = 0x22, +#endif adc0_ready = 0x24, usart0_xck = 0x60, usart1_xck = 0x61, @@ -33,16 +37,22 @@ namespace gen tca0_cmp1 = 0x85, tca0_cmp2 = 0x86, tcb0_capt = 0xA0, + tcb0 = 0xA0, tcb1_capt = 0xA2, + tcb1 = 0xA2, tcb2_capt = 0xA4, + tcb2 = 0xA4, #if defined(TCB3) tcb3_capt = 0xA6, + tcb3 = 0xA6, +#endif +#if defined(TCB4) + tcb4_capt = 0xA8, + tcb4 = 0xA8, #endif #if defined(__AVR_DA__) || defined(__AVR_DB__) ccl4_out = 0x14, ccl5_out = 0x15, - ac1_out = 0x21, - ac2_out = 0x22, zcd0_out = 0x30, zcd1_out = 0x31, #if defined(ZCD2) @@ -62,23 +72,34 @@ namespace gen tca1_cmp1 = 0x8D, tca1_cmp2 = 0x8E, #endif +#endif // defined(__AVR_DA__) || defined(__AVR_DB__) +#if defined(DXCORE) +// These are present on every modern part released since the 0/1-series and will probably continue to be, so check tcb0_ovf = 0xA1, tcb1_ovf = 0xA3, +#if defined(TCB2) tcb2_ovf = 0xA5, +#endif #if defined(TCB3) tcb3_ovf = 0xA7, #endif #if defined(TCB4) - tcb4_capt = 0xA8, tcb4_ovf = 0xA9, #endif +#endif +#if defined(TCD0) tcd0_cmpbclr = 0xB0, tcd0_cmpaset = 0xB1, tcd0_cmpbset = 0xB2, tcd0_progev = 0xB3, -#endif // defined(__AVR_DA__) || defined(__AVR_DB__) -#if defined(__AVR_DB__) +#endif +#if defined(MVIO) mvio_ok = 0x05, +#endif +#if defined(ZCD3) + zcd3_out = 0x30, // The ZCD is numbered differently, I think just because it's on different pins. Still has the same event channel +#endif +#if defined(__AVR_DB__) opamp0_ready = 0x34, opamp1_ready = 0x35, #if defined(OPAMP2) @@ -90,308 +111,310 @@ namespace gen // Features unique to event generator channel 0 #if defined(EVSYS_CHANNEL0) - namespace gen0 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4D, -#endif -#if defined(Dx_64_PINS) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, -#endif - }; +namespace gen0 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, +#if !defined(DXCORE) || defined(PIN_PA2) + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, +#endif +#if defined(PIN_PB0) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4D, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, +#endif }; +}; #endif // Features unique to event generator channel 1 #if defined(EVSYS_CHANNEL1) - namespace gen1 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4D, -#endif -#if defined(Dx_64_PINS) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, -#endif - }; +namespace gen1 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, +#if defined(PIN_PA2) + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, +#endif +#if defined(PIN_PB0) + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4D, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, +#endif }; +}; #endif // Features unique to event generator channel 2 #if defined(EVSYS_CHANNEL2) - namespace gen2 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, -#endif - pin_pd0 = 0x48, - pin_pd1 = 0x49, - pin_pd2 = 0x4A, - pin_pd3 = 0x4B, - pin_pd4 = 0x4C, - pin_pd5 = 0x4D, - pin_pd6 = 0x4E, - pin_pd7 = 0x4F, - }; +namespace gen2 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, +#if !defined(DD_14_PINS) // Can't just check PIN_PC0 - the 0-pin of any port with any pins present is always defined by DxCore. + // I considered both ways, but there are to many reasons we need to have the 0-pin defined. + pin_pc0 = 0x40, +#endif + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, +#endif +#if defined(PIN_PD1) // See above for note on PIN_PD0 and why we can't test that, this even impacts DBs. +#if !defined(MVIO) || defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pd0 = 0x48, +#endif + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, +#endif + pin_pd4 = 0x4C, + pin_pd5 = 0x4D, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, }; +}; #endif // Features unique to event generator channel 3 #if defined(EVSYS_CHANNEL3) - namespace gen3 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, -#endif - pin_pd0 = 0x48, - pin_pd1 = 0x49, - pin_pd2 = 0x4A, - pin_pd3 = 0x4B, - pin_pd4 = 0x4C, - pin_pd5 = 0x4D, - pin_pd6 = 0x4E, - pin_pd7 = 0x4F, - }; +namespace gen3 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, +#if !defined(DD_14_PINS) + pin_pc0 = 0x40, +#endif + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, +#endif +#if defined(PIN_PD1) // See above for note on PIN_PD0 and why we can't test that, this even impacts DBs. +#if !defined(MVIO) || defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) + pin_pd0 = 0x48, +#endif + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, +#endif + pin_pd4 = 0x4C, + pin_pd5 = 0x4D, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, }; +}; #endif // Features unique to event generator channel 4 #if defined(EVSYS_CHANNEL4) - namespace gen4 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, -#endif -#if defined(Dx_64_PINS) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, -#endif - pin_pf0 = 0x48, - pin_pf1 = 0x49, -#if !defined(Dx_28_PINS) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, -#endif - pin_pf6 = 0x4E, - }; +namespace gen4 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, +#if defined(PIN_PE0) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, +#endif +#if defined(PIN_PE4) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, +#endif + pin_pf0 = 0x48, + pin_pf1 = 0x49, +#if defined(PIN_PF2) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, +#endif + pin_pf6 = 0x4E, +#if defined(PIN_PF7) + pin_pf7 = 0x4F, +#endif }; +}; #endif // Features unique to event generator channel 5 #if defined(EVSYS_CHANNEL5) - namespace gen5 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, -#if defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, -#endif -#if defined(Dx_64_PINS) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, -#endif - pin_pf0 = 0x48, - pin_pf1 = 0x49, -#if !defined(Dx_28_PINS) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, -#endif - pin_pf6 = 0x4E, - }; +namespace gen5 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, +#if defined(PIN_PE0) + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, +#endif +#if defined(PIN_PE4) + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, +#endif + pin_pf0 = 0x48, + pin_pf1 = 0x49, +#if defined(PIN_PF2) + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, +#endif + pin_pf6 = 0x4E, +#if defined(PIN_PF7) + pin_pf7 = 0x4F, +#endif }; +}; #endif // Features unique to event generator channel 6 #if defined(EVSYS_CHANNEL6) - namespace gen6 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, -#if defined(Dx_64_PINS) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, -#endif - }; +namespace gen6 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, +#if defined(PIN_PG0) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif }; +}; #endif // Features unique to event generator channel 7 #if defined(EVSYS_CHANNEL7) - namespace gen7 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, -#if defined(Dx_64_PINS) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, -#endif - }; +namespace gen7 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, +#if defined(PIN_PG0) + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif }; +}; #endif // Features unique to event generator channel 8 #if defined(EVSYS_CHANNEL8) - namespace gen8 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - }; +namespace gen8 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, }; +}; #endif // Features unique to event generator channel 9 #if defined(EVSYS_CHANNEL9) - namespace gen9 - { - enum generator_t : uint8_t - { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - }; +namespace gen9 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, }; +}; #endif + // Generator users -namespace user -{ - enum user_t : uint8_t - { -#if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) +namespace user { + enum user_t : uint8_t { +#if defined(MEGACOREX) ccl0_event_a = 0x00, ccl0_event_b = 0x01, ccl1_event_a = 0x02, @@ -402,14 +425,14 @@ namespace user ccl3_event_b = 0x07, adc0_start = 0x08, evouta_pin_pa2 = 0x09, -#if defined(__AVR_ATmegax09__) +#if defined(PIN_PB2) evoutb_pin_pb2 = 0x0A, #endif evoutc_pin_pc2 = 0x0B, evoutd_pin_pd2 = 0x0C, -#if defined(__AVR_ATmegax09__) +#if defined(PIN_PE2) evoute_pin_pe2 = 0x0D, - #endif +#endif evoutf_pin_pf2 = 0x0E, usart0_irda = 0x0F, usart1_irda = 0x10, @@ -418,7 +441,7 @@ namespace user usart3_irda = 0x12, #endif tca0 = 0x13, - tca0_capt = 0x13, + tca0_cnt_a = 0x13, tcb0 = 0x14, tcb0_capt = 0x14, tcb1 = 0x15, @@ -431,91 +454,100 @@ namespace user #endif // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX evouta_pin_pa7 = 0x89, -#if defined(__AVR_ATmegax09__) +#if defined(PIN_PC7) evoutc_pin_pc7 = 0x8B, #endif evoutd_pin_pd7 = 0x8C, -#endif // defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) +#endif // defined(MEGACOREX) + #if defined(__AVR_DA__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, #if defined(LUT4) - ccl4_event_a = 0x08, - ccl4_event_b = 0x09, - ccl5_event_a = 0x0A, - ccl5_event_b = 0x0B, -#endif - adc0_start = 0x0C, - ptc_start = 0x0D, - evouta_pin_pa2 = 0x0E, -#if defined(Dx_48_PINS) || defined(Dx_64_PINS) - evoutb_pin_pb2 = 0x0F, -#endif - evoutc_pin_pc2 = 0x10, - evoutd_pin_pd2 = 0x11, -#if defined(Dx_48_PINS) || defined(Dx_64_PINS) - evoute_pin_pe2 = 0x12, -#endif -#if !defined(Dx_28_PINS) - evoutf_pin_pf2 = 0x13, -#endif -#if defined(Dx_64_PINS) - evoutg_pin_pg2 = 0x14, -#endif - usart0_irda = 0x15, - usart1_irda = 0x16, - usart2_irda = 0x17, + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, +#endif + adc0_start = 0x0C, + ptc_start = 0x0D, + evouta_pin_pa2 = 0x0E, +#if defined(PIN_PB2) + evoutb_pin_pb2 = 0x0F, +#endif + evoutc_pin_pc2 = 0x10, + evoutd_pin_pd2 = 0x11, +#if defined(PIN_PE2) + evoute_pin_pe2 = 0x12, +#endif +#if defined(PIN_PF2) + evoutf_pin_pf2 = 0x13, +#endif +#if defined(PIN_PG2) + evoutg_pin_pg2 = 0x14, +#endif + usart0_irda = 0x15, + usart1_irda = 0x16, + usart2_irda = 0x17, #if defined(USART5) - usart3_irda = 0x18, + usart3_irda = 0x18, #endif #if defined(USART4) - usart4_irda = 0x19, + usart4_irda = 0x19, #endif #if defined(USART5) - usart5_irda = 0x1A, -#endif - tca0_cnt_a = 0x1B, - tca0_cnt_b = 0x1C, - tca1_cnt_a = 0x1D, - tca1_cnt_b = 0x1E, - tcb0_capt = 0x1F, - tcb0_cnt = 0x20, - tcb1_capt = 0x21, - tcb1_cnt = 0x22, - tcb2_capt = 0x23, - tcb2_cnt = 0x24, + usart5_irda = 0x1A, +#endif + tca0 = 0x1B, + tca0_cnt_a = 0x1B, + tca0_cnt_b = 0x1C, + tca1 = 0x1D, + tca1_cnt_a = 0x1D, + tca1_cnt_b = 0x1E, + tcb0_capt = 0x1F, + tcb0 = 0x1F, + tcb0_cnt = 0x20, + tcb1_capt = 0x21, + tcb1 = 0x21, + tcb1_cnt = 0x22, + tcb2_capt = 0x23, + tcb2 = 0x23, + tcb2_cnt = 0x24, #if defined(TCB3) - tcb3_capt = 0x25, - tcb3_cnt = 0x26, + tcb3_capt = 0x25, + tcb3 = 0x25, + tcb3_cnt = 0x26, #endif -#if defined(TCB3) - tcb4_capt = 0x27, - tcb4_cnt = 0x28, +#if defined(TCB4) + tcb4_capt = 0x27, + tcb4 = 0x27, + tcb4_cnt = 0x28, #endif - tcd0_in_a = 0x29, - tcd0_in_b = 0x2A, - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x8E, -#if defined(Dx_64_PINS) - evoutb_pin_pb7 = 0x8F, + tcd0_in_a = 0x29, + tcd0_in_b = 0x2A, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8E, +#if defined(PIN_PB7) + evoutb_pin_pb7 = 0x8F, #endif -#if defined(Dx_48_PINS) || defined(Dx_64_PINS) - evoutc_pin_pc7 = 0x90, +#if defined(PIN_PC7) + evoutc_pin_pc7 = 0x90, #endif - evoutd_pin_pd7 = 0x91, -#if defined(Dx_64_PINS) - evoutb_pin_pe7 = 0x92, + evoutd_pin_pd7 = 0x91, +#if defined(PIN_PE7) + evoute_pin_pe7 = 0x92, #endif -#if (defined(Dx_64_PINS)) - evoutb_pin_pg7 = 0x94, + // evoutf_pin_pf7 = 0x93, never available on DA/DB +#if defined(PIN_PG7) + evoutg_pin_pg7 = 0x94, #endif -#endif //defined(__AVR_DA__) +#endif // defined(__AVR_DA__) #if defined(__AVR_DB__) ccl0_event_a = 0x00, ccl0_event_b = 0x01, @@ -533,20 +565,20 @@ namespace user #endif adc0_start = 0x0C, evouta_pin_pa2 = 0x0D, -#if defined(Dx_64_PINS) || defined(Dx_48_PINS) +#if defined(PIN_PB2) evoutb_pin_pb2 = 0x0E, #endif evoutc_pin_pc2 = 0x0F, evoutd_pin_pd2 = 0x10, -#if defined(Dx_64_PINS) || defined(Dx_48_PINS) +#if defined(PIN_PE2) evoute_pin_pe2 = 0x11, #endif -#if !defined(Dx_28_PINS) +#if defined(PIN_PF2) evoutf_pin_pf2 = 0x12, #endif -#if defined(Dx_64_PINS) +#if defined(PIN_PG2) evoutg_pin_pg2 = 0x13, - #endif +#endif usart0_irda = 0x14, usart1_irda = 0x15, usart2_irda = 0x16, @@ -559,8 +591,10 @@ namespace user #if defined(USART5) usart5_irda = 0x19, #endif + tca0 = 0x1A, tca0_cnt_a = 0x1A, tca0_cnt_b = 0x1B, + tca1 = 0x1C, tca1_cnt_a = 0x1C, tca1_cnt_b = 0x1D, tcb0_capt = 0x1E, @@ -573,7 +607,7 @@ namespace user tcb3_capt = 0x24, tcb3_cnt = 0x25, #endif -#if defined(TCB3) +#if defined(TCB4) tcb4_capt = 0x26, tcb4_cnt = 0x27, #endif @@ -595,25 +629,514 @@ namespace user #endif // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX evouta_pin_pa7 = 0x8D, -#if defined(Dx_64_PINS) +#if defined(PIN_PB7) evoutb_pin_pb7 = 0x8E, #endif -#if defined(Dx_48_PINS) || defined(Dx_64_PINS) +#if defined(PIN_PC7) evoutc_pin_pc7 = 0x8F, #endif evoutd_pin_pd7 = 0x90, -#if defined(Dx_64_PINS) - evoutb_pin_pe7 = 0x91, +#if defined(PIN_PE7) + evoute_pin_pe7 = 0x91, #endif -#if defined(Dx_64_PINS) - evoutb_pin_pg7 = 0x93, +#if defined(PIN_PG7) + evoutg_pin_pg7 = 0x93, #endif #endif // defined(__AVR_DB__) + +#if defined(__AVR_DD__) + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x0C, +#if defined(PIN_PA2) // not on 14-pin ones. + evouta_pin_pa2 = 0x0D, +#endif + evoutc_pin_pc2 = 0x0F, +#if defined(PIN_PD2) // only on 28 or 32 pin ones. + evoutd_pin_pd2 = 0x10, +#endif +#if defined(PIN_PF2) // only on 32-pin ones. + evoutf_pin_pf2 = 0x12, +#endif + usart0_irda = 0x14, + usart1_irda = 0x15, + tca0 = 0x1A, + tca0_cnt_a = 0x1A, + tca0_cnt_b = 0x1B, + tcb0 = 0x1E, + tcb0_capt = 0x1E, + tcb0_cnt = 0x1F, + tcb1 = 0x20, + tcb1_capt = 0x20, + tcb1_cnt = 0x21, + tcb2 = 0x22, + tcb2_capt = 0x22, + tcb2_cnt = 0x23, + tcd0_in_a = 0x28, + tcd0_in_b = 0x29, +#if defined(PIN_PA7) // not on 14-pin ones. + evouta_pin_pa7 = 0x8D, +#endif +#if defined(PIN_PC7) + evoutc_pin_pc7 = 0x8F, +#endif + evoutd_pin_pd7 = 0x90, +#endif // __AVR_DD__ + }; +}; +// END MegaCorex and DxCore definitions + + +// tinyAVR-2 definitions +#elif MEGATINYCORE_SERIES == 2 +namespace gen { + enum generator_t : uint8_t { + disable = 0x00, + updi_synch = 0x1, + rtc_ovf = 0x6, + rtc_cmp = 0x7, + ccl0_out = 0x10, + ccl1_out = 0x11, + ccl2_out = 0x12, + ccl3_out = 0x13, + ac0_out = 0x20, + adc0_ready = 0x24, + adc0_sample = 0x25, + adc0_window = 0x26, + usart0_xck = 0x60, + usart1_xck = 0x61, + spi0_sck = 0x68, + tca0_ovf_lunf = 0x80, + tca0_hunf = 0x81, + tca0_cmp0 = 0x84, + tca0_cmp1 = 0x85, + tca0_cmp2 = 0x86, + tcb0 = 0xA0, + tcb0_capt = 0xA0, + tcb0_ovf = 0xA1, + tcb1 = 0xA2, + tcb1_capt = 0xA2, + tcb1_ovf = 0xA3, + }; +}; + +namespace gen0 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, +#if defined(PIN_PB4) + pin_pb4 = 0x44, + pin_pb5 = 0x45, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x46, + pin_pb7 = 0x47, +#endif + }; +}; + +namespace gen1 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, +#if defined(PIN_PB4) + pin_pb4 = 0x44, + pin_pb5 = 0x45, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x46, + pin_pb7 = 0x47, +#endif + }; +}; + +namespace gen2 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, +#if defined(PIN_PC0) + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + }; +}; + +namespace gen3 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, +#if defined(PIN_PC0) + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + }; +}; + +namespace gen4 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, +#if defined(PIN_PB4) + pin_pb4 = 0x44, + pin_pb5 = 0x45, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x46, + pin_pb7 = 0x47, +#endif +#if defined(PIN_PC0) + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + }; +}; + +namespace gen5 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, +#if defined(PIN_PB4) + pin_pb4 = 0x44, + pin_pb5 = 0x45, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x46, + pin_pb7 = 0x47, +#endif +#if defined(PIN_PC0) + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + }; +}; + + +namespace user { + enum user_t : uint8_t { + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta_pin_pa2 = 0x09, + evouta_pin_pa7 = 0x89, + evoutb_pin_pb2 = 0x0A, +#if defined(PIN_PB7) + evoutb_pin_pb7 = 0x8A, +#endif +#if defined(PIN_PC2) + evoutc_pin_pc2 = 0x0B, +#endif + usart0_irda = 0x0C, + usart1_irda = 0x0D, + tca0 = 0x0E, + tca0_cnt_a = 0x0E, + tca0_cnt_b = 0x0F, + tcb0 = 0x11, + tcb0_capt = 0x11, + tcb0_cnt = 0x12, + tcb1 = 0x13, + tcb1_capt = 0x13, + tcb1_cnt = 0x14, + }; +}; + + +// tinyAVR-0/1 definitions +#else + +namespace gen0 { + enum generator_t : uint8_t { +#if defined(PIN_PC0) + pin_pc0 = 0x07, + pin_pc1 = 0x08, + pin_pc2 = 0x09, + pin_pc3 = 0x0A, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x0B, + pin_pc5 = 0x0C, +#endif + pin_pa0 = 0x0D, + pin_pa1 = 0x0E, + pin_pa2 = 0x0F, + pin_pa3 = 0x10, + pin_pa4 = 0x11, + pin_pa5 = 0x12, + pin_pa6 = 0x13, + pin_pa7 = 0x14, +#if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) + tcb1 = 0x15, + tcb1_capt = 0x15, +#endif + }; +}; +namespace gen2 { + enum generator_t : uint8_t { + pin_pa0 = 0x0A, + pin_pa1 = 0x0B, + pin_pa2 = 0x0C, + pin_pa3 = 0x0D, + pin_pa4 = 0x0E, + pin_pa5 = 0x0F, + pin_pa6 = 0x10, + pin_pa7 = 0x11, + updi = 0x12, +#if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) + ac1_out = 0x13, + ac2_out = 0x14, +#endif + }; +}; + +// Only on parts with > 8 pins does this have any unique options +#if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) +namespace gen3 { + enum generator_t : uint8_t { + pin_pb0 = 0x0A, + pin_pb1 = 0x0B, + pin_pb2 = 0x0C, + pin_pb3 = 0x0D, +#if defined(PIN_PB4) + pin_pb4 = 0x0E, + pin_pb5 = 0x0F, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x10, + pin_pb7 = 0x11, +#endif +#if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) + ac1_out = 0x12, + ac2_out = 0x13, +#endif + }; +}; +#endif + +#if MEGATINYCORE_SERIES == 1 +// Only 1-series parts have third and fourth async sync channel. +// and only parts with 20/24 pins, or the 1614 have any items on this list available +#if !(defined(__AVR_ATtinyxy2__) || (defined(__AVR_ATtinyxy4__) && PROGMEM_SIZE <= 8192)) +namespace gen4 { + enum generator_t : uint8_t { +#if defined(PIN_PC0) + pin_pc0 = 0x0A, + pin_pc1 = 0x0B, + pin_pc2 = 0x0C, + pin_pc3 = 0x0D, +#endif +#if defined(PIN_PC4) + pin_pc4 = 0x0E, + pin_pc5 = 0x0F, +#endif +#if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here + ac1_out = 0x10, + ac2_out = 0x11, +#endif + }; +}; +#endif + +namespace gen5 { + enum generator_t : uint8_t { + rtc_div8192 = 0x0A, + rtc_div4096 = 0x0B, + rtc_div2048 = 0x0C, + rtc_div1024 = 0x0D, + rtc_div512 = 0x0E, + rtc_div256 = 0x0F, + rtc_div128 = 0x10, + rtc_div64 = 0x11, +#if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series + ac1_out = 0x12, + ac2_out = 0x13, +#endif }; }; -class Event -{ +#if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) +// Only 1-series parts have second sync channel. +// Only on parts with > 8 pins does it have any unique options +namespace gen1 { + enum generator_t : uint8_t { + pin_pb0 = 0x08, + pin_pb1 = 0x09, + pin_pb2 = 0x0A, + pin_pb3 = 0x0B, +#if defined(PIN_PB0) + pin_pb4 = 0x0C, + pin_pb5 = 0x0D, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x0E, + pin_pb7 = 0x0F, +#endif +#if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here + tcb1 = 0x10, + tcb1_capt = 0x10, +#endif + }; +}; +#endif +#endif // end of 1-series only part. + +namespace gens { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + tcb0 = 0x01, + tcb0_capt = 0x01, + tca0_ovf_lunf = 0x02, + tca0_hunf = 0x03, + tca0_cmp0 = 0x04, + tca0_cmp1 = 0x05, + tca0_cmp2 = 0x06, + }; +}; + +namespace gen { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + ccl_lut0 = 0x01, + ccl_lut1 = 0x02, + ac0_out = 0x03, +#if MEGATINYCORE_SERIES == 1 + tcd0_cmpbclr = 0x04, + tcd0_cmpaset = 0x05, + tcd0_cmpbset = 0x06, + tcd0_progev = 0x07, +#endif + rtc_ovf = 0x08, + rtc_cmp = 0x09, + }; +}; + +namespace user { + enum user_t : uint8_t { + tcb0 = 0x00, + tcb0_capt = 0x00, + adc0_start = 0x01, + ccl0_event_a = 0x02, + ccl1_event_a = 0x03, + ccl0_event_b = 0x04, + ccl1_event_b = 0x05, + tcd0_in_a = 0x06, + tcd0_in_b = 0x07, + evouta_pin_pa2 = 0x08, + evoutb_pin_pb2 = 0x09, + evoutc_pin_pc2 = 0x0A, + tcb1 = 0x0B, + tcb1_capt = 0x0B, + adc1_start = 0x0c, + tca0 = 0x10, + tca0_cnt_a = 0x10, + usart0_irda = 0x11, + }; +}; +#endif // tinyAVR-0/1 + +class Event { public: Event(uint8_t channel_num, volatile uint8_t &channel_addr); uint8_t get_channel_number(); @@ -677,6 +1200,7 @@ class Event void long_soft_event(uint8_t length); void start(bool state = true); void stop(); + gen::generator_t gen_from_peripheral(AC_t& comp); private: const uint8_t channel_number; // Holds the event generator channel number @@ -684,35 +1208,115 @@ class Event uint8_t generator_type; // Generator type the event channel is using }; -#if defined(EVSYS_CHANNEL0) +#if defined(MEGACOREX) || defined(DXCORE) || MEGATINYCORE_SERIES == 2 + #if defined(EVSYS_CHANNEL0) + extern Event Event0; + #endif + #if defined(EVSYS_CHANNEL1) + extern Event Event1; + #endif + #if defined(EVSYS_CHANNEL2) + extern Event Event2; + #endif + #if defined(EVSYS_CHANNEL3) + extern Event Event3; + #endif + #if defined(EVSYS_CHANNEL4) + extern Event Event4; + #endif + #if defined(EVSYS_CHANNEL5) + extern Event Event5; + #endif + #if defined(EVSYS_CHANNEL6) + extern Event Event6; + #endif + #if defined(EVSYS_CHANNEL7) + extern Event Event7; + #endif + #if defined(EVSYS_CHANNEL8) + extern Event Event8; + #endif + #if defined(EVSYS_CHANNEL9) + extern Event Event9; + #endif + +// tinyAVR-0/1 +#else +#if defined(EVSYS_SYNCCH0) extern Event Event0; + #define EventSync0 Event0 + #define EVSYS_CHANNEL0 EVSYS_SYNCCH0 #endif -#if defined(EVSYS_CHANNEL1) +#if defined(EVSYS_SYNCCH1) extern Event Event1; + #define EventSync1 Event1 + #define EVSYS_CHANNEL1 EVSYS_SYNCCH1 #endif -#if defined(EVSYS_CHANNEL2) +#if defined(EVSYS_ASYNCCH0) extern Event Event2; + #define EventAsync0 Event2 + #define EVSYS_CHANNEL2 EVSYS_ASYNCCH0 #endif -#if defined(EVSYS_CHANNEL3) +#if defined(EVSYS_ASYNCCH1) extern Event Event3; + #define EventAsync1 Event3 + #define EVSYS_CHANNEL3 EVSYS_ASYNCCH1 #endif -#if defined(EVSYS_CHANNEL4) +#if defined(EVSYS_ASYNCCH2) extern Event Event4; + #define EventAsync2 Event4 + #define EVSYS_CHANNEL4 EVSYS_ASYNCCH2 #endif -#if defined(EVSYS_CHANNEL5) +#if defined(EVSYS_ASYNCCH3) extern Event Event5; + #define EventAsync3 Event5 + #define EVSYS_CHANNEL5 EVSYS_ASYNCCH3 #endif -#if defined(EVSYS_CHANNEL6) - extern Event Event6; +#if defined(EVSYS_SYNCUSER0) + #define EVSYS_USERTCA0CNTA EVSYS_SYNCUSER0 #endif -#if defined(EVSYS_CHANNEL7) - extern Event Event7; +#if defined(EVSYS_SYNCUSER1) + #define EVSYS_USERUSART0IRDA EVSYS_SYNCUSER1 #endif -#if defined(EVSYS_CHANNEL8) - extern Event Event8; +#if defined(EVSYS_ASYNCUSER0) + #define EVSYS_USERTCB0CAPT EVSYS_ASYNCUSER0 #endif -#if defined(EVSYS_CHANNEL9) - extern Event Event9; +#if defined(EVSYS_ASYNCUSER1) + #define EVSYS_USERADC0START EVSYS_ASYNCUSER1 +#endif +#if defined(EVSYS_ASYNCUSER2) + #define EVSYS_USERCCLLUT0A EVSYS_ASYNCUSER2 +#endif +#if defined(EVSYS_ASYNCUSER3) + #define EVSYS_USERCCLLUT1A EVSYS_ASYNCUSER3 +#endif +#if defined(EVSYS_ASYNCUSER4) + #define EVSYS_USERCCLLUT0B EVSYS_ASYNCUSER4 +#endif +#if defined(EVSYS_ASYNCUSER5) + #define EVSYS_USERCCLLUT1B EVSYS_ASYNCUSER5 +#endif +#if defined(EVSYS_ASYNCUSER6) + #define EVSYS_USERTCD0INPUTA EVSYS_ASYNCUSER6 +#endif +#if defined(EVSYS_ASYNCUSER7) + #define EVSYS_USERTCD0INPUTB EVSYS_ASYNCUSER7 +#endif +#if defined(EVSYS_ASYNCUSER8) + #define EVSYS_USEREVSYSEVOUTA EVSYS_ASYNCUSER8 +#endif +#if defined(EVSYS_ASYNCUSER9) + #define EVSYS_USEREVSYSEVOUTB EVSYS_ASYNCUSER9 +#endif +#if defined(EVSYS_ASYNCUSER10) + #define EVSYS_USEREVSYSEVOUTC EVSYS_ASYNCUSER10 +#endif +#if defined(EVSYS_ASYNCUSER11) + #define EVSYS_USERTCB1CAPT EVSYS_ASYNCUSER11 +#endif +#if defined(EVSYS_ASYNCUSER12) + #define EVSYS_USERADC1START EVSYS_ASYNCUSER12 #endif +#endif // tinyAVR-0/1 #endif // EVENT_H From 1c7082dea152e42e1902a7f9594d71a8084fb6c9 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Dec 2021 00:33:53 +0100 Subject: [PATCH 277/351] Formatting + Add tiny0/1/2 support to assign_generator_pin() --- megaavr/libraries/Event/src/Event.cpp | 144 +++++++++++++++++++------- 1 file changed, 108 insertions(+), 36 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index fbb1f3f..0791c7d 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -292,65 +292,137 @@ void Event::set_generator(uint8_t pin_number) * Event_empty object if passed Arduino pin is invalid or no event * channel is available */ -Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) -{ - if(port != NOT_A_PIN && port_pin != NOT_A_PIN) - { - uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; - if(port == PA || port == PB) - { - if(Event0.generator_type == gen::disable || Event0.generator_type == gen) - { +Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { + #if defined(MEGACOREX) || defined(DXCORE) + uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; + if(port == PA || port == PB) { + if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { + Event0.generator_type = gen; + return Event0; + } + else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { + Event1.generator_type = gen; + return Event1; + } + } + else if(port == PC || port == PD) { + if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { + Event2.generator_type = gen; + return Event2; + } + else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { + Event3.generator_type = gen; + return Event3; + } + } + else if(port == PE || port == PF) { + if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { + Event4.generator_type = gen; + return Event4; + } + else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) { + Event5.generator_type = gen; + return Event5; + } + } + #if defined(Dx_64_PINS) + else if(port == PG) { + if(Event6.generator_type == gen::disable || Event6.generator_type == gen) { + Event6.generator_type = gen; + return Event6; + } + else if(Event7.generator_type == gen::disable || Event7.generator_type == gen) { + Event7.generator_type = gen; + return Event7; + } + } + #endif + + return Event_empty; + #elif MEGATINYCORE_SERIES == 2 + if(port != PC) { + uint8_t gen = port_pin | (port == PB ? 0x40 : 0x48); + if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } - else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) - { + else if (Event1.generator_type == gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } } - else if(port == PC || port == PD) - { - if(Event2.generator_type == gen::disable || Event2.generator_type == gen) - { + if (port != PB) { + uint8_t gen = port_pin | (port == PA ? 0x40 : 0x48); + if (Event2.generator_type == gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } - else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) - { + else if (Event3.generator_type == gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } } - else if(port == PE || port == PF) + if (port != PA) { - if(Event4.generator_type == gen::disable || Event4.generator_type == gen) - { + uint8_t gen = port_pin | (port == PC ? 0x40 : 0x48); + if (Event4.generator_type == gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } - else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) - { + else if (Event5.generator_type == gen::disable || Event5.generator_type == gen) { Event5.generator_type = gen; return Event5; } } - #if defined(Dx_64_PINS) - else if(port == PG) - { - if(Event6.generator_type == gen::disable || Event6.generator_type == gen) - { - Event6.generator_type = gen; - return Event6; - } - else if(Event7.generator_type == gen::disable || Event7.generator_type == gen) - { - Event7.generator_type = gen; - return Event7; + return Event_empty; + #else // tinyAVR-0/1 series + uint8_t gen = port_pin + 0x0A; + #if !defined(__AVR_ATtinyxy2__) + if (port == PA) { + #endif + if (Event2.generator_type == gen::disable || Event2.generator_type == gen) { + Event2.generator_type = gen; + return Event2; + } + gen += 3; + if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { + Event0.generator_type = gen; + return Event0; + } + #if !defined(__AVR_ATtinyxy2__) + } + #endif + if (port == PB) { + if (Event3.generator_type == gen::disable || Event3.generator_type == gen) { + Event3.generator_type = gen; + return Event3; + } + #if MEGATINYCORE_SERIES == 1 // No Event1 on 0-series + gen -= 2; + if (Event1.generator_type == gen::disable || Event1.generator_type == gen) { + Event1.generator_type = gen; + return Event1; + } + #endif } - } - #endif + #if defined (PIN_PC0) // can't test if PORTx is defined - all are defined everywhere) + if (port == PC) { + #if MEGATINYCORE_SERIES == 1 // no event 4 on 0-series + if (Event4.generator_type == gen::disable || Event4.generator_type == gen) { + Event4.generator_type = gen; + return Event4; + } + #endif + gen -= 3; + if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { + Event0.generator_type = gen; + return Event0; + } + } + #endif // PC-bearing parts end here + + #endif // end of tiny 0/1 assign_generator_pin() } return Event_empty; } From 7d94198bb82169358d27445321d8b0bfdc4b400a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Dec 2021 23:11:12 +0100 Subject: [PATCH 278/351] Formatting + tinyAVR-0/1/2 improvements --- megaavr/libraries/Event/src/Event.cpp | 403 +++++++++++++------------- megaavr/libraries/Event/src/Event.h | 83 +++--- 2 files changed, 248 insertions(+), 238 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 0791c7d..dd20a1c 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -41,8 +41,7 @@ * @param channel_addr Register address to channel generator */ Event::Event(uint8_t channel_num, volatile uint8_t &channel_addr) - : channel_number(channel_num), channel_address(channel_addr) -{ + : channel_number(channel_num), channel_address(channel_addr) { } @@ -51,8 +50,7 @@ Event::Event(uint8_t channel_num, volatile uint8_t &channel_addr) * * @return uint8_t Event channel number */ -uint8_t Event::get_channel_number() -{ +uint8_t Event::get_channel_number() { return channel_number; } @@ -64,52 +62,62 @@ uint8_t Event::get_channel_number() * @return Event& Event object associated with the channel number. * Returns the Event_empty object if invalid channel number */ -Event& Event::get_channel(uint8_t ch_number) -{ +Event& Event::get_channel(uint8_t ch_number) { #if defined(EVSYS_CHANNEL0) - if(Event0.channel_number == ch_number) + if(Event0.channel_number == ch_number) { return Event0; + } #endif #if defined(EVSYS_CHANNEL1) - if(Event1.channel_number == ch_number) + if(Event1.channel_number == ch_number) { return Event1; + } #endif #if defined(EVSYS_CHANNEL2) - if(Event2.channel_number == ch_number) + if(Event2.channel_number == ch_number) { return Event2; + } #endif #if defined(EVSYS_CHANNEL3) - if(Event3.channel_number == ch_number) + if(Event3.channel_number == ch_number) { return Event3; + } #endif #if defined(EVSYS_CHANNEL4) - if(Event4.channel_number == ch_number) + if(Event4.channel_number == ch_number) { return Event4; + } #endif #if defined(EVSYS_CHANNEL5) - if(Event5.channel_number == ch_number) + if(Event5.channel_number == ch_number) { return Event5; + } #endif #if defined(EVSYS_CHANNEL6) - if(Event6.channel_number == ch_number) + if(Event6.channel_number == ch_number) { return Event6; + } #endif #if defined(EVSYS_CHANNEL7) - if(Event7.channel_number == ch_number) + if(Event7.channel_number == ch_number) { return Event7; + } #endif #if defined(EVSYS_CHANNEL8) - if(Event8.channel_number == ch_number) + if(Event8.channel_number == ch_number) { return Event8; + } #endif #if defined(EVSYS_CHANNEL9) - if(Event9.channel_number == ch_number) + if(Event9.channel_number == ch_number) { return Event9; + } #endif #if defined(EVSYS_CHANNEL0) - else + else { return Event_empty; + } #endif } @@ -120,52 +128,62 @@ Event& Event::get_channel(uint8_t ch_number) * @param generator Event generator * @return Event& Event channel object used with this event generator */ -Event& Event::get_generator_channel(gen::generator_t generator) -{ +Event& Event::get_generator_channel(gen::generator_t generator) { #if defined(EVSYS_CHANNEL0) - if(Event0.generator_type == generator) + if(Event0.generator_type == generator) { return Event0; + } #endif #if defined(EVSYS_CHANNEL1) - if(Event1.generator_type == generator) + if(Event1.generator_type == generator) { return Event1; + } #endif #if defined(EVSYS_CHANNEL2) - if(Event2.generator_type == generator) + if(Event2.generator_type == generator) { return Event2; + } #endif #if defined(EVSYS_CHANNEL3) - if(Event3.generator_type == generator) + if(Event3.generator_type == generator) { return Event3; + } #endif #if defined(EVSYS_CHANNEL4) - if(Event4.generator_type == generator) + if(Event4.generator_type == generator) { return Event4; + } #endif #if defined(EVSYS_CHANNEL5) - if(Event5.generator_type == generator) + if(Event5.generator_type == generator) { return Event5; + } #endif #if defined(EVSYS_CHANNEL6) - if(Event6.generator_type == generator) + if(Event6.generator_type == generator) { return Event6; + } #endif #if defined(EVSYS_CHANNEL7) - if(Event7.generator_type == generator) + if(Event7.generator_type == generator) { return Event7; + } #endif #if defined(EVSYS_CHANNEL8) - if(Event8.generator_type == generator) + if(Event8.generator_type == generator) { return Event8; + } #endif #if defined(EVSYS_CHANNEL9) - if(Event9.generator_type == generator) + if(Event9.generator_type == generator) { return Event9; + } #endif #if defined(EVSYS_CHANNEL0) - else + else { return Event_empty; + } #endif } @@ -176,54 +194,56 @@ Event& Event::get_generator_channel(gen::generator_t generator) * @param generator_pin Event generator Arduino pin number * @return Event& Event channel object used with this event generator */ -Event& Event::get_generator_channel(uint8_t generator_pin) -{ +Event& Event::get_generator_channel(uint8_t generator_pin) { uint8_t port = digitalPinToPort(generator_pin); uint8_t port_pin = digitalPinToBitPosition(generator_pin); - if(port != NOT_A_PIN && port_pin != NOT_A_PIN) - { + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; - if(port == PA || port == PB) - { + if(port == PA || port == PB) { #if defined(EVSYS_CHANNEL0) - if(Event0.generator_type == gen) + if(Event0.generator_type == gen) { return Event0; + } #endif #if defined(EVSYS_CHANNEL1) - else if(Event1.generator_type == gen) + else if(Event1.generator_type == gen) { return Event1; + } #endif } - else if(port == PC || port == PD) - { + else if(port == PC || port == PD) { #if defined(EVSYS_CHANNEL2) - if(Event2.generator_type == gen) + if(Event2.generator_type == gen) { return Event2; + } #endif #if defined(EVSYS_CHANNEL3) - else if(Event3.generator_type == gen) + else if(Event3.generator_type == gen) { return Event3; + } #endif } - else if(port == PE || port == PF) - { + else if(port == PE || port == PF) { #if defined(EVSYS_CHANNEL4) - if(Event4.generator_type == gen) + if(Event4.generator_type == gen) { return Event4; + } #endif #if defined(EVSYS_CHANNEL5) - else if(Event5.generator_type == gen) + else if(Event5.generator_type == gen) { return Event5; + } #endif } #if defined(Dx_64_PINS) - else if(port == PG) - { - if(Event6.generator_type == gen) + else if(port == PG) { + if(Event6.generator_type == gen) { return Event6; - else if(Event7.generator_type == gen) + } + else if(Event7.generator_type == gen) { return Event7; + } } #endif } @@ -239,8 +259,7 @@ Event& Event::get_generator_channel(uint8_t generator_pin) * * @return uint8_t Generator type. Returns 0 if no generator is used */ -uint8_t Event::get_generator() -{ +uint8_t Event::get_generator() { return generator_type; } @@ -252,8 +271,7 @@ uint8_t Event::get_generator() * Use gen:: for functionality present on all event channels. * Use genN:: for functionality present on channel N. */ -void Event::set_generator(gen::generator_t event_generator) -{ +void Event::set_generator(gen::generator_t event_generator) { // Store event generator setting for use in start() and stop() generator_type = (uint8_t)event_generator; } @@ -268,16 +286,17 @@ void Event::set_generator(gen::generator_t event_generator) * * @param pin_number Arduino pin number to use as event generator */ -void Event::set_generator(uint8_t pin_number) -{ +void Event::set_generator(uint8_t pin_number) { uint8_t port = digitalPinToPort(pin_number); uint8_t port_pin = digitalPinToBitPosition(pin_number); // Store event generator setting for use in start() and stop() - if(port != NOT_A_PIN && port_pin != NOT_A_PIN) + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { generator_type = 0x40 | (port & 0x01) << 3 | port_pin; - else + } + else { generator_type = gen::disable; + } } @@ -340,82 +359,82 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { #endif return Event_empty; - #elif MEGATINYCORE_SERIES == 2 + #elif defined(TINY_2_SERIES) if(port != PC) { uint8_t gen = port_pin | (port == PB ? 0x40 : 0x48); - if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } - else if (Event1.generator_type == gen::disable || Event1.generator_type == gen) { + else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } } - if (port != PB) { + if(port != PB) { uint8_t gen = port_pin | (port == PA ? 0x40 : 0x48); - if (Event2.generator_type == gen::disable || Event2.generator_type == gen) { + if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } - else if (Event3.generator_type == gen::disable || Event3.generator_type == gen) { + else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } } - if (port != PA) + if(port != PA) { uint8_t gen = port_pin | (port == PC ? 0x40 : 0x48); - if (Event4.generator_type == gen::disable || Event4.generator_type == gen) { + if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } - else if (Event5.generator_type == gen::disable || Event5.generator_type == gen) { + else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) { Event5.generator_type = gen; return Event5; } } return Event_empty; - #else // tinyAVR-0/1 series + #elif defined(TINY_0_SERIES) || defined(TINY_1_SERIES) uint8_t gen = port_pin + 0x0A; #if !defined(__AVR_ATtinyxy2__) - if (port == PA) { + if(port == PA) { #endif - if (Event2.generator_type == gen::disable || Event2.generator_type == gen) { + if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } gen += 3; - if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } #if !defined(__AVR_ATtinyxy2__) } #endif - if (port == PB) { - if (Event3.generator_type == gen::disable || Event3.generator_type == gen) { + if(port == PB) { + if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } - #if MEGATINYCORE_SERIES == 1 // No Event1 on 0-series + #if defined(TINY_1_SERIES) // No Event1 on 0-series gen -= 2; - if (Event1.generator_type == gen::disable || Event1.generator_type == gen) { + if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } #endif } #if defined (PIN_PC0) // can't test if PORTx is defined - all are defined everywhere) - if (port == PC) { - #if MEGATINYCORE_SERIES == 1 // no event 4 on 0-series - if (Event4.generator_type == gen::disable || Event4.generator_type == gen) { + if(port == PC) { + #if defined(TINY_1_SERIES) // no event 4 on 0-series + if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } #endif gen -= 3; - if (Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } @@ -438,8 +457,7 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { * Event_empty object if passed Arduino pin is invalid or no event * channel is available */ -Event& Event::assign_generator_pin(uint8_t pin_number) -{ +Event& Event::assign_generator_pin(uint8_t pin_number) { uint8_t port = digitalPinToPort(pin_number); uint8_t port_pin = digitalPinToBitPosition(pin_number); return Event::assign_generator_pin(port, port_pin); @@ -455,90 +473,79 @@ Event& Event::assign_generator_pin(uint8_t pin_number) * @return Event& Reference to the event object the generator has been assigned to. * Returns the Event_empty object if no generator has been assigned to a channel */ -Event& Event::assign_generator(gen::generator_t event_generator) -{ +Event& Event::assign_generator(gen::generator_t event_generator) { // Check if generator is already in use Event& channel = Event::get_generator_channel(event_generator); - if(channel.get_channel_number() != 255) + if(channel.get_channel_number() != 255) { return channel; + } - else - { + else { #if defined(EVSYS_CHANNEL9) - if(Event9.get_generator() == gen::disable) - { + if(Event9.get_generator() == gen::disable) { Event9.set_generator(event_generator); return Event9; } else #endif #if defined(EVSYS_CHANNEL8) - if(Event8.get_generator() == gen::disable) - { + if(Event8.get_generator() == gen::disable) { Event8.set_generator(event_generator); return Event8; } else #endif #if defined(EVSYS_CHANNEL7) - if(Event7.get_generator() == gen::disable) - { + if(Event7.get_generator() == gen::disable) { Event7.set_generator(event_generator); return Event7; } else #endif #if defined(EVSYS_CHANNEL6) - if(Event6.get_generator() == gen::disable) - { + if(Event6.get_generator() == gen::disable) { Event6.set_generator(event_generator); return Event6; } else #endif #if defined(EVSYS_CHANNEL5) - if(Event5.get_generator() == gen::disable) - { + if(Event5.get_generator() == gen::disable) { Event5.set_generator(event_generator); return Event5; } else #endif #if defined(EVSYS_CHANNEL4) - if(Event4.get_generator() == gen::disable) - { + if(Event4.get_generator() == gen::disable) { Event4.set_generator(event_generator); return Event4; } else #endif #if defined(EVSYS_CHANNEL3) - if(Event3.get_generator() == gen::disable) - { + if(Event3.get_generator() == gen::disable) { Event3.set_generator(event_generator); return Event3; } else #endif #if defined(EVSYS_CHANNEL2) - if(Event2.get_generator() == gen::disable) - { + if(Event2.get_generator() == gen::disable) { Event2.set_generator(event_generator); return Event2; } else #endif #if defined(EVSYS_CHANNEL1) - if(Event1.get_generator() == gen::disable) - { + if(Event1.get_generator() == gen::disable) { Event1.set_generator(event_generator); return Event1; } else #endif #if defined(EVSYS_CHANNEL0) - if(Event0.get_generator() == gen::disable) - { + if(Event0.get_generator() == gen::disable) { Event0.set_generator(event_generator); return Event0; } @@ -556,8 +563,7 @@ Event& Event::assign_generator(gen::generator_t event_generator) * @return int8_t Event channel number. * Returns -1 if not connected to any event channel */ -int8_t Event::get_user_channel_number(user::user_t event_user) -{ +int8_t Event::get_user_channel_number(user::user_t event_user) { // Figure out what user register to read from to based on the passed parameter volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; @@ -573,54 +579,64 @@ int8_t Event::get_user_channel_number(user::user_t event_user) * @return Event& Event channel object. Returns the Event_empty object if the * user is not connected to any event channel */ -Event& Event::get_user_channel(user::user_t event_user) -{ +Event& Event::get_user_channel(user::user_t event_user) { int8_t ch_number = get_user_channel_number(event_user); #if defined(EVSYS_CHANNEL0) - if(Event0.channel_number == ch_number) + if(Event0.channel_number == ch_number) { return Event0; + } #endif #if defined(EVSYS_CHANNEL1) - if(Event1.channel_number == ch_number) + if(Event1.channel_number == ch_number) { return Event1; + } #endif #if defined(EVSYS_CHANNEL2) - if(Event2.channel_number == ch_number) + if(Event2.channel_number == ch_number) { return Event2; + } #endif #if defined(EVSYS_CHANNEL3) - if(Event3.channel_number == ch_number) + if(Event3.channel_number == ch_number) { return Event3; + } #endif #if defined(EVSYS_CHANNEL4) - if(Event4.channel_number == ch_number) + if(Event4.channel_number == ch_number) { return Event4; + } #endif #if defined(EVSYS_CHANNEL5) - if(Event5.channel_number == ch_number) + if(Event5.channel_number == ch_number) { return Event5; + } #endif #if defined(EVSYS_CHANNEL6) - if(Event6.channel_number == ch_number) + if(Event6.channel_number == ch_number) { return Event6; + } #endif #if defined(EVSYS_CHANNEL7) - if(Event7.channel_number == ch_number) + if(Event7.channel_number == ch_number) { return Event7; + } #endif #if defined(EVSYS_CHANNEL8) - if(Event8.channel_number == ch_number) + if(Event8.channel_number == ch_number) { return Event8; + } #endif #if defined(EVSYS_CHANNEL9) - if(Event9.channel_number == ch_number) + if(Event9.channel_number == ch_number) { return Event9; + } #endif #if defined(EVSYS_CHANNEL0) - else + else { return Event_empty; + } #endif } @@ -630,23 +646,26 @@ Event& Event::get_user_channel(user::user_t event_user) * * @param event_user The event user to connect to a particular channel */ -void Event::set_user(user::user_t event_user) -{ +void Event::set_user(user::user_t event_user) { // Figure out what user register to write to based on the passed parameter uint8_t event_user_mask = event_user & 0x7F; - volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; + + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + volatile uint8_t *user_register = &EVSYS_ASYNCUSER0 + (volatile uint8_t &)event_user_mask; + #else + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t &)event_user_mask; + #endif // Connect user to the channel we're working with *user_register = channel_number + 1; // Set PORTMUX pin swap for EVOUT if selected as channel generator - if(event_user & 0x80) - { - #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) + if(event_user & 0x80) { + #if defined(MEGACOREX) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); #elif defined(__AVR_DA__) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0E)); - #elif defined(__AVR_DB__) + #elif defined(__AVR_DB__) || defined(__AVR_DD__) || defined(TINY_2_SERIES) PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0D)); #endif } @@ -661,56 +680,24 @@ void Event::set_user(user::user_t event_user) (for instance user::evouta_pin_pa2 pin PIN_PA2 is passed) * Returns -1 if invalid pin is passed */ -int8_t Event::set_user_pin(uint8_t pin_number) -{ +int8_t Event::set_user_pin(uint8_t pin_number) { uint8_t port = digitalPinToPort(pin_number); uint8_t port_pin = digitalPinToBitPosition(pin_number); - int8_t event_user = -1; - if(port != NOT_A_PIN && port_pin != NOT_A_PIN) - { - if(port == PA) - { - if(port_pin == 2) - event_user = user::evouta_pin_pa2; - else if(port_pin == 7) - event_user = user::evouta_pin_pa7; - } - #if defined(PIN_PB2) - else if(port == PB) - { - if(port_pin == 2) - event_user = user::evoutb_pin_pb2; - } - #endif - else if(port == PC) - { - if(port_pin == 2) - event_user = user::evoutc_pin_pc2; - #if defined(PIN_PC7) - else if(port_pin == 7) - event_user = user::evoutc_pin_pc7; - #endif + if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { + uint8_t evout_user = (uint8_t)user::evouta_pin_pa2; + if(port_pin == 2) { + event_user = (user::user_t)(evout_user + port); } - else if(port == PD) - { - if(port_pin == 2) - event_user = user::evoutd_pin_pd2; - else if(port_pin == 7) - event_user = user::evoutd_pin_pd7; - } - #if defined(PIN_PE2) - else if(port == PE) - { - if(port_pin == 2) - event_user = user::evoute_pin_pe2; + #if !defined(TINY_0_SERIES) && !defined(TINY_1_SERIES) + else if(port_pin == 7) { + event_user = (user::user_t)(evout_user + port); } + #endif - else if(port == PF) - { - if(port_pin == 2) - event_user = user::evoutf_pin_pf2; + else { + return -1; } set_user((user::user_t)event_user); } @@ -723,8 +710,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) * * @param event_user The event user to remove from a particular channel */ -void Event::clear_user(user::user_t event_user) -{ +void Event::clear_user(user::user_t event_user) { // Figure out what user register to write to based on the passed parameter uint8_t event_user_mask = event_user & 0x7F; volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; @@ -733,9 +719,8 @@ void Event::clear_user(user::user_t event_user) *user_register = 0x00; // Clear PORTMUX pin swap for EVOUT if selected as channel generator - if(event_user & 0x80) - { - #if defined(__AVR_ATmegax08__) || defined(__AVR_ATmegax09__) + if(event_user & 0x80) { + #if defined(MEGACOREX) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); #elif defined(__AVR_DA__) PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0E)); @@ -750,22 +735,34 @@ void Event::clear_user(user::user_t event_user) * @brief Creates a software event for a particular event channel * */ -void Event::soft_event() -{ +void Event::soft_event() { // Write to the bit that represent the channel in the strobe register #if defined(EVSYS_STROBE) - // megaAVR 0-series + // megaAVR 0-series calls the register EVSYS.STROBE EVSYS.STROBE = (1 << channel_number); - #elif defined(EVSYS_ASYNCCH0) - // tinyAVR 0/1-series + #elif defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + // Channels 0 and 1 are the sync channels, which are strobbed with the syncstrobe registers. The others are the async channels, + // strobed with the asyncstrobe. Since the sync strobe has only 2 possible thing s to strobe, bit 0 or bit 1 corresponding to byte + // values 1 and 2, we can just add 1 to the byte value to achieve that. + if(channel_number < 2) { + EVSYS.SYNCSTROBE = (channel_number + 1); + } + else { + EVSYS.ASYNCSTROBE = (1 << (channel_number - 2)); + } #else - // tinyAVR 2-series and AVR-Dx - // We expect there to be an EVSYS.SWEVENTA channel plus an - // EVSYS.SWEVENTB it it has more than 8 event channels. + // Everything newer calls the registers EVSYS.SWEVENTA or SWEVENTB for the few devices lucky enough to have more than 8 channels. #if defined(EVSYS_SWEVENTB) - if(channel_number < 8) + if(channel_number < 8) { EVSYS.SWEVENTA = (1 << channel_number); - else + } + else { + /* Dirty trick: No available part has more than 10 event channels. + * So if we are strobing one of those last two, the value we are writing to the register is iwith 1 or 2 (as with sync channel + * on tiny 0/1). So channel number is 8 or 9, subtract 7 to get 1 or 2, and write that. + * Doesn't save much flash, but variable-shift operations are surprisignly inefficient in speed. The case for SWEVENTA involves + * a loop, 5 clocks in duration per bit + */ EVSYS.SWEVENTB = channel_number - 7; } #else @@ -775,22 +772,27 @@ void Event::soft_event() } -void Event::long_soft_event(uint8_t length) -{ +/** + * @brief Creates a software event for a particular event channel with a set + * time duration + * + * @param length Length in CPU clock cycles + */ +void Event::long_soft_event(uint8_t length) { uint8_t channel = channel_number; uint16_t strobeaddr; #if defined(EVSYS_STROBE) strobeaddr = (uint16_t) &EVSYS_STROBE; #elif defined(EVSYS_SWEVENTB) - if(channel > 7) - { + if(channel > 7) { channel -= 8; - strobeaddr = (uint16_t) &EVSYS_SWEVENTB; + strobeaddr = (uint16_t)&EVSYS_SWEVENTB; + } + else { + strobeaddr = (uint16_t)&EVSYS_SWEVENTA; } - else - strobeaddr = (uint16_t) &EVSYS_SWEVENTA; #elif defined(EVSYS_SWEVENTA) - strobeaddr = (uint16_t) &EVSYS_SWEVENTA; + strobeaddr = (uint16_t)&EVSYS_SWEVENTA; #else #error "Don't know the strobe register!" #endif @@ -829,21 +831,17 @@ void Event::long_soft_event(uint8_t length) } - /** * @brief Starts the event generator for a particular event channel * * @param state Optional parameter. Defaults to true */ -void Event::start(bool state) -{ - if(state) - { +void Event::start(bool state) { + if(state) { // Write event generator setting to EVSYS_CHANNELn register channel_address = generator_type; } - else - { + else { // Disable event generator channel_address = gen::disable; } @@ -854,7 +852,6 @@ void Event::start(bool state) * @brief Stops the event generator for a particular event channel * */ -void Event::stop() -{ +void Event::stop() { start(false); } diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 7974833..c8574a2 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -3,6 +3,16 @@ #include +#if defined(MEGATINYCORE) + #if (MEGATINYCORE_SERIES == 0) + #define TINY_0_SERIES + #elif (MEGATINYCORE_SERIES == 1) + #define TINY_1_SERIES + #elif (MEGATINYCORE_SERIES == 2) + #define TINY_2_SERIES + #endif +#endif + #if defined(MEGACOREX) || defined(DXCORE) // Features present on all generator channels namespace gen { @@ -694,7 +704,7 @@ namespace user { // tinyAVR-2 definitions -#elif MEGATINYCORE_SERIES == 2 +#elif defined(TINY_2_SERIES) namespace gen { enum generator_t : uint8_t { disable = 0x00, @@ -941,10 +951,8 @@ namespace user { }; }; - // tinyAVR-0/1 definitions -#else - +#elif defined(TINY_0_SERIES) || defined(TINY_1_SERIES) namespace gen0 { enum generator_t : uint8_t { #if defined(PIN_PC0) @@ -965,7 +973,7 @@ namespace gen0 { pin_pa5 = 0x12, pin_pa6 = 0x13, pin_pa7 = 0x14, -#if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) +#if (PROGMEM_SIZE > 8192 && defined(TINY_1_SERIES)) tcb1 = 0x15, tcb1_capt = 0x15, #endif @@ -982,7 +990,7 @@ namespace gen2 { pin_pa6 = 0x10, pin_pa7 = 0x11, updi = 0x12, -#if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) +#if (PROGMEM_SIZE > 8192 && defined(TINY_1_SERIES)) ac1_out = 0x13, ac2_out = 0x14, #endif @@ -1013,7 +1021,33 @@ namespace gen3 { }; #endif -#if MEGATINYCORE_SERIES == 1 +#if defined(TINY_1_SERIES) + +#if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) +// Only 1-series parts have second sync channel. +// Only on parts with > 8 pins does it have any unique options +namespace gen1 { + enum generator_t : uint8_t { + pin_pb0 = 0x08, + pin_pb1 = 0x09, + pin_pb2 = 0x0A, + pin_pb3 = 0x0B, +#if defined(PIN_PB0) + pin_pb4 = 0x0C, + pin_pb5 = 0x0D, +#endif +#if defined(PIN_PB6) + pin_pb6 = 0x0E, + pin_pb7 = 0x0F, +#endif +#if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here + tcb1 = 0x10, + tcb1_capt = 0x10, +#endif + }; +}; +#endif + // Only 1-series parts have third and fourth async sync channel. // and only parts with 20/24 pins, or the 1614 have any items on this list available #if !(defined(__AVR_ATtinyxy2__) || (defined(__AVR_ATtinyxy4__) && PROGMEM_SIZE <= 8192)) @@ -1053,31 +1087,6 @@ namespace gen5 { #endif }; }; - -#if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) -// Only 1-series parts have second sync channel. -// Only on parts with > 8 pins does it have any unique options -namespace gen1 { - enum generator_t : uint8_t { - pin_pb0 = 0x08, - pin_pb1 = 0x09, - pin_pb2 = 0x0A, - pin_pb3 = 0x0B, -#if defined(PIN_PB0) - pin_pb4 = 0x0C, - pin_pb5 = 0x0D, -#endif -#if defined(PIN_PB6) - pin_pb6 = 0x0E, - pin_pb7 = 0x0F, -#endif -#if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here - tcb1 = 0x10, - tcb1_capt = 0x10, -#endif - }; -}; -#endif #endif // end of 1-series only part. namespace gens { @@ -1101,7 +1110,7 @@ namespace gen { ccl_lut0 = 0x01, ccl_lut1 = 0x02, ac0_out = 0x03, -#if MEGATINYCORE_SERIES == 1 +#if defined(TINY_1_SERIES) tcd0_cmpbclr = 0x04, tcd0_cmpaset = 0x05, tcd0_cmpbset = 0x06, @@ -1134,7 +1143,7 @@ namespace user { usart0_irda = 0x11, }; }; -#endif // tinyAVR-0/1 +#endif // TINY_0_SERIES || TINY_1_SERIES class Event { public: @@ -1190,6 +1199,10 @@ class Event { void get_generator_channel(gen9::generator_t generator) { get_generator_channel((gen::generator_t)generator); } void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } #endif + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + void get_generator_channel(gens::generator_t generator) { get_generator_channel((gen::generator_t)generator); } + void set_generator(gen::generator_t generator) { set_generator((gen::generator_t)generator); } + #endif static int8_t get_user_channel_number(user::user_t event_user); static Event& get_user_channel(user::user_t event_user); @@ -1208,7 +1221,7 @@ class Event { uint8_t generator_type; // Generator type the event channel is using }; -#if defined(MEGACOREX) || defined(DXCORE) || MEGATINYCORE_SERIES == 2 +#if defined(MEGACOREX) || defined(DXCORE) || defined(TINY_2_SERIES) #if defined(EVSYS_CHANNEL0) extern Event Event0; #endif From 6c5a6ddb77a77e7c84de31110f135b52acc7e047 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 14 Dec 2021 20:48:07 +0100 Subject: [PATCH 279/351] Add EEPROM retain tools menu option --- README.md | 5 ++ megaavr/boards.txt | 193 ++++++++++++++++++++++++++++----------------- 2 files changed, 126 insertions(+), 72 deletions(-) diff --git a/README.md b/README.md index f23bcaa..da0b53c 100644 --- a/README.md +++ b/README.md @@ -18,6 +18,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB - [Using a bootloader](#using-a-bootloader) * [Supported clock frequencies](#supported-clock-frequencies) * [BOD option](#bod-option) +* [EEPROM retain option](#eeprom-option) * [Reset pin](#reset-pin) * [Printf support](#printf-support) * [Fast IO](#fast-io) @@ -113,6 +114,10 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol | Disabled | +## EEPROM option +If you want the EEPROM to be erased every time you burn the bootloader or upload using a programmer, you can turn off this option. You'll have to connect a UPDI programmer and hit "Burn bootloader" to enable or disable EEPROM retain. Note that when uploading using a bootloader, the EEPROM will always be retained. + + ## Reset pin None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed over the UPDI interface. This means that the reset pin can be used as a GPIO pin instead! There's no need for a high voltage programmer to turn that pin into a reset pin again either. If you have a development board you can instead use the reset button as a general-purpose button for your project. Note that the reset pin cannot be usd as a GPIO when using a bootloader. diff --git a/megaavr/boards.txt b/megaavr/boards.txt index a5e0d81..74e4904 100644 --- a/megaavr/boards.txt +++ b/megaavr/boards.txt @@ -1,5 +1,6 @@ menu.clock=Clock menu.BOD=BOD +menu.eeprom=EEPROM menu.pinout=Pinout menu.resetpin=Reset pin menu.bootloader=Bootloader @@ -48,11 +49,17 @@ menu.bootloader=Bootloader 4809.menu.pinout.nano_every.program.extra_params=-P{serial.port} -e 4809.menu.pinout.nano_every.build.compat= +# EEPROM +4809.menu.eeprom.keep=EEPROM retained +4809.menu.eeprom.keep.bootloader.eesave_bit=1 +4809.menu.eeprom.erase=EEPROM not retained +4809.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 4809.menu.resetpin.reset=Reset -4809.menu.resetpin.reset.bootloader.SYSCFG0=0xC9 +4809.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.resetpin.gpio=GPIO -4809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +4809.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 4809.menu.BOD.2v6=BOD 2.6V @@ -177,7 +184,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_default.build.export_merged_output=true 4809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 4809.menu.bootloader.uart0_alternative.upload.maximum_size=48640 @@ -188,7 +195,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart0_alternative.build.export_merged_output=true 4809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 4809.menu.bootloader.uart1_default.upload.maximum_size=48640 @@ -199,7 +206,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_default.build.export_merged_output=true 4809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 4809.menu.bootloader.uart1_alternative.upload.maximum_size=48640 @@ -210,7 +217,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart1_alternative.build.export_merged_output=true 4809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 4809.menu.bootloader.uart2_default.upload.maximum_size=48640 @@ -221,7 +228,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_default.build.export_merged_output=true 4809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 4809.menu.bootloader.uart2_alternative.upload.maximum_size=48640 @@ -232,7 +239,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart2_alternative.build.export_merged_output=true 4809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 4809.menu.bootloader.uart3_default.upload.maximum_size=48640 @@ -243,7 +250,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_default.build.export_merged_output=true 4809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 4809.menu.bootloader.uart3_alternative.upload.maximum_size=48640 @@ -254,7 +261,7 @@ menu.bootloader=Bootloader 4809.menu.bootloader.uart3_alternative.build.export_merged_output=true 4809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 -4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 +4809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} #################### @@ -293,11 +300,17 @@ menu.bootloader=Bootloader 4808.menu.pinout.nano_4808.upload.protocol=jtag2updi 4808.menu.pinout.nano_4808.program.extra_params=-P{serial.port} -e +# EEPROM +4808.menu.eeprom.keep=EEPROM retained +4808.menu.eeprom.keep.bootloader.eesave_bit=1 +4808.menu.eeprom.erase=EEPROM not retained +4808.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 4808.menu.resetpin.reset=Reset -4808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +4808.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.resetpin.gpio=GPIO -4808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +4808.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 4808.menu.BOD.2v6=BOD 2.6V @@ -416,7 +429,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_default.build.export_merged_output=true 4808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 4808.menu.bootloader.uart0_alternative.upload.maximum_size=48640 @@ -427,7 +440,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart0_alternative.build.export_merged_output=true 4808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 4808.menu.bootloader.uart1_default.upload.maximum_size=48640 @@ -438,7 +451,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_default.build.export_merged_output=true 4808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 4808.menu.bootloader.uart1_alternative.upload.maximum_size=48640 @@ -449,7 +462,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart1_alternative.build.export_merged_output=true 4808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 4808.menu.bootloader.uart2_default.upload.maximum_size=48640 @@ -460,7 +473,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_default.build.export_merged_output=true 4808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 4808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 4808.menu.bootloader.uart2_alternative.upload.maximum_size=48640 @@ -471,7 +484,7 @@ menu.bootloader=Bootloader 4808.menu.bootloader.uart2_alternative.build.export_merged_output=true 4808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 4808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +4808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} @@ -505,11 +518,17 @@ menu.bootloader=Bootloader 3209.menu.pinout.uno_wifi.build.variant=uno-wifi 3209.menu.pinout.uno_wifi.build.compat= +# EEPROM +3209.menu.eeprom.keep=EEPROM retained +3209.menu.eeprom.keep.bootloader.eesave_bit=1 +3209.menu.eeprom.erase=EEPROM not retained +3209.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 3209.menu.resetpin.reset=Reset -3209.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +3209.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.resetpin.gpio=GPIO -3209.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +3209.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 3209.menu.BOD.2v6=BOD 2.6V @@ -628,7 +647,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_default.build.export_merged_output=true 3209.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 3209.menu.bootloader.uart0_alternative.upload.maximum_size=32256 @@ -639,7 +658,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart0_alternative.build.export_merged_output=true 3209.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 3209.menu.bootloader.uart1_default.upload.maximum_size=32256 @@ -650,7 +669,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_default.build.export_merged_output=true 3209.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 3209.menu.bootloader.uart1_alternative.upload.maximum_size=32256 @@ -661,7 +680,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart1_alternative.build.export_merged_output=true 3209.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 3209.menu.bootloader.uart2_default.upload.maximum_size=32256 @@ -672,7 +691,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_default.build.export_merged_output=true 3209.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 3209.menu.bootloader.uart2_alternative.upload.maximum_size=32256 @@ -683,7 +702,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart2_alternative.build.export_merged_output=true 3209.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 3209.menu.bootloader.uart3_default.upload.maximum_size=32256 @@ -694,7 +713,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_default.build.export_merged_output=true 3209.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart3_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3209.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 3209.menu.bootloader.uart3_alternative.upload.maximum_size=32256 @@ -705,7 +724,7 @@ menu.bootloader=Bootloader 3209.menu.bootloader.uart3_alternative.build.export_merged_output=true 3209.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3209.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 -3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 +3209.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} #################### @@ -736,11 +755,17 @@ menu.bootloader=Bootloader 3208.menu.pinout.28pin_standard=28 pin standard 3208.menu.pinout.28pin_standard.build.variant=28pin-standard +# EEPROM +3208.menu.eeprom.keep=EEPROM retained +3208.menu.eeprom.keep.bootloader.eesave_bit=1 +3208.menu.eeprom.erase=EEPROM not retained +3208.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 3208.menu.resetpin.reset=Reset -3208.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +3208.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.resetpin.gpio=GPIO -3208.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +3208.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 3208.menu.BOD.2v6=BOD 2.6V @@ -859,7 +884,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_default.build.export_merged_output=true 3208.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 3208.menu.bootloader.uart0_alternative.upload.maximum_size=32256 @@ -870,7 +895,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart0_alternative.build.export_merged_output=true 3208.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 3208.menu.bootloader.uart1_default.upload.maximum_size=32256 @@ -881,7 +906,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_default.build.export_merged_output=true 3208.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 3208.menu.bootloader.uart1_alternative.upload.maximum_size=32256 @@ -892,7 +917,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart1_alternative.build.export_merged_output=true 3208.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 3208.menu.bootloader.uart2_default.upload.maximum_size=32256 @@ -903,7 +928,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_default.build.export_merged_output=true 3208.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 3208.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 3208.menu.bootloader.uart2_alternative.upload.maximum_size=32256 @@ -914,7 +939,7 @@ menu.bootloader=Bootloader 3208.menu.bootloader.uart2_alternative.build.export_merged_output=true 3208.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 3208.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +3208.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} ##################### @@ -947,11 +972,17 @@ menu.bootloader=Bootloader 1609.menu.pinout.uno_wifi.build.variant=uno-wifi 1609.menu.pinout.uno_wifi.build.compat= +# EEPROM +1609.menu.eeprom.keep=EEPROM retained +1609.menu.eeprom.keep.bootloader.eesave_bit=1 +1609.menu.eeprom.erase=EEPROM not retained +1609.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 1609.menu.resetpin.reset=Reset -1609.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +1609.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.resetpin.gpio=GPIO -1609.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +1609.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 1609.menu.BOD.2v6=BOD 2.6V @@ -1070,7 +1101,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_default.build.export_merged_output=true 1609.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 1609.menu.bootloader.uart0_alternative.upload.maximum_size=15872 @@ -1081,7 +1112,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart0_alternative.build.export_merged_output=true 1609.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 1609.menu.bootloader.uart1_default.upload.maximum_size=15872 @@ -1092,7 +1123,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_default.build.export_merged_output=true 1609.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 1609.menu.bootloader.uart1_alternative.upload.maximum_size=15872 @@ -1103,7 +1134,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart1_alternative.build.export_merged_output=true 1609.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 1609.menu.bootloader.uart2_default.upload.maximum_size=15872 @@ -1114,7 +1145,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_default.build.export_merged_output=true 1609.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 1609.menu.bootloader.uart2_alternative.upload.maximum_size=15872 @@ -1125,7 +1156,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart2_alternative.build.export_merged_output=true 1609.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 1609.menu.bootloader.uart3_default.upload.maximum_size=15872 @@ -1136,7 +1167,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_default.build.export_merged_output=true 1609.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart3_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1609.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 1609.menu.bootloader.uart3_alternative.upload.maximum_size=15872 @@ -1147,7 +1178,7 @@ menu.bootloader=Bootloader 1609.menu.bootloader.uart3_alternative.build.export_merged_output=true 1609.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1609.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 -1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 +1609.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} #################### @@ -1178,11 +1209,17 @@ menu.bootloader=Bootloader 1608.menu.pinout.28pin_standard=28 pin standard 1608.menu.pinout.28pin_standard.build.variant=28pin-standard +# EEPROM +1608.menu.eeprom.keep=EEPROM retained +1608.menu.eeprom.keep.bootloader.eesave_bit=1 +1608.menu.eeprom.erase=EEPROM not retained +1608.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 1608.menu.resetpin.reset=Reset -1608.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +1608.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.resetpin.gpio=GPIO -1608.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +1608.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 1608.menu.BOD.2v6=BOD 2.6V @@ -1301,7 +1338,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_default.build.export_merged_output=true 1608.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 1608.menu.bootloader.uart0_alternative.upload.maximum_size=15872 @@ -1312,7 +1349,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart0_alternative.build.export_merged_output=true 1608.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 1608.menu.bootloader.uart1_default.upload.maximum_size=15872 @@ -1323,7 +1360,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_default.build.export_merged_output=true 1608.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 1608.menu.bootloader.uart1_alternative.upload.maximum_size=15872 @@ -1334,7 +1371,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart1_alternative.build.export_merged_output=true 1608.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 1608.menu.bootloader.uart2_default.upload.maximum_size=15872 @@ -1345,7 +1382,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_default.build.export_merged_output=true 1608.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 1608.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 1608.menu.bootloader.uart2_alternative.upload.maximum_size=15872 @@ -1356,7 +1393,7 @@ menu.bootloader=Bootloader 1608.menu.bootloader.uart2_alternative.build.export_merged_output=true 1608.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 1608.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +1608.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} ################### @@ -1389,11 +1426,17 @@ menu.bootloader=Bootloader 809.menu.pinout.uno_wifi.build.variant=uno-wifi 809.menu.pinout.uno_wifi.build.compat= +# EEPROM +809.menu.eeprom.keep=EEPROM retained +809.menu.eeprom.keep.bootloader.eesave_bit=1 +809.menu.eeprom.erase=EEPROM not retained +809.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 809.menu.resetpin.reset=Reset -809.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +809.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.resetpin.gpio=GPIO -809.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +809.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 809.menu.BOD.2v6=BOD 2.6V @@ -1512,7 +1555,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_default.build.export_merged_output=true 809.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 809.menu.bootloader.uart0_alternative.upload.maximum_size=7680 @@ -1523,7 +1566,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart0_alternative.build.export_merged_output=true 809.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 809.menu.bootloader.uart1_default.upload.maximum_size=7680 @@ -1534,7 +1577,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_default.build.export_merged_output=true 809.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 809.menu.bootloader.uart1_alternative.upload.maximum_size=7680 @@ -1545,7 +1588,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart1_alternative.build.export_merged_output=true 809.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 809.menu.bootloader.uart2_default.upload.maximum_size=7680 @@ -1556,7 +1599,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_default.build.export_merged_output=true 809.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 809.menu.bootloader.uart2_alternative.upload.maximum_size=7680 @@ -1567,7 +1610,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart2_alternative.build.export_merged_output=true 809.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart3_default=Optiboot (UART3 default pins) 809.menu.bootloader.uart3_default.upload.maximum_size=7680 @@ -1578,7 +1621,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_default.build.export_merged_output=true 809.menu.bootloader.uart3_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_default.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart3_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 809.menu.bootloader.uart3_alternative=Optiboot (UART3 alternative pins) 809.menu.bootloader.uart3_alternative.upload.maximum_size=7680 @@ -1589,7 +1632,7 @@ menu.bootloader=Bootloader 809.menu.bootloader.uart3_alternative.build.export_merged_output=true 809.menu.bootloader.uart3_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 809.menu.bootloader.uart3_alternative.bootloader.BOOTEND=0x02 -809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0xC9 +809.menu.bootloader.uart3_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} ################### @@ -1620,11 +1663,17 @@ menu.bootloader=Bootloader 808.menu.pinout.28pin_standard=28 pin standard 808.menu.pinout.28pin_standard.build.variant=28pin-standard +# EEPROM +808.menu.eeprom.keep=EEPROM retained +808.menu.eeprom.keep.bootloader.eesave_bit=1 +808.menu.eeprom.erase=EEPROM not retained +808.menu.eeprom.erase.bootloader.eesave_bit=0 + # Reset pin 808.menu.resetpin.reset=Reset -808.menu.resetpin.reset.bootloader.SYSCFG0=0xCD +808.menu.resetpin.reset.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.resetpin.gpio=GPIO -808.menu.resetpin.gpio.bootloader.SYSCFG0=0xC1 +808.menu.resetpin.gpio.bootloader.SYSCFG0=0b1100000{bootloader.eesave_bit} # Brown out detection 808.menu.BOD.2v6=BOD 2.6V @@ -1743,7 +1792,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_default.build.export_merged_output=true 808.menu.bootloader.uart0_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_default.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart0_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.bootloader.uart0_alternative=Optiboot (UART0 alternative pins) 808.menu.bootloader.uart0_alternative.upload.maximum_size=7680 @@ -1754,7 +1803,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart0_alternative.build.export_merged_output=true 808.menu.bootloader.uart0_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart0_alternative.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart0_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.bootloader.uart1_default=Optiboot (UART1 default pins) 808.menu.bootloader.uart1_default.upload.maximum_size=7680 @@ -1765,7 +1814,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_default.build.export_merged_output=true 808.menu.bootloader.uart1_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_default.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart1_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.bootloader.uart1_alternative=Optiboot (UART1 alternative pins) 808.menu.bootloader.uart1_alternative.upload.maximum_size=7680 @@ -1776,7 +1825,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart1_alternative.build.export_merged_output=true 808.menu.bootloader.uart1_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart1_alternative.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart1_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.bootloader.uart2_default=Optiboot (UART2 default pins) 808.menu.bootloader.uart2_default.upload.maximum_size=7680 @@ -1787,7 +1836,7 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_default.build.export_merged_output=true 808.menu.bootloader.uart2_default.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_default.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart2_default.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} 808.menu.bootloader.uart2_alternative=Optiboot (UART2 alternative pins) 808.menu.bootloader.uart2_alternative.upload.maximum_size=7680 @@ -1798,4 +1847,4 @@ menu.bootloader=Bootloader 808.menu.bootloader.uart2_alternative.build.export_merged_output=true 808.menu.bootloader.uart2_alternative.bootloader.file=optiboot/bootloaders/mega0/{upload.speed}/Optiboot_mega0_{upload.port}_{upload.speed}_A7.hex 808.menu.bootloader.uart2_alternative.bootloader.BOOTEND=0x02 -808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0xC9 +808.menu.bootloader.uart2_alternative.bootloader.SYSCFG0=0b1100100{bootloader.eesave_bit} From be26387909d2c6c188409a1c7137db741810f648 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 17 Dec 2021 10:42:14 +0100 Subject: [PATCH 280/351] Formatting and add missing tinyAVR implementations --- megaavr/libraries/Event/src/Event.cpp | 61 +++++++++++++++++---------- megaavr/libraries/Event/src/Event.h | 21 +++++---- 2 files changed, 49 insertions(+), 33 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index dd20a1c..9bddc4b 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -425,7 +425,7 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { } #endif } - #if defined (PIN_PC0) // can't test if PORTx is defined - all are defined everywhere) + #if defined(PIN_PC0) // can't test if PORTx is defined - all are defined everywhere) if(port == PC) { #if defined(TINY_1_SERIES) // no event 4 on 0-series if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { @@ -651,24 +651,30 @@ void Event::set_user(user::user_t event_user) { uint8_t event_user_mask = event_user & 0x7F; #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) - volatile uint8_t *user_register = &EVSYS_ASYNCUSER0 + (volatile uint8_t &)event_user_mask; + volatile uint8_t *user_register = &EVSYS_ASYNCUSER0 + (volatile uint8_t&)event_user_mask; #else - volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t &)event_user_mask; + volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; #endif // Connect user to the channel we're working with *user_register = channel_number + 1; // Set PORTMUX pin swap for EVOUT if selected as channel generator - if(event_user & 0x80) { - #if defined(MEGACOREX) - PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); - #elif defined(__AVR_DA__) - PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0E)); - #elif defined(__AVR_DB__) || defined(__AVR_DD__) || defined(TINY_2_SERIES) - PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0D)); - #endif - } + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + if(event_user >= 0x08 && event_user <= 0x0A) { + PORTMUX.CTRLA |= (1 << (event_user - 0x08)); + } + #else + if(event_user & 0x80) { + #if defined(MEGACOREX) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x09)); + #elif defined(__AVR_DA__) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0E)); + #elif defined(__AVR_DB__) || defined(__AVR_DD__) || defined(TINY_2_SERIES) + PORTMUX_EVSYSROUTEA |= (1 << ((event_user & 0x7F) - 0x0D)); + #endif + } + #endif } @@ -719,15 +725,21 @@ void Event::clear_user(user::user_t event_user) { *user_register = 0x00; // Clear PORTMUX pin swap for EVOUT if selected as channel generator - if(event_user & 0x80) { - #if defined(MEGACOREX) - PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); - #elif defined(__AVR_DA__) - PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0E)); - #elif defined(__AVR_DB__) - PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0D)); - #endif - } + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + if(event_user >= 0x08 && event_user <= 0x0A) { + PORTMUX.CTRLA &= ~(1 << (event_user - 0x08)); + } + #else + if(event_user & 0x80) { + #if defined(MEGACOREX) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x09)); + #elif defined(__AVR_DA__) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0E)); + #elif defined(__AVR_DB__) || defined(__AVR_DD__) || defined(TINY_2_SERIES) + PORTMUX_EVSYSROUTEA &= ~(1 << ((event_user & 0x7F) - 0x0D)); + #endif + } + #endif } @@ -782,7 +794,12 @@ void Event::long_soft_event(uint8_t length) { uint8_t channel = channel_number; uint16_t strobeaddr; #if defined(EVSYS_STROBE) - strobeaddr = (uint16_t) &EVSYS_STROBE; + strobeaddr = (uint16_t)&EVSYS_STROBE; + #elif defined(EVSYS_SYNCSTROBE) + if(channel > 1) + strobeaddr = (uint16_t)&EVSYS_ASYNCSTROBE; + else + strobeaddr = (uint16_t)&EVSYS_SYNCSTROBE; #elif defined(EVSYS_SWEVENTB) if(channel > 7) { channel -= 8; diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index c8574a2..0e2dca2 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -1158,6 +1158,16 @@ class Event { void set_generator(uint8_t pin_number); static Event& assign_generator_pin(uint8_t port, uint8_t port_pin); static Event& assign_generator_pin(uint8_t pin_number); + static int8_t get_user_channel_number(user::user_t event_user); + static Event& get_user_channel(user::user_t event_user); + void set_user(user::user_t event_user); + int8_t set_user_pin(uint8_t pin_number); + static void clear_user(user::user_t event_user); + void soft_event(); + void long_soft_event(uint8_t length); + void start(bool state = true); + void stop(); + gen::generator_t gen_from_peripheral(AC_t& comp); #if defined(EVSYS_CHANNEL0) void get_generator_channel(gen0::generator_t generator) { get_generator_channel((gen::generator_t)generator); } @@ -1204,17 +1214,6 @@ class Event { void set_generator(gen::generator_t generator) { set_generator((gen::generator_t)generator); } #endif - static int8_t get_user_channel_number(user::user_t event_user); - static Event& get_user_channel(user::user_t event_user); - void set_user(user::user_t event_user); - int8_t set_user_pin(uint8_t pin_number); - static void clear_user(user::user_t event_user); - void soft_event(); - void long_soft_event(uint8_t length); - void start(bool state = true); - void stop(); - gen::generator_t gen_from_peripheral(AC_t& comp); - private: const uint8_t channel_number; // Holds the event generator channel number volatile uint8_t &channel_address; // Reference to the event channel address From d43c82e5a9676b39163679e03b68d31c8e846402 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 17 Dec 2021 12:21:09 +0100 Subject: [PATCH 281/351] Add gen_from_peripheral and user_from_peripheral --- megaavr/libraries/Event/keywords.txt | 2 + megaavr/libraries/Event/src/Event.cpp | 306 ++++++++++++++++++++++++++ megaavr/libraries/Event/src/Event.h | 10 +- 3 files changed, 317 insertions(+), 1 deletion(-) diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index 95525a3..5d24f37 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -23,6 +23,8 @@ set_user KEYWORD2 set_user_pin KEYWORD2 clear_user KEYWORD2 soft_event KEYWORD2 +gen_from_peripheral KEYWORD2 +user_from_peripheral KEYWORD2 long_soft_event KEYWORD2 start KEYWORD2 stop KEYWORD2 diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 9bddc4b..195013b 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -848,6 +848,312 @@ void Event::long_soft_event(uint8_t length) { } +/** + * @brief Static function used to get the generator number the analog + * comparator peripheral + * + * @param comp Analog comparator struct + * @return gen::generator_t generator type + */ +gen::generator_t Event::gen_from_peripheral(AC_t& comp) +{ + #if defined(TINY_1_SERIES) && PROGMEM_SIZE > 8192 + badCall("gen_from_peripheral() does not support channel-specific generators. The AC's larger 1-series are."); + #else + #if defined(AC0) + if(&comp == &AC0) { + return gen::ac0_out; + } + #if defined(AC1) + else if(&comp == &AC1) { + return gen::ac1_out; + } + #if defined(AC2) + else if(&comp == &AC2) { + return gen::ac2_out; + } + #endif + #endif + #endif + #endif + return (gen::generator_t) -1; +} + + +/** + * @brief Static function used to get the generator type from the CCL peripheral + * + * @param logic CCL struct + * @param logic_block Logic block number (0, 1, 2 or 3 for megaAVR-0's) + * @return gen::generator_t generator type + */ +gen::generator_t Event::gen_from_peripheral(CCL_t& logic, uint8_t logic_block) { + uint8_t retval = -1; + if(&logic == &CCL) { + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + if(logic_block < 2) + #elif defined(CCL_LUT4CTRLA) + if(logic_block < 6) + #else + if(logic_block < 4) + #endif + { + retval = (int8_t)(gen::ccl0_out) + logic_block; + } + } + return (gen::generator_t)retval; +} + + +/** + * @brief Static function used to get the possible users the CCL peripheral has + * to offer + * + * @param logic CCL struct + * @param user_type + * @return user::user_t CCL user number. + */ +user::user_t Event::user_from_peripheral(CCL_t& logic, uint8_t user_type) { + uint8_t retval = -1; + if(&logic == &CCL) { + #if !defined(TINY_0_SERIES) && !defined(TINY_1_SERIES) + #if defined(CCL_TRUTH4) + if(user_type < 13) + #else + if(user_type < 9) + #endif + { + retval = user_type; + } + #else + if(user_type < 5) { + retval = user_type + 2; + } + #endif + } + return (user::user_t)retval; +} + + +/** + * @brief Static function used to get the generator type from timer A + * + * @param logic TCA struct + * @param event_type TCA has multiple generators. This parameter provides the number, + * and ranges from 0 to 4 for megaAVR-0's + * @return gen::generator_t generator type + */ +gen::generator_t Event::gen_from_peripheral(TCA_t& timer, uint8_t event_type) { + uint8_t retval = -1; + if(event_type < 5) { + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) + retval = event_type + 2; + #else + if(&TCA0 == &timer) { + retval = event_type + 0x80; + } + #if defined(TCA1) + else if(&TCA1 == &timer) { + retval = event_type += 0x88; + } + #endif + #endif + } + return (gen::generator_t)retval; +} + + +/** + * @brief Static function used to get the possible users the TCA timer has to offer + * + * @param timer TCA struct + * @param user_type TCA has only has one user on megaAVR-0's. + * Leave this parameter unused + * @return user::user_t TCA user number + */ +user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { + uint8_t user = -1; + + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) || defined(MEGACOREX) + if(user_type != 0) { + return (user::user_t) -1; + } + #else + if(user_type > 1) { + return (user::user_t) -1; + } + #endif + user = user_type; // 0 or 1 for event user a or b (on parts with both, or 0 for parts that only have one + #if defined(TCA1) + if(&timer == &TCA1) { + user += 2; + } else + #endif + if(&timer != &TCA0) { + return (user::user_t) -1; + } + #if defined(__AVR_DA__) + user += 0x1B; + #elif defined(__AVR_DB__) || defined(__AVR_DD__) + user += 0x1A; + #elif defined(MEGACOREX) + user += 0x13; + #elif defined(TINY_2_SERIES) + user += 0x0E; + #else + user += 0x10; + #endif + return (user::user_t)user; +} + + +/** + * @brief Static function used to get the generator type from timer B + * + * @param timer TCB struct + * @param event_type TCB only has one generators on megaAVR-0's. + * Leave this parameter unused + * @return gen::generator_t generator type + */ +gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { + int8_t gentype = -1; + #if defined(TINY_0_OR_1_SERIES) + badCall("gen_from_peripheral() does not support channel-specific generators. The TCBs on 0/1-series are."); + #else + #if defined(MEGACOREX) // Dx-series and 2-series have ovf event, others don't. + if(event_type != 1) { + return (gen::generator_t) -1; + } + else { + gentype = 0; + } + #else + if(event_type < 2) { + gentype = event_type; + } + #endif + if(&timer == &TCB0) { + gentype += (uint8_t)gen::tcb0_capt; + } else + #if defined(TCB1) + if (&timer == &TCB1) { + gentype += (uint8_t)gen::tcb1_capt; + } else + #endif + #if defined(TCB2) + if (&timer == &TCB2) { + gentype += (uint8_t)gen::tcb2_capt; + } else + #endif + #if defined(TCB3) + if (&timer == &TCB3) { + gentype += (uint8_t)gen::tcb3_capt; + } else + #endif + #if defined(TCB4) + if (&timer == &TCB4) { + gentype += (uint8_t)gen::tcb4_capt; + } else + #endif + { + gentype = -1; + } + #endif + return (gen::generator_t) gentype; +} + + +/** + * @brief Static function used to get the possible users the TCB timer has to offer + * + * @param timer TCB struct + * @param user_type + * @return user::user_t TCA user number + */ +user::user_t Event::user_from_peripheral(TCB_t& timer, uint8_t user_type) { + uint8_t user = -1; + #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) || defined(MEGACOREX) // Dx-series and 2-series have event count input, others don't. + if (user_type != 1) { + return (user::user_t) -1; + } + else { + user = 0; + } + #else + if (user_type < 2) { + user = user_type; + } + #endif + if (&timer == &TCB0) { + user += (uint8_t)user::tcb0_capt; + } else + #if defined(TCB1) + if (&timer == &TCB1) { + user += (uint8_t)user::tcb1_capt; + } else + #endif + #if defined(TCB2) + if (&timer == &TCB2) { + user += (uint8_t)user::tcb2_capt; + } else + #endif + #if defined(TCB3) + if (&timer == &TCB3) { + user += (uint8_t)user::tcb3_capt; + } else + #endif + #if defined(TCB4) + if (&timer == &TCB4) { + user += (uint8_t)user::tcb4_capt; + } else + #endif + { + user = -1; + } + return (user::user_t)user; +} + + +/** + * @brief Static function used to get the possible users the USART peripheral has + * to offer + * + * @param usart USART struct + * @return user::user_t USART related event channel user + */ +user::user_t Event::user_from_peripheral(USART_t& usart) { + if(&usart == &USART0) { + return user::usart0_irda; + } + #if defined(USART1) + else if(&usart == &USART1) { + return user::usart1_irda; + } + #endif + #if defined(USART2) + else if(&usart == &USART2) { + return user::usart2_irda; + } + #endif + #if defined(USART3) + else if(&usart == &USART3) { + return user::usart3_irda; + } + #endif + #if defined(USART4) + else if(&usart == &USART4) { + return user::usart4_irda; + } + #endif + #if defined(USART5) + else if(&usart == &USART5) { + return user::usart5_irda; + } + #endif + return (user::user_t) -1; +} + + /** * @brief Starts the event generator for a particular event channel * diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 0e2dca2..8660bb2 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -1165,9 +1165,17 @@ class Event { static void clear_user(user::user_t event_user); void soft_event(); void long_soft_event(uint8_t length); + // event_types: They start from 0x00 for inputs, outputs start at 0x40 + static gen::generator_t gen_from_peripheral(AC_t& comp); + static gen::generator_t gen_from_peripheral(CCL_t& logic, uint8_t event_type = 0); + static user::user_t user_from_peripheral(CCL_t& logic, uint8_t user_type = 0); + static gen::generator_t gen_from_peripheral(TCA_t& timer, uint8_t event_type = 0); + static user::user_t user_from_peripheral(TCA_t& timer, uint8_t user_type = 0); + static gen::generator_t gen_from_peripheral(TCB_t& timer, uint8_t event_type = 0); + static user::user_t user_from_peripheral(TCB_t& timer, uint8_t user_type = 0); + static user::user_t user_from_peripheral(USART_t& usart); void start(bool state = true); void stop(); - gen::generator_t gen_from_peripheral(AC_t& comp); #if defined(EVSYS_CHANNEL0) void get_generator_channel(gen0::generator_t generator) { get_generator_channel((gen::generator_t)generator); } From 035e6edf2bf8d263843555b324c9b2a0d14323e4 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Dec 2021 22:44:14 +0100 Subject: [PATCH 282/351] Formatting --- megaavr/libraries/Event/src/Event.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 8660bb2..6e0e505 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -939,8 +939,8 @@ namespace user { #endif usart0_irda = 0x0C, usart1_irda = 0x0D, - tca0 = 0x0E, - tca0_cnt_a = 0x0E, + tca0 = 0x0E, + tca0_cnt_a = 0x0E, tca0_cnt_b = 0x0F, tcb0 = 0x11, tcb0_capt = 0x11, From c70587e5a9f55d4904fcdbb41240974382d3637c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Dec 2021 22:45:15 +0100 Subject: [PATCH 283/351] Update README --- megaavr/libraries/Event/README.md | 54 +++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 6f97b26..4917f9e 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -393,3 +393,57 @@ void stop(); ```c++ Event0.stop(); // Stops the Event0 generator channel ``` + + +## gen_from_peripheral() and user_from_peripheral() +These two static functions allow you to pass a reference to a peripheral module, and get back the generator or user associated with it. In this context the "Peripheral Modules" are the structs containing the registers, defined in the io headers; for example `TCB0` or `USART1` or `CCL`. + +This is most useful if you are writing portable (library) code that uses the Event library to interact with the event system. Say you made a library that lets users make one-shot pulses with timerB. You use the Event library to handle that part. You would of course need to know which timer to use - the natural way would be to ask the user to pass a reference or pointer. +But then what? The fact that you've got the pointer to something which, as it happens, is TCB0 (which itself is annoying to determine from an unknown pointer)... though even KNOWING THAT, you're not able to use it with the event library, since it needs user::tcb0 (or user::tcb0_capt). As the function names imply, one gives generators, the other gives users. They take 2 arguments, the first being a pointer to a peripheral struct. +The second, defaulting to 0, is the "type" of generator or user. Some peripherals have more than one event input or output. These are ordered in the same order as they are in the tables here and in the datasheet listings. + +### Usage +```c +// Here we see a typical use case - you get the generator, and immediately ask Event to assign a channel to it and give that to you. After getting it, you test to make sure it's not Event_empty, which indicates that either gen_from_peripheral failed, or assign_generator was out of event channels. Either way that's probably the user's fault, so you decide to return an error code. +uint8_t init(TCB_t* some_timer, /*and more arguments, most likely */) +{ + &Event_TCBnCapt = Event::assign_generator(Event::gen_from_peripheral(some_timer, 0)); + if (_TCBnCapt.get_channel_number() == 255) + return MY_ERROR_INVALID_TIMER_OR_NO_FREE_EVENT; + doMoreCoolStuff(); +} +``` + +Shown below, generators/user per instance (second argument should be less than this; zero-indexed), and the number of instances (for reference) + +| Peripheral | mega0 | +|------------|----------| +| TCAn | 5 / 1 x1 | +| TCBn | 1/1 x3-4 | +| CCL * | 4 / 8 | +| ACn | 1 / 0 x1 | +| USARTn | !/1 x3-4 | + +`*` - There is only one CCL peripheral, with multiple logic blocks. Each logic block has 1 event generator and 2 event users. If using the logic library, get the Logic instance number. The output generator is that number. The input is twice that number, and twice that number + 1. +`!` - These parts do have an option, but we didn't bother to implement it because it isn't particularly useful. But the Event RX mode combined with the TX input to the CCL permit arbitrary remapping of RX and very flexible remapping of TX. + +And what they are: + +| Peripheral | TCAn | TCBn | CCL* | ACn | USARTn | +|------------|----------|------|---------|-----|---------| +| gen 0 | OVF/LUNF | CAPT | LUT0OUT | OUT | ! | +| gen 1 | HUNF | | LUT1OUT | | | +| gen 2 | CMP0 | | LUT2OUT | | | +| gen 3 | CMP1 | | LUT3OUT | | | +| gen 4 | CMP2 | | ETC. | | | +| user 0 | EVACTA | CAPT | LUT0EVA | - | EVENTRX | +| user 1 | | | LUT0EVB | | | +| user 2 | | | LUT1EVA | | | +| user 3 | | | LUT1EVB | | | +| user 4 | | | ETC. | | | + +`*` - Since there's only one CCL, the pointer (or rather, its type) is just used to select which implementation is used. But this does mean that the CCL can have an insane number of options. But that's fine, because there are plenty of numbers between 0 and 255. +`!` - These parts do have an option, but we didn't bother to implement it because it isn't particularly useful. But the Event RX mode combined with the TX input to the CCL permit arbitrary remapping of RX and very flexible remapping of TX! + + +Asking for a generator that doesn't exist will return 0 (disabled); be sure to check for this in some way. Asking for a user that doesn't exist will return 255, which the library is smart enough not to accept. From a57eb575d3b89546b8efad9b8c1dfcd708068e9f Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Dec 2021 22:46:32 +0100 Subject: [PATCH 284/351] Bump library version --- megaavr/libraries/Event/library.properties | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Event/library.properties b/megaavr/libraries/Event/library.properties index 228af79..3a0551c 100644 --- a/megaavr/libraries/Event/library.properties +++ b/megaavr/libraries/Event/library.properties @@ -1,7 +1,7 @@ name=Event System -version=1.0.0 +version=1.2.0 author=MCUdude -maintainer=MCUdude +maintainer=MCUdude and Spence Konde sentence=A library for interfacing with the built-in event system paragraph= category=Signal Input/Output From f0238e7d90ed967c55c66416fce9d58f0a8dae6a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Dec 2021 22:55:15 +0100 Subject: [PATCH 285/351] Speed up 'available' function by inserting uint16_t cast See https://github.com/arduino/ArduinoCore-avr/pull/433 for details --- .../SoftwareSerial/src/SoftwareSerial.cpp | 28 +++++++++---------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp index 6c101a1..b6cb8e4 100644 --- a/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp +++ b/megaavr/libraries/SoftwareSerial/src/SoftwareSerial.cpp @@ -1,11 +1,11 @@ /* -SoftwareSerial.cpp (formerly NewSoftSerial.cpp) - +SoftwareSerial.cpp (formerly NewSoftSerial.cpp) - Multi-instance software serial library for Arduino/Wiring -- Interrupt-driven receive and other improvements by ladyada (http://ladyada.net) -- Tuning, circular buffer, derivation from class Print/Stream, multi-instance support, porting to 8MHz processors, - various optimizations, PROGMEM delay tables, inverse logic and + various optimizations, PROGMEM delay tables, inverse logic and direct port writing by Mikal Hart (http://www.arduiniana.org) -- Pin change interrupt macros by Paul Stoffregen (http://www.pjrc.com) -- 20MHz processor support by Garrett Mace (http://www.macetech.com) @@ -35,9 +35,9 @@ The latest version of this library can always be found at #define _DEBUG 0 #define _DEBUG_PIN1 11 #define _DEBUG_PIN2 13 -// +// // Includes -// +// #include #include #include @@ -48,7 +48,7 @@ The latest version of this library can always be found at // Statics // SoftwareSerial *SoftwareSerial::active_object = 0; -uint8_t SoftwareSerial::_receive_buffer[_SS_MAX_RX_BUFF]; +uint8_t SoftwareSerial::_receive_buffer[_SS_MAX_RX_BUFF]; volatile uint8_t SoftwareSerial::_receive_buffer_tail = 0; volatile uint8_t SoftwareSerial::_receive_buffer_head = 0; @@ -77,13 +77,13 @@ inline void DebugPulse(uint8_t, uint8_t) {} // Private methods // -/* static */ -inline void SoftwareSerial::tunedDelay(uint16_t delay) { +/* static */ +inline void SoftwareSerial::tunedDelay(uint16_t delay) { _delay_loop_2(delay); } // This function sets the current object as the "listening" -// one and returns true if it replaces another +// one and returns true if it replaces another bool SoftwareSerial::listen() { if (!_rx_delay_stopbit) @@ -137,7 +137,7 @@ void SoftwareSerial::recv() "push r26 \n\t" "push r27 \n\t" ::); -#endif +#endif uint8_t d = 0; @@ -174,8 +174,8 @@ void SoftwareSerial::recv() // save new data in buffer: tail points to where byte goes _receive_buffer[_receive_buffer_tail] = d; // save new byte _receive_buffer_tail = next; - } - else + } + else { DebugPulse(_DEBUG_PIN1, 1); _buffer_overflow = true; @@ -227,7 +227,7 @@ inline void SoftwareSerial::handle_interrupt() // // Constructor // -SoftwareSerial::SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic /* = false */) : +SoftwareSerial::SoftwareSerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic /* = false */) : _rx_delay_centering(0), _rx_delay_intrabit(0), _rx_delay_stopbit(0), @@ -382,7 +382,7 @@ int SoftwareSerial::available() if (!isListening()) return 0; - return (_receive_buffer_tail + _SS_MAX_RX_BUFF - _receive_buffer_head) % _SS_MAX_RX_BUFF; + return ((uint16_t)(_receive_buffer_tail + _SS_MAX_RX_BUFF - _receive_buffer_head)) % _SS_MAX_RX_BUFF; } size_t SoftwareSerial::write(uint8_t b) @@ -436,7 +436,7 @@ size_t SoftwareSerial::write(uint8_t b) SREG = oldSREG; // turn interrupts back on tunedDelay(_tx_delay); - + return 1; } From 47ef471683d9856af8147705d410bf096ba282c8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 26 Dec 2021 21:31:18 +0100 Subject: [PATCH 286/351] Add pinConfigure function #136 related --- megaavr/cores/coreX-corefiles/Arduino.h | 186 ++++++++++++++++++++++-- 1 file changed, 171 insertions(+), 15 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 1ee6ad7..4dc2d84 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -30,32 +30,18 @@ extern "C"{ #endif -/* Analog reference options */ - -/* Change in mega4809: two places to define analog reference - - VREF peripheral defines internal reference - - analog peripherals define internal/Vdd/external -*/ - - // internal from VREF - - /* Values shifted to avoid clashing with ADC REFSEL defines - Will shift back in analog_reference function - */ +// Analog reference options #define INTERNAL0V55 (VREF_ADC0REFSEL_0V55_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL1V1 (VREF_ADC0REFSEL_1V1_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL1V5 (VREF_ADC0REFSEL_1V5_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL2V5 (VREF_ADC0REFSEL_2V5_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL4V3 (VREF_ADC0REFSEL_4V34_gc >> VREF_ADC0REFSEL_gp) #define INTERNAL4V34 INTERNAL4V3 - #define DEFAULT ADC_REFSEL_VDDREF_gc #define INTERNAL ADC_REFSEL_INTREF_gc #define VDD ADC_REFSEL_VDDREF_gc #define EXTERNAL ADC_REFSEL_VREFA_gc - #define ADC_TEMPERATURE ADC_MUXPOS_TEMPSENSE_gc - #define VCC_5V0 2 #define VCC_3V3 1 #define VCC_1V8 0 @@ -149,6 +135,176 @@ void setup_timers(); #error "Targets with both UART0 and CDC serial not supported" #endif +// These are used as the second to N argument to pinConfigure(pin, ...) +// Directives are handled in the order they show up on this list, by pin function: +// PIN_DIR Direction +// PIN_OUT Output value +// PIN_ISC Enable and interrupt mode. If interrupts are turned on w/out the ISR, it will trigger dirty reset. +// PIN_PULLUP Pullups +// PIN_INLVL Input levels (MVIO parts only - everything else is schmitt trigger only, except on I2C pins acting as I2C with SMBus levels enabled. ) +// PIN_INVERT Invert pin +// +// Systematically named constants can be made by combining those names with the postfixes here +// except for PIN_ISC which is not a non-binary option. Valid values are listed below. +// _SET, _CLR, and _TGL can be used as a postfix on all binary options. +// _TOGGLE and _TGL are interchangeable as well. +// Additional names are defined where they might be easier to remember. +typedef enum : uint16_t +{ + // OUTPUT + PIN_DIR_SET = 0x0001, + PIN_DIRSET = 0x0001, + PIN_DIR_OUTPUT = 0x0001, + PIN_DIR_OUT = 0x0001, + // INPUT + PIN_DIR_CLR = 0x0002, + PIN_DIRCLR = 0x0002, + PIN_DIR_INPUT = 0x0002, + PIN_DIR_IN = 0x0002, + // TOGGLE INPUT/OUTPUT + PIN_DIR_TGL = 0x0003, + PIN_DIRTGL = 0x0003, + PIN_DIR_TOGGLE = 0x0003, + // HIGH + PIN_OUT_SET = 0x0004, + PIN_OUTSET = 0x0004, + PIN_OUT_HIGH = 0x0004, + // LOW + PIN_OUT_CLR = 0x0008, + PIN_OUTCLR = 0x0008, + PIN_OUT_LOW = 0x0008, +// CHANGE/TOGGLE + PIN_OUT_TGL = 0x000C, + PIN_OUTTGL = 0x000C, + PIN_OUT_TOGGLE = 0x000C, +//Interrupt disabled but input buffer enabled + PIN_ISC_ENABLE = 0x0080, + PIN_INPUT_ENABLE = 0x0080, + // Interrupt on change + PIN_ISC_CHANGE = 0x0090, + PIN_INT_CHANGE = 0x0090, +// Interrupt on rising edge + PIN_ISC_RISE = 0x00A0, + PIN_INT_RISE = 0x00A0, +// Interrupt on falling edge + PIN_ISC_FALL = 0x00B0, + PIN_INT_FALL = 0x00B0, +// Interrupt and input buffer disabled + PIN_ISC_DISABLE = 0x00C0, + PIN_INPUT_DISABLE = 0x00C0, +// Interrupt enabled with sense on low level + PIN_ISC_LEVEL = 0x00D0, + PIN_INT_LEVEL = 0x00D0, +// PULLUP ON + PIN_PULLUP_ON = 0x0100, + PIN_PULLUP = 0x0100, + PIN_PULLUP_SET = 0x0100, +// PULLUP OFF + PIN_PULLUP_OFF = 0x0200, + PIN_PULLUP_CLR = 0x0200, + PIN_NOPULLUP = 0x0200, +// PULLUP TOGGLE + PIN_PULLUP_TGL = 0x0300, + PIN_PULLUP_TOGGLE = 0x0300, +// PIN INVERT ON + PIN_INVERT_ON = 0x4000, + PIN_INVERT_SET = 0x4000, +// PIN INVERT OFF + PIN_INVERT_OFF = 0x8000, + PIN_INVERT_CLR = 0x8000, +// PIN_INVERT_TOGGLE + PIN_INVERT_TGL = 0xC000, + PIN_INVERT_TOGGLE = 0xC000, +} pin_configure_t; + +/** + * @brief Helper function to catch the last argument in the pinConfigure recursion loop + * + * @param digital_pin Arduino pin + * @param mode Mode parameter + * @return pin_configure_t + */ +inline pin_configure_t pinConfigure(const uint8_t digital_pin, const pin_configure_t mode) +{ + (void)digital_pin; + return mode; +} + + +/** + * @brief Variadic template function for configuring a pin + * + * @param digital_pin Arduino pin number + * @param mode First "mode" parameter + * @param modes Nth "mode" parameter + */ +template +void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) +{ + // Or-ing together the arguments using recursion + uint8_t pin_config = pinConfigure(digital_pin, mode) | pinConfigure(digital_pin, modes...); + + uint8_t bit_mask = digitalPinToBitMask(digital_pin); + if(bit_mask == NOT_A_PIN || !pin_config) // Return if digital pin is invalid or the other parameters or out to zero + return; + + uint8_t bit_pos = digitalPinToBitPosition(digital_pin); + volatile uint8_t *portbase = (volatile uint8_t*) digitalPinToPortStruct(digital_pin); + + // Write to selected pin direction register + uint8_t setting = pin_config & 0x03; // Mask out direction bits (DIR, DIRSET, DIRCLR, DIRTGL) + if(setting) + *(portbase + setting) = bit_mask; + + // Write to selected output register + pin_config >>= 2; + setting = pin_config & 0x03; + if(setting) + *(portbase + 4 + setting) = bit_mask; + + // Return if there is nothing more to configure + if(!(pin_config & 0x3FFC)) + return; + + uint8_t oldSREG = SREG; // Store SREG + cli(); // Disable interrupts + + // PINnCTRL register + pin_config >>= 2; + uint8_t pinncfg = *(portbase + 0x10 + bit_pos); + // Input sense configuration (ISC) + if(pin_config & 0x08) + pinncfg = (pinncfg & 0xF8) | (pin_config & PORT_ISC_gm); + // Pullup resistor + uint8_t temp = pin_config & 0x30; + if(temp) + { + if(temp == 0x30) + pinncfg ^= PORT_PULLUPEN_bm; // Toggle pullup + else if(temp == 0x20) + pinncfg &= ~(PORT_PULLUPEN_bm); // Clear pullup + else + pinncfg |= PORT_PULLUPEN_bm; // Set pullup + } + // Invert pin + pin_config >>= 8; + temp = pin_config & 0x0C; + if(temp) + { + if(temp == 0x0C) + pinncfg ^= PORT_INVEN_bm; // Toggle invert + else if(temp == 0x08) + pinncfg &= ~(PORT_INVEN_bm); // Clear + else + pinncfg |= PORT_INVEN_bm; // Set + } + // Write to PINnCTRL register + *(portbase + 0x10 + bit_pos) = pinncfg; + + // Restore SREG + SREG = oldSREG; +} + #endif #include "pins_arduino.h" From a7dd83c062ea4f0284bf243bbe4c4025e7dcd979 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 1 Jan 2022 20:17:48 +0100 Subject: [PATCH 287/351] Fix issue where pinConfigure could only take three parameters --- megaavr/cores/coreX-corefiles/Arduino.h | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 4dc2d84..2527297 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -230,7 +230,6 @@ inline pin_configure_t pinConfigure(const uint8_t digital_pin, const pin_configu return mode; } - /** * @brief Variadic template function for configuring a pin * @@ -239,14 +238,14 @@ inline pin_configure_t pinConfigure(const uint8_t digital_pin, const pin_configu * @param modes Nth "mode" parameter */ template -void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) +uint16_t pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) { // Or-ing together the arguments using recursion - uint8_t pin_config = pinConfigure(digital_pin, mode) | pinConfigure(digital_pin, modes...); + uint16_t pin_config = mode | (pin_configure_t)pinConfigure(digital_pin, modes...); uint8_t bit_mask = digitalPinToBitMask(digital_pin); if(bit_mask == NOT_A_PIN || !pin_config) // Return if digital pin is invalid or the other parameters or out to zero - return; + return 0; uint8_t bit_pos = digitalPinToBitPosition(digital_pin); volatile uint8_t *portbase = (volatile uint8_t*) digitalPinToPortStruct(digital_pin); @@ -264,7 +263,7 @@ void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... m // Return if there is nothing more to configure if(!(pin_config & 0x3FFC)) - return; + return 0; uint8_t oldSREG = SREG; // Store SREG cli(); // Disable interrupts @@ -303,6 +302,8 @@ void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... m // Restore SREG SREG = oldSREG; + + return pin_config; } #endif From 854d9e1041bef33e3bc50458f5efa686ab5118ec Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 3 Jan 2022 21:18:37 +0100 Subject: [PATCH 288/351] Fix issue where or'ing were done at run time instead of compile time --- megaavr/cores/coreX-corefiles/Arduino.h | 32 +++++++++++++++++-------- 1 file changed, 22 insertions(+), 10 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 2527297..c376697 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -218,18 +218,32 @@ typedef enum : uint16_t } pin_configure_t; /** - * @brief Helper function to catch the last argument in the pinConfigure recursion loop + * @brief Helper functions to catch the last argument in the pincfg recursion loop * - * @param digital_pin Arduino pin * @param mode Mode parameter * @return pin_configure_t */ -inline pin_configure_t pinConfigure(const uint8_t digital_pin, const pin_configure_t mode) +template +pin_configure_t pincfg(const MODE& mode) { - (void)digital_pin; return mode; } +/** + * @brief Helper functions to catch the nth in the pincfg recursion loop + * + * @param digital_pin Arduino pin + * @param mode First "mode" parameter + * @param modes Nth "mode" parameter + * @return uint16_t pin configuration or'ed together + */ +template +uint16_t pincfg(const MODE& mode, const MODES&... modes) +{ + return mode | pincfg(modes...); +} + + /** * @brief Variadic template function for configuring a pin * @@ -238,14 +252,14 @@ inline pin_configure_t pinConfigure(const uint8_t digital_pin, const pin_configu * @param modes Nth "mode" parameter */ template -uint16_t pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) +void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) { // Or-ing together the arguments using recursion - uint16_t pin_config = mode | (pin_configure_t)pinConfigure(digital_pin, modes...); + uint16_t pin_config = pincfg(mode, modes...); uint8_t bit_mask = digitalPinToBitMask(digital_pin); if(bit_mask == NOT_A_PIN || !pin_config) // Return if digital pin is invalid or the other parameters or out to zero - return 0; + return; uint8_t bit_pos = digitalPinToBitPosition(digital_pin); volatile uint8_t *portbase = (volatile uint8_t*) digitalPinToPortStruct(digital_pin); @@ -263,7 +277,7 @@ uint16_t pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&. // Return if there is nothing more to configure if(!(pin_config & 0x3FFC)) - return 0; + return; uint8_t oldSREG = SREG; // Store SREG cli(); // Disable interrupts @@ -302,8 +316,6 @@ uint16_t pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&. // Restore SREG SREG = oldSREG; - - return pin_config; } #endif From 815fb9feba2f2283d0f9baf6ddf1095db2413a04 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 5 Jan 2022 23:13:12 +0100 Subject: [PATCH 289/351] Don't allow other arguments than pin_configure_t enums --- megaavr/cores/coreX-corefiles/Arduino.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index c376697..4baa483 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -223,8 +223,8 @@ typedef enum : uint16_t * @param mode Mode parameter * @return pin_configure_t */ -template -pin_configure_t pincfg(const MODE& mode) + +inline pin_configure_t pincfg(const pin_configure_t mode) { return mode; } @@ -237,8 +237,8 @@ pin_configure_t pincfg(const MODE& mode) * @param modes Nth "mode" parameter * @return uint16_t pin configuration or'ed together */ -template -uint16_t pincfg(const MODE& mode, const MODES&... modes) +template +uint16_t pincfg(const pin_configure_t mode, const MODES&... modes) { return mode | pincfg(modes...); } @@ -251,8 +251,8 @@ uint16_t pincfg(const MODE& mode, const MODES&... modes) * @param mode First "mode" parameter * @param modes Nth "mode" parameter */ -template -void pinConfigure(const uint8_t digital_pin, const MODE& mode, const MODES&... modes) +template +void pinConfigure(const uint8_t digital_pin, const pin_configure_t mode, const MODES&... modes) { // Or-ing together the arguments using recursion uint16_t pin_config = pincfg(mode, modes...); From 60cab113bd0662a238c92637fe2460f5206dae8b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 18 Jan 2022 22:03:51 +0100 Subject: [PATCH 290/351] Add Extended API document --- Extended-API.md | 142 ++++++++++++++++++++++++++++++++++++++++++++++++ README.md | 101 +++++----------------------------- 2 files changed, 157 insertions(+), 86 deletions(-) create mode 100644 Extended-API.md diff --git a/Extended-API.md b/Extended-API.md new file mode 100644 index 0000000..6e509ac --- /dev/null +++ b/Extended-API.md @@ -0,0 +1,142 @@ +# Extended Arduino API + +MegaCoreX is Arduino compatible out of the box, but also includes extra functionality that's not available on the official Arduino "megaavr" core. This is functionality that I personally have been missing in the official Arduino API, and have added to MegaCoreX instead. + +My goal isn't to "Arduino wrap" all hardware functionality the megaAVR-0 series brings to the table, but to expose functionality advanced users may benefit from and actually use. If you have a very niche application that utilizes one of the more obscure features the chip has, you're probably better off writing the low-level code yourself. Very spesific needs for ADC readings? Obscure timer needs? Read the approperiate Microchip application note w! + + +## Table of contents +* [Analog read resolution](#analog-read-resolution) +* [Fast IO](#fast-io) +* [Peripheral pin swapping](#peripheral-pin-swapping) +* [pinConfigure](#pinConfigure---extended-pin-configuration) +* [Printf support](#printf-support) + + +## Analog read resolution +The default analog read resolution for these chips is 10 bit, which gives you values between 0 - 1023. If you need lower resolution you can turn it down to 8 bits instead, which gives you values between 0 - 255. +Simply call `analogReadResolution` like this: +```c +analogReadResolution(8); // Set resolution to 8 bits +analogReadResolution(10); // Set resolution to 10 bits +``` + + +## Fast IO +For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compiles down to a single instruction. +Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these.
+**Note that the pin number and pin state has to be known at compile time!** + +### Declaration +```c++ +uint8_t digitalReadFast(uint8_t pinNumber); +void digitalWriteFast(uint8_t pinNumber, uint8_t state); +``` + + +## Peripheral pin swapping +The megaAVR-0 microcontrollers support alternative pin assignments for some of their built-in peripherals. +This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. +They will return `true` if that swap or pin combination is supported. +For `Serial` peripherals the method is `pins(tx,rx)`, for `Wire` it's `pins(sda,scl)` and for `SPI` it's `pins(mosi,miso,sck,ss)`. +(Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) + +Note that `swap()` and `pins()` do the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. + +If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral, +note that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. + +`swap()` or `pins()` are called like this. **Use either `swap()` or `pins()`, not both!** + +``` c++ +// UART pin swapping +Serial3.swap(1); +Serial3.begin(9600); + +// Wire pin swapping +Wire.swap(1); +Wire.begin(); + +// SPI pin swapping +SPI.swap(1); +SPI.begin(); +``` + +Available pin combinations for the *48 pin standard* pinout are: + +| Peripheral | Default | Alternative 1 | Alternative 2 | +|------------|------------------------------- |------------------------------------|------------------------------------| +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | | +| Serial1 | swap(0) **or** pins(14,15) | swap(1) **or** pins(18,19) | | +| Serial2 | swap(0) **or** pins(34,35) | swap(1) **or** pins(38,39) | | +| Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | | +| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(14,15,16,17) | swap(2) **or** pins(30,31,32,33) | + +Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: + +| Peripheral | Default | Alternative | +|------------|--------------------------------|----------------------------------| +| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | +| Serial1 | swap(0) **or** pins(8,9) | | +| Serial2 | swap(0) **or** pins(20,21) | swap(1) **or** pins(24,25) | +| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | +| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(8,9,10,11) | + +Available pin combinations for the *Uno WiFi* pinout are: + +| Peripheral | Default | Alternative | +|------------|--------------------------------------------------------------|--------------------------------------------------------| +| Serial | swap(0) **or** pins(27,26)
(connected to mEDBG) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) (available on SPI header) | +| Serial2 | swap(0) **or** pins(24,23)
(connected to Wifi module) | swap(1) **or** pins(2,7) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | + +Available pin combinations for the *Nano Every* pinout are: + +| Peripheral | Default | Alternative | +|------------|------------------------------------------------------------------|-----------------------------------------------| +| Serial | swap(0) **or** pins(25,24)
(connected to USB-serial chip) | swap(1) **or** pins(9,10) | +| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | +| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | +| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | + + +## pinConfigure - extended pin configuration +pinConfigure is a template based function that exposes all functions that can be configured on a per-pin basis. The first argument is the Arduino pin number to configure, and the second to nth parameter are the configuration parameters. The order the arguments has does not matter. The function will set the pin functionality regardless if it "makes sense" or not. If you enable interupts on a pin and there's no interrupt handler in your code, the microcontroller will crash. + +### Declaration +```c++ +template +void pinConfigure(const uint8_t digital_pin, const pin_configure_t mode, const MODES&... modes); +``` + +### Example +```c++ +// Set pin PA0 to output and drive the pin high +pinConfigure(PIN_PA0, PIN_DIR_OUTPUT, PIN_OUT_HIGH); +// Disable pin PA1 completely to save power +pinConfigure(PIN_PA1, PIN_INPUT_DISABLE); +``` + +### Table of valid pin modes +The following parameters ca be used to set the pinConfigure modes: +| Functionality | Enable | Disable | Toggle | +|---------------|-------|---------------------|--------------------| +| Direction, pinMode() | `PIN_DIR_OUTPUT`
`PIN_DIR_OUT`
`PIN_DIRSET` | `PIN_DIR_INPUT`
`PIN_DIR_IN`
`PIN_DIRCLR` | `PIN_DIR_TOGGLE`
`PIN_DIRTGL` | +| Pin output, `HIGH` or LOW | `PIN_OUT_HIGH`
`PIN_OUTSET` | `PIN_OUT_LOW`
`PIN_OUTCLR` | `PIN_OUT_TOGGLE`
`PIN_OUTTGL` | +| Internal Pullup | `PIN_PULLUP_ON`
`PIN_PULLUP` | `PIN_PULLUP_OFF`
`PIN_NOPULLUP` | `PIN_PULLUP_TGL` | +| Invert `HIGH` and LOW |`PIN_INVERT_ON` | `PIN_INVERT_OFF` | `PIN_INVERT_TGL` | +| Digital input buffer | `PIN_INPUT_ENABLE` or
`PIN_ISC_ENABLE` | `PIN_ISC_DISABLE` or
`PIN_INPUT_DISABLE` | Not supported | +| Interrupt on change | `PIN_ISC_ENABLE` or
`PIN_INPUT_ENABLE` | `PIN_ISC_ENABLE` or
`PIN_ISC_DISABLE` | Not applicable | +| Interrupt on Rise | `PIN_ISC_RISE` or
`PIN_INT_RISE` | `PIN_ISC_ENABLE` or
`PIN_ISC_DISABLE` | Not applicable | +| Interrupt on Fall | `PIN_ISC_FALL` or
`PIN_INT_FALL` | `PIN_ISC_ENABLE` or
`PIN_ISC_DISABLE` | Not applicable | +| Interrupt on LOW | `PIN_ISC_LEVEL` or
`PIN_INT_LEVEL` | `PIN_ISC_ENABLE` or
`PIN_ISC_DISABLE` | Not applicable | + + +## Printf support +Unlike the official Arduino core, MegaCoreX has printf support out of the box. If you're not familiar with printf you should probably [read this first](https://www.tutorialspoint.com/c_standard_library/c_function_printf.htm). It's added to the Print class and will work with all libraries that inherit Print. Printf is a standard C function that lets you format text much easier than using Arduino's built-in print and println. + +Note that the default printf implementation will NOT print floats or doubles by default. This is a limitation of the avr-libc printf implementation on AVR microcontrollers, but can be enabled by setting a build flag. This can easily be done if you're using [PlatformIO](https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md). + +If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other common libraries that inherit the Print class (and thus supports printf) are SoftwareSerial, the LiquidCrystal LCD library and the u8g2 graphical LCD library. diff --git a/README.md b/README.md index da0b53c..4879383 100644 --- a/README.md +++ b/README.md @@ -1,9 +1,9 @@ # MegaCoreX [![Build Status](https://travis-ci.com/MCUdude/MegaCoreX.svg?branch=master)](https://travis-ci.com/MCUdude/MegaCoreX) -An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. Its largest variant, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis. +An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. The largest one, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis and much more! -Compared to older AVR families they also have more advanced and accurate internal oscillators which can provide base frequencies of 16 and 20 MHz. These can again be divided down internally to reduce the processor speed and power consumption. This means in most applications an external clock isn't necessary anymore. You can read more about clocks and clock frequencies in the [Supported clock frequencies](#supported-clock-frequencies) section. +Compared to older AVR families they also have more advanced and accurate internal oscillators which can provide base frequencies of 16 and 20 MHz. These can then be divided down internally to reduce the processor speed and power consumption. This means in most applications an external clock isn't necessary anymore. You can read more about clocks and clock frequencies in the [Supported clock frequencies](#supported-clock-frequencies) section. For programming, these chips use a UPDI programming interface. This is a bi-directional single wire interface and requires a programmer that supports UPDI. If you rather prefer uploading using a USB to serial adapter there is an option to use the Optiboot bootloader. Read more about UPDI and bootloaders in the [Programming](#programming) section below. @@ -28,11 +28,10 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) - - [Analog read resolution](#analog-read-resolution) - [Configurable Custom Logic (CCL)](#configurable-custom-logic-ccl) - [Analog Comparator (AC)](#analog-comparator-ac) - [Event System (EVSYS)](#event-system-evsys) - - [Alternative pins](#alternative-pins) + - [Peripheral pin swapping](#peripheral-pin-swapping) * [How to install](#how-to-install) - [Boards Manager Installation](#boards-manager-installation) - [Manual Installation](#manual-installation) @@ -58,9 +57,9 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB | **IO pins** | 41
33*** | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | 41 | 27*
24** | | **Packages** | TQFP48
QFN48
DIP40 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | TQFP48
QFN48 | TQFP32
QFN32
SSOP28 | - 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library -* TQFP32/QFN32 package -** SSOP28 package + 64 bytes of USERROW, accessible from address 256 to 319 using the EEPROM.h library
+* TQFP32/QFN32 package
+** SSOP28 package
*** DIP40 package @@ -123,14 +122,15 @@ None of the megaAVR-0 microcontrollers needs the reset line to be reprogrammed o ## Printf support -Unlike the official Arduino core, MegaCoreX has printf support out of the box. If you're not familiar with printf you should probably [read this first](https://www.tutorialspoint.com/c_standard_library/c_function_printf.htm). It's added to the Print class and will work with all libraries that inherit Print. Printf is a standard C function that lets you format text much easier than using Arduino's built-in print and println. Note that this implementation of printf will NOT print floats or doubles. This is a limitation of the avr-libc printf implementation on AVR microcontrollers, and nothing I can easily fix. +Unlike the official Arduino core, MegaCoreX has printf support out of the box. If you're not familiar with printf you should probably [read this first](https://www.tutorialspoint.com/c_standard_library/c_function_printf.htm). It's added to the Print class and will work with all libraries that inherit Print. Printf is a standard C function that lets you format text much easier than using Arduino's built-in print and println. -If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other libraries that inherit the Print class (and thus supports printf) are SoftwareSerial and the LiquidCrystal LCD library. +[**See the extended API documentation for more information!**](https://github.com/MCUdude/MegaCoreX/tree/master/Extended-API.md#printf-support) ## Fast IO -For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also includes some improved variants that compiles down to a single instruction. -Call `digitalReadFast(myPin)` or `digitalWriteFast(mypin, state)` to use these. Note that the pin number has to be known at compile time. +For timing critical applications the standard `digitalRead()` and `digitalWrite()` functions may be too slow. To solve this, MegaCoreX also incorporates `digitalReadFast(myPin)` and `digitalWriteFast(mypin, state)` which compiles down to a single instruction. + +[**See the extended API documentation for more information!**](https://github.com/MCUdude/MegaCoreX/tree/master/Extended-API.md#fast-io) ## Pin macros @@ -205,13 +205,6 @@ The repeat frequency for the pulses on all PWM outputs can be changed with the n Note also that tone() will use TCB1, so the corresponding PWM output is not available if it is used. -### Analog read resolution -The default analog read resolution for these chips is 10 bit, which gives you values between 0 - 1023. If you need less resolution you can turn it down to 8 bits instead, which gives you values between 0 - 255. -Simply call `analogReadResolution` like this: -```c -analogReadResolution(8); // Set resolution to 8 bits -``` - ### Configurable Custom Logic (CCL) The megaAVR-0 microcontrollers are equipped with four independent configurable logic blocks that can be used to improve speed and performance. The CCL pins are marked on all pinout diagrams in a dark blue/grey color. The logic blocks can be used independently from each other, connected together or generate an interrupt to the CPU. I've made a [light weight, high-level library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Logic) for easy integration with the CCL hardware. @@ -222,75 +215,11 @@ Try out the [Comparator library](https://github.com/MCUdude/MegaCoreX/tree/maste ### Event System (EVSYS) The Event System (EVSYS) enables direct peripheral-to-peripheral signaling. It allows a change in one peripheral (the event generator) to trigger actions in other peripherals (the event users) through event channels, without using the CPU. It is designed to provide short and predictable response times between peripherals, allowing for autonomous peripheral control and interaction, and also for synchronized timing of actions in several peripheral modules. It is thus a powerful tool for reducing the complexity, size, and execution time of the software. Give the [Event library](https://github.com/MCUdude/MegaCoreX/tree/master/megaavr/libraries/Event) a try! Here you'll find documentation and useful library examples. -### Alternative pins -The megaAVR-0 microcontrollers support alternative pin assignments for some of their built-in peripherals. -This is specified by invoking the `swap()` or `pins()` method before `begin()` for the associated peripheral. -They will return `true` if that swap or pin combination is supported. -For `Serial` peripherals the method is `pins(tx,rx)`, for `Wire` it's `pins(sda,scl)` and for `SPI` it's `pins(mosi,miso,sck,ss)`. -(Note that this is the same pin sequence as used for the ESP8266 `pins` method, but the opposite of the one SoftwareSerial uses.) - -Note that `swap()` and `pins()` do the exact same thing, but `swap()` is MUX swap oriented, while `pins()` is pin oriented. - -If you want to use this feature to implement communication with two different external devices connected to different pins using one internal peripheral, -note that the proper way to switch is first to invoke `end()` to cleanly shut down, then `swap()` or `pins()` to switch assigned pins, and finally `begin()` to cleanly start again. - -`swap()` or `pins()` are called like this. **Use either `swap()` or `pins()`, not both!** - -``` c++ -// UART pin swapping -Serial3.swap(1); -Serial3.begin(9600); - -// Wire pin swapping -Wire.swap(1); -Wire.begin(); - -// SPI pin swapping -SPI.swap(1); -SPI.begin(); -``` - -Available pin combinations for the *48 pin standard* pinout are: - -| Peripheral | Default | Alternative 1 | Alternative 2 | -|------------|------------------------------- |------------------------------------|------------------------------------| -| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | | -| Serial1 | swap(0) **or** pins(14,15) | swap(1) **or** pins(18,19) | | -| Serial2 | swap(0) **or** pins(34,35) | swap(1) **or** pins(38,39) | | -| Serial3 | swap(0) **or** pins(8,9) | swap(1) **or** pins(12,13) | | -| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(16,17) | | -| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(14,15,16,17) | swap(2) **or** pins(30,31,32,33) | - - -Available pin combinations for the *28 pin* and *32 pin standard* pinouts are: - -| Peripheral | Default | Alternative | -|------------|--------------------------------|----------------------------------| -| Serial | swap(0) **or** pins(0,1) | swap(1) **or** pins(4,5) | -| Serial1 | swap(0) **or** pins(8,9) | | -| Serial2 | swap(0) **or** pins(20,21) | swap(1) **or** pins(24,25) | -| Wire | swap(0) **or** pins(2,3) | swap(1) **or** pins(10,11) | -| SPI | swap(0) **or** pins(4,5,6,7) | swap(1) **or** pins(8,9,10,11) | - - -Available pin combinations for the *Uno WiFi* pinout are: - -| Peripheral | Default | Alternative | -|------------|--------------------------------------------------------------|--------------------------------------------------------| -| Serial | swap(0) **or** pins(27,26)
(connected to mEDBG) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(32,33) (available on SPI header) | -| Serial2 | swap(0) **or** pins(24,23)
(connected to Wifi module) | swap(1) **or** pins(2,7) | -| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | - - -Available pin combinations for the *Nano Every* pinout are: +### Peripheral pin swapping +The megaAVR-0 microcontrollers support alternative pin assignments for some of their built-in peripherals.
+MegaCoreX currently supports pinswapping the SPI, i2c and UART peripheral pins. -| Peripheral | Default | Alternative | -|------------|------------------------------------------------------------------|-----------------------------------------------| -| Serial | swap(0) **or** pins(25,24)
(connected to USB-serial chip) | swap(1) **or** pins(9,10) | -| Serial1 | swap(0) **or** pins(1,0) | swap(1) **or** pins(34,35) (not broken out) | -| Serial2 | swap(0) **or** pins(2,7) | swap(1) **or** pins(28,27) (not broken out) | -| Serial3 | swap(0) **or** pins(6,3) | swap(1) **or** pins(37,38) (not broken out) | +[**See the extended API documentation for more information!**](https://github.com/MCUdude/MegaCoreX/tree/master/Extended-API.md#peripheral-pin-swapping) ## How to install From 0d7b0d1a3a28f351ab796c8aaabc4ba1c267ff80 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 11 Mar 2022 10:06:08 +0100 Subject: [PATCH 291/351] Add "start app on power-on reset" functionality --- megaavr/bootloaders/optiboot/Makefile | 8 +- .../Optiboot_mega0_UART0_ALT_115200_A7.hex | 59 ++++----- .../Optiboot_mega0_UART0_DEF_115200_A7.hex | 58 ++++----- .../Optiboot_mega0_UART1_ALT_115200_A7.hex | 59 ++++----- .../Optiboot_mega0_UART1_DEF_115200_A7.hex | 58 ++++----- .../Optiboot_mega0_UART2_ALT_115200_A7.hex | 59 ++++----- .../Optiboot_mega0_UART2_DEF_115200_A7.hex | 58 ++++----- .../Optiboot_mega0_UART3_ALT_115200_A7.hex | 59 ++++----- .../Optiboot_mega0_UART3_DEF_115200_A7.hex | 58 ++++----- megaavr/bootloaders/optiboot/makeall | 16 +-- megaavr/bootloaders/optiboot/optiboot_x.c | 122 +++++++++++------- megaavr/bootloaders/optiboot/parse_options.mk | 4 + 12 files changed, 328 insertions(+), 290 deletions(-) diff --git a/megaavr/bootloaders/optiboot/Makefile b/megaavr/bootloaders/optiboot/Makefile index 35d6ea9..f6620a3 100755 --- a/megaavr/bootloaders/optiboot/Makefile +++ b/megaavr/bootloaders/optiboot/Makefile @@ -62,6 +62,12 @@ else LISTING= @true endif +ifeq ($(SKIP_BOOTLOADER_ON_POR), 0) +START_APP_ON_POR=0 +else +START_APP_ON_POR=1 +endif + ifeq ($(UARTTX), A0) UART=0 UARTMUX=DEF @@ -122,7 +128,7 @@ optiboot_%.hex: optiboot_%.elf $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O ihex $< $@ %.elf: optiboot_x.c FORCE - $(CC) $(CFLAGS) $(CPU_OPTIONS) $(LED_OPTIONS) $(UART_OPTIONS) $(COMMON_OPTIONS) $(LDFLAGS) $(PACK_OPT) -mmcu=$(TARGET) -o $@ $< + $(CC) $(CFLAGS) $(CPU_OPTIONS) $(LED_OPTIONS) $(UART_OPTIONS) $(COMMON_OPTIONS) $(POR) $(LDFLAGS) $(PACK_OPT) -mmcu=$(TARGET) -o $@ $< $(SIZE) $@ diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex index 519918a..5ea5b82 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_ALT_115200_A7.hex @@ -1,31 +1,32 @@ -:1000000001C0D2C01124809140008093400083FF42 -:1000100004C0282E80E0B0D0F3C0A895049A0C9AB2 -:1000200081E08093E205809182128370813029F50E -:100030008CE590E0809308089093090881E0809314 -:100040000B0883E0809307081092050880EC8093EA -:10005000060888E091D0079A87E0815089F4A89536 -:100060000DE983E0D82E7CD08134F1F479D0182FBB -:100070008CD0123889F480E013C083E790E0DACFA7 -:10008000179A2EEC36E5A8959091040897FDE8CFD5 -:1000900021503109C1F7E1CF89E0113809F083E03F -:1000A00058D080E156D0DFCF823419F484E175D086 -:1000B000F8CF853411F485E0FACF853531F450D08E -:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC -:1000D00064D0D1CF8436B9F443D042D0182F40D069 -:1000E000863479F4D05C3CD0888321961150D9F7BE -:1000F0004CD004BFD0920010809102108370E1F7C1 -:10010000D0CFDC5EF0CF843791F42AD029D0182FDD -:1001100027D0F82E3AD086E4F81207C0D05C888148 -:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 -:1001300051F42BD0809100110CD08091011109D085 -:1001400080910211ADCF813509F0BDCF81E014D08F -:10015000BACF9091040895FFFCCF809302080895D0 -:100160008091040887FFFCCF9091010880910008DE -:1001700092FD01C0A89508959091010190FDFCCFDA -:1001800098ED94BF809300010895EADF803219F062 -:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 -:1001B00060930010809102108370E1F70895FC01B4 -:0401C00040830895DB +:1000000001C0D9C0112480914000882369F0282FB5 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0B0D0ECC0A895049A0C9A81E01B +:100030008093E205809182128370813029F58CE5EE +:1000400090E0809308089093090881E080930B0862 +:1000500083E0809307081092050880EC80930608DF +:1000600088E091D0079A87E0815089F4A8950DE93E +:1000700083E0D82E7CD08134F1F479D0182F8CD045 +:10008000123889F480E013C083E790E0DACF179A42 +:100090002EEC36E5A8959091040897FDE8CF215005 +:1000A0003109C1F7E1CF89E0113809F083E058D078 +:1000B00080E156D0DFCF823419F484E175D0F8CFD7 +:1000C000853411F485E0FACF853531F450D0C82F4E +:1000D0004ED0D82F61D0ECCF863519F484E064D0AF +:1000E000D1CF8436B9F443D042D0182F40D08634D3 +:1000F00079F4D05C3CD0888321961150D9F74CD04C +:1001000004BFD0920010809102108370E1F7D0CF2D +:10011000DC5EF0CF843791F42AD029D0182F27D075 +:10012000F82E3AD086E4F81207C0D05C8881219678 +:1001300017D01150D9F7BCCFDC5EF8CF853751F41A +:100140002BD0809100110CD08091011109D08091A9 +:100150000211ADCF813509F0BDCF81E014D0BACF07 +:100160009091040895FFFCCF809302080895809138 +:10017000040887FFFCCF909101088091000892FD50 +:1001800001C0A89508959091010190FDFCCF98EDD4 +:1001900094BF809300010895EADF803219F081E076 +:1001A000F2DFFFCF84E1DCCFCF93C82FE0DFC15077 +:1001B000E9F7CF91F1CF683048F48DE984BF6093BF +:1001C0000010809102108370E1F70895FC014083D4 +:0201D000089590 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex index 8237a5b..516ec1f 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART0_DEF_115200_A7.hex @@ -1,31 +1,31 @@ -:1000000001C0D1C01124809140008093400083FF43 -:1000100004C0282E80E0AFD0F3C0A895009A089ABB -:100020001092E205809182128370813029F58CE56F -:1000300090E0809308089093090881E080930B0872 -:1000400083E0809307081092050880EC80930608EF -:1000500088E091D0079A87E0815089F4A8950DE94E -:1000600083E0D82E7CD08134F1F479D0182F8CD055 -:10007000123889F480E013C083E790E0DACF179A52 -:100080002EEC36E5A8959091040897FDE8CF215015 -:100090003109C1F7E1CF89E0113809F083E058D088 -:1000A00080E156D0DFCF823419F484E175D0F8CFE7 -:1000B000853411F485E0FACF853531F450D0C82F5E -:1000C0004ED0D82F61D0ECCF863519F484E064D0BF -:1000D000D1CF8436B9F443D042D0182F40D08634E3 -:1000E00079F4D05C3CD0888321961150D9F74CD05C -:1000F00004BFD0920010809102108370E1F7D0CF3E -:10010000DC5EF0CF843791F42AD029D0182F27D085 -:10011000F82E3AD086E4F81207C0D05C8881219688 -:1001200017D01150D9F7BCCFDC5EF8CF853751F42A -:100130002BD0809100110CD08091011109D08091B9 -:100140000211ADCF813509F0BDCF81E014D0BACF17 -:100150009091040895FFFCCF809302080895809148 -:10016000040887FFFCCF909101088091000892FD60 -:1001700001C0A89508959091010190FDFCCF98EDE4 -:1001800094BF809300010895EADF803219F081E086 -:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF683048F48DE984BF6093CF -:1001B0000010809102108370E1F70895FC014083E4 -:0201C0000895A0 +:1000000001C0D8C0112480914000882369F0282FB6 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0AFD0ECC0A895009A089A1092E3 +:10003000E205809182128370813029F58CE590E091 +:10004000809308089093090881E080930B0883E06F +:10005000809307081092050880EC8093060888E0DA +:1000600091D0079A87E0815089F4A8950DE983E043 +:10007000D82E7CD08134F1F479D0182F8CD012385E +:1000800089F480E013C083E790E0DACF179A2EEC72 +:1000900036E5A8959091040897FDE8CF21503109E5 +:1000A000C1F7E1CF89E0113809F083E058D080E151 +:1000B00056D0DFCF823419F484E175D0F8CF85347F +:1000C00011F485E0FACF853531F450D0C82F4ED0E9 +:1000D000D82F61D0ECCF863519F484E064D0D1CF2D +:1000E0008436B9F443D042D0182F40D0863479F406 +:1000F000D05C3CD0888321961150D9F74CD004BFF6 +:10010000D0920010809102108370E1F7D0CFDC5EB6 +:10011000F0CF843791F42AD029D0182F27D0F82E89 +:100120003AD086E4F81207C0D05C8881219617D0B7 +:100130001150D9F7BCCFDC5EF8CF853751F42BD006 +:10014000809100110CD08091011109D08091021191 +:10015000ADCF813509F0BDCF81E014D0BACF9091F9 +:10016000040895FFFCCF809302080895809104084D +:1001700087FFFCCF909101088091000892FD01C09B +:10018000A89508959091010190FDFCCF98ED94BF42 +:10019000809300010895EADF803219F081E0F2DFF8 +:1001A000FFCF84E1DCCFCF93C82FE0DFC150E9F768 +:1001B000CF91F1CF683048F48DE984BF609300108F +:1001C000809102108370E1F70895FC014083089547 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex index 120e3d2..e54179a 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_ALT_115200_A7.hex @@ -1,31 +1,32 @@ -:1000000001C0D2C01124809140008093400083FF42 -:1000100004C0282E80E0B0D0F3C0A895449A4C9A32 -:1000200084E08093E205809182128370813029F50B -:100030008CE590E0809328089093290881E08093D4 -:100040002B0883E0809327081092250880EC80938A -:10005000260888E091D0079A87E0815089F4A89516 -:100060000DE983E0D82E7CD08134F1F479D0182FBB -:100070008CD0123889F480E013C083E790E0DACFA7 -:10008000179A2EEC36E5A8959091240897FDE8CFB5 -:1000900021503109C1F7E1CF89E0113809F083E03F -:1000A00058D080E156D0DFCF823419F484E175D086 -:1000B000F8CF853411F485E0FACF853531F450D08E -:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC -:1000D00064D0D1CF8436B9F443D042D0182F40D069 -:1000E000863479F4D05C3CD0888321961150D9F7BE -:1000F0004CD004BFD0920010809102108370E1F7C1 -:10010000D0CFDC5EF0CF843791F42AD029D0182FDD -:1001100027D0F82E3AD086E4F81207C0D05C888148 -:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 -:1001300051F42BD0809100110CD08091011109D085 -:1001400080910211ADCF813509F0BDCF81E014D08F -:10015000BACF9091240895FFFCCF80932208089590 -:100160008091240887FFFCCF90912108809120087E -:1001700092FD01C0A89508959091010190FDFCCFDA -:1001800098ED94BF809300010895EADF803219F062 -:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 -:1001B00060930010809102108370E1F70895FC01B4 -:0401C00040830895DB +:1000000001C0D9C0112480914000882369F0282FB5 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0B0D0ECC0A895449A4C9A84E098 +:100030008093E205809182128370813029F58CE5EE +:1000400090E0809328089093290881E080932B0802 +:1000500083E0809327081092250880EC809326087F +:1000600088E091D0079A87E0815089F4A8950DE93E +:1000700083E0D82E7CD08134F1F479D0182F8CD045 +:10008000123889F480E013C083E790E0DACF179A42 +:100090002EEC36E5A8959091240897FDE8CF2150E5 +:1000A0003109C1F7E1CF89E0113809F083E058D078 +:1000B00080E156D0DFCF823419F484E175D0F8CFD7 +:1000C000853411F485E0FACF853531F450D0C82F4E +:1000D0004ED0D82F61D0ECCF863519F484E064D0AF +:1000E000D1CF8436B9F443D042D0182F40D08634D3 +:1000F00079F4D05C3CD0888321961150D9F74CD04C +:1001000004BFD0920010809102108370E1F7D0CF2D +:10011000DC5EF0CF843791F42AD029D0182F27D075 +:10012000F82E3AD086E4F81207C0D05C8881219678 +:1001300017D01150D9F7BCCFDC5EF8CF853751F41A +:100140002BD0809100110CD08091011109D08091A9 +:100150000211ADCF813509F0BDCF81E014D0BACF07 +:100160009091240895FFFCCF8093220808958091F8 +:10017000240887FFFCCF909121088091200892FDF0 +:1001800001C0A89508959091010190FDFCCF98EDD4 +:1001900094BF809300010895EADF803219F081E076 +:1001A000F2DFFFCF84E1DCCFCF93C82FE0DFC15077 +:1001B000E9F7CF91F1CF683048F48DE984BF6093BF +:1001C0000010809102108370E1F70895FC014083D4 +:0201D000089590 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex index c42f3aa..e91e29a 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART1_DEF_115200_A7.hex @@ -1,31 +1,31 @@ -:1000000001C0D1C01124809140008093400083FF43 -:1000100004C0282E80E0AFD0F3C0A895409A489A3B -:100020001092E205809182128370813029F58CE56F -:1000300090E0809328089093290881E080932B0812 -:1000400083E0809327081092250880EC809326088F -:1000500088E091D0079A87E0815089F4A8950DE94E -:1000600083E0D82E7CD08134F1F479D0182F8CD055 -:10007000123889F480E013C083E790E0DACF179A52 -:100080002EEC36E5A8959091240897FDE8CF2150F5 -:100090003109C1F7E1CF89E0113809F083E058D088 -:1000A00080E156D0DFCF823419F484E175D0F8CFE7 -:1000B000853411F485E0FACF853531F450D0C82F5E -:1000C0004ED0D82F61D0ECCF863519F484E064D0BF -:1000D000D1CF8436B9F443D042D0182F40D08634E3 -:1000E00079F4D05C3CD0888321961150D9F74CD05C -:1000F00004BFD0920010809102108370E1F7D0CF3E -:10010000DC5EF0CF843791F42AD029D0182F27D085 -:10011000F82E3AD086E4F81207C0D05C8881219688 -:1001200017D01150D9F7BCCFDC5EF8CF853751F42A -:100130002BD0809100110CD08091011109D08091B9 -:100140000211ADCF813509F0BDCF81E014D0BACF17 -:100150009091240895FFFCCF809322080895809108 -:10016000240887FFFCCF909121088091200892FD00 -:1001700001C0A89508959091010190FDFCCF98EDE4 -:1001800094BF809300010895EADF803219F081E086 -:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF683048F48DE984BF6093CF -:1001B0000010809102108370E1F70895FC014083E4 -:0201C0000895A0 +:1000000001C0D8C0112480914000882369F0282FB6 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0AFD0ECC0A895409A489A109263 +:10003000E205809182128370813029F58CE590E091 +:10004000809328089093290881E080932B0883E00F +:10005000809327081092250880EC8093260888E07A +:1000600091D0079A87E0815089F4A8950DE983E043 +:10007000D82E7CD08134F1F479D0182F8CD012385E +:1000800089F480E013C083E790E0DACF179A2EEC72 +:1000900036E5A8959091240897FDE8CF21503109C5 +:1000A000C1F7E1CF89E0113809F083E058D080E151 +:1000B00056D0DFCF823419F484E175D0F8CF85347F +:1000C00011F485E0FACF853531F450D0C82F4ED0E9 +:1000D000D82F61D0ECCF863519F484E064D0D1CF2D +:1000E0008436B9F443D042D0182F40D0863479F406 +:1000F000D05C3CD0888321961150D9F74CD004BFF6 +:10010000D0920010809102108370E1F7D0CFDC5EB6 +:10011000F0CF843791F42AD029D0182F27D0F82E89 +:100120003AD086E4F81207C0D05C8881219617D0B7 +:100130001150D9F7BCCFDC5EF8CF853751F42BD006 +:10014000809100110CD08091011109D08091021191 +:10015000ADCF813509F0BDCF81E014D0BACF9091F9 +:10016000240895FFFCCF80932208089580912408ED +:1001700087FFFCCF909121088091200892FD01C05B +:10018000A89508959091010190FDFCCF98ED94BF42 +:10019000809300010895EADF803219F081E0F2DFF8 +:1001A000FFCF84E1DCCFCF93C82FE0DFC150E9F768 +:1001B000CF91F1CF683048F48DE984BF609300108F +:1001C000809102108370E1F70895FC014083089547 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex index 67b0c0a..0442ebf 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_ALT_115200_A7.hex @@ -1,31 +1,32 @@ -:1000000001C0D2C01124809140008093400083FF42 -:1000100004C0282E80E0B0D0F3C0A895A49AAC9A72 -:1000200080E18093E205809182128370813029F50E -:100030008CE590E0809348089093490881E0809394 -:100040004B0883E0809347081092450880EC80932A -:10005000460888E091D0079A87E0815089F4A895F6 -:100060000DE983E0D82E7CD08134F1F479D0182FBB -:100070008CD0123889F480E013C083E790E0DACFA7 -:10008000179A2EEC36E5A8959091440897FDE8CF95 -:1000900021503109C1F7E1CF89E0113809F083E03F -:1000A00058D080E156D0DFCF823419F484E175D086 -:1000B000F8CF853411F485E0FACF853531F450D08E -:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC -:1000D00064D0D1CF8436B9F443D042D0182F40D069 -:1000E000863479F4D05C3CD0888321961150D9F7BE -:1000F0004CD004BFD0920010809102108370E1F7C1 -:10010000D0CFDC5EF0CF843791F42AD029D0182FDD -:1001100027D0F82E3AD086E4F81207C0D05C888148 -:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 -:1001300051F42BD0809100110CD08091011109D085 -:1001400080910211ADCF813509F0BDCF81E014D08F -:10015000BACF9091440895FFFCCF80934208089550 -:100160008091440887FFFCCF90914108809140081E -:1001700092FD01C0A89508959091010190FDFCCFDA -:1001800098ED94BF809300010895EADF803219F062 -:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 -:1001B00060930010809102108370E1F70895FC01B4 -:0401C00040830895DB +:1000000001C0D9C0112480914000882369F0282FB5 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0B0D0ECC0A895A49AAC9A80E1DB +:100030008093E205809182128370813029F58CE5EE +:1000400090E0809348089093490881E080934B08A2 +:1000500083E0809347081092450880EC809346081F +:1000600088E091D0079A87E0815089F4A8950DE93E +:1000700083E0D82E7CD08134F1F479D0182F8CD045 +:10008000123889F480E013C083E790E0DACF179A42 +:100090002EEC36E5A8959091440897FDE8CF2150C5 +:1000A0003109C1F7E1CF89E0113809F083E058D078 +:1000B00080E156D0DFCF823419F484E175D0F8CFD7 +:1000C000853411F485E0FACF853531F450D0C82F4E +:1000D0004ED0D82F61D0ECCF863519F484E064D0AF +:1000E000D1CF8436B9F443D042D0182F40D08634D3 +:1000F00079F4D05C3CD0888321961150D9F74CD04C +:1001000004BFD0920010809102108370E1F7D0CF2D +:10011000DC5EF0CF843791F42AD029D0182F27D075 +:10012000F82E3AD086E4F81207C0D05C8881219678 +:1001300017D01150D9F7BCCFDC5EF8CF853751F41A +:100140002BD0809100110CD08091011109D08091A9 +:100150000211ADCF813509F0BDCF81E014D0BACF07 +:100160009091440895FFFCCF8093420808958091B8 +:10017000440887FFFCCF909141088091400892FD90 +:1001800001C0A89508959091010190FDFCCF98EDD4 +:1001900094BF809300010895EADF803219F081E076 +:1001A000F2DFFFCF84E1DCCFCF93C82FE0DFC15077 +:1001B000E9F7CF91F1CF683048F48DE984BF6093BF +:1001C0000010809102108370E1F70895FC014083D4 +:0201D000089590 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex index 4b6d606..ac3719b 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART2_DEF_115200_A7.hex @@ -1,31 +1,31 @@ -:1000000001C0D1C01124809140008093400083FF43 -:1000100004C0282E80E0AFD0F3C0A895A09AA89A7B -:100020001092E205809182128370813029F58CE56F -:1000300090E0809348089093490881E080934B08B2 -:1000400083E0809347081092450880EC809346082F -:1000500088E091D0079A87E0815089F4A8950DE94E -:1000600083E0D82E7CD08134F1F479D0182F8CD055 -:10007000123889F480E013C083E790E0DACF179A52 -:100080002EEC36E5A8959091440897FDE8CF2150D5 -:100090003109C1F7E1CF89E0113809F083E058D088 -:1000A00080E156D0DFCF823419F484E175D0F8CFE7 -:1000B000853411F485E0FACF853531F450D0C82F5E -:1000C0004ED0D82F61D0ECCF863519F484E064D0BF -:1000D000D1CF8436B9F443D042D0182F40D08634E3 -:1000E00079F4D05C3CD0888321961150D9F74CD05C -:1000F00004BFD0920010809102108370E1F7D0CF3E -:10010000DC5EF0CF843791F42AD029D0182F27D085 -:10011000F82E3AD086E4F81207C0D05C8881219688 -:1001200017D01150D9F7BCCFDC5EF8CF853751F42A -:100130002BD0809100110CD08091011109D08091B9 -:100140000211ADCF813509F0BDCF81E014D0BACF17 -:100150009091440895FFFCCF8093420808958091C8 -:10016000440887FFFCCF909141088091400892FDA0 -:1001700001C0A89508959091010190FDFCCF98EDE4 -:1001800094BF809300010895EADF803219F081E086 -:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF683048F48DE984BF6093CF -:1001B0000010809102108370E1F70895FC014083E4 -:0201C0000895A0 +:1000000001C0D8C0112480914000882369F0282FB6 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0AFD0ECC0A895A09AA89A1092A3 +:10003000E205809182128370813029F58CE590E091 +:10004000809348089093490881E080934B0883E0AF +:10005000809347081092450880EC8093460888E01A +:1000600091D0079A87E0815089F4A8950DE983E043 +:10007000D82E7CD08134F1F479D0182F8CD012385E +:1000800089F480E013C083E790E0DACF179A2EEC72 +:1000900036E5A8959091440897FDE8CF21503109A5 +:1000A000C1F7E1CF89E0113809F083E058D080E151 +:1000B00056D0DFCF823419F484E175D0F8CF85347F +:1000C00011F485E0FACF853531F450D0C82F4ED0E9 +:1000D000D82F61D0ECCF863519F484E064D0D1CF2D +:1000E0008436B9F443D042D0182F40D0863479F406 +:1000F000D05C3CD0888321961150D9F74CD004BFF6 +:10010000D0920010809102108370E1F7D0CFDC5EB6 +:10011000F0CF843791F42AD029D0182F27D0F82E89 +:100120003AD086E4F81207C0D05C8881219617D0B7 +:100130001150D9F7BCCFDC5EF8CF853751F42BD006 +:10014000809100110CD08091011109D08091021191 +:10015000ADCF813509F0BDCF81E014D0BACF9091F9 +:10016000440895FFFCCF809342080895809144088D +:1001700087FFFCCF909141088091400892FD01C01B +:10018000A89508959091010190FDFCCF98ED94BF42 +:10019000809300010895EADF803219F081E0F2DFF8 +:1001A000FFCF84E1DCCFCF93C82FE0DFC150E9F768 +:1001B000CF91F1CF683048F48DE984BF609300108F +:1001C000809102108370E1F70895FC014083089547 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex index 3969d98..3d026f0 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_ALT_115200_A7.hex @@ -1,31 +1,32 @@ -:1000000001C0D2C01124809140008093400083FF42 -:1000100004C0282E80E0B0D0F3C0A895249A2C9A72 -:1000200080E48093E205809182128370813029F50B -:100030008CE590E0809368089093690881E0809354 -:100040006B0883E0809367081092650880EC8093CA -:10005000660888E091D0079A87E0815089F4A895D6 -:100060000DE983E0D82E7CD08134F1F479D0182FBB -:100070008CD0123889F480E013C083E790E0DACFA7 -:10008000179A2EEC36E5A8959091640897FDE8CF75 -:1000900021503109C1F7E1CF89E0113809F083E03F -:1000A00058D080E156D0DFCF823419F484E175D086 -:1000B000F8CF853411F485E0FACF853531F450D08E -:1000C000C82F4ED0D82F61D0ECCF863519F484E0FC -:1000D00064D0D1CF8436B9F443D042D0182F40D069 -:1000E000863479F4D05C3CD0888321961150D9F7BE -:1000F0004CD004BFD0920010809102108370E1F7C1 -:10010000D0CFDC5EF0CF843791F42AD029D0182FDD -:1001100027D0F82E3AD086E4F81207C0D05C888148 -:10012000219617D01150D9F7BCCFDC5EF8CF8537B8 -:1001300051F42BD0809100110CD08091011109D085 -:1001400080910211ADCF813509F0BDCF81E014D08F -:10015000BACF9091640895FFFCCF80936208089510 -:100160008091640887FFFCCF9091610880916008BE -:1001700092FD01C0A89508959091010190FDFCCFDA -:1001800098ED94BF809300010895EADF803219F062 -:1001900081E0F2DFFFCF84E1DCCFCF93C82FE0DF37 -:1001A000C150E9F7CF91F1CF683048F48DE984BFB1 -:1001B00060930010809102108370E1F70895FC01B4 -:0401C00040830895DB +:1000000001C0D9C0112480914000882369F0282FB5 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0B0D0ECC0A895249A2C9A80E4D8 +:100030008093E205809182128370813029F58CE5EE +:1000400090E0809368089093690881E080936B0842 +:1000500083E0809367081092650880EC80936608BF +:1000600088E091D0079A87E0815089F4A8950DE93E +:1000700083E0D82E7CD08134F1F479D0182F8CD045 +:10008000123889F480E013C083E790E0DACF179A42 +:100090002EEC36E5A8959091640897FDE8CF2150A5 +:1000A0003109C1F7E1CF89E0113809F083E058D078 +:1000B00080E156D0DFCF823419F484E175D0F8CFD7 +:1000C000853411F485E0FACF853531F450D0C82F4E +:1000D0004ED0D82F61D0ECCF863519F484E064D0AF +:1000E000D1CF8436B9F443D042D0182F40D08634D3 +:1000F00079F4D05C3CD0888321961150D9F74CD04C +:1001000004BFD0920010809102108370E1F7D0CF2D +:10011000DC5EF0CF843791F42AD029D0182F27D075 +:10012000F82E3AD086E4F81207C0D05C8881219678 +:1001300017D01150D9F7BCCFDC5EF8CF853751F41A +:100140002BD0809100110CD08091011109D08091A9 +:100150000211ADCF813509F0BDCF81E014D0BACF07 +:100160009091640895FFFCCF809362080895809178 +:10017000640887FFFCCF909161088091600892FD30 +:1001800001C0A89508959091010190FDFCCF98EDD4 +:1001900094BF809300010895EADF803219F081E076 +:1001A000F2DFFFCF84E1DCCFCF93C82FE0DFC15077 +:1001B000E9F7CF91F1CF683048F48DE984BF6093BF +:1001C0000010809102108370E1F70895FC014083D4 +:0201D000089590 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex index 4441661..f654a0c 100644 --- a/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex +++ b/megaavr/bootloaders/optiboot/bootloaders/mega0/115200/Optiboot_mega0_UART3_DEF_115200_A7.hex @@ -1,31 +1,31 @@ -:1000000001C0D1C01124809140008093400083FF43 -:1000100004C0282E80E0AFD0F3C0A895209A289A7B -:100020001092E205809182128370813029F58CE56F -:1000300090E0809368089093690881E080936B0852 -:1000400083E0809367081092650880EC80936608CF -:1000500088E091D0079A87E0815089F4A8950DE94E -:1000600083E0D82E7CD08134F1F479D0182F8CD055 -:10007000123889F480E013C083E790E0DACF179A52 -:100080002EEC36E5A8959091640897FDE8CF2150B5 -:100090003109C1F7E1CF89E0113809F083E058D088 -:1000A00080E156D0DFCF823419F484E175D0F8CFE7 -:1000B000853411F485E0FACF853531F450D0C82F5E -:1000C0004ED0D82F61D0ECCF863519F484E064D0BF -:1000D000D1CF8436B9F443D042D0182F40D08634E3 -:1000E00079F4D05C3CD0888321961150D9F74CD05C -:1000F00004BFD0920010809102108370E1F7D0CF3E -:10010000DC5EF0CF843791F42AD029D0182F27D085 -:10011000F82E3AD086E4F81207C0D05C8881219688 -:1001200017D01150D9F7BCCFDC5EF8CF853751F42A -:100130002BD0809100110CD08091011109D08091B9 -:100140000211ADCF813509F0BDCF81E014D0BACF17 -:100150009091640895FFFCCF809362080895809188 -:10016000640887FFFCCF909161088091600892FD40 -:1001700001C0A89508959091010190FDFCCF98EDE4 -:1001800094BF809300010895EADF803219F081E086 -:10019000F2DFFFCF84E1DCCFCF93C82FE0DFC15087 -:1001A000E9F7CF91F1CF683048F48DE984BF6093CF -:1001B0000010809102108370E1F70895FC014083E4 -:0201C0000895A0 +:1000000001C0D8C0112480914000882369F0282FB6 +:1000100030E083FD03C02C7F232B31F4809340001C +:100020008CBB80E0AFD0ECC0A895209A289A1092A3 +:10003000E205809182128370813029F58CE590E091 +:10004000809368089093690881E080936B0883E04F +:10005000809367081092650880EC8093660888E0BA +:1000600091D0079A87E0815089F4A8950DE983E043 +:10007000D82E7CD08134F1F479D0182F8CD012385E +:1000800089F480E013C083E790E0DACF179A2EEC72 +:1000900036E5A8959091640897FDE8CF2150310985 +:1000A000C1F7E1CF89E0113809F083E058D080E151 +:1000B00056D0DFCF823419F484E175D0F8CF85347F +:1000C00011F485E0FACF853531F450D0C82F4ED0E9 +:1000D000D82F61D0ECCF863519F484E064D0D1CF2D +:1000E0008436B9F443D042D0182F40D0863479F406 +:1000F000D05C3CD0888321961150D9F74CD004BFF6 +:10010000D0920010809102108370E1F7D0CFDC5EB6 +:10011000F0CF843791F42AD029D0182F27D0F82E89 +:100120003AD086E4F81207C0D05C8881219617D0B7 +:100130001150D9F7BCCFDC5EF8CF853751F42BD006 +:10014000809100110CD08091011109D08091021191 +:10015000ADCF813509F0BDCF81E014D0BACF9091F9 +:10016000640895FFFCCF809362080895809164082D +:1001700087FFFCCF909161088091600892FD01C0DB +:10018000A89508959091010190FDFCCF98ED94BF42 +:10019000809300010895EADF803219F081E0F2DFF8 +:1001A000FFCF84E1DCCFCF93C82FE0DFC150E9F768 +:1001B000CF91F1CF683048F48DE984BF609300108F +:1001C000809102108370E1F70895FC014083089547 :0201FE000009F6 :00000001FF diff --git a/megaavr/bootloaders/optiboot/makeall b/megaavr/bootloaders/optiboot/makeall index f2d7625..95c1b1c 100755 --- a/megaavr/bootloaders/optiboot/makeall +++ b/megaavr/bootloaders/optiboot/makeall @@ -1,9 +1,9 @@ # Build for 115200 baud -make mega0 UARTTX=A0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=A4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=B0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=B4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=C0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=C4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=F0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 -make mega0 UARTTX=F4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 +make mega0 UARTTX=A0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=A4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=B0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=B4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=C0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=C4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=F0 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 +make mega0 UARTTX=F4 TIMEOUT=1 LED=A7 BAUD_RATE=115200 SKIP_BOOTLOADER_ON_POR=1 diff --git a/megaavr/bootloaders/optiboot/optiboot_x.c b/megaavr/bootloaders/optiboot/optiboot_x.c index f5be99f..607d682 100755 --- a/megaavr/bootloaders/optiboot/optiboot_x.c +++ b/megaavr/bootloaders/optiboot/optiboot_x.c @@ -322,59 +322,83 @@ int main (void) { __asm__ __volatile__ ("clr __zero_reg__"); // known-zero required by avr-libc #define RESET_EXTERNAL (RSTCTRL_EXTRF_bm|RSTCTRL_UPDIRF_bm|RSTCTRL_SWRF_bm) #ifndef FANCY_RESET_LOGIC - ch = RSTCTRL.RSTFR; // get reset cause - RSTCTRL.RSTFR = ch; // and reset them all! - if (ch & RSTCTRL_WDRF_bm) { - // Start the app. - __asm__ __volatile__ ("mov r2, %0\n" :: "r" (ch)); - watchdogConfig(WDT_PERIOD_OFF_gc); - __asm__ __volatile__ ( - "jmp app\n" - ); - } + ch = RSTCTRL.RSTFR; // get reset cause +#ifdef START_APP_ON_POR + /* + * If WDRF is set OR nothing except BORF and PORF are set, that's + * not bootloader entry condition so jump to app - this is for when + * UPDI pin is used as reset, so we go straight to app on start. + * 11/14: NASTY bug - we also need to check for no reset flags being + * set (ie, direct entry) and run bootloader in that case, otherwise + * bootloader won't run, among other things, after fresh bootloading! + */ + + if (ch && (ch & RSTCTRL_WDRF_bm || + (!(ch & (~(RSTCTRL_BORF_bm | RSTCTRL_PORF_bm)))))) { +#else + /* + * If WDRF is set OR nothing except BORF is set, that's not + * bootloader entry condition so jump to app - let's see if this + * works okay or not... + */ + if (ch && (ch & RSTCTRL_WDRF_bm || (!(ch & (~RSTCTRL_BORF_bm))))) { +#endif + /* Start the app. + * Dont bother trying to stuff it in r2, which requires heroic + * effort to fish out we'll put it in GPIOR0 where it won't get + * stomped on. + */ + // __asm__ __volatile__ (" mov r2, %0\n" :: "r" (ch)); + RSTCTRL.RSTFR = ch; //clear the reset causes before jumping to app... + GPIOR0 = ch; // but, stash the reset cause in GPIOR0 for use by app... + watchdogConfig(WDT_PERIOD_OFF_gc); + __asm__ __volatile__( + " jmp app\n" + ); + } #else + /* + * Protect as much Reset Cause as possible for application + * and still skip bootloader if not necessary + */ + ch = RSTCTRL.RSTFR; + if (ch != 0) { /* - * Protect as much Reset Cause as possible for application - * and still skip bootloader if not necessary + * We want to run the bootloader when an external reset has occurred. + * On these mega0/XTiny chips, there are three types of ext reset: + * reset pin (may not exist), UPDI reset, and SW-request reset. + * One of these reset causes, together with watchdog reset, should + * mean that Optiboot timed out, and it's time to run the app. + * Other reset causes (notably poweron) should run the app directly. + * If a user app wants to utilize and detect watchdog resets, it + * must make sure that the other reset causes are cleared. */ - ch = RSTCTRL.RSTFR; - if (ch != 0) { - /* - * We want to run the bootloader when an external reset has occurred. - * On these mega0/XTiny chips, there are three types of ext reset: - * reset pin (may not exist), UPDI reset, and SW-request reset. - * One of these reset causes, together with watchdog reset, should - * mean that Optiboot timed out, and it's time to run the app. - * Other reset causes (notably poweron) should run the app directly. - * If a user app wants to utilize and detect watchdog resets, it - * must make sure that the other reset causes are cleared. - */ - if (ch & RSTCTRL_WDRF_bm) { - if (ch & RESET_EXTERNAL) { - /* - * Clear WDRF because it was most probably set by wdr in - * bootloader. It's also needed to avoid loop by broken - * application which could prevent entering bootloader. - */ - RSTCTRL.RSTFR = RSTCTRL_WDRF_bm; - } - } - if (!(ch & RESET_EXTERNAL)) { - /* - * save the reset flags in the designated register. - * This can be saved in a main program by putting code in - * .init0 (which executes before normal c init code) to save R2 - * to a global variable. - */ - __asm__ __volatile__ ("mov r2, %0\n" :: "r" (ch)); - - // switch off watchdog - watchdogConfig(WDT_PERIOD_OFF_gc); - __asm__ __volatile__ ( - "jmp 512\n" - ); - } + if (ch & RSTCTRL_WDRF_bm) { + if (ch & RESET_EXTERNAL) { + /* + * Clear WDRF because it was most probably set by wdr in + * bootloader. It's also needed to avoid loop by broken + * application which could prevent entering bootloader. + */ + RSTCTRL.RSTFR = RSTCTRL_WDRF_bm; + } + } + if (!(ch & RESET_EXTERNAL)) { + /* + * save the reset flags in the designated register. + * This can be saved in a main program by putting code in + * .init0 (which executes before normal c init code) to save R2 + * to a global variable. + */ + __asm__ __volatile__(" mov r2, %0\n" :: "r"(ch)); + + // switch off watchdog + watchdogConfig(WDT_PERIOD_OFF_gc); + __asm__ __volatile__( + " jmp app\n" + ); } + } #endif // Fancy reset cause stuff watchdogReset(); diff --git a/megaavr/bootloaders/optiboot/parse_options.mk b/megaavr/bootloaders/optiboot/parse_options.mk index 7da4ff2..3905200 100755 --- a/megaavr/bootloaders/optiboot/parse_options.mk +++ b/megaavr/bootloaders/optiboot/parse_options.mk @@ -136,3 +136,7 @@ UART_CMD = -DUARTTX=$(UARTTX) endif UART_OPTIONS = $(UART_CMD) $(BAUD_RATE_CMD) $(SOFT_UART_CMD) $(SS_CMD) + +ifneq ($(SKIP_BOOTLOADER_ON_POR),0) +POR = -DSTART_APP_ON_POR +endif From ce1baeb9ca526a42fba621b65f95599c846028a6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Mar 2022 07:20:48 +0100 Subject: [PATCH 292/351] Add -mrelax build flag Closes #141 --- megaavr/platform.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 93480f2..fb4d2e3 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -20,12 +20,12 @@ compiler.warning_flags.all=-Wall -Wextra # Default "compiler.path" is correct, change only if you want to override the initial value compiler.path={runtime.tools.avr-gcc.path}/bin/ compiler.c.cmd=avr-gcc -compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto -fno-fat-lto-objects -compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin -Wl,--gc-sections -Wl,--section-start={build.text_section_start} +compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto -fno-fat-lto-objects -mrelax +compiler.c.elf.flags={compiler.warning_flags} -Os -g -flto -fuse-linker-plugin -mrelax -Wl,--gc-sections -Wl,--section-start={build.text_section_start} compiler.c.elf.cmd=avr-gcc compiler.S.flags=-c -g -x assembler-with-cpp -flto -MMD compiler.cpp.cmd=avr-g++ -compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++17 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -Wno-error=narrowing -MMD -flto +compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++17 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -Wno-error=narrowing -MMD -flto -mrelax compiler.ar.cmd=avr-gcc-ar compiler.ar.flags=rcs compiler.objcopy.cmd=avr-objcopy From 31bc8f27f93e8129d3c72503885c98baac03ac10 Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 16 Mar 2022 07:31:47 +0100 Subject: [PATCH 293/351] Fix incorrect LED pin on Curiosity Nano and Xplained Pro pinouts Closes #93 --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 4879383..f3a71f1 100644 --- a/README.md +++ b/README.md @@ -281,7 +281,7 @@ Click to enlarge: Click to enlarge: - + ### AVR-IOT WG [The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. @@ -295,4 +295,4 @@ Click to enlarge: Click to enlarge: - + From 531beba634cdb05d6f8bd67b9ed45c646a0ac4d8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 16 Mar 2022 07:38:41 +0100 Subject: [PATCH 294/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index fb4d2e3..5e99cdc 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.9 +version=1.0.10 # AVR compile variables # --------------------- From 17115775ca95535a95d8b5c657811578271ce610 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Apr 2022 20:52:27 +0200 Subject: [PATCH 295/351] Fix issue where registers were written to incorrectly Applies to megaTinyCore and DxCore as well. See https://github.com/SpenceKonde/DxCore/issues/271 for detail --- megaavr/libraries/Logic/src/Logic.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index e6b50cf..bb0e4f7 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -460,8 +460,8 @@ void Logic::init() } // Set inputs modes - block.LUTCTRLB = (input1 << CCL_INSEL1_gp) | (input0 << CCL_INSEL0_gp); - block.LUTCTRLC = (input2 << CCL_INSEL2_gp); + block.LUTCTRLB = ((input1 & 0x0f) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); + block.LUTCTRLC = ((input2 & 0x0f) << CCL_INSEL2_gp); // Set truth table block.TRUTH = truth; From b509bf6cff50df57b7bd6d171b63cfcd42a1b11a Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 17 Apr 2022 21:00:15 +0200 Subject: [PATCH 296/351] Preserve the state of the in:: parameters --- megaavr/libraries/Logic/src/Logic.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index bb0e4f7..cbe139a 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -430,7 +430,6 @@ void Logic::initInput(in::input_t &input, PORT_t &port, const uint8_t pin_bm) { } else { PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; } - input = in::input; } } From e27173a07c1e6ab2db33e8811aa748c13e47b455 Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 17 Apr 2022 22:54:31 +0200 Subject: [PATCH 297/351] Update README.md #145 related --- README.md | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/README.md b/README.md index f3a71f1..7f03110 100644 --- a/README.md +++ b/README.md @@ -25,6 +25,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Pin macros](#pin-macros) * [Write to own flash](#write-to-own-flash) * [Memory-mapped flash](#memory-mapped-flash) +* [Identifying MegaCoreX](#identifying-megacorex) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -160,6 +161,28 @@ This also includes quoted strings, which means that the string in `Serial.print( If you explicitly declare a variable PROGMEM, you must still use the `pgm_read_byte()/pgm_read_word()` functions, just like on "classic" AVRs. Do note that declaring things PROGMEM or using the `F()` macro works fine, but it is slower and consumes more flash than simply declaring something `const` or omitting the `F()` macro. +# Identifying MegaCoreX +If you're writing code that has MegaCoreX specific code in it, you can identify this core and various pinouts with the list of macros below. + + +| Core specific | Pinout specific | Chip family specific | Chip specific | +|---------------------|----------------------------------|----------------------|----------------------| +| `MEGACOREX` | `MEGACOREX_DEFAULT_48PIN_PINOUT` | `__AVR_ATmegax09__` | `__AVR_ATmega4809__` | +| `MCUDUDE_MEGACOREX` | `MEGACOREX_DEFAULT_40PIN_PINOUT` | `__AVR_ATmegax08__` | `__AVR_ATmega4808__` | +| | `MEGACOREX_DEFAULT_32PIN_PINOUT` | | `__AVR_ATmega3209__` | +| | `MEGACOREX_DEFAULT_28PIN_PINOUT` | | `__AVR_ATmega3208__` | +| | | | `__AVR_ATmega1609__` | +| | | | `__AVR_ATmega1608__` | +| | | | `__AVR_ATmega809__` | +| | | | `__AVR_ATmega808__` | + +Usage: +```c++ +#if defined(MEGACOREX) +// Code +#endif +``` + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. From 19d91ec4eb0372be3f68e16acb907abdd71dccd2 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 21 May 2022 19:48:21 +0200 Subject: [PATCH 298/351] Fix typo --- megaavr/libraries/Logic/src/Logic.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index cbe139a..dbf7614 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -459,7 +459,7 @@ void Logic::init() } // Set inputs modes - block.LUTCTRLB = ((input1 & 0x0f) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); + block.LUTCTRLB = ((input1 & 0xf0) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); block.LUTCTRLC = ((input2 & 0x0f) << CCL_INSEL2_gp); // Set truth table From 09f3a6e04f6ab9b83063260bb43053c122c7e512 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 7 Jun 2022 09:41:41 +0200 Subject: [PATCH 299/351] Prepare for Avrdude 7.0 and SerialUPDI --- megaavr/avrdude.conf | 13290 +++++++++++++++++++++++--------------- megaavr/programmers.txt | 40 +- 2 files changed, 8142 insertions(+), 5188 deletions(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index d92878f..36c62ce 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -339,10 +339,6 @@ default_parallel = "unknown"; default_serial = "unknown"; # default_bitclock = 2.5; -# Turn off safemode by default -#default_safemode = no; - - # # PROGRAMMER DEFINITIONS # @@ -363,6 +359,14 @@ programmer type = "arduino"; connection_type = serial; ; + +programmer + id = "xbee"; + desc = "XBee Series 2 Over-The-Air (XBeeBoot)"; + type = "xbee"; + connection_type = serial; +; + # this will interface with the chips on these programmers: # # http://real.kiev.ua/old/avreal/en/adapters @@ -468,63 +472,47 @@ programmer # from Amontec ; -# UM232H module from FTDI and Glyn.com.au. -# See helix.air.net.au for detailed usage information. -# J1: Connect pin 2 and 3 for USB power. -# J2: Connect pin 2 and 3 for USB power. -# J2: Pin 7 is SCK -# : Pin 8 is MOSI -# : Pin 9 is MISO -# : Pin 11 is RST -# : Pin 6 is ground -# Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get -# a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. programmer - id = "UM232H"; - desc = "FT232H based module from FTDI and Glyn.com.au"; + id = "ft232h"; + desc = "FT232H in MPSSE mode"; type = "avrftdi"; + connection_type = usb; usbvid = 0x0403; -# Note: This PID is reserved for generic 232H devices and -# should be programmed into the EEPROM usbpid = 0x6014; usbdev = "A"; usbvendor = ""; usbproduct = ""; usbsn = ""; #ISP-signals - sck = 0; - mosi = 1; - miso = 2; - reset = 3; + sck = 0; # AD0 (TCK) + mosi = 1; # AD1 (TDI) + miso = 2; # AD2 (TDO) + reset = 3; # AD3 (TMS) ; -# C232HM module from FTDI and Glyn.com.au. -# : Orange is SCK -# : Yellow is MOSI -# : Green is MISO -# : Brown is RST -# : Black is ground +# Pin J2-7 (AD0) is SCK +# Pin J2-8 (AD1) is MOSI +# Pin J2-9 (AD2) is MISO +# Pin J2-10 (AD3) is RESET +# Pin J2-6 is GND # Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get # a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. -programmer - id = "C232HM"; - desc = "FT232H based module from FTDI and Glyn.com.au"; - type = "avrftdi"; - usbvid = 0x0403; -# Note: This PID is reserved for generic 232H devices and -# should be programmed into the EEPROM - usbpid = 0x6014; - usbdev = "A"; - usbvendor = ""; - usbproduct = ""; - usbsn = ""; -#ISP-signals - sck = 0; - mosi = 1; - miso = 2; - reset = 3; +programmer parent "ft232h" + id = "um232h"; + desc = "UM232H module from FTDI"; ; +# Orange (Pin 2) is SCK +# Yellow (Pin 3) is MOSI +# Green (Pin 4) is MISO +# Brown (Pin 5) is RESET +# Black (Pin 10) is GND +# Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get +# a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. +programmer parent "ft232h" + id = "c232hm"; + desc = "C232HM cable from FTDI"; +; # On the adapter you can read "O-Link". On the PCB is printed "OpenJTAG v3.1" # You can find it as "OpenJTAG ARM JTAG USB" in the internet. @@ -605,6 +593,13 @@ programmer reset = 3; # TMS 7 ; +programmer + id = "serialupdi"; + desc = "SerialUPDI"; + type = "serialupdi"; + connection_type = serial; +; + programmer id = "avrisp"; desc = "Atmel AVR ISP"; @@ -772,6 +767,18 @@ programmer reset = 7; # RI X3(4) ; +programmer + id = "tc2030"; + desc = "Tag-Connect TC2030"; + type = "ftdi_syncbb"; + connection_type = usb; + # FOR TPI devices: + mosi = 0; # TxD = D0 (wire to TPIDATA via 1k resistor) + miso = 1; # RxD = D1 (wire to TPIDATA directly) + sck = 2; # RTS = D2 (wire to SCK) + reset = 3; # CTS = D3 (wire to ~RESET) +; + # website mentioned above uses this id programmer parent "arduino-ft232r" id = "diecimila"; @@ -879,6 +886,24 @@ programmer usbpid = 0x0c9f; ; +programmer + id = "arduinoisp"; + desc = "Arduino ISP Programmer"; + type = "usbtiny"; + connection_type = usb; + usbvid = 0x2341; + usbpid = 0x0049; +; + +programmer + id = "arduinoisporg"; + desc = "Arduino ISP Programmer"; + type = "usbtiny"; + connection_type = usb; + usbvid = 0x2A03; + usbpid = 0x0049; +; + # commercial version of USBtiny, using a separate VID/PID programmer id = "ehajo-isp"; @@ -889,22 +914,32 @@ programmer usbpid = 0x0BA5; ; +# commercial version of USBtiny, using a separate VID/PID programmer - id = "arduinoisp"; - desc = "Arduino ISP Programmer"; + id = "iseavrprog"; + desc = "USBtiny-based USB programmer, https://github.com/IowaScaledEngineering/ckt-avrprogrammer"; type = "usbtiny"; connection_type = usb; - usbvid = 0x2341; - usbpid = 0x0049; + usbvid = 0x1209; + usbpid = 0x6570; ; programmer - id = "arduinoisporg"; - desc = "Arduino ISP Programmer"; - type = "usbtiny"; + id = "micronucleus"; + desc = "Micronucleus Bootloader"; + type = "micronucleus"; connection_type = usb; - usbvid = 0x2A03; - usbpid = 0x0049; + usbvid = 0x16D0; + usbpid = 0x0753; +; + +programmer + id = "teensy"; + desc = "Teensy Bootloader"; + type = "teensy"; + connection_type = usb; + usbvid = 0x16C0; + usbpid = 0x0478; ; programmer @@ -1103,6 +1138,14 @@ programmer usbpid = 0x2110, 0x2140; ; +programmer + id = "jtag3updi"; + desc = "Atmel AVR JTAGICE3 in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2110, 0x2140; +; + programmer id = "jtag3dw"; desc = "Atmel AVR JTAGICE3 in debugWIRE mode"; @@ -1159,14 +1202,6 @@ programmer usbpid = 0x2145; ; -programmer - id = "curiosity_updi"; - desc = "Curiosity in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2175; -; - programmer id = "atmelice"; desc = "Atmel-ICE (ARM/AVR) in JTAG mode"; @@ -1248,28 +1283,68 @@ programmer ; programmer - id = "pickit4_updi"; - desc = "MPLAB(R) PICkit 4 in UPDI mode"; - type = "jtagice3_updi"; + id = "pickit4_updi"; + desc = "MPLAB(R) PICkit 4 in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; +; + +programmer + id = "pickit4_pdi"; + desc = "MPLAB(R) PICkit 4 in PDI mode"; + type = "jtagice3_pdi"; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; +; + +programmer + id = "pickit4_isp"; + desc = "MPLAB(R) PICkit 4 in ISP mode"; + type = "jtagice3_isp"; connection_type = usb; usbpid = 0x2177, 0x2178, 0x2179, 0x9018; - ; +; - programmer - id = "snap_updi"; - desc = "MPLAB(R) SNAP in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x217F, 0x2180, 0x2181; - ; +programmer + id = "snap_updi"; + desc = "MPLAB(R) SNAP in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x217F, 0x2180, 0x2181; +; - programmer - id = "pkobn_updi"; - desc = "PKOB nano (nEDBG) in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2175; - ; +programmer + id = "snap_pdi"; + desc = "MPLAB(R) SNAP in PDI mode"; + type = "jtagice3_pdi"; + connection_type = usb; + usbpid = 0x217F, 0x2180, 0x2181; +; + +programmer + id = "snap_isp"; + desc = "MPLAB(R) SNAP in ISP mode"; + type = "jtagice3_isp"; + connection_type = usb; + usbpid = 0x217F, 0x2180, 0x2181; +; + +programmer + id = "pkobn_updi"; + desc = "Curiosity nano (nEDBG) in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2175; +; + +programmer + id = "curiosity_updi"; + desc = "Curiosity in UPDI mode"; + type = "jtagice3_updi"; + connection_type = usb; + usbpid = 0x2175; +; programmer id = "pavr"; @@ -1300,40 +1375,8 @@ programmer ; -#This programmer bitbangs GPIO lines using the Linux sysfs GPIO interface -# -#To enable it set the configuration below to match the GPIO lines connected to the -#relevant ISP header pins and uncomment the entry definition. In case you don't -#have the required permissions to edit this system wide config file put the -#entry in a separate .conf file and use it with -C+.conf -#on the command line. -# -#To check if your avrdude build has support for the linuxgpio programmer compiled in, -#use -c?type on the command line and look for linuxgpio in the list. If it's not available -#you need pass the --enable-linuxgpio=yes option to configure and recompile avrdude. -# -#programmer -# id = "linuxgpio"; -# desc = "Use the Linux sysfs interface to bitbang GPIO lines"; -# type = "linuxgpio"; -# reset = ?; -# sck = ?; -# mosi = ?; -# miso = ?; -#; - - -#This programmer uses the built in linux SPI bus devices to program an -#attached AVR. A GPIO accessed through the sysfs GPIO interface needs to -#be specified for a reset pin since the linux SPI userspace functions do -#not allow for control over the slave select/chip select signal. -# -programmer - id = "linuxspi"; - desc = "Use Linux SPI device in /dev/spidev*"; - type = "linuxspi"; - reset = 25; -; + + # some ultra cheap programmers use bitbanging on the # serialport. @@ -1419,6 +1462,7 @@ programmer # JTAG2UPDI # https://github.com/ElTangas/jtag2updi + programmer id = "jtag2updi"; desc = "JTAGv2 to UPDI bridge"; @@ -1766,7 +1810,7 @@ part max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -1801,9 +1845,16 @@ part read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; ; - ; +#------------------------------------------------------------ +# ATtiny13A +#------------------------------------------------------------ + +part parent "t13" + id = "t13a"; + desc = "ATtiny13A"; + ; #------------------------------------------------------------ # ATtiny15 @@ -3273,7 +3324,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -3294,8 +3345,14 @@ part ; ; +#------------------------------------------------------------ +# ATmega64A +#------------------------------------------------------------ - +part parent "m64" + id = "m64a"; + desc = "ATmega64A"; + ; #------------------------------------------------------------ # ATmega128 @@ -3456,7 +3513,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -3477,6 +3534,15 @@ part ; ; +#------------------------------------------------------------ +# ATmega128A +#------------------------------------------------------------ + +part parent "m128" + id = "m128a"; + desc = "ATmega128A"; + ; + #------------------------------------------------------------ # AT90CAN128 #------------------------------------------------------------ @@ -3648,7 +3714,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -3840,7 +3906,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4032,7 +4098,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4189,7 +4255,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4231,36 +4297,19 @@ part ; ; - #------------------------------------------------------------ -# ATmega164P +# ATmega16A #------------------------------------------------------------ -# close to ATmega16 - part parent "m16" - id = "m164p"; - desc = "ATmega164P"; - signature = 0x1e 0x94 0x0a; - - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - allowfullpagebitstream = no; - chip_erase_delay = 55000; - - ocdrev = 3; + id = "m16a"; + desc = "ATmega16A"; ; - #------------------------------------------------------------ # ATmega324P #------------------------------------------------------------ -# similar to ATmega164P - part id = "m324p"; desc = "ATmega324P"; @@ -4391,7 +4440,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4447,28 +4496,81 @@ part ; ; +#------------------------------------------------------------ +# ATmega164P +#------------------------------------------------------------ + +part parent "m324p" + id = "m164p"; + desc = "ATmega164P"; + signature = 0x1e 0x94 0x0a; + + memory "eeprom" + size = 512; + page_size = 4; + ; + + memory "flash" + paged = yes; + size = 16384; + page_size = 128; + num_pages = 128; + ; + ; + +#------------------------------------------------------------ +# ATmega164PA +#------------------------------------------------------------ + +part parent "m164p" + id = "m164pa"; + desc = "ATmega164PA"; + ; + +#------------------------------------------------------------ +# ATmega164A +#------------------------------------------------------------ + +part parent "m164p" + id = "m164a"; + desc = "ATmega164A"; + signature = 0x1e 0x94 0x0f; + ; #------------------------------------------------------------ -# ATmega324PA +# ATmega324PB #------------------------------------------------------------ -# similar to ATmega324P +part parent "m324p" + id = "m324pb"; + desc = "ATmega324PB"; + signature = 0x1e 0x95 0x17; + ; + +#------------------------------------------------------------ +# ATmega324PA +#------------------------------------------------------------ part parent "m324p" id = "m324pa"; desc = "ATmega324PA"; signature = 0x1e 0x95 0x11; - - ocdrev = 3; ; +#------------------------------------------------------------ +# ATmega324A +#------------------------------------------------------------ + +part parent "m324p" + id = "m324a"; + desc = "ATmega324A"; + signature = 0x1e 0x95 0x15; + ; #------------------------------------------------------------ # ATmega644 #------------------------------------------------------------ -# similar to ATmega164 - part id = "m644"; desc = "ATmega644"; @@ -4599,7 +4701,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4656,27 +4758,38 @@ part ; #------------------------------------------------------------ -# ATmega644P +# ATmega644A #------------------------------------------------------------ -# similar to ATmega164p +part parent "m644" + id = "m644a"; + desc = "ATmega644A"; + ; + +#------------------------------------------------------------ +# ATmega644P +#------------------------------------------------------------ part parent "m644" id = "m644p"; desc = "ATmega644P"; signature = 0x1e 0x96 0x0a; - - ocdrev = 3; ; +#------------------------------------------------------------ +# ATmega644PA +#------------------------------------------------------------ +part parent "m644" + id = "m644pa"; + desc = "ATmega644PA"; + signature = 0x1e 0x96 0x0a; + ; #------------------------------------------------------------ # ATmega1284 #------------------------------------------------------------ -# similar to ATmega164 - part id = "m1284"; desc = "ATmega1284"; @@ -4807,7 +4920,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -4863,202 +4976,16 @@ part ; ; - - #------------------------------------------------------------ # ATmega1284P #------------------------------------------------------------ -# similar to ATmega164p - -part +part parent "m1284" id = "m1284p"; desc = "ATmega1284P"; - has_jtag = yes; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; signature = 0x1e 0x97 0x05; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 55000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 256; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - - memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; ; - - #------------------------------------------------------------ # ATmega162 #------------------------------------------------------------ @@ -5234,7 +5161,7 @@ part max_write_delay = 16000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -5396,7 +5323,7 @@ part min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x 0 x x x x x o o o o o o"; + "x x x x 0 x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -5578,7 +5505,7 @@ part min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -5597,6 +5524,36 @@ part ; ; +#------------------------------------------------------------ +# ATmega169A +#------------------------------------------------------------ + +part parent "m169" + id = "m169a"; + desc = "ATmega169A"; + signature = 0x1E 0x94 0x11; + ; + +#------------------------------------------------------------ +# ATmega169P +#------------------------------------------------------------ + +part parent "m169" + id = "m169p"; + desc = "ATmega169P"; + signature = 0x1E 0x94 0x05; + ; + +#------------------------------------------------------------ +# ATmega169PA +#------------------------------------------------------------ + +part parent "m169" + id = "m169pa"; + desc = "ATmega169PA"; + signature = 0x1E 0x94 0x05; + ; + #------------------------------------------------------------ # ATmega329 #------------------------------------------------------------ @@ -5763,7 +5720,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -5782,45 +5739,73 @@ part ; ; +#------------------------------------------------------------ +# ATmega329A +#------------------------------------------------------------ + +part parent "m329" + id = "m329a"; + desc = "ATmega329A"; + ; + #------------------------------------------------------------ # ATmega329P #------------------------------------------------------------ -# Identical to ATmega329 except of the signature part parent "m329" id = "m329p"; desc = "ATmega329P"; signature = 0x1e 0x95 0x0b; + ; - ocdrev = 3; +#------------------------------------------------------------ +# ATmega329PA +#------------------------------------------------------------ + +part parent "m329" + id = "m329pa"; + desc = "ATmega329PA"; + signature = 0x1e 0x95 0x0b; ; #------------------------------------------------------------ # ATmega3290 #------------------------------------------------------------ -# identical to ATmega329 - part parent "m329" id = "m3290"; desc = "ATmega3290"; signature = 0x1e 0x95 0x04; + ; - ocdrev = 3; +#------------------------------------------------------------ +# ATmega3290A +#------------------------------------------------------------ + +part parent "m329" + id = "m3290a"; + desc = "ATmega3290A"; + signature = 0x1e 0x95 0x04; ; #------------------------------------------------------------ # ATmega3290P #------------------------------------------------------------ -# identical to ATmega3290 except of the signature - -part parent "m3290" +part parent "m329" id = "m3290p"; desc = "ATmega3290P"; signature = 0x1e 0x95 0x0c; + ; - ocdrev = 3; +#------------------------------------------------------------ +# ATmega3290PA +#------------------------------------------------------------ + +part parent "m329" + id = "m3290pa"; + desc = "ATmega3290PA"; + signature = 0x1e 0x95 0x0c; ; #------------------------------------------------------------ @@ -5989,7 +5974,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6009,27 +5994,62 @@ part ; #------------------------------------------------------------ -# ATmega6490 +# ATmega649A #------------------------------------------------------------ -# identical to ATmega649 +part parent "m649" + id = "m649a"; + desc = "ATmega649A"; + ; + +#------------------------------------------------------------ +# ATmega649P +#------------------------------------------------------------ + +part parent "m649" + id = "m649p"; + desc = "ATmega649P"; + signature = 0x1e 0x96 0x0b; + ; + +#------------------------------------------------------------ +# ATmega6490 +#------------------------------------------------------------ part parent "m649" id = "m6490"; desc = "ATmega6490"; signature = 0x1e 0x96 0x04; + ; - ocdrev = 3; +#------------------------------------------------------------ +# ATmega6490A +#------------------------------------------------------------ + +part parent "m649" + id = "m6490a"; + desc = "ATmega6490A"; + signature = 0x1e 0x96 0x04; ; #------------------------------------------------------------ -# ATmega32 +# ATmega6490P #------------------------------------------------------------ -part - id = "m32"; - desc = "ATmega32"; - has_jtag = yes; +part parent "m649" + id = "m6490p"; + desc = "ATmega6490P"; + signature = 0x1e 0x96 0x0C; + ; + +#------------------------------------------------------------ +# ATmega32 +#------------------------------------------------------------ + +part + id = "m32"; + desc = "ATmega32"; + has_jtag = yes; stk500_devcode = 0x91; avr910_devcode = 0x72; signature = 0x1e 0x95 0x02; @@ -6175,12 +6195,16 @@ part "x x x x x x x x i i i i i i i i"; ; + memory "efuse" + size = 0; + ; + memory "lock" size = 1; min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6326,7 +6350,7 @@ part min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6338,6 +6362,14 @@ part ; ; +#------------------------------------------------------------ +# ATmega32A +#------------------------------------------------------------ + +part parent "m32" + id = "m32a"; + desc = "ATmega32A"; + ; #------------------------------------------------------------ # ATmega8 @@ -6474,19 +6506,16 @@ part "x x x x x x x x i i i i i i i i"; ; - # Required for Arduino IDE - # see: https://github.com/arduino/Arduino/issues/2075 - # https://github.com/arduino/Arduino/issues/2075#issuecomment-238031689 memory "efuse" - size = 0; - ; + size = 0; + ; memory "lock" size = 1; min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6507,6 +6536,15 @@ part +#------------------------------------------------------------ +# ATmega8A +#------------------------------------------------------------ + +part parent "m8" + id = "m8a"; + desc = "ATmega8A"; + ; + #------------------------------------------------------------ # ATmega8515 #------------------------------------------------------------ @@ -6643,7 +6681,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6803,7 +6841,7 @@ part min_write_delay = 2000; max_write_delay = 2000; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -6975,14 +7013,11 @@ part read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 a1 a0 o o o o o o o o"; ; - ; - #------------------------------------------------------------ # ATtiny261 #------------------------------------------------------------ -# Close to ATtiny26 part id = "t261"; @@ -7166,14 +7201,20 @@ part read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; - ; +#------------------------------------------------------------ +# ATtiny261A +#------------------------------------------------------------ + +part parent "t261" + id = "t261a"; + desc = "ATtiny261A"; + ; #------------------------------------------------------------ # ATtiny461 #------------------------------------------------------------ -# Close to ATtiny261 part id = "t461"; @@ -7357,14 +7398,20 @@ part read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; - ; +#------------------------------------------------------------ +# ATtiny461A +#------------------------------------------------------------ + +part parent "t461" + id = "t461a"; + desc = "ATtiny461A"; + ; #------------------------------------------------------------ # ATtiny861 #------------------------------------------------------------ -# Close to ATtiny461 part id = "t861"; @@ -7548,9 +7595,16 @@ part read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; - ; +#------------------------------------------------------------ +# ATtiny861A +#------------------------------------------------------------ + +part parent "t861" + id = "t861a"; + desc = "ATtiny861A"; + ; #------------------------------------------------------------ # ATtiny28 @@ -7781,7 +7835,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -7800,6 +7854,15 @@ part ; ; +#------------------------------------------------------------ +# ATmega48A +#------------------------------------------------------------ + +part parent "m48" + id = "m48a"; + desc = "ATmega48A"; + ; + #------------------------------------------------------------ # ATmega48P #------------------------------------------------------------ @@ -7808,8 +7871,16 @@ part parent "m48" id = "m48p"; desc = "ATmega48P"; signature = 0x1e 0x92 0x0a; + ; - ocdrev = 1; +#------------------------------------------------------------ +# ATmega48PA +#------------------------------------------------------------ + +part parent "m48" + id = "m48pa"; + desc = "ATmega48PA"; + signature = 0x1e 0x92 0x0a; ; #------------------------------------------------------------ @@ -7820,8 +7891,6 @@ part parent "m48" id = "m48pb"; desc = "ATmega48PB"; signature = 0x1e 0x92 0x10; - - ocdrev = 1; ; #------------------------------------------------------------ @@ -7993,7 +8062,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -8012,6 +8081,15 @@ part ; ; +#------------------------------------------------------------ +# ATmega88A +#------------------------------------------------------------ + +part parent "m88" + id = "m88a"; + desc = "ATmega88A"; + ; + #------------------------------------------------------------ # ATmega88P #------------------------------------------------------------ @@ -8020,8 +8098,16 @@ part parent "m88" id = "m88p"; desc = "ATmega88P"; signature = 0x1e 0x93 0x0f; + ; - ocdrev = 1; +#------------------------------------------------------------ +# ATmega88PA +#------------------------------------------------------------ + +part parent "m88" + id = "m88pa"; + desc = "ATmega88PA"; + signature = 0x1e 0x93 0x0f; ; #------------------------------------------------------------ @@ -8032,8 +8118,6 @@ part parent "m88" id = "m88pb"; desc = "ATmega88PB"; signature = 0x1e 0x93 0x16; - - ocdrev = 1; ; #------------------------------------------------------------ @@ -8207,7 +8291,7 @@ part min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -8226,6 +8310,15 @@ part ; ; +#------------------------------------------------------------ +# ATmega168A +#------------------------------------------------------------ + +part parent "m168" + id = "m168a"; + desc = "ATmega168A"; + ; + #------------------------------------------------------------ # ATmega168P #------------------------------------------------------------ @@ -8234,9 +8327,17 @@ part parent "m168" id = "m168p"; desc = "ATmega168P"; signature = 0x1e 0x94 0x0b; + ; - ocdrev = 1; -; +#------------------------------------------------------------ +# ATmega168PA +#------------------------------------------------------------ + +part parent "m168" + id = "m168pa"; + desc = "ATmega168PA"; + signature = 0x1e 0x94 0x0b; + ; #------------------------------------------------------------ # ATmega168PB @@ -8246,50 +8347,48 @@ part parent "m168" id = "m168pb"; desc = "ATmega168PB"; signature = 0x1e 0x94 0x15; - - ocdrev = 1; -; + ; #------------------------------------------------------------ -# ATtiny88 +# ATtiny828 #------------------------------------------------------------ part - id = "t88"; - desc = "ATtiny88"; + id = "t828"; + desc = "ATtiny828"; has_debugwire = yes; flash_instr = 0xB6, 0x01, 0x11; eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x73; -# avr910_devcode = 0x; - signature = 0x1e 0x93 0x11; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, + 0x99, 0xF9, 0xBB, 0xAF; + stk500_devcode = 0x86; + # avr910_devcode = 0x; + signature = 0x1e 0x93 0x14; + pagel = 0xd7; + bs2 = 0xc2; + chip_erase_delay = 15000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; @@ -8306,41 +8405,40 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 1; - memory "eeprom" paged = no; page_size = 4; - size = 64; + size = 256; min_write_delay = 3600; max_write_delay = 3600; readback_p1 = 0xff; readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 x x x x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 x x x x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; +writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 5; + blocksize = 4; + readsize = 256; + ; - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 64; - ; memory "flash" paged = yes; size = 8192; @@ -8350,364 +8448,310 @@ part max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + + ; memory "lfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; memory "hfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; memory "efuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x 1 1 1 i i i i i"; + ; memory "lock" size = 1; min_write_delay = 4500; max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + ; memory "calibration" size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; memory "signature" size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; +; + +#------------------------------------------------------------ +# ATtiny828R +#------------------------------------------------------------ + +part parent "t828" + id = "t828r"; + desc = "ATtiny828R"; ; #------------------------------------------------------------ -# ATmega328 +# ATtiny87 #------------------------------------------------------------ part - id = "m328"; - desc = "ATmega328"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x95 0x14; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "t87"; + desc = "ATtiny87"; + has_debugwire = yes; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, + 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, + 0xBF, 0x99, 0xF9, 0xBB, 0xAF; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x93 0x87; + reset = io; + chip_erase_delay = 15000; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 0; + + pp_controlstack = + 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, + 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, + 0x06, 0x16, 0x46, 0x56, 0x0A, 0x1A, 0x4A, 0x5A, + 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 20; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; programfusepolltimeout = 5; programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 1; + idr = 0x00; + spmcr = 0x57; + allowfullpagebitstream = no; - memory "eeprom" - paged = no; - page_size = 4; - size = 1024; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 512; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 x x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 x x x x x a8", + "a8 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x x", + " 0 0 a5 a4 a3 a2 0 0", + " x x x x x x x x"; - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; + mode = 0x41; + delay = 10; + blocksize = 4; + readsize = 256; + ; + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; + mode = 0x41; + delay = 10; + blocksize = 64; + readsize = 256; + ; +# ATtiny87 has Signature Bytes: 0x1E 0x93 0x87. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x x x x x x x i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; - ; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; -; - -part parent "m328" - id = "m328p"; - desc = "ATmega328P"; - signature = 0x1e 0x95 0x0F; - - ocdrev = 1; -; - -part parent "m328" - id = "m328pb"; - desc = "ATmega328PB"; - signature = 0x1e 0x95 0x16; - - ocdrev = 1; -; - -#------------------------------------------------------------ -# ATmega32m1 -#------------------------------------------------------------ - -part parent "m328" - id = "m32m1"; - desc = "ATmega32M1"; - # stk500_devcode = 0x; - # avr910_devcode = 0x; - signature = 0x1e 0x95 0x84; - bs2 = 0xe2; - - memory "efuse" - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x i i i i i i"; - ; -; - -#------------------------------------------------------------ -# ATmega64m1 -#------------------------------------------------------------ + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; -part parent "m328" - id = "m64m1"; - desc = "ATmega64M1"; - # stk500_devcode = 0x; - # avr910_devcode = 0x; - signature = 0x1e 0x96 0x84; - bs2 = 0xe2; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x i i i i i i"; - ; -; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; + ; #------------------------------------------------------------ -# ATtiny2313 +# ATtiny167 #------------------------------------------------------------ part - id = "t2313"; - desc = "ATtiny2313"; + id = "t167"; + desc = "ATtiny167"; has_debugwire = yes; - flash_instr = 0xB2, 0x0F, 0x1F; - eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x23; -## Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - signature = 0x1e 0x91 0x0a; - pagel = 0xD4; - bs2 = 0xD6; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, + 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, + 0xBF, 0x99, 0xF9, 0xBB, 0xAF; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x94 0x87; reset = io; - chip_erase_delay = 9000; + chip_erase_delay = 15000; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; @@ -8715,27 +8759,27 @@ part chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 0; pp_controlstack = 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x06, 0x16, 0x46, 0x56, 0x0A, 0x1A, 0x4A, 0x5A, + 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; togglevtg = 1; - poweroffdelay = 15; + poweroffdelay = 20; resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; @@ -8746,91 +8790,91 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 0; + idr = 0x00; + spmcr = 0x57; + allowfullpagebitstream = no; memory "eeprom" - size = 128; + size = 512; paged = no; page_size = 4; min_write_delay = 4000; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + read = "1 0 1 0 0 0 0 0 0 0 x x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 x x x x x a8", + "a8 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x x", + " 0 0 a5 a4 a3 a2 0 0", + " x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; + mode = 0x41; + delay = 10; + blocksize = 4; + readsize = 256; ; memory "flash" paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; + size = 16384; + page_size = 128; + num_pages = 128; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; -# The information in the data sheet of April/2004 is wrong, this works: loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", + " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; -# The information in the data sheet of April/2004 is wrong, this works: loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", + " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; -# The information in the data sheet of April/2004 is wrong, this works: - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", " x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; + mode = 0x41; + delay = 10; + blocksize = 64; + readsize = 256; ; -# ATtiny2313 has Signature Bytes: 0x1E 0x91 0x0A. +# ATtiny167 has Signature Bytes: 0x1E 0x94 0x87. memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", "x x x x x x a1 a0 o o o o o o o o"; ; + memory "lock" size = 1; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x x x x x x x i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; ; @@ -8867,59 +8911,54 @@ part min_write_delay = 9000; max_write_delay = 9000; ; -# The Tiny2313 has calibration data for both 4 MHz and 8 MHz. -# The information in the data sheet of April/2004 is wrong, this works: memory "calibration" - size = 2; + size = 1; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 a0 o o o o o o o o"; ; ; #------------------------------------------------------------ -# ATtiny4313 +# ATtiny48 #------------------------------------------------------------ part - id = "t4313"; - desc = "ATtiny4313"; + id = "t48"; + desc = "ATtiny48"; has_debugwire = yes; - flash_instr = 0xB2, 0x0F, 0x1F; - eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x23; -## Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - signature = 0x1e 0x92 0x0d; - pagel = 0xD4; - bs2 = 0xD6; - reset = io; - chip_erase_delay = 9000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, + 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, + 0x99, 0xF9, 0xBB, 0xAF; + stk500_devcode = 0x73; +# avr910_devcode = 0x; + signature = 0x1e 0x92 0x09; + pagel = 0xd7; + bs2 = 0xc2; + chip_erase_delay = 15000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; @@ -8928,6 +8967,7 @@ part resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; + resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; @@ -8935,157 +8975,161 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 0; + ocdrev = 1; - memory "eeprom" - size = 256; + memory "eeprom" paged = no; page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + size = 64; + min_write_delay = 3600; + max_write_delay = 3600; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x x", + " x a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 64; + ; + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; -# ATtiny4313 has Signature Bytes: 0x1E 0x92 0x0D. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + mode = 0x41; + delay = 6; + blocksize = 64; + readsize = 256; + ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x 1 1 1 1 1 1 1 i"; + ; - memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# AT90PWM2 +# ATtiny88 #------------------------------------------------------------ part - id = "pwm2"; - desc = "AT90PWM2"; + id = "t88"; + desc = "ATtiny88"; has_debugwire = yes; flash_instr = 0xB6, 0x01, 0x11; eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x65; -## avr910_devcode = ?; - signature = 0x1e 0x93 0x81; - pagel = 0xD8; - bs2 = 0xE2; - reset = io; - chip_erase_delay = 9000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + stk500_devcode = 0x73; +# avr910_devcode = 0x; + signature = 0x1e 0x93 0x11; + pagel = 0xd7; + bs2 = 0xc2; + chip_erase_delay = 9000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -9099,10 +9143,10 @@ part pollmethod = 1; pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; @@ -9111,6 +9155,7 @@ part resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; + resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; @@ -9118,19 +9163,25 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - memory "eeprom" - size = 512; + ocdrev = 1; + + memory "eeprom" paged = no; page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + size = 64; + min_write_delay = 3600; + max_write_delay = 3600; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", @@ -9139,414 +9190,409 @@ part writepage = " 1 1 0 0 0 0 1 0", " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 6; + delay = 20; blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + readsize = 64; + ; + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; blocksize = 64; readsize = 256; - ; -# AT90PWM2 has Signature Bytes: 0x1E 0x93 0x81. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; -#------------------------------------------------------------ -# AT90PWM3 -#------------------------------------------------------------ + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + ; -# Completely identical to AT90PWM2 (including the signature!) + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; -part parent "pwm2" - id = "pwm3"; - desc = "AT90PWM3"; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# AT90PWM2B +# ATmega328 #------------------------------------------------------------ -# Same as AT90PWM2 but different signature. -part parent "pwm2" - id = "pwm2b"; - desc = "AT90PWM2B"; - signature = 0x1e 0x93 0x83; +part + id = "m328"; + desc = "ATmega328"; + has_debugwire = yes; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, + 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, + 0x99, 0xF9, 0xBB, 0xAF; + stk500_devcode = 0x86; + # avr910_devcode = 0x; + signature = 0x1e 0x95 0x14; + pagel = 0xd7; + bs2 = 0xc2; + chip_erase_delay = 9000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - ocdrev = 1; - ; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; -#------------------------------------------------------------ -# AT90PWM3B -#------------------------------------------------------------ + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; -# Completely identical to AT90PWM2B (including the signature!) - -part parent "pwm2b" - id = "pwm3b"; - desc = "AT90PWM3B"; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; ocdrev = 1; - ; -#------------------------------------------------------------ -# AT90PWM316 -#------------------------------------------------------------ + memory "eeprom" + paged = no; + page_size = 4; + size = 1024; + min_write_delay = 3600; + max_write_delay = 3600; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 x x x a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; -# Similar to AT90PWM3B, but with 16 kiB flash, 512 B EEPROM, and 1024 B SRAM. + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 x x x a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; -part parent "pwm3b" - id = "pwm316"; - desc = "AT90PWM316"; - signature = 0x1e 0x94 0x83; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - ocdrev = 1; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + paged = yes; + size = 32768; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; - mode = 0x21; + mode = 0x41; delay = 6; blocksize = 128; readsize = 256; - ; - ; -#------------------------------------------------------------ -# AT90PWM216 -#------------------------------------------------------------ -# Completely identical to AT90PWM316 (including the signature!) + ; -part parent "pwm316" - id = "pwm216"; - desc = "AT90PWM216"; - ; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; -#------------------------------------------------------------ -# ATtiny25 -#------------------------------------------------------------ + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; -part - id = "t25"; - desc = "ATtiny25"; - has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x91 0x08; - reset = io; - chip_erase_delay = 4500; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x i i i"; + ; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - ocdrev = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + ; - memory "eeprom" - size = 128; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; +; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; +#------------------------------------------------------------ +# ATmega328P +#------------------------------------------------------------ - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; +part parent "m328" + id = "m328p"; + desc = "ATmega328P"; + signature = 0x1e 0x95 0x0f; +; - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; +#------------------------------------------------------------ +# ATmega328PB +#------------------------------------------------------------ - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; +part parent "m328" + id = "m328pb"; + desc = "ATmega328PB"; + signature = 0x1e 0x95 0x16; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x i i i i"; + ; +; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; +#------------------------------------------------------------ +# ATmega32m1 +#------------------------------------------------------------ - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; -# ATtiny25 has Signature Bytes: 0x1E 0x91 0x08. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +part parent "m328" + id = "m32m1"; + desc = "ATmega32M1"; + # stk500_devcode = 0x; + # avr910_devcode = 0x; + signature = 0x1e 0x95 0x84; + bs2 = 0xe2; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "efuse" + size = 1; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x i i i i i i"; + ; +; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +#------------------------------------------------------------ +# ATmega64m1 +#------------------------------------------------------------ - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; +part parent "m328" + id = "m64m1"; + desc = "ATmega64M1"; + # stk500_devcode = 0x; + # avr910_devcode = 0x; + signature = 0x1e 0x96 0x84; + bs2 = 0xe2; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "eeprom" + size = 2048; + page_size = 8; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + memory "flash" + paged = yes; + size = 65536; + page_size = 256; + num_pages = 256; + ; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x i i i i i i"; + ; +; #------------------------------------------------------------ -# ATtiny45 +# ATtiny2313 #------------------------------------------------------------ part - id = "t45"; - desc = "ATtiny45"; + id = "t2313"; + desc = "ATtiny2313"; has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, + flash_instr = 0xB2, 0x0F, 0x1F; + eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x06; + stk500_devcode = 0x23; +## Use the ATtiny26 devcode: + avr910_devcode = 0x5e; + signature = 0x1e 0x91 0x0a; + pagel = 0xD4; + bs2 = 0xD6; reset = io; - chip_erase_delay = 4500; + chip_erase_delay = 9000; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; @@ -9565,41 +9611,41 @@ part postdelay = 1; pollmethod = 1; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; + pp_controlstack = + 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, + 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, + 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, + 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; + latchcycles = 5; togglevtg = 1; - poweroffdelay = 25; + poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; - ocdrev = 1; + ocdrev = 0; memory "eeprom" - size = 256; - page_size = 4; + size = 128; + paged = no; + page_size = 4; min_write_delay = 4000; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", @@ -9608,7 +9654,7 @@ part writepage = " 1 1 0 0 0 0 1 0", " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; @@ -9618,36 +9664,39 @@ part ; memory "flash" paged = yes; - size = 4096; - page_size = 64; + size = 2048; + page_size = 32; num_pages = 64; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", + " 0 0 0 0 0 0 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", + " 0 0 0 0 0 0 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; +# The information in the data sheet of April/2004 is wrong, this works: loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", + " x x x x a3 a2 a1 a0", " i i i i i i i i"; +# The information in the data sheet of April/2004 is wrong, this works: loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", + " x x x x a3 a2 a1 a0", " i i i i i i i i"; +# The information in the data sheet of April/2004 is wrong, this works: writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 x x x x", " x x x x x x x x"; mode = 0x41; @@ -9655,7 +9704,7 @@ part blocksize = 32; readsize = 256; ; -# ATtiny45 has Signature Bytes: 0x1E 0x92 0x08. (Data sheet 2586C-AVR-06/05 (doc2586.pdf) indicates otherwise!) +# ATtiny2313 has Signature Bytes: 0x1E 0x91 0x0A. memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", @@ -9665,8 +9714,8 @@ part size = 1; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; ; @@ -9703,34 +9752,45 @@ part min_write_delay = 9000; max_write_delay = 9000; ; +# The Tiny2313 has calibration data for both 4 MHz and 8 MHz. +# The information in the data sheet of April/2004 is wrong, this works: memory "calibration" - size = 1; + size = 2; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 a0 o o o o o o o o"; ; ; #------------------------------------------------------------ -# ATtiny85 +# ATtiny2313A +#------------------------------------------------------------ + +part parent "t2313" + id = "t2313a"; + desc = "ATtiny2313A"; + ; + +#------------------------------------------------------------ +# ATtiny4313 #------------------------------------------------------------ part - id = "t85"; - desc = "ATtiny85"; + id = "t4313"; + desc = "ATtiny4313"; has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, + flash_instr = 0xB2, 0x0F, 0x1F; + eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x93 0x0b; + stk500_devcode = 0x23; +## Use the ATtiny26 devcode: + avr910_devcode = 0x5e; + signature = 0x1e 0x92 0x0d; + pagel = 0xD4; + bs2 = 0xD6; reset = io; - chip_erase_delay = 400000; + chip_erase_delay = 9000; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; @@ -9749,40 +9809,40 @@ part postdelay = 1; pollmethod = 1; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; + pp_controlstack = + 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, + 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, + 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, + 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; + progmodedelay = 0; + latchcycles = 5; togglevtg = 1; - poweroffdelay = 25; + poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; - ocdrev = 1; + ocdrev = 0; memory "eeprom" - size = 512; + size = 256; paged = no; page_size = 4; min_write_delay = 4000; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", @@ -9791,31 +9851,31 @@ part " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", + " 0 0 x x x x x x", " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 12; + delay = 6; blocksize = 4; readsize = 256; ; memory "flash" paged = yes; - size = 8192; + size = 4096; page_size = 64; - num_pages = 128; - min_write_delay = 30000; - max_write_delay = 30000; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " 0 0 0 0 0 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " 0 0 0 0 0 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; @@ -9829,17 +9889,17 @@ part " x x x a4 a3 a2 a1 a0", " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; blocksize = 32; readsize = 256; ; -# ATtiny85 has Signature Bytes: 0x1E 0x93 0x08. +# ATtiny4313 has Signature Bytes: 0x1E 0x92 0x0D. memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", @@ -9849,8 +9909,8 @@ part size = 1; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; ; @@ -9889,33 +9949,37 @@ part ; memory "calibration" - size = 1; + size = 2; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 a0 o o o o o o o o"; ; ; #------------------------------------------------------------ -# ATmega640 +# AT90PWM2 #------------------------------------------------------------ -# Almost same as ATmega1280, except for different memory sizes part - id = "m640"; - desc = "ATmega640"; - signature = 0x1e 0x96 0x08; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "pwm2"; + desc = "AT90PWM2"; + has_debugwire = yes; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, + 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, + 0x99, 0xF9, 0xBB, 0xAF; + stk500_devcode = 0x65; +## avr910_devcode = ?; + signature = 0x1e 0x93 0x81; + pagel = 0xD8; + bs2 = 0xE2; + reset = io; + chip_erase_delay = 9000; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -9948,367 +10012,258 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 512; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", + " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", + " 0 0 x x x x x x", + " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 8; + delay = 6; + blocksize = 4; readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 256; + delay = 6; + blocksize = 64; readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + ; +# AT90PWM2 has Signature Bytes: 0x1E 0x93 0x81. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 x x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# ATmega1280 +# AT90PWM3 #------------------------------------------------------------ -part - id = "m1280"; - desc = "ATmega1280"; - signature = 0x1e 0x97 0x03; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; +# Completely identical to AT90PWM2 (including the signature!) - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; +part parent "pwm2" + id = "pwm3"; + desc = "AT90PWM3"; + ; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; +#------------------------------------------------------------ +# AT90PWM2B +#------------------------------------------------------------ +# Same as AT90PWM2 but different signature. - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; +part parent "pwm2" + id = "pwm2b"; + desc = "AT90PWM2B"; + signature = 0x1e 0x93 0x83; - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; + ocdrev = 1; + ; - ocdrev = 3; +#------------------------------------------------------------ +# AT90PWM3B +#------------------------------------------------------------ - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; +# Completely identical to AT90PWM2B (including the signature!) - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; +part parent "pwm2b" + id = "pwm3b"; + desc = "AT90PWM3B"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; + ocdrev = 1; + ; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; +#------------------------------------------------------------ +# AT90PWM316 +#------------------------------------------------------------ - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; +# Similar to AT90PWM3B, but with 16 kiB flash, 512 B EEPROM, and 1024 B SRAM. + +part parent "pwm3b" + id = "pwm316"; + desc = "AT90PWM316"; + signature = 0x1e 0x94 0x83; + + ocdrev = 1; memory "flash" paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; + size = 16384; + page_size = 128; + num_pages = 128; min_write_delay = 4500; max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; + readback_p1 = 0xff; + readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", + " 0 0 x x x x x x", + " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", + " 0 0 x x x x x x", + " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", + " 0 0 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", " x x x x x x x x"; - mode = 0x41; - delay = 10; - blocksize = 256; + mode = 0x21; + delay = 6; + blocksize = 128; readsize = 256; ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; ; #------------------------------------------------------------ -# ATmega1281 +# AT90PWM216 #------------------------------------------------------------ -# Identical to ATmega1280 - -part parent "m1280" - id = "m1281"; - desc = "ATmega1281"; - signature = 0x1e 0x97 0x04; +# Completely identical to AT90PWM316 (including the signature!) - ocdrev = 3; +part parent "pwm316" + id = "pwm216"; + desc = "AT90PWM216"; ; #------------------------------------------------------------ -# ATmega2560 +# ATtiny25 #------------------------------------------------------------ part - id = "m2560"; - desc = "ATmega2560"; - signature = 0x1e 0x98 0x01; - has_jtag = yes; - stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "t25"; + desc = "ATtiny25"; + has_debugwire = yes; + flash_instr = 0xB4, 0x02, 0x12; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x91 0x08; + reset = io; + chip_erase_delay = 4500; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -10321,435 +10276,353 @@ part postdelay = 1; pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; + hvsp_controlstack = + 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, + 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; + hvspcmdexedelay = 0; + synchcycles = 6; + latchcycles = 1; togglevtg = 1; - poweroffdelay = 15; + poweroffdelay = 25; resetdelayms = 1; resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + chiperasetime = 0; + programfusepolltimeout = 25; + programlockpolltimeout = 25; - ocdrev = 4; + ocdrev = 1; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 128; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", + " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", + " 0 0 x x x x x x", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 8; + delay = 6; + blocksize = 4; readsize = 256; - ; - - memory "flash" - paged = yes; - size = 262144; - page_size = 256; - num_pages = 1024; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x x a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x x a3 a2 a1 a0", + " i i i i i i i i"; - load_ext_addr = " 0 1 0 0 1 1 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 a16", - " 0 0 0 0 0 0 0 0"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 x x x x", + " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 256; + delay = 6; + blocksize = 32; readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + ; +# ATtiny25 has Signature Bytes: 0x1E 0x91 0x08. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; - -#------------------------------------------------------------ -# ATmega2561 -#------------------------------------------------------------ - -part parent "m2560" - id = "m2561"; - desc = "ATmega2561"; - signature = 0x1e 0x98 0x02; - - ocdrev = 4; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; + ; #------------------------------------------------------------ -# ATmega128RFA1 +# ATtiny45 #------------------------------------------------------------ -# Identical to ATmega2561 but half the ROM - -part parent "m2561" - id = "m128rfa1"; - desc = "ATmega128RFA1"; - signature = 0x1e 0xa7 0x01; - chip_erase_delay = 55000; - bs2 = 0xE2; - - ocdrev = 3; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 50000; - max_write_delay = 50000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; +part + id = "t45"; + desc = "ATtiny45"; + has_debugwire = yes; + flash_instr = 0xB4, 0x02, 0x12; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x92 0x06; + reset = io; + chip_erase_delay = 4500; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; - mode = 0x41; - delay = 20; - blocksize = 256; - readsize = 256; - ; - ; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; -#------------------------------------------------------------ -# ATmega256RFR2 -#------------------------------------------------------------ + hvsp_controlstack = + 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, + 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + hvspcmdexedelay = 0; + synchcycles = 6; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + chiperasetime = 0; + programfusepolltimeout = 25; + programlockpolltimeout = 25; -part parent "m2561" - id = "m256rfr2"; - desc = "ATmega256RFR2"; - signature = 0x1e 0xa8 0x02; - chip_erase_delay = 18500; - bs2 = 0xE2; + ocdrev = 1; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 8192; - min_write_delay = 13000; - max_write_delay = 13000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", + " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", + " 0 0 x x x x x x", + " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 8; + delay = 6; + blocksize = 4; readsize = 256; - ; + ; + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - ocdrev = 4; - ; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; -#------------------------------------------------------------ -# ATmega128RFR2 -#------------------------------------------------------------ + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; -part parent "m128rfa1" - id = "m128rfr2"; - desc = "ATmega128RFR2"; - signature = 0x1e 0xa7 0x02; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; + mode = 0x41; + delay = 6; + blocksize = 32; + readsize = 256; + ; +# ATtiny45 has Signature Bytes: 0x1E 0x92 0x08. (Data sheet 2586C-AVR-06/05 (doc2586.pdf) indicates otherwise!) + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; - ocdrev = 3; - ; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; -#------------------------------------------------------------ -# ATmega64RFR2 -#------------------------------------------------------------ + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; -part parent "m128rfa1" - id = "m64rfr2"; - desc = "ATmega64RFR2"; - signature = 0x1e 0xa6 0x02; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; - ocdrev = 3; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 50000; - max_write_delay = 50000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 256; - readsize = 256; - ; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 13000; - max_write_delay = 13000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - - ; - -#------------------------------------------------------------ -# ATmega2564RFR2 -#------------------------------------------------------------ - -part parent "m256rfr2" - id = "m2564rfr2"; - desc = "ATmega2564RFR2"; - signature = 0x1e 0xa8 0x03; - ; - -#------------------------------------------------------------ -# ATmega1284RFR2 -#------------------------------------------------------------ - -part parent "m128rfr2" - id = "m1284rfr2"; - desc = "ATmega1284RFR2"; - signature = 0x1e 0xa7 0x03; - ; - -#------------------------------------------------------------ -# ATmega644RFR2 -#------------------------------------------------------------ + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; -part parent "m64rfr2" - id = "m644rfr2"; - desc = "ATmega644RFR2"; - signature = 0x1e 0xa6 0x03; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# ATtiny24 +# ATtiny85 #------------------------------------------------------------ part - id = "t24"; - desc = "ATtiny24"; + id = "t85"; + desc = "ATtiny85"; has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; + flash_instr = 0xB4, 0x02, 0x12; eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, + 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, 0x99, 0xE1, 0xBB, 0xAC; ## no STK500 devcode in XML file, use the ATtiny45 one stk500_devcode = 0x14; ## avr910_devcode = ?; ## Try the AT90S2313 devcode: avr910_devcode = 0x20; - signature = 0x1e 0x91 0x0b; + signature = 0x1e 0x93 0x0b; reset = io; chip_erase_delay = 4500; @@ -10774,15 +10647,15 @@ part 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; hventerstabdelay = 100; hvspcmdexedelay = 0; synchcycles = 6; latchcycles = 1; togglevtg = 1; poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; + resetdelayms = 1; + resetdelayus = 0; hvleavestabdelay = 100; resetdelay = 25; chiperasepolltimeout = 40; @@ -10793,18 +10666,18 @@ part ocdrev = 1; memory "eeprom" - size = 128; + size = 512; paged = no; page_size = 4; min_write_delay = 4000; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", @@ -10812,8 +10685,8 @@ part " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", + " 0 0 x x x x x a8", + " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; @@ -10823,36 +10696,36 @@ part ; memory "flash" paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; + size = 8192; + page_size = 64; + num_pages = 128; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", + " 0 0 0 0 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", + " 0 0 0 0 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", + " x x x a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", + " x x x a4 a3 a2 a1 a0", " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", " x x x x x x x x"; mode = 0x41; @@ -10860,7 +10733,7 @@ part blocksize = 32; readsize = 256; ; -# ATtiny24 has Signature Bytes: 0x1E 0x91 0x0B. +# ATtiny85 has Signature Bytes: 0x1E 0x93 0x08. memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", @@ -10869,7 +10742,7 @@ part memory "lock" size = 1; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; + "x x x x x x x x 1 1 i i i i i i"; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; @@ -10917,31 +10790,26 @@ part ; #------------------------------------------------------------ -# ATtiny44 +# ATmega640 #------------------------------------------------------------ +# Almost same as ATmega1280, except for different memory sizes part - id = "t44"; - desc = "ATtiny44"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x07; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "m640"; + desc = "ATmega640"; + signature = 0x1e 0x96 0x08; + has_jtag = yes; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xD7; + bs2 = 0xA0; + reset = dedicated; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -10954,178 +10822,184 @@ part postdelay = 1; pollmethod = 1; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; + progmodedelay = 0; + latchcycles = 5; togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - - ocdrev = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; - memory "eeprom" - size = 256; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + idr = 0x31; + spmcr = 0x57; + rampz = 0x3b; + allowfullpagebitstream = no; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + ocdrev = 3; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 8; /* for parallel programming */ + size = 4096; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", + " 0 0 0 0 0 a2 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", + " 0 0 x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", " x x x x x x x x"; mode = 0x41; - delay = 6; - blocksize = 4; + delay = 10; + blocksize = 8; readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "flash" + paged = yes; + size = 65536; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", + " x x x x x x x x"; mode = 0x41; - delay = 6; - blocksize = 32; + delay = 10; + blocksize = 256; readsize = 256; - ; -# ATtiny44 has Signature Bytes: 0x1E 0x92 0x07. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 x x x x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 x x x x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# ATtiny84 +# ATmega1280 #------------------------------------------------------------ part - id = "t84"; - desc = "ATtiny84"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x93 0x0c; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "m1280"; + desc = "ATmega1280"; + signature = 0x1e 0x97 0x03; + has_jtag = yes; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xD7; + bs2 = 0xA0; + reset = dedicated; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -11138,424 +11012,325 @@ part postdelay = 1; pollmethod = 1; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; + progmodedelay = 0; + latchcycles = 5; togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; - ocdrev = 1; + idr = 0x31; + spmcr = 0x57; + rampz = 0x3b; + allowfullpagebitstream = no; - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; + ocdrev = 3; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 8; /* for parallel programming */ + size = 4096; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", + " 0 0 0 0 0 a2 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", + " 0 0 x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", " x x x x x x x x"; mode = 0x41; - delay = 6; - blocksize = 4; + delay = 10; + blocksize = 8; readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "flash" + paged = yes; + size = 131072; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", + " x x x x x x x x"; mode = 0x41; - delay = 6; - blocksize = 32; + delay = 10; + blocksize = 256; readsize = 256; - ; -# ATtiny84 has Signature Bytes: 0x1E 0x93 0x0C. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 x x x x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 x x x x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# ATtiny441 +# ATmega1281 #------------------------------------------------------------ +# Identical to ATmega1280 -part parent "t44" - id = "t441"; - desc = "ATtiny441"; - signature = 0x1e 0x92 0x15; - - memory "flash" - paged = yes; - size = 4096; - page_size = 16; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; +part parent "m1280" + id = "m1281"; + desc = "ATmega1281"; + signature = 0x1e 0x97 0x04; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ocdrev = 3; + ; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; +#------------------------------------------------------------ +# ATmega2560 +#------------------------------------------------------------ - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; +part + id = "m2560"; + desc = "ATmega2560"; + signature = 0x1e 0x98 0x01; + has_jtag = yes; + stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xD7; + bs2 = 0xA0; + reset = dedicated; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 x x x", - " x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "x x x x x x x x x x x x x x x x"; - mode = 0x41; - delay = 6; - blocksize = 16; - readsize = 256; - ; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; -; - -#------------------------------------------------------------ -# ATtiny841 -#------------------------------------------------------------ - -part parent "t84" - id = "t841"; - desc = "ATtiny841"; - signature = 0x1e 0x93 0x15; - - memory "flash" - paged = yes; - size = 8192; - page_size = 16; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 16; - readsize = 256; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; -; - -#------------------------------------------------------------ -# ATtiny43U -#------------------------------------------------------------ - -part - id = "t43u"; - desc = "ATtiny43u"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x0C; - reset = io; - chip_erase_delay = 1000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, 0x4E, 0x5E, - 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, 0x06, 0x16, 0x46, 0x56, - 0x0A, 0x1A, 0x4A, 0x5A, 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, - 0x00, 0x00; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; hventerstabdelay = 100; progmodedelay = 0; - hvspcmdexedelay = 0; latchcycles = 5; togglevtg = 1; - poweroffdelay = 20; + poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; - resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; programfusepolltimeout = 5; programlockpulsewidth = 0; programlockpolltimeout = 5; + + idr = 0x31; + spmcr = 0x57; + rampz = 0x3b; + allowfullpagebitstream = no; + + ocdrev = 4; + memory "eeprom" - size = 64; - paged = yes; - page_size = 4; - num_pages = 16; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "0 0 a4 a3 a2 a1 a0 o o o o o o o o"; + paged = no; /* leave this "no" */ + page_size = 8; /* for parallel programming */ + size = 4096; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "0 0 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + write = " 1 1 0 0 0 0 0 0", + " x x x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 a2 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " 0 0 a5 a4 a3 a2 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x a11 a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 8; + readsize = 256; + ; - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; memory "flash" paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; + size = 262144; + page_size = 256; + num_pages = 1024; min_write_delay = 4500; max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", + " x x x x x x x x"; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; + load_ext_addr = " 0 1 0 0 1 1 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 0 a16", + " 0 0 0 0 0 0 0 0"; - mode = 0x41; - delay = 10; - blocksize = 64; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "lfuse" + mode = 0x41; + delay = 10; + blocksize = 256; + readsize = 256; + ; + + memory "lfuse" size = 1; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", "x x x x x x x x i i i i i i i i"; read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + min_write_delay = 9000; + max_write_delay = 9000; + ; memory "hfuse" size = 1; @@ -11564,103 +11339,138 @@ part read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + min_write_delay = 9000; + max_write_delay = 9000; + ; memory "efuse" size = 1; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + "x x x x x x x x x x x x x i i i"; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; -; + size = 1; + read = "0 0 1 1 1 0 0 0 x x x x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 x x x x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; #------------------------------------------------------------ -# ATmega32u4 +# ATmega2561 #------------------------------------------------------------ -part - id = "m32u4"; - desc = "ATmega32U4"; - signature = 0x1e 0x95 0x87; - usbpid = 0x2ff4; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; +part parent "m2560" + id = "m2561"; + desc = "ATmega2561"; + signature = 0x1e 0x98 0x02; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + ocdrev = 4; + ; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; +#------------------------------------------------------------ +# ATmega128RFA1 +#------------------------------------------------------------ +# Identical to ATmega2561 but half the ROM - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; +part parent "m2561" + id = "m128rfa1"; + desc = "ATmega128RFA1"; + signature = 0x1e 0xa7 0x01; + chip_erase_delay = 55000; + bs2 = 0xE2; ocdrev = 3; + memory "flash" + paged = yes; + size = 131072; + page_size = 256; + num_pages = 512; + min_write_delay = 50000; + max_write_delay = 50000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 256; + readsize = 256; + ; + ; + +#------------------------------------------------------------ +# ATmega256RFR2 +#------------------------------------------------------------ + +part parent "m2561" + id = "m256rfr2"; + desc = "ATmega256RFR2"; + signature = 0x1e 0xa8 0x02; + chip_erase_delay = 18500; + bs2 = 0xE2; + memory "eeprom" paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; + page_size = 8; /* for parallel programming */ + size = 8192; + min_write_delay = 13000; + max_write_delay = 13000; readback_p1 = 0x00; readback_p2 = 0x00; read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", + " x x x a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", + " x x x a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; @@ -11670,23 +11480,52 @@ part " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", + " 0 0 x a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 0 0 0", " x x x x x x x x"; mode = 0x41; - delay = 20; - blocksize = 4; + delay = 10; + blocksize = 8; readsize = 256; ; + + ocdrev = 4; + ; + +#------------------------------------------------------------ +# ATmega128RFR2 +#------------------------------------------------------------ + +part parent "m128rfa1" + id = "m128rfr2"; + desc = "ATmega128RFR2"; + signature = 0x1e 0xa7 0x02; + + + ocdrev = 3; + ; + +#------------------------------------------------------------ +# ATmega64RFR2 +#------------------------------------------------------------ + +part parent "m128rfa1" + id = "m64rfr2"; + desc = "ATmega64RFR2"; + signature = 0x1e 0xa6 0x02; + + + ocdrev = 3; + memory "flash" paged = yes; - size = 32768; - page_size = 128; + size = 65536; + page_size = 256; num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; + min_write_delay = 50000; + max_write_delay = 50000; readback_p1 = 0x00; readback_p2 = 0x00; read_lo = " 0 0 1 0 0 0 0 0", @@ -11701,148 +11540,31 @@ part loadpage_lo = " 0 1 0 0 0 0 0 0", " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", + " x a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", + " x a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", " x x x x x x x x"; mode = 0x41; - delay = 6; - blocksize = 128; + delay = 20; + blocksize = 256; readsize = 256; ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; - -#------------------------------------------------------------ -# AT90USB646 -#------------------------------------------------------------ - -part - id = "usb646"; - desc = "AT90USB646"; - signature = 0x1e 0x96 0x82; - usbpid = 0x2ff9; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - memory "eeprom" paged = no; /* leave this "no" */ page_size = 8; /* for parallel programming */ size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; + min_write_delay = 13000; + max_write_delay = 13000; readback_p1 = 0x00; readback_p2 = 0x00; read = " 1 0 1 0 0 0 0 0", @@ -11871,137 +11593,65 @@ part readsize = 256; ; - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; +#------------------------------------------------------------ +# ATmega2564RFR2 +#------------------------------------------------------------ - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +part parent "m256rfr2" + id = "m2564rfr2"; + desc = "ATmega2564RFR2"; + signature = 0x1e 0xa8 0x03; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; +#------------------------------------------------------------ +# ATmega1284RFR2 +#------------------------------------------------------------ - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; +part parent "m128rfr2" + id = "m1284rfr2"; + desc = "ATmega1284RFR2"; + signature = 0x1e 0xa7 0x03; ; #------------------------------------------------------------ -# AT90USB647 +# ATmega644RFR2 #------------------------------------------------------------ -# identical to AT90USB646 - -part parent "usb646" - id = "usb647"; - desc = "AT90USB647"; - signature = 0x1e 0x96 0x82; - ocdrev = 3; +part parent "m64rfr2" + id = "m644rfr2"; + desc = "ATmega644RFR2"; + signature = 0x1e 0xa6 0x03; ; #------------------------------------------------------------ -# AT90USB1286 +# ATtiny24 #------------------------------------------------------------ part - id = "usb1286"; - desc = "AT90USB1286"; - signature = 0x1e 0x97 0x82; - usbpid = 0x2ffb; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + id = "t24"; + desc = "ATtiny24"; + has_debugwire = yes; + flash_instr = 0xB4, 0x07, 0x17; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x91 0x0b; + reset = io; + chip_erase_delay = 4500; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -12014,198 +11664,189 @@ part postdelay = 1; pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hvsp_controlstack = + 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, + 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; + hvspcmdexedelay = 0; + synchcycles = 6; + latchcycles = 1; togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; + poweroffdelay = 25; + resetdelayms = 0; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + chiperasetime = 0; + programfusepolltimeout = 25; + programlockpolltimeout = 25; - ocdrev = 3; + ocdrev = 1; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 128; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", + " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", + " 0 0 x x x x x x", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 10; - blocksize = 8; + delay = 6; + blocksize = 4; readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x x a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x x a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 x x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; - blocksize = 256; + blocksize = 32; readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + ; +# ATtiny24 has Signature Bytes: 0x1E 0x91 0x0B. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x x x x x x x i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# AT90USB1287 +# ATtiny24A #------------------------------------------------------------ -# identical to AT90USB1286 -part parent "usb1286" - id = "usb1287"; - desc = "AT90USB1287"; - signature = 0x1e 0x97 0x82; - - ocdrev = 3; +part parent "t24" + id = "t24a"; + desc = "ATtiny24A"; ; #------------------------------------------------------------ -# AT90USB162 +# ATtiny44 #------------------------------------------------------------ part - id = "usb162"; - desc = "AT90USB162"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x94 0x82; - usbpid = 0x2ffa; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; + id = "t44"; + desc = "ATtiny44"; + has_debugwire = yes; + flash_instr = 0xB4, 0x07, 0x17; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x92 0x07; + reset = io; + chip_erase_delay = 4500; + + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + + timeout = 200; stabdelay = 100; cmdexedelay = 25; synchloops = 32; @@ -12215,46 +11856,42 @@ part predelay = 1; postdelay = 1; pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + + hvsp_controlstack = + 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, + 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; + hvspcmdexedelay = 0; + synchcycles = 6; + latchcycles = 1; togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; + poweroffdelay = 25; + resetdelayms = 0; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + chiperasetime = 0; + programfusepolltimeout = 25; + programlockpolltimeout = 25; ocdrev = 1; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 256; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", @@ -12262,135 +11899,145 @@ part " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", + " 0 0 x x x x x x", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 20; + delay = 6; blocksize = 4; readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; - blocksize = 128; + blocksize = 32; readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + ; +# ATtiny44 has Signature Bytes: 0x1E 0x92 0x07. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x x x x x x x i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# AT90USB82 +# ATtiny44A +#------------------------------------------------------------ + +part parent "t44" + id = "t44a"; + desc = "ATtiny44A"; + ; + +#------------------------------------------------------------ +# ATtiny84 #------------------------------------------------------------ -# Changes against AT90USB162 (beside IDs) -# memory "flash" -# size = 8192; -# num_pages = 64; part - id = "usb82"; - desc = "AT90USB82"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x93 0x82; - usbpid = 0x2ff7; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; + id = "t84"; + desc = "ATtiny84"; + has_debugwire = yes; + flash_instr = 0xB4, 0x07, 0x17; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; +## no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x93 0x0c; + reset = io; + chip_erase_delay = 4500; + + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -12402,46 +12049,42 @@ part predelay = 1; postdelay = 1; pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + + hvsp_controlstack = + 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, + 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; + hvspcmdexedelay = 0; + synchcycles = 6; + latchcycles = 1; togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; + poweroffdelay = 25; + resetdelayms = 0; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + chiperasetime = 0; + programfusepolltimeout = 25; + programlockpolltimeout = 25; ocdrev = 1; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "eeprom" + size = 512; + paged = no; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", + "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", @@ -12449,325 +12092,442 @@ part " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", + " 0 0 x x x x x x", + " x a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; - delay = 20; + delay = 6; blocksize = 4; readsize = 256; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + ; + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; - blocksize = 128; + blocksize = 32; readsize = 256; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + ; +# ATtiny84 has Signature Bytes: 0x1E 0x93 0x0C. + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x x x x x x x i i"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; ; #------------------------------------------------------------ -# ATmega32U2 +# ATtiny84A #------------------------------------------------------------ -# Changes against AT90USB162 (beside IDs) -# memory "flash" -# size = 32768; -# num_pages = 256; -# memory "eeprom" -# size = 1024; -# num_pages = 256; -part - id = "m32u2"; - desc = "ATmega32U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x95 0x8a; - usbpid = 0x2ff0; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - num_pages = 256; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; +part parent "t84" + id = "t84a"; + desc = "ATtiny84A"; + ; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; +#------------------------------------------------------------ +# ATtiny441 +#------------------------------------------------------------ - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; +part parent "t44" + id = "t441"; + desc = "ATtiny441"; + signature = 0x1e 0x92 0x15; - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "flash" + paged = yes; + size = 4096; + page_size = 16; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x x x a2 a1 a0", + " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x x x a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 x x x", + " x x x x x x x x"; mode = 0x41; delay = 6; - blocksize = 128; + blocksize = 16; readsize = 256; - ; + ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; +; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; +#------------------------------------------------------------ +# ATtiny841 +#------------------------------------------------------------ - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +part parent "t84" + id = "t841"; + desc = "ATtiny841"; + signature = 0x1e 0x93 0x15; - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + memory "flash" + paged = yes; + size = 8192; + page_size = 16; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x x x a2 a1 a0", + " i i i i i i i i"; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x x x a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 16; + readsize = 256; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; min_write_delay = 9000; max_write_delay = 9000; - ; + ; +; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; #------------------------------------------------------------ -# ATmega16U2 +# ATtiny43U #------------------------------------------------------------ -# Changes against ATmega32U2 (beside IDs) -# memory "flash" -# size = 16384; -# num_pages = 128; -# memory "eeprom" -# size = 512; -# num_pages = 128; + part - id = "m16u2"; - desc = "ATmega16U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x94 0x89; - usbpid = 0x2fef; - chip_erase_delay = 9000; + id = "t43u"; + desc = "ATtiny43U"; + has_debugwire = yes; + flash_instr = 0xB4, 0x07, 0x17; + eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, + 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, + 0x99, 0xE1, 0xBB, 0xAC; + stk500_devcode = 0x14; +## avr910_devcode = ?; +## Try the AT90S2313 devcode: + avr910_devcode = 0x20; + signature = 0x1e 0x92 0x0C; reset = io; + chip_erase_delay = 1000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; + "x x x x x x x x x x x x x x x x"; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, 0x4E, 0x5E, + 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, 0x06, 0x16, 0x46, 0x56, + 0x0A, 0x1A, 0x4A, 0x5A, 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, + 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + hvspcmdexedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 20; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + memory "eeprom" + size = 64; + paged = yes; + page_size = 4; + num_pages = 16; + min_write_delay = 4000; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", + "0 0 a4 a3 a2 a1 a0 o o o o o o o o"; + + write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", + "0 0 a5 a4 a3 a2 a1 a0 i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x x", + " 0 0 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 5; + blocksize = 4; + readsize = 256; + ; + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x x a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 64; + readsize = 256; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + memory "lock" + size = 1; + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 4500; + max_write_delay = 4500; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 4500; + max_write_delay = 4500; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 4500; + max_write_delay = 4500; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x x x x i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 4500; + max_write_delay = 4500; + ; + + memory "calibration" + size = 2; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 a0 o o o o o o o o"; + ; +; + +#------------------------------------------------------------ +# ATmega32u4 +#------------------------------------------------------------ + +part + id = "m32u4"; + desc = "ATmega32U4"; + signature = 0x1e 0x95 0x87; + usbpid = 0x2ff4; + has_jtag = yes; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; pagel = 0xD7; - bs2 = 0xC6; + bs2 = 0xA0; + reset = dedicated; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; @@ -12779,6 +12539,7 @@ part predelay = 1; postdelay = 1; pollmethod = 1; + pp_controlstack = 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, @@ -12799,35 +12560,39 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 1; + idr = 0x31; + spmcr = 0x57; + rampz = 0x3b; + allowfullpagebitstream = no; + + ocdrev = 3; memory "eeprom" paged = no; /* leave this "no" */ page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; + size = 1024; min_write_delay = 9000; max_write_delay = 9000; readback_p1 = 0x00; readback_p2 = 0x00; read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " x x x x x a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " x x x x x a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", + " 0 0 0 0 0 a2 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", + " 0 0 x x x a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", " x x x x x x x x"; mode = 0x41; @@ -12838,20 +12603,20 @@ part memory "flash" paged = yes; - size = 16384; + size = 32768; page_size = 128; - num_pages = 128; + num_pages = 256; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0x00; readback_p2 = 0x00; read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; @@ -12866,7 +12631,7 @@ part " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " a15 a14 a13 a12 a11 a10 a9 a8", " a7 a6 x x x x x x", " x x x x x x x x"; @@ -12901,7 +12666,7 @@ part memory "efuse" size = 1; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + "x x x x x x x x x x x x i i i i"; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; @@ -12912,7 +12677,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -12922,40 +12687,38 @@ part memory "calibration" size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; + memory "signature" size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + read = "0 0 1 1 0 0 0 0 x x x x x x x x", "x x x x x x a1 a0 o o o o o o o o"; ; ; #------------------------------------------------------------ -# ATmega8U2 +# AT90USB646 #------------------------------------------------------------ -# Changes against ATmega16U2 (beside IDs) -# memory "flash" -# size = 8192; -# page_size = 64; -# blocksize = 64; part - id = "m8u2"; - desc = "ATmega8U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x93 0x89; - usbpid = 0x2fee; - chip_erase_delay = 9000; - reset = io; + id = "usb646"; + desc = "AT90USB646"; + signature = 0x1e 0x96 0x82; + usbpid = 0x2ff9; + has_jtag = yes; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xD7; + bs2 = 0xA0; + reset = dedicated; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; timeout = 200; stabdelay = 100; @@ -12967,6 +12730,7 @@ part predelay = 1; postdelay = 1; pollmethod = 1; + pp_controlstack = 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, @@ -12987,80 +12751,84 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - ocdrev = 1; + idr = 0x31; + spmcr = 0x57; + rampz = 0x3b; + allowfullpagebitstream = no; + + ocdrev = 3; memory "eeprom" paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; + page_size = 8; /* for parallel programming */ + size = 2048; min_write_delay = 9000; max_write_delay = 9000; readback_p1 = 0x00; readback_p2 = 0x00; read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " x x x x x a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", + " x x x x x a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", + " 0 0 0 0 0 a2 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", + " 0 0 x x x a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", " x x x x x x x x"; mode = 0x41; - delay = 20; - blocksize = 4; + delay = 10; + blocksize = 8; readsize = 256; ; memory "flash" paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; + size = 65536; + page_size = 256; + num_pages = 256; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0x00; readback_p2 = 0x00; read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", + " 0 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", + " x a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", + " x a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", " x x x x x x x x"; mode = 0x41; delay = 6; - blocksize = 128; + blocksize = 256; readsize = 256; ; @@ -13089,7 +12857,7 @@ part memory "efuse" size = 1; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; + "x x x x x x x x x x x x i i i i"; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; @@ -13100,7 +12868,7 @@ part memory "lock" size = 1; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; @@ -13110,46 +12878,62 @@ part memory "calibration" size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + read = "0 0 1 1 1 0 0 0 x x x x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; + memory "signature" size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + read = "0 0 1 1 0 0 0 0 x x x x x x x x", "x x x x x x a1 a0 o o o o o o o o"; ; ; + #------------------------------------------------------------ -# ATmega325 +# AT90USB647 +#------------------------------------------------------------ +# identical to AT90USB646 + +part parent "usb646" + id = "usb647"; + desc = "AT90USB647"; + signature = 0x1e 0x96 0x82; + + ocdrev = 3; + ; + +#------------------------------------------------------------ +# AT90USB1286 #------------------------------------------------------------ part - id = "m325"; - desc = "ATmega325"; - signature = 0x1e 0x95 0x05; + id = "usb1286"; + desc = "AT90USB1286"; + signature = 0x1e 0x97 0x82; + usbpid = 0x2ffb; has_jtag = yes; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - pagel = 0xd7; - bs2 = 0xa0; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; chip_erase_delay = 9000; + pagel = 0xD7; + bs2 = 0xA0; + reset = dedicated; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + "x x x x x x x x x x x x x x x x"; chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; pp_controlstack = 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, @@ -13173,188 +12957,3043 @@ part idr = 0x31; spmcr = 0x57; + rampz = 0x3b; allowfullpagebitstream = no; ocdrev = 3; memory "eeprom" paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; + page_size = 8; /* for parallel programming */ + size = 4096; min_write_delay = 9000; max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; + readback_p1 = 0x00; + readback_p2 = 0x00; read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", + " x x x x a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", + " x x x x a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 a2 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", + " x x x x x x x x"; - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; + mode = 0x41; + delay = 10; + blocksize = 8; + readsize = 256; ; memory "flash" paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; + size = 131072; + page_size = 256; + num_pages = 512; min_write_delay = 4500; max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; + readback_p1 = 0x00; + readback_p2 = 0x00; read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", + "a15 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", + "a15 a14 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 x x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 256; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 x x x x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 x x x x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# AT90USB1287 +#------------------------------------------------------------ +# identical to AT90USB1286 + +part parent "usb1286" + id = "usb1287"; + desc = "AT90USB1287"; + signature = 0x1e 0x97 0x82; + + ocdrev = 3; + ; + +#------------------------------------------------------------ +# AT90USB162 +#------------------------------------------------------------ + +part + id = "usb162"; + desc = "AT90USB162"; + has_jtag = no; + has_debugwire = yes; + signature = 0x1e 0x94 0x82; + usbpid = 0x2ffa; + chip_erase_delay = 9000; + reset = io; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + pagel = 0xD7; + bs2 = 0xC6; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + ocdrev = 1; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 512; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 16384; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# AT90USB82 +#------------------------------------------------------------ +# Changes against AT90USB162 (beside IDs) +# memory "flash" +# size = 8192; +# num_pages = 64; + +part + id = "usb82"; + desc = "AT90USB82"; + has_jtag = no; + has_debugwire = yes; + signature = 0x1e 0x93 0x82; + usbpid = 0x2ff7; + chip_erase_delay = 9000; + reset = io; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + pagel = 0xD7; + bs2 = 0xC6; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + ocdrev = 1; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 512; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega32U2 +#------------------------------------------------------------ +# Changes against AT90USB162 (beside IDs) +# memory "flash" +# size = 32768; +# num_pages = 256; +# memory "eeprom" +# size = 1024; +# num_pages = 256; +part + id = "m32u2"; + desc = "ATmega32U2"; + has_jtag = no; + has_debugwire = yes; + signature = 0x1e 0x95 0x8a; + usbpid = 0x2ff0; + chip_erase_delay = 9000; + reset = io; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + pagel = 0xD7; + bs2 = 0xC6; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + ocdrev = 1; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 1024; + num_pages = 256; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 32768; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; +#------------------------------------------------------------ +# ATmega16U2 +#------------------------------------------------------------ +# Changes against ATmega32U2 (beside IDs) +# memory "flash" +# size = 16384; +# num_pages = 128; +# memory "eeprom" +# size = 512; +# num_pages = 128; +part + id = "m16u2"; + desc = "ATmega16U2"; + has_jtag = no; + has_debugwire = yes; + signature = 0x1e 0x94 0x89; + usbpid = 0x2fef; + chip_erase_delay = 9000; + reset = io; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + pagel = 0xD7; + bs2 = 0xC6; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + ocdrev = 1; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 512; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 16384; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega8U2 +#------------------------------------------------------------ +# Changes against ATmega16U2 (beside IDs) +# memory "flash" +# size = 8192; +# page_size = 64; +# blocksize = 64; + +part + id = "m8u2"; + desc = "ATmega8U2"; + has_jtag = no; + has_debugwire = yes; + signature = 0x1e 0x93 0x89; + usbpid = 0x2fee; + chip_erase_delay = 9000; + reset = io; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + pagel = 0xD7; + bs2 = 0xC6; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + ocdrev = 1; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 512; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " x x x x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + "a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x i i i i i i i i"; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega165 +#------------------------------------------------------------ + +part + id = "m165"; + desc = "ATmega165"; + signature = 0x1e 0x94 0x07; + has_jtag = yes; +# stk500_devcode = 0x??; +# avr910_devcode = 0x??; + chip_erase_delay = 9000; + reset = io; + pagel = 0xd7; + bs2 = 0xa0; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 6; + togglevtg = 0; + poweroffdelay = 0; + resetdelayms = 0; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + resetdelay = 15; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + idr = 0x31; + spmcr = 0x57; + eecr = 0x3f; + allowfullpagebitstream = no; + + ocdrev = 3; + + memory "eeprom" + paged = no; + page_size = 4; + size = 512; + num_pages = 128; + min_write_delay = 3600; + max_write_delay = 3600; + readback_p1 = 0x00; + readback_p2 = 0x00; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 0 0 x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 0 0 x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 0 0 x a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 20; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 16384; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0x00; + readback_p2 = 0x00; + read_lo = " 0 0 1 0 0 0 0 0", + " x x x a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + " x x x a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 0 x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 0 x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " x x x a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 128; + readsize = 256; + ; + + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; + + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x x i i i i"; + ; + + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 i i i i i i"; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x a1 a0 o o o o o o o o"; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega165A +#------------------------------------------------------------ + +part parent "m165" + id = "m165a"; + desc = "ATmega165A"; + signature = 0x1e 0x94 0x10; + ; + +#------------------------------------------------------------ +# ATmega165P +#------------------------------------------------------------ + +part parent "m165" + id = "m165p"; + desc = "ATmega165P"; + signature = 0x1e 0x94 0x07; + ; + +#------------------------------------------------------------ +# ATmega165PA +#------------------------------------------------------------ + +part parent "m165" + id = "m165pa"; + desc = "ATmega165PA"; + signature = 0x1e 0x94 0x07; + ; + +#------------------------------------------------------------ +# ATmega325 +#------------------------------------------------------------ + +part + id = "m325"; + desc = "ATmega325"; + signature = 0x1e 0x95 0x05; + has_jtag = yes; +# stk500_devcode = 0x??; # No STK500v1 support? +# avr910_devcode = 0x??; # Try the ATmega16 one + avr910_devcode = 0x74; + pagel = 0xd7; + bs2 = 0xa0; + chip_erase_delay = 9000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + idr = 0x31; + spmcr = 0x57; + allowfullpagebitstream = no; + + ocdrev = 3; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 4; /* for parallel programming */ + size = 1024; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 0 0 a9 a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 4; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 32768; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 0 0 0 0 0", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 0 0 0 0 0", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " 0 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 128; + readsize = 256; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", + "0 0 0 0 0 0 0 0 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lfuse" + size = 1; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "0 0 0 0 0 0 0 0 i i i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "0 0 0 0 0 0 0 0 i i i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + ; + + memory "calibration" + size = 1; + + read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega325A +#------------------------------------------------------------ + +part parent "m325" + id = "m325a"; + desc = "ATmega325A"; + ; + +#------------------------------------------------------------ +# ATmega325P +#------------------------------------------------------------ + +part parent "m325" + id = "m325p"; + desc = "ATmega325P"; + signature = 0x1e 0x95 0x0d; + ; + +#------------------------------------------------------------ +# ATmega325PA +#------------------------------------------------------------ + +part parent "m325" + id = "m325pa"; + desc = "ATmega325PA"; + signature = 0x1e 0x95 0x0d; + ; + +#------------------------------------------------------------ +# ATmega645 +#------------------------------------------------------------ + +part + id = "m645"; + desc = "ATmega645"; + signature = 0x1E 0x96 0x05; + has_jtag = yes; +# stk500_devcode = 0x??; # No STK500v1 support? +# avr910_devcode = 0x??; # Try the ATmega16 one + avr910_devcode = 0x74; + pagel = 0xd7; + bs2 = 0xa0; + chip_erase_delay = 9000; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + + pp_controlstack = + 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, + 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, + 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, + 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 0; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + resetdelayus = 0; + hvleavestabdelay = 15; + chiperasepulsewidth = 0; + chiperasepolltimeout = 10; + programfusepulsewidth = 0; + programfusepolltimeout = 5; + programlockpulsewidth = 0; + programlockpolltimeout = 5; + + idr = 0x31; + spmcr = 0x57; + allowfullpagebitstream = no; + + ocdrev = 3; + + memory "eeprom" + paged = no; /* leave this "no" */ + page_size = 8; /* for parallel programming */ + size = 2048; + min_write_delay = 9000; + max_write_delay = 9000; + readback_p1 = 0xff; + readback_p2 = 0xff; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 0 0 0 a10 a9 a8", + " a7 a6 a5 a4 a3 0 0 0", + " x x x x x x x x"; + + mode = 0x41; + delay = 10; + blocksize = 8; + readsize = 256; + ; + + memory "flash" + paged = yes; + size = 65536; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback_p1 = 0xff; + readback_p2 = 0xff; + read_lo = " 0 0 1 0 0 0 0 0", + " a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + read_hi = " 0 0 1 0 1 0 0 0", + " a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; + + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 0 0 0 0 0", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 0 0 0 0 0", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; + + writepage = " 0 1 0 0 1 1 0 0", + " a15 a14 a13 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " 0 0 0 0 0 0 0 0"; + + mode = 0x41; + delay = 10; + blocksize = 128; + readsize = 256; + ; + + memory "lock" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", + "0 0 0 0 0 0 0 0 1 1 i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "lfuse" + size = 1; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "0 0 0 0 0 0 0 0 i i i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "hfuse" + size = 1; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "0 0 0 0 0 0 0 0 i i i i i i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "efuse" + size = 1; + + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; + min_write_delay = 9000; + max_write_delay = 9000; + ; + + memory "signature" + size = 3; + read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + ; + + memory "calibration" + size = 1; + + read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; + ; + +#------------------------------------------------------------ +# ATmega645A +#------------------------------------------------------------ + +part parent "m645" + id = "m645a"; + desc = "ATmega645A"; + ; + +#------------------------------------------------------------ +# ATmega645P +#------------------------------------------------------------ + +part parent "m645" + id = "m645p"; + desc = "ATmega645P"; + signature = 0x1e 0x96 0x0d; + ; + +#------------------------------------------------------------ +# ATmega3250 +#------------------------------------------------------------ + +part parent "m325" + id = "m3250"; + desc = "ATmega3250"; + signature = 0x1E 0x95 0x06; + ; + +#------------------------------------------------------------ +# ATmega3250A +#------------------------------------------------------------ + +part parent "m325" + id = "m3250a"; + desc = "ATmega3250A"; + signature = 0x1E 0x95 0x06; + ; + +#------------------------------------------------------------ +# ATmega3250P +#------------------------------------------------------------ + +part parent "m325" + id = "m3250p"; + desc = "ATmega3250P"; + signature = 0x1E 0x95 0x0e; + ; + +#------------------------------------------------------------ +# ATmega3250PA +#------------------------------------------------------------ + +part parent "m325" + id = "m3250pa"; + desc = "ATmega3250PA"; + signature = 0x1E 0x95 0x0e; + ; + +#------------------------------------------------------------ +# ATmega6450 +#------------------------------------------------------------ + +part parent "m645" + id = "m6450"; + desc = "ATmega6450"; + signature = 0x1E 0x96 0x06; + ; + +#------------------------------------------------------------ +# ATmega6450A +#------------------------------------------------------------ + +part parent "m645" + id = "m6450a"; + desc = "ATmega6450A"; + signature = 0x1E 0x96 0x06; + ; + +#------------------------------------------------------------ +# ATmega6450P +#------------------------------------------------------------ + +part parent "m645" + id = "m6450p"; + desc = "ATmega6450P"; + signature = 0x1E 0x96 0x0e; + ; + +#------------------------------------------------------------ +# AVR XMEGA family common values +#------------------------------------------------------------ + +part + id = ".xmega"; + desc = "AVR XMEGA family common values"; + has_pdi = yes; + nvm_base = 0x01c0; + mcu_base = 0x0090; + + memory "signature" + size = 3; + offset = 0x1000090; + ; + + memory "prodsig" + size = 0x32; + offset = 0x8e0200; + page_size = 0x32; + readsize = 0x32; + ; + + memory "fuse1" + size = 1; + offset = 0x8f0021; + ; + + memory "fuse2" + size = 1; + offset = 0x8f0022; + ; + + memory "fuse4" + size = 1; + offset = 0x8f0024; + ; + + memory "fuse5" + size = 1; + offset = 0x8f0025; + ; + + memory "lock" + size = 1; + offset = 0x8f0027; + ; + + memory "data" + # SRAM, only used to supply the offset + offset = 0x1000000; + ; +; + +#------------------------------------------------------------ +# ATxmega16A4U +#------------------------------------------------------------ + +part parent ".xmega" + id = "x16a4u"; + desc = "ATxmega16A4U"; + signature = 0x1e 0x94 0x41; + usbpid = 0x2fe3; + + memory "eeprom" + size = 0x400; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x4000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x803000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "boot" + size = 0x1000; + offset = 0x804000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "flash" + size = 0x5000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "usersig" + size = 0x100; + offset = 0x8e0400; + page_size = 0x100; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega16C4 +#------------------------------------------------------------ + +part parent "x16a4u" + id = "x16c4"; + desc = "ATxmega16C4"; + signature = 0x1e 0x94 0x43; +; + +#------------------------------------------------------------ +# ATxmega16D4 +#------------------------------------------------------------ + +part parent "x16a4u" + id = "x16d4"; + desc = "ATxmega16D4"; + signature = 0x1e 0x94 0x42; +; + +#------------------------------------------------------------ +# ATxmega16A4 +#------------------------------------------------------------ + +part parent "x16a4u" + id = "x16a4"; + desc = "ATxmega16A4"; + signature = 0x1e 0x94 0x41; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega32A4U +#------------------------------------------------------------ + +part parent ".xmega" + id = "x32a4u"; + desc = "ATxmega32A4U"; + signature = 0x1e 0x95 0x41; + usbpid = 0x2fe4; + + memory "eeprom" + size = 0x400; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x8000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x807000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "boot" + size = 0x1000; + offset = 0x808000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "flash" + size = 0x9000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "usersig" + size = 0x100; + offset = 0x8e0400; + page_size = 0x100; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega32C4 +#------------------------------------------------------------ + +part parent "x32a4u" + id = "x32c4"; + desc = "ATxmega32C4"; + signature = 0x1e 0x95 0x44; +; + +#------------------------------------------------------------ +# ATxmega32D4 +#------------------------------------------------------------ + +part parent "x32a4u" + id = "x32d4"; + desc = "ATxmega32D4"; + signature = 0x1e 0x95 0x42; +; + +#------------------------------------------------------------ +# ATxmega32A4 +#------------------------------------------------------------ + +part parent "x32a4u" + id = "x32a4"; + desc = "ATxmega32A4"; + signature = 0x1e 0x95 0x41; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega64A4U +#------------------------------------------------------------ + +part parent ".xmega" + id = "x64a4u"; + desc = "ATxmega64A4U"; + signature = 0x1e 0x96 0x46; + usbpid = 0x2fe5; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x10000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x80f000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "boot" + size = 0x1000; + offset = 0x810000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "flash" + size = 0x11000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "usersig" + size = 0x100; + offset = 0x8e0400; + page_size = 0x100; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega64C3 +#------------------------------------------------------------ + +part parent "x64a4u" + id = "x64c3"; + desc = "ATxmega64C3"; + signature = 0x1e 0x96 0x49; + usbpid = 0x2fd6; +; + +#------------------------------------------------------------ +# ATxmega64D3 +#------------------------------------------------------------ + +part parent "x64a4u" + id = "x64d3"; + desc = "ATxmega64D3"; + signature = 0x1e 0x96 0x4a; +; + +#------------------------------------------------------------ +# ATxmega64D4 +#------------------------------------------------------------ + +part parent "x64a4u" + id = "x64d4"; + desc = "ATxmega64D4"; + signature = 0x1e 0x96 0x47; +; + +#------------------------------------------------------------ +# ATxmega64A1 +#------------------------------------------------------------ + +part parent "x64a4u" + id = "x64a1"; + desc = "ATxmega64A1"; + signature = 0x1e 0x96 0x4e; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega64A1U +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64a1u"; + desc = "ATxmega64A1U"; + signature = 0x1e 0x96 0x4e; + usbpid = 0x2fe8; +; + +#------------------------------------------------------------ +# ATxmega64A3 +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64a3"; + desc = "ATxmega64A3"; + signature = 0x1e 0x96 0x42; +; + +#------------------------------------------------------------ +# ATxmega64A3U +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64a3u"; + desc = "ATxmega64A3U"; + signature = 0x1e 0x96 0x42; + usbpid = 0x2fe5; +; + +#------------------------------------------------------------ +# ATxmega64A4 +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64a4"; + desc = "ATxmega64A4"; + signature = 0x1e 0x96 0x46; +; + +#------------------------------------------------------------ +# ATxmega64B1 +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64b1"; + desc = "ATxmega64B1"; + signature = 0x1e 0x96 0x52; + usbpid = 0x2fe1; +; + +#------------------------------------------------------------ +# ATxmega64B3 +#------------------------------------------------------------ + +part parent "x64a1" + id = "x64b3"; + desc = "ATxmega64B3"; + signature = 0x1e 0x96 0x51; + usbpid = 0x2fdf; +; + +#------------------------------------------------------------ +# ATxmega128C3 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x128c3"; + desc = "ATxmega128C3"; + signature = 0x1e 0x97 0x52; + usbpid = 0x2fd7; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "apptable" + size = 0x2000; + offset = 0x81e000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x820000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "flash" + size = 0x22000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "usersig" + size = 0x200; + offset = 0x8e0400; + page_size = 0x200; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega128D3 +#------------------------------------------------------------ + +part parent "x128c3" + id = "x128d3"; + desc = "ATxmega128D3"; + signature = 0x1e 0x97 0x48; +; + +#------------------------------------------------------------ +# ATxmega128D4 +#------------------------------------------------------------ + +part parent "x128c3" + id = "x128d4"; + desc = "ATxmega128D4"; + signature = 0x1e 0x97 0x47; + + memory "flash" + size = 0x22000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega128A1 +#------------------------------------------------------------ + +part parent "x128c3" + id = "x128a1"; + desc = "ATxmega128A1"; + signature = 0x1e 0x97 0x4c; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega128A1 revision D +#------------------------------------------------------------ + +part parent "x128a1" + id = "x128a1d"; + desc = "ATxmega128A1revD"; + signature = 0x1e 0x97 0x41; +; + +#------------------------------------------------------------ +# ATxmega128A1U +#------------------------------------------------------------ + +part parent "x128a1" + id = "x128a1u"; + desc = "ATxmega128A1U"; + signature = 0x1e 0x97 0x4c; + usbpid = 0x2fed; +; + +#------------------------------------------------------------ +# ATxmega128A3 +#------------------------------------------------------------ + +part parent "x128a1" + id = "x128a3"; + desc = "ATxmega128A3"; + signature = 0x1e 0x97 0x42; +; + +#------------------------------------------------------------ +# ATxmega128A3U +#------------------------------------------------------------ + +part parent "x128a1" + id = "x128a3u"; + desc = "ATxmega128A3U"; + signature = 0x1e 0x97 0x42; + usbpid = 0x2fe6; +; + +#------------------------------------------------------------ +# ATxmega128A4 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x128a4"; + desc = "ATxmega128A4"; + signature = 0x1e 0x97 0x46; + has_jtag = yes; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x81f000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x820000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "flash" + size = 0x22000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "usersig" + size = 0x200; + offset = 0x8e0400; + page_size = 0x200; + readsize = 0x100; + ; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega128A4U +#------------------------------------------------------------ + +part parent ".xmega" + id = "x128a4u"; + desc = "ATxmega128A4U"; + signature = 0x1e 0x97 0x46; + usbpid = 0x2fde; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x20000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x81f000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x820000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "flash" + size = 0x22000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "usersig" + size = 0x100; + offset = 0x8e0400; + page_size = 0x100; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega128B1 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x128b1"; + desc = "ATxmega128B1"; + signature = 0x1e 0x97 0x4d; + usbpid = 0x2fea; + has_jtag = yes; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x20000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "apptable" + size = 0x2000; + offset = 0x81e000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x820000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "flash" + size = 0x22000; + offset = 0x800000; + page_size = 0x100; + readsize = 0x100; + ; + + memory "usersig" + size = 0x100; + offset = 0x8e0400; + page_size = 0x100; + readsize = 0x100; + ; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega128B3 +#------------------------------------------------------------ + +part parent "x128b1" + id = "x128b3"; + desc = "ATxmega128B3"; + signature = 0x1e 0x97 0x4b; + usbpid = 0x2fe0; +; + +#------------------------------------------------------------ +# ATxmega192C3 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x192c3"; + desc = "ATxmega192C3"; + signature = 0x1e 0x97 0x51; + # usbpid = 0x2f??; + + memory "eeprom" + size = 0x800; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x30000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "apptable" + size = 0x2000; + offset = 0x82e000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x830000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "flash" + size = 0x32000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "usersig" + size = 0x200; + offset = 0x8e0400; + page_size = 0x200; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega192D3 +#------------------------------------------------------------ + +part parent "x192c3" + id = "x192d3"; + desc = "ATxmega192D3"; + signature = 0x1e 0x97 0x49; +; + +#------------------------------------------------------------ +# ATxmega192A1 +#------------------------------------------------------------ + +part parent "x192c3" + id = "x192a1"; + desc = "ATxmega192A1"; + signature = 0x1e 0x97 0x4e; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega192A3 +#------------------------------------------------------------ + +part parent "x192a1" + id = "x192a3"; + desc = "ATxmega192A3"; + signature = 0x1e 0x97 0x44; +; + +#------------------------------------------------------------ +# ATxmega192A3U +#------------------------------------------------------------ + +part parent "x192a1" + id = "x192a3u"; + desc = "ATxmega192A3U"; + signature = 0x1e 0x97 0x44; + usbpid = 0x2fe7; +; + +#------------------------------------------------------------ +# ATxmega256C3 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x256c3"; + desc = "ATxmega256C3"; + signature = 0x1e 0x98 0x46; + usbpid = 0x2fda; + + memory "eeprom" + size = 0x1000; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x40000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "apptable" + size = 0x2000; + offset = 0x83e000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x840000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "flash" + size = 0x42000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "usersig" + size = 0x200; + offset = 0x8e0400; + page_size = 0x200; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega256D3 +#------------------------------------------------------------ + +part parent "x256c3" + id = "x256d3"; + desc = "ATxmega256D3"; + signature = 0x1e 0x98 0x44; +; + +#------------------------------------------------------------ +# ATxmega256A1 +#------------------------------------------------------------ + +part parent "x256c3" + id = "x256a1"; + desc = "ATxmega256A1"; + signature = 0x1e 0x98 0x46; + has_jtag = yes; + + memory "fuse0" + size = 1; + offset = 0x8f0020; + ; +; + +#------------------------------------------------------------ +# ATxmega256A3 +#------------------------------------------------------------ + +part parent "x256a1" + id = "x256a3"; + desc = "ATxmega256A3"; + signature = 0x1e 0x98 0x42; +; + +#------------------------------------------------------------ +# ATxmega256A3U +#------------------------------------------------------------ + +part parent "x256a1" + id = "x256a3u"; + desc = "ATxmega256A3U"; + signature = 0x1e 0x98 0x42; + usbpid = 0x2fec; +; + +#------------------------------------------------------------ +# ATxmega256A3B +#------------------------------------------------------------ + +part parent "x256a1" + id = "x256a3b"; + desc = "ATxmega256A3B"; + signature = 0x1e 0x98 0x43; +; + +#------------------------------------------------------------ +# ATxmega256A3BU +#------------------------------------------------------------ + +part parent "x256a1" + id = "x256a3bu"; + desc = "ATxmega256A3BU"; + signature = 0x1e 0x98 0x43; + usbpid = 0x2fe2; +; + +#------------------------------------------------------------ +# ATxmega384C3 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x384c3"; + desc = "ATxmega384C3"; + signature = 0x1e 0x98 0x45; + usbpid = 0x2fdb; + + memory "eeprom" + size = 0x1000; + offset = 0x8c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x60000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "apptable" + size = 0x2000; + offset = 0x85e000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "boot" + size = 0x2000; + offset = 0x860000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "flash" + size = 0x62000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "usersig" + size = 0x200; + offset = 0x8e0400; + page_size = 0x200; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega384D3 +#------------------------------------------------------------ + +part parent "x384c3" + id = "x384d3"; + desc = "ATxmega384D3"; + signature = 0x1e 0x98 0x47; +; + +#------------------------------------------------------------ +# ATxmega8E5 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x8e5"; + desc = "ATxmega8E5"; + signature = 0x1e 0x93 0x41; + + memory "eeprom" + size = 0x0200; + offset = 0x08c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x2000; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "apptable" + size = 0x800; + offset = 0x00801800; + page_size = 0x80; + readsize = 0x100; + ; + + memory "boot" + size = 0x800; + offset = 0x00802000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "flash" + size = 0x2800; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "usersig" + size = 0x80; + offset = 0x8e0400; + page_size = 0x80; + readsize = 0x100; + ; +; + +#------------------------------------------------------------ +# ATxmega16E5 +#------------------------------------------------------------ + +part parent ".xmega" + id = "x16e5"; + desc = "ATxmega16E5"; + signature = 0x1e 0x94 0x45; + + memory "eeprom" + size = 0x0200; + offset = 0x08c0000; + page_size = 0x20; + readsize = 0x100; + ; + + memory "application" + size = 0x4000; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "apptable" + size = 0x1000; + offset = 0x00803000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "boot" + size = 0x1000; + offset = 0x00804000; + page_size = 0x80; + readsize = 0x100; + ; - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " x x x x x x x x"; + memory "flash" + size = 0x5000; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; + memory "usersig" + size = 0x80; + offset = 0x8e0400; + page_size = 0x80; + readsize = 0x100; + ; +; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; +#------------------------------------------------------------ +# ATxmega32E5 +#------------------------------------------------------------ - write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +part parent ".xmega" + id = "x32e5"; + desc = "ATxmega32E5"; + signature = 0x1e 0x95 0x4c; - memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "eeprom" + size = 0x0400; + offset = 0x08c0000; + page_size = 0x20; + readsize = 0x100; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "application" + size = 0x8000; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; - memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "apptable" + size = 0x1000; + offset = 0x00807000; + page_size = 0x80; + readsize = 0x100; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "boot" + size = 0x1000; + offset = 0x00808000; + page_size = 0x80; + readsize = 0x100; + ; - memory "efuse" - size = 1; + memory "flash" + size = 0x9000; + offset = 0x0800000; + page_size = 0x80; + readsize = 0x100; + ; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "usersig" + size = 0x80; + offset = 0x8e0400; + page_size = 0x80; + readsize = 0x100; + ; +; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +#------------------------------------------------------------ +# AVR32UC3A0512 +#------------------------------------------------------------ - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; +part + id = "uc3a0512"; + desc = "AT32UC3A0512"; + signature = 0xED 0xC0 0x3F; + has_jtag = yes; + is_avr32 = yes; - memory "calibration" - size = 1; + memory "flash" + paged = yes; + page_size = 512; # bytes + readsize = 512; # bytes + num_pages = 1024; # could be set dynamicly + size = 0x00080000; # could be set dynamicly + offset = 0x80000000; + ; +; - read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; +part parent "uc3a0512" + id = "ucr2"; + desc = "deprecated, use 'uc3a0512'"; +; #------------------------------------------------------------ -# ATmega645 +# ATtiny1634 #------------------------------------------------------------ part - id = "m645"; - desc = "ATmega645"; - signature = 0x1E 0x96 0x05; - has_jtag = yes; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - pagel = 0xd7; - bs2 = 0xa0; + id = "t1634"; + desc = "ATtiny1634"; + has_debugwire = yes; + flash_instr = 0xB6, 0x01, 0x11; + eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, + 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, + 0x99, 0xF9, 0xBB, 0xAF; + stk500_devcode = 0x86; + # avr910_devcode = 0x; + signature = 0x1e 0x94 0x12; + pagel = 0xB3; + bs2 = 0xB1; + reset = io; chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", + "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; + chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", + "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + bytedelay = 0; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, + 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, + 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, + 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; - latchcycles = 5; + latchcycles = 0; togglevtg = 1; poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; + resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; @@ -13362,2649 +16001,2940 @@ part programlockpulsewidth = 0; programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; + paged = no; + page_size = 4; + size = 256; + min_write_delay = 3600; + max_write_delay = 3600; readback_p1 = 0xff; readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read = " 1 0 1 0 0 0 0 0", + " 0 0 0 x x x x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + write = " 1 1 0 0 0 0 0 0", + " 0 0 0 x x x x a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 1 1 0 0 0 0 0 1", + " 0 0 0 0 0 0 0 0", + " 0 0 0 0 0 0 a1 a0", + " i i i i i i i i"; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; + writepage = " 1 1 0 0 0 0 1 0", + " 0 0 x x x x x a8", + " a7 a6 a5 a4 a3 a2 0 0", + " x x x x x x x x"; - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; + mode = 0x41; + delay = 5; + blocksize = 4; + readsize = 256; + ; memory "flash" paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; + size = 16384; + page_size = 32; + num_pages = 512; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + read_lo = " 0 0 1 0 0 0 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + read_hi = " 0 0 1 0 1 0 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 a5 a4 a3 a2 a1 a0", + " o o o o o o o o"; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + loadpage_lo = " 0 1 0 0 0 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - writepage = " 0 1 0 0 1 1 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " 0 0 0 0 0 0 0 0"; + loadpage_hi = " 0 1 0 0 1 0 0 0", + " 0 0 0 x x x x x", + " x x a5 a4 a3 a2 a1 a0", + " i i i i i i i i"; - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; + writepage = " 0 1 0 0 1 1 0 0", + " 0 0 0 a12 a11 a10 a9 a8", + " a7 a6 x x x x x x", + " x x x x x x x x"; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x o o o o o o"; + mode = 0x41; + delay = 6; + blocksize = 128; + readsize = 256; - write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + ; memory "lfuse" size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; memory "hfuse" size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", + "x x x x x x x x i i i i i i i i"; + ; memory "efuse" size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", + "x x x x x x x x o o o o o o o o"; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", + "x x x x x x x x x x x i i i i i"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", + "x x x x x x x x o o o o o o o o"; + + write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", + "x x x x x x x x 1 1 1 1 1 1 i i"; + ; + + memory "calibration" + size = 1; + read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", + "0 0 0 0 0 0 0 0 o o o o o o o o"; + ; memory "signature" size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", + "x x x x x x a1 a0 o o o o o o o o"; + ; +; + +#------------------------------------------------------------ +# ATtiny1634R +#------------------------------------------------------------ + +part parent "t1634" + id = "t1634r"; + desc = "ATtiny1634R"; + ; + +#------------------------------------------------------------ +# Common values for reduced core tinys (4/5/9/10/20/40) +#------------------------------------------------------------ + +part + id = ".reduced_core_tiny"; + desc = "Common values for reduced core tinys"; + has_tpi = yes; + + memory "signature" + size = 3; + offset = 0x3fc0; + page_size = 16; + ; + + memory "fuse" + size = 1; + offset = 0x3f40; + page_size = 16; + blocksize = 4; + ; memory "calibration" - size = 1; + size = 1; + offset = 0x3f80; + page_size = 16; + ; + + memory "lockbits" + size = 1; + offset = 0x3f00; + page_size = 16; + ; +; + +#------------------------------------------------------------ +# ATtiny4 +#------------------------------------------------------------ + +part parent ".reduced_core_tiny" + id = "t4"; + desc = "ATtiny4"; + signature = 0x1e 0x8f 0x0a; + + memory "flash" + size = 512; + offset = 0x4000; + page_size = 16; + blocksize = 128; + ; +; + +#------------------------------------------------------------ +# ATtiny5 +#------------------------------------------------------------ + +part parent "t4" + id = "t5"; + desc = "ATtiny5"; + signature = 0x1e 0x8f 0x09; +; + +#------------------------------------------------------------ +# ATtiny9 +#------------------------------------------------------------ + +part parent ".reduced_core_tiny" + id = "t9"; + desc = "ATtiny9"; + signature = 0x1e 0x90 0x08; + + memory "flash" + size = 1024; + offset = 0x4000; + page_size = 16; + blocksize = 128; + ; +; + +#------------------------------------------------------------ +# ATtiny10 +#------------------------------------------------------------ + +part parent "t9" + id = "t10"; + desc = "ATtiny10"; + signature = 0x1e 0x90 0x03; +; + +#------------------------------------------------------------ +# ATtiny20 +#------------------------------------------------------------ + +part parent ".reduced_core_tiny" + id = "t20"; + desc = "ATtiny20"; + signature = 0x1e 0x91 0x0F; + + memory "flash" + size = 2048; + offset = 0x4000; + page_size = 16; + blocksize = 128; + ; +; + +#------------------------------------------------------------ +# ATtiny40 +#------------------------------------------------------------ + +part parent ".reduced_core_tiny" + id = "t40"; + desc = "ATtiny40"; + signature = 0x1e 0x92 0x0E; - read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + memory "flash" + size = 4096; + offset = 0x4000; + page_size = 64; + blocksize = 128; + ; +; #------------------------------------------------------------ -# ATmega3250 +# ATtiny102 #------------------------------------------------------------ -part parent "m325" - id = "m3250"; - desc = "ATmega3250"; - signature = 0x1E 0x95 0x06; +part parent ".reduced_core_tiny" + id = "t102"; + desc = "ATtiny102"; + signature = 0x1e 0x90 0x0C; - ocdrev = 3; - ; + memory "flash" + size = 1024; + offset = 0x4000; + page_size = 16; + blocksize = 128; + ; +; #------------------------------------------------------------ -# ATmega6450 +# ATtiny104 #------------------------------------------------------------ -part parent "m645" - id = "m6450"; - desc = "ATmega6450"; - signature = 0x1E 0x96 0x06; +part parent ".reduced_core_tiny" + id = "t104"; + desc = "ATtiny104"; + signature = 0x1e 0x90 0x0B; - ocdrev = 3; - ; + memory "flash" + size = 1024; + offset = 0x4000; + page_size = 16; + blocksize = 128; + ; +; #------------------------------------------------------------ -# AVR XMEGA family common values +# ATmega406 #------------------------------------------------------------ part - id = ".xmega"; - desc = "AVR XMEGA family common values"; - has_pdi = yes; - nvm_base = 0x01c0; - mcu_base = 0x0090; + id = "m406"; + desc = "ATmega406"; + has_jtag = yes; + signature = 0x1e 0x95 0x07; - memory "signature" - size = 3; - offset = 0x1000090; - ; + # STK500 parameters (parallel programming IO lines) + pagel = 0xa7; + bs2 = 0xa0; + serial = no; + parallel = yes; - memory "prodsig" - size = 0x32; - offset = 0x8e0200; - page_size = 0x32; - readsize = 0x32; - ; + # STK500v2 HV programming parameters, from XML + pp_controlstack = 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - memory "fuse1" - size = 1; - offset = 0x8f0021; + # JTAG ICE mkII parameters, also from XML files + allowfullpagebitstream = no; + enablepageprogramming = yes; + idr = 0x51; + rampz = 0x00; + spmcr = 0x57; + eecr = 0x3f; + + memory "eeprom" + paged = no; + size = 512; + page_size = 4; + blocksize = 4; + readsize = 4; + num_pages = 128; ; - memory "fuse2" - size = 1; - offset = 0x8f0022; + memory "flash" + paged = yes; + size = 40960; + page_size = 128; + blocksize = 128; + readsize = 128; + num_pages = 320; ; - memory "fuse4" - size = 1; - offset = 0x8f0024; + memory "hfuse" + size = 1; ; - memory "fuse5" - size = 1; - offset = 0x8f0025; + memory "lfuse" + size = 1; ; - memory "lock" + memory "lockbits" size = 1; - offset = 0x8f0027; ; - memory "data" - # SRAM, only used to supply the offset - offset = 0x1000000; + memory "signature" + size = 3; ; ; #------------------------------------------------------------ -# ATxmega16A4U +# AVR8X family common values #------------------------------------------------------------ -part parent ".xmega" - id = "x16a4u"; - desc = "ATxmega16A4U"; - signature = 0x1e 0x94 0x41; - usbpid = 0x2fe3; +part + id = ".avr8x"; + desc = "AVR8X family common values"; + has_updi = yes; + nvm_base = 0x1000; + ocd_base = 0x0F80; - memory "eeprom" - size = 0x400; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "signature" + size = 3; + offset = 0x1100; + readsize = 0x3; ; - memory "application" - size = 0x4000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "prodsig" + size = 0x3D; + offset = 0x1103; + page_size = 0x3D; + readsize = 0x3D; ; - memory "apptable" - size = 0x1000; - offset = 0x803000; - page_size = 0x100; - readsize = 0x100; + memory "sernum" + size = 10; + offset = 0x1104; + readsize = 1; ; - memory "boot" - size = 0x1000; - offset = 0x804000; - page_size = 0x100; - readsize = 0x100; + memory "osccal16" + size = 2; + offset = 0x1118; + readsize = 1; ; - memory "flash" - size = 0x5000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "osccal20" + size = 2; + offset = 0x111A; + readsize = 1; ; - memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + memory "tempsense" + size = 2; + offset = 0x1120; + readsize = 1; ; -; - -#------------------------------------------------------------ -# ATxmega16C4 -#------------------------------------------------------------ -part parent "x16a4u" - id = "x16c4"; - desc = "ATxmega16C4"; - signature = 0x1e 0x94 0x43; -; + memory "osc16err" + size = 2; + offset = 0x1122; + readsize = 1; + ; -#------------------------------------------------------------ -# ATxmega16D4 -#------------------------------------------------------------ + memory "osc20err" + size = 2; + offset = 0x1124; + readsize = 1; + ; -part parent "x16a4u" - id = "x16d4"; - desc = "ATxmega16D4"; - signature = 0x1e 0x94 0x42; -; + memory "fuses" + size = 9; + offset = 0x1280; + page_size = 0x0A; + readsize = 0x0A; + ; -#------------------------------------------------------------ -# ATxmega16A4 -#------------------------------------------------------------ + memory "fuse0" + size = 1; + offset = 0x1280; + readsize = 1; + ; -part parent "x16a4u" - id = "x16a4"; - desc = "ATxmega16A4"; - signature = 0x1e 0x94 0x41; - has_jtag = yes; + memory "wdtcfg" + alias "fuse0"; + ; - memory "fuse0" + memory "fuse1" size = 1; - offset = 0x8f0020; + offset = 0x1281; + readsize = 1; ; -; -#------------------------------------------------------------ -# ATxmega32A4U -#------------------------------------------------------------ + memory "bodcfg" + alias "fuse1"; + ; -part parent ".xmega" - id = "x32a4u"; - desc = "ATxmega32A4U"; - signature = 0x1e 0x95 0x41; - usbpid = 0x2fe4; + memory "fuse2" + size = 1; + offset = 0x1282; + readsize = 1; + ; - memory "eeprom" - size = 0x400; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "osccfg" + alias "fuse2"; ; - memory "application" - size = 0x8000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "fuse4" + size = 1; + offset = 0x1284; + readsize = 1; ; - memory "apptable" - size = 0x1000; - offset = 0x807000; - page_size = 0x100; - readsize = 0x100; + memory "tcd0cfg" + alias "fuse4"; ; - memory "boot" - size = 0x1000; - offset = 0x808000; - page_size = 0x100; - readsize = 0x100; + memory "fuse5" + size = 1; + offset = 0x1285; + readsize = 1; ; - memory "flash" - size = 0x9000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "syscfg0" + alias "fuse5"; + ; + + memory "fuse6" + size = 1; + offset = 0x1286; + readsize = 1; ; - memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + memory "syscfg1" + alias "fuse6"; ; -; -#------------------------------------------------------------ -# ATxmega32C4 -#------------------------------------------------------------ + memory "fuse7" + size = 1; + offset = 0x1287; + readsize = 1; + ; -part parent "x32a4u" - id = "x32c4"; - desc = "ATxmega32C4"; - signature = 0x1e 0x95 0x44; -; + memory "append" + alias "fuse7"; + ; -#------------------------------------------------------------ -# ATxmega32D4 -#------------------------------------------------------------ + memory "codesize" + alias "fuse7"; + ; -part parent "x32a4u" - id = "x32d4"; - desc = "ATxmega32D4"; - signature = 0x1e 0x95 0x42; -; + memory "fuse8" + size = 1; + offset = 0x1288; + readsize = 1; + ; -#------------------------------------------------------------ -# ATxmega32A4 -#------------------------------------------------------------ + memory "bootend" + alias "fuse8"; + ; -part parent "x32a4u" - id = "x32a4"; - desc = "ATxmega32A4"; - signature = 0x1e 0x95 0x41; - has_jtag = yes; + memory "bootsize" + alias "fuse8"; + ; - memory "fuse0" + memory "lock" size = 1; - offset = 0x8f0020; + offset = 0x128a; + readsize = 1; + ; + + memory "data" + # SRAM, only used to supply the offset + offset = 0x1000000; ; ; #------------------------------------------------------------ -# ATxmega64A4U +# AVR8X tiny family common values #------------------------------------------------------------ -part parent ".xmega" - id = "x64a4u"; - desc = "ATxmega64A4U"; - signature = 0x1e 0x96 0x46; - usbpid = 0x2fe5; +part parent ".avr8x" + id = ".avr8x_tiny"; + desc = "AVR8X tiny family common values"; + family_id = "tinyAVR"; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; + memory "userrow" + size = 0x20; + offset = 0x1300; page_size = 0x20; readsize = 0x100; ; - memory "application" - size = 0x10000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "usersig" + alias "userrow"; ; +; - memory "apptable" - size = 0x1000; - offset = 0x80f000; - page_size = 0x100; - readsize = 0x100; - ; +#------------------------------------------------------------ +# AVR8X mega family common values +#------------------------------------------------------------ - memory "boot" - size = 0x1000; - offset = 0x810000; - page_size = 0x100; - readsize = 0x100; - ; +part parent ".avr8x" + id = ".avr8x_mega"; + desc = "AVR8X mega family common values"; + family_id = "megaAVR"; - memory "flash" - size = 0x11000; - offset = 0x800000; - page_size = 0x100; + memory "userrow" + size = 0x40; + offset = 0x1300; + page_size = 0x40; readsize = 0x100; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + alias "userrow"; ; ; #------------------------------------------------------------ -# ATxmega64C3 +# ATtiny202 #------------------------------------------------------------ -part parent "x64a4u" - id = "x64c3"; - desc = "ATxmega64C3"; - signature = 0x1e 0x96 0x49; - usbpid = 0x2fd6; -; +part parent ".avr8x_tiny" + id = "t202"; + desc = "ATtiny202"; + signature = 0x1E 0x91 0x23; -#------------------------------------------------------------ -# ATxmega64D3 -#------------------------------------------------------------ + memory "flash" + size = 0x800; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x64a4u" - id = "x64d3"; - desc = "ATxmega64D3"; - signature = 0x1e 0x96 0x4a; + memory "eeprom" + size = 0x40; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64D4 +# ATtiny204 #------------------------------------------------------------ -part parent "x64a4u" - id = "x64d4"; - desc = "ATxmega64D4"; - signature = 0x1e 0x96 0x47; +part parent ".avr8x_tiny" + id = "t204"; + desc = "ATtiny204"; + signature = 0x1E 0x91 0x22; + + memory "flash" + size = 0x800; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x40; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64A1 +# ATtiny402 #------------------------------------------------------------ -part parent "x64a4u" - id = "x64a1"; - desc = "ATxmega64A1"; - signature = 0x1e 0x96 0x4e; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t402"; + desc = "ATtiny402"; + signature = 0x1E 0x92 0x27; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega64A1U +# ATtiny404 #------------------------------------------------------------ -part parent "x64a1" - id = "x64a1u"; - desc = "ATxmega64A1U"; - signature = 0x1e 0x96 0x4e; - usbpid = 0x2fe8; +part parent ".avr8x_tiny" + id = "t404"; + desc = "ATtiny404"; + signature = 0x1E 0x92 0x26; + + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64A3 +# ATtiny406 #------------------------------------------------------------ -part parent "x64a1" - id = "x64a3"; - desc = "ATxmega64A3"; - signature = 0x1e 0x96 0x42; +part parent ".avr8x_tiny" + id = "t406"; + desc = "ATtiny406"; + signature = 0x1E 0x92 0x25; + + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64A3U +# ATtiny804 #------------------------------------------------------------ -part parent "x64a1" - id = "x64a3u"; - desc = "ATxmega64A3U"; - signature = 0x1e 0x96 0x42; - usbpid = 0x2fe5; +part parent ".avr8x_tiny" + id = "t804"; + desc = "ATtiny804"; + signature = 0x1E 0x93 0x25; + + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64A4 +# ATtiny806 #------------------------------------------------------------ -part parent "x64a1" - id = "x64a4"; - desc = "ATxmega64A4"; - signature = 0x1e 0x96 0x46; -; +part parent ".avr8x_tiny" + id = "t806"; + desc = "ATtiny806"; + signature = 0x1E 0x93 0x24; -#------------------------------------------------------------ -# ATxmega64B1 -#------------------------------------------------------------ + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x64a1" - id = "x64b1"; - desc = "ATxmega64B1"; - signature = 0x1e 0x96 0x52; - usbpid = 0x2fe1; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega64B3 +# ATtiny807 #------------------------------------------------------------ -part parent "x64a1" - id = "x64b3"; - desc = "ATxmega64B3"; - signature = 0x1e 0x96 0x51; - usbpid = 0x2fdf; +part parent ".avr8x_tiny" + id = "t807"; + desc = "ATtiny807"; + signature = 0x1E 0x93 0x23; + + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega128C3 +# ATtiny1604 #------------------------------------------------------------ -part parent ".xmega" - id = "x128c3"; - desc = "ATxmega128C3"; - signature = 0x1e 0x97 0x52; - usbpid = 0x2fd7; +part parent ".avr8x_tiny" + id = "t1604"; + desc = "ATtiny1604"; + signature = 0x1E 0x94 0x25; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x2000; - offset = 0x81e000; - page_size = 0x200; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny1606 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x200; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t1606"; + desc = "ATtiny1606"; + signature = 0x1E 0x94 0x24; memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega128D3 +# ATtiny1607 #------------------------------------------------------------ -part parent "x128c3" - id = "x128d3"; - desc = "ATxmega128D3"; - signature = 0x1e 0x97 0x48; -; +part parent ".avr8x_tiny" + id = "t1607"; + desc = "ATtiny1607"; + signature = 0x1E 0x94 0x23; -#------------------------------------------------------------ -# ATxmega128D4 -#------------------------------------------------------------ + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x128c3" - id = "x128d4"; - desc = "ATxmega128D4"; - signature = 0x1e 0x97 0x47; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega128A1 +# ATtiny212 #------------------------------------------------------------ -part parent "x128c3" - id = "x128a1"; - desc = "ATxmega128A1"; - signature = 0x1e 0x97 0x4c; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t212"; + desc = "ATtiny212"; + signature = 0x1E 0x91 0x21; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "flash" + size = 0x800; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x40; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega128A1 revision D +# ATtiny214 #------------------------------------------------------------ -part parent "x128a1" - id = "x128a1d"; - desc = "ATxmega128A1revD"; - signature = 0x1e 0x97 0x41; -; +part parent ".avr8x_tiny" + id = "t214"; + desc = "ATtiny214"; + signature = 0x1E 0x91 0x20; -#------------------------------------------------------------ -# ATxmega128A1U -#------------------------------------------------------------ + memory "flash" + size = 0x800; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x128a1" - id = "x128a1u"; - desc = "ATxmega128A1U"; - signature = 0x1e 0x97 0x4c; - usbpid = 0x2fed; + memory "eeprom" + size = 0x40; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega128A3 +# ATtiny412 #------------------------------------------------------------ -part parent "x128a1" - id = "x128a3"; - desc = "ATxmega128A3"; - signature = 0x1e 0x97 0x42; -; +part parent ".avr8x_tiny" + id = "t412"; + desc = "ATtiny412"; + signature = 0x1E 0x92 0x23; -#------------------------------------------------------------ -# ATxmega128A3U -#------------------------------------------------------------ + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x128a1" - id = "x128a3u"; - desc = "ATxmega128A3U"; - signature = 0x1e 0x97 0x42; - usbpid = 0x2fe6; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; + #------------------------------------------------------------ -# ATxmega128A4 +# ATtiny414 #------------------------------------------------------------ -part parent ".xmega" - id = "x128a4"; - desc = "ATxmega128A4"; - signature = 0x1e 0x97 0x46; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t414"; + desc = "ATtiny414"; + signature = 0x1E 0x92 0x22; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x1000; - offset = 0x81f000; - page_size = 0x200; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny416 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x200; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t416"; + desc = "ATtiny416"; + signature = 0x1E 0x92 0x21; memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; - ; - - memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; + #------------------------------------------------------------ -# ATxmega128A4U +# ATtiny417 #------------------------------------------------------------ -part parent ".xmega" - id = "x128a4u"; - desc = "ATxmega128A4U"; - signature = 0x1e 0x97 0x46; - usbpid = 0x2fde; +part parent ".avr8x_tiny" + id = "t417"; + desc = "ATtiny417"; + signature = 0x1E 0x92 0x20; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x1000; - offset = 0x81f000; - page_size = 0x100; - readsize = 0x100; - ; - memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x100; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny814 +#------------------------------------------------------------ + +part parent ".avr8x_tiny" + id = "t814"; + desc = "ATtiny814"; + signature = 0x1E 0x93 0x22; memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; + #------------------------------------------------------------ -# ATxmega128B1 +# ATtiny816 #------------------------------------------------------------ -part parent ".xmega" - id = "x128b1"; - desc = "ATxmega128B1"; - signature = 0x1e 0x97 0x4d; - usbpid = 0x2fea; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t816"; + desc = "ATtiny816"; + signature = 0x1E 0x93 0x21; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x2000; - offset = 0x81e000; - page_size = 0x100; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny817 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x100; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t817"; + desc = "ATtiny817"; + signature = 0x1E 0x93 0x20; memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; - ; - - memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega128B3 +# ATtiny1614 #------------------------------------------------------------ -part parent "x128b1" - id = "x128b3"; - desc = "ATxmega128B3"; - signature = 0x1e 0x97 0x4b; - usbpid = 0x2fe0; +part parent ".avr8x_tiny" + id = "t1614"; + desc = "ATtiny1614"; + signature = 0x1E 0x94 0x22; + + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega192C3 +# ATtiny1616 #------------------------------------------------------------ -part parent ".xmega" - id = "x192c3"; - desc = "ATxmega192C3"; - signature = 0x1e 0x97 0x51; - # usbpid = 0x2f??; +part parent ".avr8x_tiny" + id = "t1616"; + desc = "ATtiny1616"; + signature = 0x1E 0x94 0x21; - memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x30000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x2000; - offset = 0x82e000; - page_size = 0x200; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny1617 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x830000; - page_size = 0x200; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t1617"; + desc = "ATtiny1617"; + signature = 0x1E 0x94 0x20; memory "flash" - size = 0x32000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega192D3 +# ATtiny3216 #------------------------------------------------------------ -part parent "x192c3" - id = "x192d3"; - desc = "ATxmega192D3"; - signature = 0x1e 0x97 0x49; +part parent ".avr8x_tiny" + id = "t3216"; + desc = "ATtiny3216"; + signature = 0x1E 0x95 0x21; + + memory "flash" + size = 0x8000; + offset = 0x8000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega192A1 +# ATtiny3217 #------------------------------------------------------------ -part parent "x192c3" - id = "x192a1"; - desc = "ATxmega192A1"; - signature = 0x1e 0x97 0x4e; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t3217"; + desc = "ATtiny3217"; + signature = 0x1E 0x95 0x22; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "flash" + size = 0x8000; + offset = 0x8000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega192A3 +# ATtiny424 #------------------------------------------------------------ -part parent "x192a1" - id = "x192a3"; - desc = "ATxmega192A3"; - signature = 0x1e 0x97 0x44; -; +part parent ".avr8x_tiny" + id = "t424"; + desc = "ATtiny424"; + signature = 0x1E 0x92 0x2C; -#------------------------------------------------------------ -# ATxmega192A3U -#------------------------------------------------------------ + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x192a1" - id = "x192a3u"; - desc = "ATxmega192A3U"; - signature = 0x1e 0x97 0x44; - usbpid = 0x2fe7; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega256C3 +# ATtiny426 #------------------------------------------------------------ -part parent ".xmega" - id = "x256c3"; - desc = "ATxmega256C3"; - signature = 0x1e 0x98 0x46; - usbpid = 0x2fda; +part parent ".avr8x_tiny" + id = "t426"; + desc = "ATtiny426"; + signature = 0x1E 0x92 0x2B; - memory "eeprom" - size = 0x1000; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x40000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x2000; - offset = 0x83e000; - page_size = 0x200; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny427 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x840000; - page_size = 0x200; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t427"; + desc = "ATtiny427"; + signature = 0x1E 0x92 0x2A; memory "flash" - size = 0x42000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x1000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega256D3 +# ATtiny824 #------------------------------------------------------------ -part parent "x256c3" - id = "x256d3"; - desc = "ATxmega256D3"; - signature = 0x1e 0x98 0x44; +part parent ".avr8x_tiny" + id = "t824"; + desc = "ATtiny824"; + signature = 0x1E 0x93 0x29; + + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega256A1 +# ATtiny826 #------------------------------------------------------------ -part parent "x256c3" - id = "x256a1"; - desc = "ATxmega256A1"; - signature = 0x1e 0x98 0x46; - has_jtag = yes; +part parent ".avr8x_tiny" + id = "t826"; + desc = "ATtiny826"; + signature = 0x1E 0x93 0x28; - memory "fuse0" - size = 1; - offset = 0x8f0020; + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega256A3 +# ATtiny827 #------------------------------------------------------------ -part parent "x256a1" - id = "x256a3"; - desc = "ATxmega256A3"; - signature = 0x1e 0x98 0x42; -; +part parent ".avr8x_tiny" + id = "t827"; + desc = "ATtiny827"; + signature = 0x1E 0x93 0x27; -#------------------------------------------------------------ -# ATxmega256A3U -#------------------------------------------------------------ + memory "flash" + size = 0x2000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; -part parent "x256a1" - id = "x256a3u"; - desc = "ATxmega256A3U"; - signature = 0x1e 0x98 0x42; - usbpid = 0x2fec; + memory "eeprom" + size = 0x80; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega256A3B +# ATtiny1624 #------------------------------------------------------------ -part parent "x256a1" - id = "x256a3b"; - desc = "ATxmega256A3B"; - signature = 0x1e 0x98 0x43; -; +part parent ".avr8x_tiny" + id = "t1624"; + desc = "ATtiny1624"; + signature = 0x1E 0x94 0x2A; + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; +; #------------------------------------------------------------ -# ATxmega256A3BU +# ATtiny1626 #------------------------------------------------------------ -part parent "x256a1" - id = "x256a3bu"; - desc = "ATxmega256A3BU"; - signature = 0x1e 0x98 0x43; - usbpid = 0x2fe2; +part parent ".avr8x_tiny" + id = "t1626"; + desc = "ATtiny1626"; + signature = 0x1E 0x94 0x29; + + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega384C3 +# ATtiny1627 #------------------------------------------------------------ -part parent ".xmega" - id = "x384c3"; - desc = "ATxmega384C3"; - signature = 0x1e 0x98 0x45; - usbpid = 0x2fdb; +part parent ".avr8x_tiny" + id = "t1627"; + desc = "ATtiny1627"; + signature = 0x1E 0x94 0x28; - memory "eeprom" - size = 0x1000; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + offset = 0x8000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x60000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x2000; - offset = 0x85e000; - page_size = 0x200; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATtiny3224 +#------------------------------------------------------------ - memory "boot" - size = 0x2000; - offset = 0x860000; - page_size = 0x200; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "t3224"; + desc = "ATtiny3224"; + signature = 0x1E 0x95 0x28; memory "flash" - size = 0x62000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x8000; + offset = 0x8000; + page_size = 0x80; + readsize = 0x100; ; - memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega384D3 +# ATtiny3226 #------------------------------------------------------------ -part parent "x384c3" - id = "x384d3"; - desc = "ATxmega384D3"; - signature = 0x1e 0x98 0x47; +part parent ".avr8x_tiny" + id = "t3226"; + desc = "ATtiny3226"; + signature = 0x1E 0x95 0x27; + + memory "flash" + size = 0x8000; + offset = 0x8000; + page_size = 0x80; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATxmega8E5 +# ATtiny3227 #------------------------------------------------------------ -part parent ".xmega" - id = "x8e5"; - desc = "ATxmega8E5"; - signature = 0x1e 0x93 0x41; +part parent ".avr8x_tiny" + id = "t3227"; + desc = "ATtiny3227"; + signature = 0x1E 0x95 0x26; - memory "eeprom" - size = 0x0200; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x8000; + offset = 0x8000; + page_size = 0x80; + readsize = 0x100; ; - memory "application" - size = 0x2000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; ; +; - memory "apptable" - size = 0x800; - offset = 0x00801800; - page_size = 0x80; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATmega808 +#------------------------------------------------------------ - memory "boot" - size = 0x800; - offset = 0x00802000; - page_size = 0x80; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "m808"; + desc = "ATmega808"; + signature = 0x1E 0x93 0x26; memory "flash" - size = 0x2800; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 0x2000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega16E5 +# ATmega809 #------------------------------------------------------------ -part parent ".xmega" - id = "x16e5"; - desc = "ATxmega16E5"; - signature = 0x1e 0x94 0x45; +part parent ".avr8x_tiny" + id = "m809"; + desc = "ATmega809"; + signature = 0x1E 0x93 0x2A; - memory "eeprom" - size = 0x0200; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x2000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x4000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x1000; - offset = 0x00803000; - page_size = 0x80; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATmega1608 +#------------------------------------------------------------ - memory "boot" - size = 0x1000; - offset = 0x00804000; - page_size = 0x80; - readsize = 0x100; - ; +part parent ".avr8x_tiny" + id = "m1608"; + desc = "ATmega1608"; + signature = 0x1E 0x94 0x27; memory "flash" - size = 0x5000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 0x4000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; ; - memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATxmega32E5 +# ATmega1609 #------------------------------------------------------------ -part parent ".xmega" - id = "x32e5"; - desc = "ATxmega32E5"; - signature = 0x1e 0x95 0x4c; +part parent ".avr8x_tiny" + id = "m1609"; + desc = "ATmega1609"; + signature = 0x1E 0x94 0x26; - memory "eeprom" - size = 0x0400; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + offset = 0x4000; + page_size = 0x40; + readsize = 0x100; ; - memory "application" - size = 0x8000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x20; + readsize = 0x100; ; +; - memory "apptable" - size = 0x1000; - offset = 0x00807000; - page_size = 0x80; - readsize = 0x100; - ; +#------------------------------------------------------------ +# ATmega3208 +#------------------------------------------------------------ - memory "boot" - size = 0x1000; - offset = 0x00808000; - page_size = 0x80; - readsize = 0x100; - ; +part parent ".avr8x_mega" + id = "m3208"; + desc = "ATmega3208"; + signature = 0x1E 0x95 0x30; memory "flash" - size = 0x9000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 0x8000; + offset = 0x4000; + page_size = 0x80; + readsize = 0x100; ; - memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; ; ; #------------------------------------------------------------ -# AVR32UC3A0512 +# ATmega3209 #------------------------------------------------------------ -part - id = "uc3a0512"; - desc = "AT32UC3A0512"; - signature = 0xED 0xC0 0x3F; - has_jtag = yes; - is_avr32 = yes; +part parent ".avr8x_mega" + id = "m3209"; + desc = "ATmega3209"; + signature = 0x1E 0x95 0x31; memory "flash" - paged = yes; - page_size = 512; # bytes - readsize = 512; # bytes - num_pages = 1024; # could be set dynamicly - size = 0x00080000; # could be set dynamicly - offset = 0x80000000; + size = 0x8000; + offset = 0x4000; + page_size = 0x80; + readsize = 0x100; ; -; -part parent "uc3a0512" - id = "ucr2"; - desc = "deprecated, use 'uc3a0512'"; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATtiny1634. +# ATmega4808 #------------------------------------------------------------ -part - id = "t1634"; - desc = "ATtiny1634"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x94 0x12; - pagel = 0xB3; - bs2 = 0xB1; - reset = io; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; +part parent ".avr8x_mega" + id = "m4808"; + desc = "ATmega4808"; + signature = 0x1E 0x96 0x50; - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; + memory "flash" + size = 0xC000; + offset = 0x4000; + page_size = 0x80; + readsize = 0x100; + ; memory "eeprom" - paged = no; - page_size = 4; - size = 256; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; + ; +; - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; +#------------------------------------------------------------ +# ATmega4809 +#------------------------------------------------------------ - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; +part parent ".avr8x_mega" + id = "m4809"; + desc = "ATmega4809"; + signature = 0x1E 0x96 0x51; memory "flash" - paged = yes; - size = 16384; - page_size = 32; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + size = 0xC000; + offset = 0x4000; + page_size = 0x80; + readsize = 0x100; + ; - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; + memory "eeprom" + size = 0x100; + offset = 0x1400; + page_size = 0x40; + readsize = 0x100; + ; +; - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; +#------------------------------------------------------------ +# AVR-Dx family common values +#------------------------------------------------------------ - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; +part + id = ".avrdx"; + desc = "AVR-Dx family common values"; + has_updi = yes; + nvm_base = 0x1000; + ocd_base = 0x0F80; - ; + memory "signature" + size = 3; + offset = 0x1100; + readsize = 0x3; + ; - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + memory "prodsig" + size = 0x7D; + offset = 0x1103; + page_size = 0x7D; + readsize = 0x7D; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + memory "tempsense" + size = 2; + offset = 0x1104; + readsize = 1; + ; - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + memory "sernum" + size = 16; + offset = 0x1110; + readsize = 1; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + memory "fuses" + size = 9; + offset = 0x1050; + page_size = 0x10; + readsize = 0x10; + ; - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + memory "fuse0" + size = 1; + offset = 0x1050; + readsize = 1; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x i i i i i"; - ; + memory "wdtcfg" + alias "fuse0"; + ; - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x o o"; + memory "fuse1" + size = 1; + offset = 0x1051; + readsize = 1; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 1 1 1 1 i i"; - ; + memory "bodcfg" + alias "fuse1"; + ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + memory "fuse2" + size = 1; + offset = 0x1052; + readsize = 1; + ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; -; + memory "osccfg" + alias "fuse2"; + ; -#------------------------------------------------------------ -# Common values for reduced core tinys (4/5/9/10/20/40) -#------------------------------------------------------------ + memory "fuse4" + size = 1; + offset = 0x1054; + readsize = 1; + ; -part - id = ".reduced_core_tiny"; - desc = "Common values for reduced core tinys"; - has_tpi = yes; + memory "tcd0cfg" + alias "fuse4"; + ; - memory "signature" - size = 3; - offset = 0x3fc0; - page_size = 16; + memory "fuse5" + size = 1; + offset = 0x1055; + readsize = 1; ; - memory "fuse" + memory "syscfg0" + alias "fuse5"; + ; + + memory "fuse6" size = 1; - offset = 0x3f40; - page_size = 16; - blocksize = 4; + offset = 0x1056; + readsize = 1; ; - memory "calibration" + memory "syscfg1" + alias "fuse6"; + ; + + memory "fuse7" size = 1; - offset = 0x3f80; - page_size = 16; + offset = 0x1057; + readsize = 1; ; - memory "lockbits" + memory "codesize" + alias "fuse7"; + ; + + memory "append" + alias "fuse7"; + ; + + memory "fuse8" size = 1; - offset = 0x3f00; - page_size = 16; + offset = 0x1058; + readsize = 1; ; -; -#------------------------------------------------------------ -# ATtiny4 -#------------------------------------------------------------ + memory "bootsize" + alias "fuse8"; + ; -part parent ".reduced_core_tiny" - id = "t4"; - desc = "ATtiny4"; - signature = 0x1e 0x8f 0x0a; + memory "bootend" + alias "fuse8"; + ; - memory "flash" - size = 512; - offset = 0x4000; - page_size = 16; - blocksize = 128; + memory "lock" + size = 4; + offset = 0x1040; + page_size = 0x1; + readsize = 0x4; ; -; -#------------------------------------------------------------ -# ATtiny5 -#------------------------------------------------------------ + memory "userrow" + size = 0x20; + offset = 0x1080; + page_size = 0x20; + readsize = 0x20; + ; -part parent "t4" - id = "t5"; - desc = "ATtiny5"; - signature = 0x1e 0x8f 0x09; + memory "usersig" + alias "userrow"; + ; + + memory "data" + # SRAM, only used to supply the offset + offset = 0x1000000; + ; ; #------------------------------------------------------------ -# ATtiny9 +# AVR32DA28 #------------------------------------------------------------ -part parent ".reduced_core_tiny" - id = "t9"; - desc = "ATtiny9"; - signature = 0x1e 0x90 0x08; +part parent ".avrdx" + id = "avr32da28"; + desc = "AVR32DA28"; + signature = 0x1E 0x95 0x34; memory "flash" - size = 1024; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; -; - -#------------------------------------------------------------ -# ATtiny10 -#------------------------------------------------------------ -part parent "t9" - id = "t10"; - desc = "ATtiny10"; - signature = 0x1e 0x90 0x03; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; + ; ; #------------------------------------------------------------ -# ATtiny20 +# AVR32DA32 #------------------------------------------------------------ -part parent ".reduced_core_tiny" - id = "t20"; - desc = "ATtiny20"; - signature = 0x1e 0x91 0x0F; +part parent ".avrdx" + id = "avr32da32"; + desc = "AVR32DA32"; + signature = 0x1E 0x95 0x33; memory "flash" - size = 2048; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny40 +# AVR32DA48 #------------------------------------------------------------ -part parent ".reduced_core_tiny" - id = "t40"; - desc = "ATtiny40"; - signature = 0x1e 0x92 0x0E; +part parent ".avrdx" + id = "avr32da48"; + desc = "AVR32DA48"; + signature = 0x1E 0x95 0x32; memory "flash" - size = 4096; - offset = 0x4000; - page_size = 64; - blocksize = 128; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega406 +# AVR64DA28 #------------------------------------------------------------ -part - id = "m406"; - desc = "ATMEGA406"; - has_jtag = yes; - signature = 0x1e 0x95 0x07; - - # STK500 parameters (parallel programming IO lines) - pagel = 0xa7; - bs2 = 0xa0; - serial = no; - parallel = yes; - - # STK500v2 HV programming parameters, from XML - pp_controlstack = 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; +part parent ".avrdx" + id = "avr64da28"; + desc = "AVR64DA28"; + signature = 0x1E 0x96 0x15; - # JTAG ICE mkII parameters, also from XML files - allowfullpagebitstream = no; - enablepageprogramming = yes; - idr = 0x51; - rampz = 0x00; - spmcr = 0x57; - eecr = 0x3f; + memory "flash" + size = 0x10000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; memory "eeprom" - paged = no; - size = 512; - page_size = 4; - blocksize = 4; - readsize = 4; - num_pages = 128; + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; +; + +#------------------------------------------------------------ +# AVR64DA32 +#------------------------------------------------------------ + +part parent ".avrdx" + id = "avr64da32"; + desc = "AVR64DA32"; + signature = 0x1E 0x96 0x14; memory "flash" - paged = yes; - size = 40960; - page_size = 128; - blocksize = 128; - readsize = 128; - num_pages = 320; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "hfuse" - size = 1; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; +; - memory "lfuse" - size = 1; - ; +#------------------------------------------------------------ +# AVR64DA48 +#------------------------------------------------------------ - memory "lockbits" - size = 1; +part parent ".avrdx" + id = "avr64da48"; + desc = "AVR64DA48"; + signature = 0x1E 0x96 0x13; + + memory "flash" + size = 0x10000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "signature" - size = 3; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# AVR8X family common values +# AVR64DA64 #------------------------------------------------------------ -part - id = ".avr8x"; - desc = "AVR8X family common values"; - has_updi = yes; - nvm_base = 0x1000; - ocd_base = 0x0F80; +part parent ".avrdx" + id = "avr64da64"; + desc = "AVR64DA64"; + signature = 0x1E 0x96 0x12; - memory "signature" - size = 3; - offset = 0x1100; + memory "flash" + size = 0x10000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "prodsig" - size = 0x3D; - offset = 0x1103; - page_size = 0x3D; - readsize = 0x3D; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; +; - memory "fuses" - size = 9; - offset = 0x1280; - ; +#------------------------------------------------------------ +# AVR128DA28 +#------------------------------------------------------------ - memory "fuse0" - size = 1; - offset = 0x1280; - ; +part parent ".avrdx" + id = "avr128da28"; + desc = "AVR128DA28"; + signature = 0x1E 0x97 0x0A; - memory "fuse1" - size = 1; - offset = 0x1281; + memory "flash" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "fuse2" - size = 1; - offset = 0x1282; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; +; - memory "fuse4" - size = 1; - offset = 0x1284; - ; +#------------------------------------------------------------ +# AVR128DA32 +#------------------------------------------------------------ - memory "fuse5" - size = 1; - offset = 0x1285; - ; +part parent ".avrdx" + id = "avr128da32"; + desc = "AVR128DA32"; + signature = 0x1E 0x97 0x09; - memory "fuse6" - size = 1; - offset = 0x1286; + memory "flash" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "fuse7" - size = 1; - offset = 0x1287; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; +; - memory "fuse8" - size = 1; - offset = 0x1288; - ; +#------------------------------------------------------------ +# AVR128DA48 +#------------------------------------------------------------ - memory "lock" - size = 1; - offset = 0x128a; +part parent ".avrdx" + id = "avr128da48"; + desc = "AVR128DA48"; + signature = 0x1E 0x97 0x08; + + memory "flash" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; ; - memory "data" - # SRAM, only used to supply the offset - offset = 0x1000000; + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# AVR8X tiny family common values +# AVR128DA64 #------------------------------------------------------------ -part parent ".avr8x" - id = ".avr8x_tiny"; - desc = "AVR8X tiny family common values"; - family_id = "tinyAVR"; +part parent ".avrdx" + id = "avr128da64"; + desc = "AVR128DA64"; + signature = 0x1E 0x97 0x07; - memory "usersig" - size = 0x20; - offset = 0x1300; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x20000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# AVR8X mega family common values +# AVR32DB28 #------------------------------------------------------------ -part parent ".avr8x" - id = ".avr8x_mega"; - desc = "AVR8X mega family common values"; - family_id = "megaAVR"; +part parent ".avrdx" + id = "avr32db28"; + desc = "AVR32DB28"; + signature = 0x1E 0x95 0x37; - memory "usersig" - size = 0x40; - offset = 0x1300; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + offset = 0x800000; + page_size = 0x200; + readsize = 0x100; + ; + + memory "eeprom" + size = 0x200; + offset = 0x1400; + page_size = 0x1; + readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny202 +# AVR32DB32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t202"; - desc = "ATtiny202"; - signature = 0x1E 0x91 0x23; +part parent ".avrdx" + id = "avr32db32"; + desc = "AVR32DB32"; + signature = 0x1E 0x95 0x36; memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x40; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny204 +# AVR32DB48 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t204"; - desc = "ATtiny204"; - signature = 0x1E 0x91 0x22; +part parent ".avrdx" + id = "avr32db48"; + desc = "AVR32DB48"; + signature = 0x1E 0x95 0x35; memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x40; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny402 +# AVR64DB28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t402"; - desc = "ATtiny402"; - signature = 0x1E 0x92 0x23; +part parent ".avrdx" + id = "avr64db28"; + desc = "AVR64DB28"; + signature = 0x1E 0x96 0x19; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny404 +# AVR64DB32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t404"; - desc = "ATtiny404"; - signature = 0x1E 0x92 0x26; +part parent ".avrdx" + id = "avr64db32"; + desc = "AVR64DB32"; + signature = 0x1E 0x96 0x18; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny406 +# AVR64DB48 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t406"; - desc = "ATtiny406"; - signature = 0x1E 0x92 0x25; +part parent ".avrdx" + id = "avr64db48"; + desc = "AVR64DB48"; + signature = 0x1E 0x96 0x17; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny804 +# AVR64DB64 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t804"; - desc = "ATtiny804"; - signature = 0x1E 0x93 0x25; +part parent ".avrdx" + id = "avr64db64"; + desc = "AVR64DB64"; + signature = 0x1E 0x96 0x16; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny806 +# AVR128DB28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t806"; - desc = "ATtiny806"; - signature = 0x1E 0x93 0x24; +part parent ".avrdx" + id = "avr128db28"; + desc = "AVR128DB28"; + signature = 0x1E 0x97 0x0E; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x20000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny807 +# AVR128DB32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t807"; - desc = "ATtiny807"; - signature = 0x1E 0x93 0x23; +part parent ".avrdx" + id = "avr128db32"; + desc = "AVR128DB32"; + signature = 0x1E 0x97 0x0D; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x20000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1604 +# AVR128DB48 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1604"; - desc = "ATtiny1604"; - signature = 0x1E 0x94 0x25; +part parent ".avrdx" + id = "avr128db48"; + desc = "AVR128DB48"; + signature = 0x1E 0x97 0x0C; memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; + size = 0x20000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1606 +# AVR128DB64 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1606"; - desc = "ATtiny1606"; - signature = 0x1E 0x94 0x24; +part parent ".avrdx" + id = "avr128db64"; + desc = "AVR128DB64"; + signature = 0x1E 0x97 0x0B; memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; + size = 0x20000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1607 +# AVR16DD14 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1607"; - desc = "ATtiny1607"; - signature = 0x1E 0x94 0x23; +part parent ".avrdx" + id = "avr16dd14"; + desc = "AVR16DD14"; + signature = 0x1E 0x94 0x34; memory "flash" size = 0x4000; - offset = 0x8000; - page_size = 0x40; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny212 +# AVR16DD20 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t212"; - desc = "ATtiny212"; - signature = 0x1E 0x91 0x21; +part parent ".avrdx" + id = "avr16dd20"; + desc = "AVR16DD20"; + signature = 0x1E 0x94 0x33; memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; + size = 0x4000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x40; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny214 +# AVR16DD28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t214"; - desc = "ATtiny214"; - signature = 0x1E 0x91 0x20; +part parent ".avrdx" + id = "avr16dd28"; + desc = "AVR16DD28"; + signature = 0x1E 0x94 0x32; memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; + size = 0x4000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x40; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny412 +# AVR16DD32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t412"; - desc = "ATtiny412"; - signature = 0x1E 0x92 0x23; +part parent ".avrdx" + id = "avr16dd32"; + desc = "AVR16DD32"; + signature = 0x1E 0x94 0x31; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x4000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; - #------------------------------------------------------------ -# ATtiny414 +# AVR32DD14 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t414"; - desc = "ATtiny414"; - signature = 0x1E 0x92 0x22; +part parent ".avrdx" + id = "avr32dd14"; + desc = "AVR32DD14"; + signature = 0x1E 0x95 0x3B; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny416 +# AVR32DD20 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t416"; - desc = "ATtiny416"; - signature = 0x1E 0x92 0x21; +part parent ".avrdx" + id = "avr32dd20"; + desc = "AVR32DD20"; + signature = 0x1E 0x95 0x3A; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; - #------------------------------------------------------------ -# ATtiny417 +# AVR32DD28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t417"; - desc = "ATtiny417"; - signature = 0x1E 0x92 0x20; +part parent ".avrdx" + id = "avr32dd28"; + desc = "AVR32DD28"; + signature = 0x1E 0x95 0x39; memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; - #------------------------------------------------------------ -# ATtiny814 +# AVR32DD32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t814"; - desc = "ATtiny814"; - signature = 0x1E 0x93 0x22; +part parent ".avrdx" + id = "avr32dd32"; + desc = "AVR32DD32"; + signature = 0x1E 0x95 0x38; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x8000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; - #------------------------------------------------------------ -# ATtiny816 +# AVR64DD14 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t816"; - desc = "ATtiny816"; - signature = 0x1E 0x93 0x21; +part parent ".avrdx" + id = "avr64dd14"; + desc = "AVR64DD14"; + signature = 0x1E 0x96 0x1D; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny817 +# AVR64DD20 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t817"; - desc = "ATtiny817"; - signature = 0x1E 0x93 0x20; +part parent ".avrdx" + id = "avr64dd20"; + desc = "AVR64DD20"; + signature = 0x1E 0x96 0x1C; memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" - size = 0x80; + size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1614 +# AVR64DD28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1614"; - desc = "ATtiny1614"; - signature = 0x1E 0x94 0x22; +part parent ".avrdx" + id = "avr64dd28"; + desc = "AVR64DD28"; + signature = 0x1E 0x96 0x1B; memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1616 +# AVR64DD32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1616"; - desc = "ATtiny1616"; - signature = 0x1E 0x94 0x21; +part parent ".avrdx" + id = "avr64dd32"; + desc = "AVR64DD32"; + signature = 0x1E 0x96 0x1A; memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; + size = 0x10000; + offset = 0x800000; + page_size = 0x200; readsize = 0x100; ; memory "eeprom" size = 0x100; offset = 0x1400; - page_size = 0x20; + page_size = 0x1; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny1617 +# AVR-Ex family common values #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1617"; - desc = "ATtiny1617"; - signature = 0x1E 0x94 0x20; +part parent ".avrdx" + id = ".avrex"; + desc = "AVR-Ex family common values"; - memory "flash" - size = 0x4000; - offset = 0x8000; + memory "userrow" + size = 0x40; + offset = 0x1080; page_size = 0x40; - readsize = 0x100; + readsize = 0x40; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "usersig" + alias "userrow"; ; ; #------------------------------------------------------------ -# ATtiny3214 +# AVR8EA28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3214"; - desc = "ATtiny3214"; - signature = 0x1E 0x95 0x20; +part parent ".avrex" + id = "avr8ea28"; + desc = "AVR8EA28"; + signature = 0x1E 0x93 0x2C; memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; + size = 0x2000; + offset = 0x800000; + page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny3216 +# AVR8EA32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3216"; - desc = "ATtiny3216"; - signature = 0x1E 0x95 0x21; +part parent ".avrex" + id = "avr8ea32"; + desc = "AVR8EA32"; + signature = 0x1E 0x93 0x2B; memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; + size = 0x2000; + offset = 0x800000; + page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATtiny3217 +# AVR16EA28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3217"; - desc = "ATtiny3217"; - signature = 0x1E 0x95 0x22; +part parent ".avrex" + id = "avr16ea28"; + desc = "AVR16EA28"; + signature = 0x1E 0x94 0x37; memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; + size = 0x4000; + offset = 0x800000; + page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega808 +# AVR16EA32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m808"; - desc = "ATmega808"; - signature = 0x1E 0x93 0x26; +part parent ".avrex" + id = "avr16ea32"; + desc = "AVR16EA32"; + signature = 0x1E 0x94 0x36; memory "flash" - size = 0x2000; - offset = 0x4000; + size = 0x4000; + offset = 0x800000; page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega809 +# AVR16EA48 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m809"; - desc = "ATmega809"; - signature = 0x1E 0x93 0x2A; +part parent ".avrex" + id = "avr16ea48"; + desc = "AVR16EA48"; + signature = 0x1E 0x94 0x35; memory "flash" - size = 0x2000; - offset = 0x4000; + size = 0x4000; + offset = 0x800000; page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega1608 +# AVR32EA28 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m1608"; - desc = "ATmega1608"; - signature = 0x1E 0x94 0x27; +part parent ".avrex" + id = "avr32ea28"; + desc = "AVR32EA28"; + signature = 0x1E 0x95 0x3E; memory "flash" - size = 0x4000; - offset = 0x4000; + size = 0x8000; + offset = 0x800000; page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega1609 +# AVR32EA32 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m1609"; - desc = "ATmega1609"; - signature = 0x1E 0x94 0x26; +part parent ".avrex" + id = "avr32ea32"; + desc = "AVR32EA32"; + signature = 0x1E 0x95 0x3D; memory "flash" - size = 0x4000; - offset = 0x4000; + size = 0x8000; + offset = 0x800000; page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x20; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega3208 +# AVR32EA48 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m3208"; - desc = "ATmega3208"; - signature = 0x1E 0x95 0x30; +part parent ".avrex" + id = "avr32ea48"; + desc = "AVR32EA48"; + signature = 0x1E 0x95 0x3C; memory "flash" size = 0x8000; - offset = 0x4000; - page_size = 0x80; + offset = 0x800000; + page_size = 0x40; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega3209 +# AVR64EA28 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m3209"; - desc = "ATmega3209"; - signature = 0x1E 0x95 0x31; +part parent ".avrex" + id = "avr64ea28"; + desc = "AVR64EA28"; + signature = 0x1E 0x96 0x20; memory "flash" - size = 0x8000; - offset = 0x4000; + size = 0x10000; + offset = 0x800000; page_size = 0x80; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega4808 +# AVR64EA32 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m4808"; - desc = "ATmega4808"; - signature = 0x1E 0x96 0x50; +part parent ".avrex" + id = "avr64ea32"; + desc = "AVR64EA32"; + signature = 0x1E 0x96 0x1F; memory "flash" - size = 0xC000; - offset = 0x4000; + size = 0x10000; + offset = 0x800000; page_size = 0x80; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; #------------------------------------------------------------ -# ATmega4809 +# AVR64EA48 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m4809"; - desc = "ATmega4809"; - signature = 0x1E 0x96 0x51; +part parent ".avrex" + id = "avr64ea48"; + desc = "AVR64EA48"; + signature = 0x1E 0x96 0x1E; memory "flash" - size = 0xC000; - offset = 0x4000; + size = 0x10000; + offset = 0x800000; page_size = 0x80; readsize = 0x100; ; memory "eeprom" - size = 0x100; + size = 0x200; offset = 0x1400; - page_size = 0x40; + page_size = 0x8; readsize = 0x100; ; ; + +#------------------------------------------------------------ +# Logic Green parts +#------------------------------------------------------------ + +part parent "m88" + id = "lgt8f88p"; + desc = "LGT8F88P"; + signature = 0x1e 0x93 0x0f; + + ocdrev = 1; + ; + +part parent "m168" + id = "lgt8f168p"; + desc = "LGT8F168P"; + signature = 0x1e 0x94 0x0b; + + ocdrev = 1; +; + +part parent "m328" + id = "lgt8f328p"; + desc = "LGT8F328P"; + signature = 0x1e 0x95 0x0F; + + ocdrev = 1; +; diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index beb2180..4b7c8ef 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -5,10 +5,40 @@ medbg.program.protocol=xplainedmini_updi medbg.program.tool=avrdude medbg.program.extra_params=-Pusb +serialupdi_57600.name=SerialUPDI (57600 baud) +serialupdi_57600.communication=serial +serialupdi_57600.protocol=serialupdi +serialupdi_57600.program.tool=avrdude +serialupdi_57600.program.extra_params=-P{serial.port} -b57600 -xrtsdtr=high + +serialupdi_115200.name=SerialUPDI (115200 baud) +serialupdi_115200.communication=serial +serialupdi_115200.protocol=serialupdi +serialupdi_115200.program.tool=avrdude +serialupdi_115200.program.extra_params=-P{serial.port} -b115200 -xrtsdtr=high + +serialupdi_230400.name=SerialUPDI (230400 baud) +serialupdi_230400.communication=serial +serialupdi_230400.protocol=serialupdi +serialupdi_230400.program.tool=avrdude +serialupdi_230400.program.extra_params=-P{serial.port} -b230400 -xrtsdtr=high + +serialupdi_460800.name=SerialUPDI (460800 baud) +serialupdi_460800.communication=serial +serialupdi_460800.protocol=serialupdi +serialupdi_460800.program.tool=avrdude +serialupdi_460800.program.extra_params=-P{serial.port} -b460800 -xrtsdtr=high + +jtag2updi.name=JTAG2UPDI +jtag2updi.communication=serial +jtag2updi.protocol=jtag2updi +jtag2updi.program.tool=avrdude +jtag2updi.program.extra_params=-P{serial.port} + nedbg.name=Atmel nEDBG/Curiosity Nano nedbg.communication=usb -nedbg.protocol=curiosity_updi -nedbg.program.protocol=curiosity_updi +nedbg.protocol=pkobn_updi +nedbg.program.protocol=pkobn_updi nedbg.program.tool=avrdude nedbg.program.extra_params=-Pusb @@ -19,12 +49,6 @@ edbg.program.protocol=xplainedpro_updi edbg.program.tool=avrdude edbg.program.extra_params=-Pusb -jtag2updi.name=JTAG2UPDI -jtag2updi.communication=serial -jtag2updi.protocol=jtag2updi -jtag2updi.program.tool=avrdude -jtag2updi.program.extra_params=-P{serial.port} - atmelice_updi.name=Atmel-ICE (UPDI) atmelice_updi.communication=usb atmelice_updi.protocol=atmelice_updi From 6824101e84b4e7e993caa94eed29dac7a118537b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 12 Jun 2022 20:17:20 +0200 Subject: [PATCH 300/351] Fix incorrect Nano 4808 analog pin macro Closes #151 --- megaavr/variants/nano-4808/pins_arduino.h | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index 0636e5a..43ae94a 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -74,8 +74,14 @@ #define ANALOG_INPUT_OFFSET 14 #define LED_BUILTIN PIN_PC2 #define EXTERNAL_NUM_INTERRUPTS 47 -#define digitalPinToAnalogInput(p) (((p) < 8) ? (p) : ((p) >= 14 && (p) >= 25) ? (p) : NOT_A_PIN) -#define digitalOrAnalogPinToDigital(p) (((p) <= 40) ? (p) : NOT_A_PIN) +#define digitalOrAnalogPinToDigital(p) (((p) <= 26) ? (p) : NOT_A_PIN) +#define digitalPinToAnalogInput(p) (((p) <= 3) ? (p) : \ + ((p) <= 7) ? ((p) + 8) : \ + ((p) <= 11) ? ((p) - 4) : \ + ((p) >= 14 && (p) <= 17) ? ((p) - 14) : \ + ((p) >= 22 && (p) <= 25) ? ((p) - 18) : \ + ((p) >= 18 && (p) <= 21) ? ((p) - 6) : NOT_A_PIN) + // Timer to use for millis/micros #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) From b96b810b0951a8de754290bbadb5936dd8d28d69 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 15 Jun 2022 20:37:17 +0200 Subject: [PATCH 301/351] Add extra namespace to Comparator constants #150 related --- megaavr/libraries/Comparator/README.md | 84 +++++++------- .../examples/Hysteresis/Hysteresis.ino | 8 +- .../Internal_reference/Internal_reference.ino | 12 +- .../examples/Interrupt/Interrupt.ino | 12 +- .../Simple_comparator/Simple_comparator.ino | 6 +- megaavr/libraries/Comparator/keywords.txt | 1 + .../libraries/Comparator/library.properties | 2 +- .../libraries/Comparator/src/Comparator.cpp | 16 +-- megaavr/libraries/Comparator/src/Comparator.h | 106 ++++++++++-------- 9 files changed, 129 insertions(+), 118 deletions(-) diff --git a/megaavr/libraries/Comparator/README.md b/megaavr/libraries/Comparator/README.md index 0de4494..4947834 100644 --- a/megaavr/libraries/Comparator/README.md +++ b/megaavr/libraries/Comparator/README.md @@ -1,6 +1,6 @@ # Comparator -A library for interfacing with the analog comparator peripheral in the megaAVR-0 series MCUs. -Developed by [MCUdude](https://github.com/MCUdude/). +A library for interfacing with the analog comparator peripheral in the megaAVR-0 series MCUs. +Developed by [MCUdude](https://github.com/MCUdude/). The megaAVR-0 has one comparator where four positive and three negative pins are available for use. An alternative for the negative pin is to use an internally generated reference voltage instead. More useful information about the analog comparator can be found in the [Microchip Application Note TB3211](http://ww1.microchip.com/downloads/en/AppNotes/TB3211-Getting-Started-with-AC-90003211A.pdf) and in the [megaAVR-0 family data sheet](http://ww1.microchip.com/downloads/en/DeviceDoc/megaAVR0-series-Family-Data-Sheet-DS40002015B.pdf). @@ -10,69 +10,69 @@ Class for interfacing with the built-in comparator. Use the predefined objects ` ### input_p -Variable for setting what input pin the positive input of the comparator should be connected to +Variable for setting what input pin the positive input of the comparator should be connected to Accepted values: ``` c++ -in_p::in0; // Use positive input pin 0 (PD2) as input -in_p::in1; // Use positive input pin 1 (PD4) as input -in_p::in2; // Use positive input pin 2 (PD6) as input -in_p::in3; // Use positive input pin 3 (PD1) as input +comparator::in_p::in0; // Use positive input pin 0 (PD2) as input +comparator::in_p::in1; // Use positive input pin 1 (PD4) as input +comparator::in_p::in2; // Use positive input pin 2 (PD6) as input +comparator::in_p::in3; // Use positive input pin 3 (PD1) as input ``` ##### Usage ``` c++ -Comparator.input_p = in_p::in0; // Connect positive input pin 0 to the positive pin of the comparator +Comparator.input_p = comparator::in_p::in0; // Connect positive input pin 0 to the positive pin of the comparator ``` ##### Default state -`Comparator.input_p` defaults to `in_p::in0` if not specified in the user program. +`Comparator.input_p` defaults to `comparator::in_p::in0` if not specified in the user program. ### input_n -Variable for setting what input pin the negative input of the comparator should be connected to +Variable for setting what input pin the negative input of the comparator should be connected to Accepted values: ``` c++ -in_n::in0; // Use positive input pin 0 (PD3) as input -in_n::in1; // Use positive input pin 1 (PD5) as input -in_n::in2; // Use positive input pin 2 (PD7) as input -in_n::dacref; // Use DACREF as input +comparator::in_n::in0; // Use positive input pin 0 (PD3) as input +comparator::in_n::in1; // Use positive input pin 1 (PD5) as input +comparator::in_n::in2; // Use positive input pin 2 (PD7) as input +comparator::in_n::dacref; // Use DACREF as input ``` ##### Usage ``` c++ -Comparator.input_n = in_n::in0; // Connect negative input pin 0 to the negative pin of the comparator +Comparator.input_n = comparator::in_n::in0; // Connect negative input pin 0 to the negative pin of the comparator ``` ##### Default state -`Comparator.input_n` defaults to `in_n::in0` if not specified in the user program. +`Comparator.input_n` defaults to `comparator::in_n::in0` if not specified in the user program. ### reference -Variable for setting what reference voltage the DACREF should be derived from. This voltage is internally generated. +Variable for setting what reference voltage the DACREF should be derived from. This voltage is internally generated. Accepted values: ``` c++ -ref::disable; // Do not use any reference -ref::vref_0v55; // 0.55V internal voltage -ref::vref_1v1; // 1.1V internal voltage -ref::vref_1v5; // 1.5V internal voltage -ref::vref_2v5; // 2.5V internal voltage -ref::vref_4v3; // 4.3V internal voltage -ref::vref_avcc; // Use voltage on AVCC pin +comparator::ref::disable; // Do not use any reference +comparator::ref::vref_0v55; // 0.55V internal voltage +comparator::ref::vref_1v1; // 1.1V internal voltage +comparator::ref::vref_1v5; // 1.5V internal voltage +comparator::ref::vref_2v5; // 2.5V internal voltage +comparator::ref::vref_4v3; // 4.3V internal voltage +comparator::ref::vref_avcc; // Use voltage on AVCC pin ``` ##### Usage ``` c++ -Comparator.reference = ref::vref_2v5; // Use the internal 2.5V reference for the DACREF +Comparator.reference = comparator::ref::vref_2v5; // Use the internal 2.5V reference for the DACREF ``` ##### Default state -`Comparator.reference` defaults to `ref::disable` if not specified in the user program. +`Comparator.reference` defaults to `comparator::ref::disable` if not specified in the user program. ### dacref -Variable for setting the DACREF value. This voltage can be selected as the input for the negative side of the comparator. -This is the formula for the DACREF output voltage: - +Variable for setting the DACREF value. This voltage can be selected as the input for the negative side of the comparator. +This is the formula for the DACREF output voltage: + ##### Usage @@ -88,39 +88,39 @@ Comparator.dacref = 127; // Divide the reference voltage by two Variable for setting the comparator input hysteresis. Useful for eliminating "bouncing". Accepted values: ``` c++ -hyst::disable; // No hysteresis -hyst::small; // 10mV hysteresis (±5mV) -hyst::medium; // 25mV hysteresis (±12.5mV) -hyst::large; // 50mV hysteresis (±25mV) +comparator::hyst::disable; // No hysteresis +comparator::hyst::small; // 10mV hysteresis (±5mV) +comparator::hyst::medium; // 25mV hysteresis (±12.5mV) +comparator::hyst::large; // 50mV hysteresis (±25mV) ``` ##### Usage ``` c++ -Comparator.hysteresis = hyst::large; // Use 50V hysteresis +Comparator.hysteresis = comparator::hyst::large; // Use 50V hysteresis ``` ##### Default state -`Comparator.hysteresis` defaults to `hyst::disable` if not specified in the user program. +`Comparator.hysteresis` defaults to `comparator::hyst::disable` if not specified in the user program. ### output Variable for setting the comparator output, internally and/or externally. Accepted values: ``` c++ -out::disable; // No output pin, signal not inverted internally -out::disable_invert; // No output pin, signal inverted internally -out::enable; // Enable output pin (PA7), signal not inverted internally -out::invert; // Enable output pin (PA7), signal inverted internally -out::enable_invert; // Identical to out::invert +comparator::out::disable; // No output pin, signal not inverted internally +comparator::out::disable_invert; // No output pin, signal inverted internally +comparator::out::enable; // Enable output pin (PA7), signal not inverted internally +comparator::out::invert; // Enable output pin (PA7), signal inverted internally +comparator::out::enable_invert; // Identical to out::invert ``` ##### Usage ``` c++ -Comparator.output = out::enable; // Enable output pin (PA7) +Comparator.output = comparator::out::enable; // Enable output pin (PA7) ``` ##### Default state -`Comparator.output` defaults to `out::disable` if not specified in the user program. +`Comparator.output` defaults to `comparator::out::disable` if not specified in the user program. ## init() diff --git a/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino b/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino index b2255e3..9fbb4d2 100644 --- a/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino +++ b/megaavr/libraries/Comparator/examples/Hysteresis/Hysteresis.ino @@ -20,10 +20,10 @@ void setup() { // Configure relevant comparator parameters - Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) - Comparator.input_n = in_n::in0; // Use negative input 0 (PD3) - Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis - Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + Comparator.input_p = comparator::in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = comparator::in_n::in0; // Use negative input 0 (PD3) + Comparator.hysteresis = comparator::hyst::large; // Use a 50mV hysteresis + Comparator.output = comparator::out::enable; // Enable output on digital pin 7 (PA7) // Initialize comparator Comparator.init(); diff --git a/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino b/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino index 65b13ef..1ff6485 100644 --- a/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino +++ b/megaavr/libraries/Comparator/examples/Internal_reference/Internal_reference.ino @@ -23,12 +23,12 @@ void setup() { // Configure relevant comparator parameters - Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) - Comparator.input_n = in_n::dacref; // Connect the negative pin to the DACREF voltage - Comparator.reference = ref::vref_2v5; // Set the DACREF voltage to 2.5V - Comparator.dacref = 127; // Gives us 1.24V -> (127 / 256) * 2.5V = 1.24V - Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis - Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + Comparator.input_p = comparator::in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = comparator::in_n::dacref; // Connect the negative pin to the DACREF voltage + Comparator.reference = comparator::ref::vref_2v5; // Set the DACREF voltage to 2.5V + Comparator.dacref = 127; // Gives us 1.24V -> (127 / 256) * 2.5V = 1.24V + Comparator.hysteresis = comparator::hyst::large; // Use a 50mV hysteresis + Comparator.output = comparator::out::enable; // Enable output on digital pin 7 (PA7) // Initialize comparator Comparator.init(); diff --git a/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino index ca8c890..2677f2d 100644 --- a/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Comparator/examples/Interrupt/Interrupt.ino @@ -28,12 +28,12 @@ void setup() Serial2.begin(9600); // Configure relevant comparator parameters - Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) - Comparator.input_n = in_n::dacref; // Connect the negative pin to the DACREF voltage - Comparator.reference = ref::vref_2v5; // Set the DACREF voltage to 2.5V - Comparator.dacref = 255; // Gives us 2.5V -> (255 / 256) * 2.5V = 2.5V - Comparator.hysteresis = hyst::large; // Use a 50mV hysteresis - Comparator.output = out::disable; // Use interrupt trigger instead of output pin + Comparator.input_p = comparator::in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = comparator::in_n::dacref; // Connect the negative pin to the DACREF voltage + Comparator.reference = comparator::ref::vref_2v5; // Set the DACREF voltage to 2.5V + Comparator.dacref = 255; // Gives us 2.5V -> (255 / 256) * 2.5V = 2.5V + Comparator.hysteresis = comparator::hyst::large; // Use a 50mV hysteresis + Comparator.output = comparator::out::disable; // Use interrupt trigger instead of output pin // Initialize comparator Comparator.init(); diff --git a/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino b/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino index 8fc2d85..29278eb 100644 --- a/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino +++ b/megaavr/libraries/Comparator/examples/Simple_comparator/Simple_comparator.ino @@ -19,9 +19,9 @@ void setup() { // Configure relevant comparator parameters - Comparator.input_p = in_p::in0; // Use positive input 0 (PD2) - Comparator.input_n = in_n::in0; // Use negative input 0 (PD3) - Comparator.output = out::enable; // Enable output on digital pin 7 (PA7) + Comparator.input_p = comparator::in_p::in0; // Use positive input 0 (PD2) + Comparator.input_n = comparator::in_n::in0; // Use negative input 0 (PD3) + Comparator.output = comparator::out::enable; // Enable output on digital pin 7 (PA7) // Initialize comparator Comparator.init(); diff --git a/megaavr/libraries/Comparator/keywords.txt b/megaavr/libraries/Comparator/keywords.txt index a8332fe..9f324e2 100644 --- a/megaavr/libraries/Comparator/keywords.txt +++ b/megaavr/libraries/Comparator/keywords.txt @@ -30,6 +30,7 @@ Comparator2 KEYWORD2 # Constants (LITERAL1) ####################################### +comparator LITERAL1 out LITERAL1 hyst LITERAL1 in_p LITERAL1 diff --git a/megaavr/libraries/Comparator/library.properties b/megaavr/libraries/Comparator/library.properties index 115b0a8..d06fc20 100644 --- a/megaavr/libraries/Comparator/library.properties +++ b/megaavr/libraries/Comparator/library.properties @@ -1,5 +1,5 @@ name=Comparator -version=1.0.0 +version=1.1.0 author=MCUdude maintainer=MCUdude sentence=A library for interfacing with the built-in analog comparator diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index c179de1..90796e8 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -21,7 +21,7 @@ AnalogComparator::AnalogComparator(const uint8_t comp_number, AC_t& ac) : compar void AnalogComparator::init() { // Set voltage reference - if(reference != ref::disable) + if(reference != comparator::ref::disable) { VREF.CTRLA = (VREF.CTRLA & ~VREF_AC0REFSEL_AVDD_gc) | reference; VREF.CTRLB = VREF_AC0REFEN_bm; @@ -36,19 +36,19 @@ void AnalogComparator::init() AC.CTRLA = (AC.CTRLA & ~AC_HYSMODE_gm) | hysteresis | (output & AC_OUTEN_bm); // Clear input pins - if(input_p == in_p::in0) + if(input_p == comparator::in_p::in0) PORTD.PIN2CTRL = PORT_ISC_INPUT_DISABLE_gc; - else if(input_p == in_p::in1) + else if(input_p == comparator::in_p::in1) PORTD.PIN4CTRL = PORT_ISC_INPUT_DISABLE_gc; - else if(input_p == in_p::in2) + else if(input_p == comparator::in_p::in2) PORTD.PIN6CTRL = PORT_ISC_INPUT_DISABLE_gc; - else if(input_p == in_p::in3) + else if(input_p == comparator::in_p::in3) PORTD.PIN1CTRL = PORT_ISC_INPUT_DISABLE_gc; - if(input_n == in_n::in0) + if(input_n == comparator::in_n::in0) PORTD.PIN3CTRL = PORT_ISC_INPUT_DISABLE_gc; - else if(input_n == in_n::in1) + else if(input_n == comparator::in_n::in1) PORTD.PIN5CTRL = PORT_ISC_INPUT_DISABLE_gc; - else if(input_n == in_n::in2) + else if(input_n == comparator::in_n::in2) PORTD.PIN7CTRL = PORT_ISC_INPUT_DISABLE_gc; // Set positive and negative pins, invert output if defined by the user diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 6b49165..956bff0 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -3,67 +3,77 @@ #include -namespace out +namespace comparator { - enum output_t : uint8_t + namespace out { - disable = 0x00, - disable_invert = 0x80, - enable = 0x40, - invert = 0xC0, - enable_invert = 0xC0, + enum output_t : uint8_t + { + disable = 0x00, + disable_invert = 0x80, + enable = 0x40, + invert = 0xC0, + enable_invert = 0xC0, + }; }; -}; -namespace hyst -{ - enum hysteresis_t : uint8_t + namespace hyst { - disable = 0x00, // No hysteresis - small = 0x02, // 10 mV - medium = 0x04, // 25 mV - large = 0x06, // 50 mV + enum hysteresis_t : uint8_t + { + disable = 0x00, // No hysteresis + small = 0x02, // 10 mV + medium = 0x04, // 25 mV + large = 0x06, // 50 mV + }; }; -}; -namespace in_p -{ - enum inputP_t : uint8_t + namespace in_p { - in0 = 0x00, - in1 = 0x01, - in2 = 0x02, - in3 = 0x03, + enum inputP_t : uint8_t + { + in0 = 0x00, + in1 = 0x01, + in2 = 0x02, + in3 = 0x03, + }; }; -}; -namespace in_n -{ - enum inputN_t : uint8_t + namespace in_n { - in0 = 0x00, - in1 = 0x01, - in2 = 0x02, - dacref = 0x03, + enum inputN_t : uint8_t + { + in0 = 0x00, + in1 = 0x01, + in2 = 0x02, + dacref = 0x03, + }; }; -}; -namespace ref -{ - enum reference_t : uint8_t + namespace ref { - vref_0v55 = 0x00, // 0.55V - vref_1v1 = 0x01, // 1.1V - vref_1v5 = 0x04, // 1.5V - vref_2v5 = 0x02, // 2.5V - vref_4v3 = 0x03, // 4.3V - vref_avcc = 0x07, // Vcc - disable = 0x08, + enum reference_t : uint8_t + { + vref_0v55 = 0x00, // 0.55V + vref_1v1 = 0x01, // 1.1V + vref_1v5 = 0x04, // 1.5V + vref_2v5 = 0x02, // 2.5V + vref_4v3 = 0x03, // 4.3V + vref_avcc = 0x07, // Vcc + disable = 0x08, + }; }; }; +// Legacy definitions +namespace out { using namespace comparator::out; }; +namespace hyst { using namespace comparator::hyst; }; +namespace in_p { using namespace comparator::in_p; }; +namespace in_n { using namespace comparator::in_n; }; +namespace ref { using namespace comparator::ref; }; + class AnalogComparator -{ +{ public: AnalogComparator(const uint8_t comparator_number, AC_t& ac); void init(); @@ -73,11 +83,11 @@ class AnalogComparator void attachInterrupt(voidFuncPtr callback, uint8_t mode); void detachInterrupt(); - out::output_t output = out::disable; - hyst::hysteresis_t hysteresis = hyst::disable; - in_p::inputP_t input_p = in_p::in0; - in_n::inputN_t input_n = in_n::in0; - ref::reference_t reference = ref::disable; + comparator::out::output_t output = comparator::out::disable; + comparator::hyst::hysteresis_t hysteresis = comparator::hyst::disable; + comparator::in_p::inputP_t input_p = comparator::in_p::in0; + comparator::in_n::inputN_t input_n = comparator::in_n::in0; + comparator::ref::reference_t reference = comparator::ref::disable; uint8_t dacref = 0xff; private: From bd556fb0da29ad51b8644658e2b7414ee1b3369c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 15 Jun 2022 20:37:35 +0200 Subject: [PATCH 302/351] Add extra namespace to Event constants #150 related --- megaavr/libraries/Event/README.md | 178 +- .../Read_event_settings.ino | 16 +- .../Route_logic_pins/Route_logic_pins.ino | 18 +- .../examples/Simple_event/Simple_event.ino | 6 +- megaavr/libraries/Event/keywords.txt | 1 + megaavr/libraries/Event/library.properties | 2 +- megaavr/libraries/Event/src/Event.cpp | 190 +- megaavr/libraries/Event/src/Event.h | 1581 +++++++++-------- 8 files changed, 1016 insertions(+), 976 deletions(-) diff --git a/megaavr/libraries/Event/README.md b/megaavr/libraries/Event/README.md index 4917f9e..a5a490f 100644 --- a/megaavr/libraries/Event/README.md +++ b/megaavr/libraries/Event/README.md @@ -35,8 +35,8 @@ Note that different channels have different functionality, so make sure you use In short terms: -* `genN::rtc_div8192`, `genN::rtc_div4096`, `genN::rtc_div2048` and `genN::rtc_div1024` are only available on odd numbered channels -* `genN::rtc_div512`, `genN::rtc_div256`, `genN::rtc_div128` and `genN::rtc_div64` are only available on even numbered channels +* `event::genN::rtc_div8192`, `event::genN::rtc_div4096`, `event::genN::rtc_div2048` and `event::genN::rtc_div1024` are only available on odd numbered channels +* `event::genN::rtc_div512`, `event::genN::rtc_div256`, `event::genN::rtc_div128` and `event::genN::rtc_div64` are only available on even numbered channels * PIN PA0..7 and PB0..5 can only be used as event generators on channel 0 and 1 * PIN PC0..7 and PD0..7 can only be used as event generators on channel 2 and 3 * PIN PE0..3 and PF0..6 can only be used as event generators on channel 4 and 5 @@ -84,18 +84,18 @@ Returns a reference to the `Event_empty` object if the generator is not connecte ### Declaration ``` c++ -static Event& get_generator_channel(gen::generator_t generator); // For all other generators (gen, gen0...gen7) -static Event& get_generator_channel(uint8_t generator); // For Arduino pins +static Event& get_generator_channel(event::gen::generator_t generator); // For all other generators (event::gen, event::gen0...gen7) +static Event& get_generator_channel(uint8_t generator); // For Arduino pins ``` ### Usage ```c++ // Set ccl0_out as event generator for channel 2 -Event2.set_generator(gen::ccl0_out); +Event2.set_generator(event::gen::ccl0_out); // Now we want to get the channel/object connected to the ccl0_out generator // Create a reference to the object get_generator_channel() returns. -Event& myEvent = Event::get_generator_channel(gen::ccl0_out); +Event& myEvent = Event::get_generator_channel(event::gen::ccl0_out); // myEvent is now a reference to Event2! ``` @@ -112,73 +112,73 @@ uint8_t get_generator(); ### Usage ```c++ uint8_t generator_used = Event0.get_generator(); -if(generator_used == gen::ccl0_out) { - Serial.println("We're using gen::ccl0_out as generator"); +if(generator_used == event::gen::ccl0_out) { + Serial.println("We're using event::gen::ccl0_out as generator"); } ``` -## set_generator(gen::generator_t) -Function to connect an event generator to a channel. Note that we use the prefix genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use gen:: when referring to generators available on all generators. +## set_generator(event::gen::generator_t) +Function to connect an event generator to a channel. Note that we use the prefix event::genN:: (where N is the channel number) when referring to generators unique to this particular channel. we use event::gen:: when referring to generators available on all generators. ### Declaration ``` c++ -void set_generator(gen::generator_t generator); -void set_generator(gen0::generator_t generator); +void set_generator(event::gen::generator_t generator); +void set_generator(event::gen0::generator_t generator); //... -void set_generator(gen7::generator_t generator); +void set_generator(event::gen7::generator_t generator); ``` ### Usage ```c++ -Event0.set_generator(gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 -Event2.set_generator(gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 +Event0.set_generator(event::gen::ccl0_out); // Use the output of logic block 0 (CCL0) as an event generator for Event0 +Event2.set_generator(event::gen2::pin_pc0); // Use pin PC0 as an event generator for Event2 ``` ### Generator table Below is a table with all possible generators for each channel. -| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | -|----------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|-----------------------------------------------------|------------------------------------------------------|------------------------------------------------------|---------------------|--------------------| -| `gen::disable` | `gen0::disable` | `gen1::disable` | `gen2::disable` | `gen3::disable` | `gen4::disable` | `gen5::disable` | `gen6::disable` | `gen7::disable` | -| `gen::updi_synch` | `gen0::rtc_div8192` | `gen1::rtc_div512` | `gen2::rtc_div8192` | `gen3::rtc_div512` | `gen4::rtc_div8192` | `gen5::rtc_div512` | `gen6::rtc_div8192` | `gen7::rtc_div512` | -| `gen::rtc_ovf` | `gen0::rtc_div4096` | `gen1::rtc_div256` | `gen2::rtc_div4096` | `gen3::rtc_div256` | `gen4::rtc_div4096` | `gen5::rtc_div256` | `gen6::rtc_div4096` | `gen7::rtc_div256` | -| `gen::rtc_cmp` | `gen0::rtc_div2048` | `gen1::rtc_div128` | `gen2::rtc_div2048` | `gen3::rtc_div128` | `gen4::rtc_div2048` | `gen5::rtc_div128` | `gen6::rtc_div2048` | `gen7::rtc_div128` | -| `gen::ccl0_out` | `gen0::rtc_div1024` | `gen1::rtc_div64` | `gen2::rtc_div1024` | `gen3::rtc_div64` | `gen4::rtc_div1024` | `gen5::rtc_div64` | `gen6::rtc_div1024` | `gen7::rtc_div64` | -| `gen::ccl1_out` | `gen0::pin_pa0` | `gen1::pin_pa0` | `gen2::pin_pc0` | `gen3::pin_pc0` | `gen4::pin_pe0`
(Only available on ATmegaX809) | `gen5::pin_pe0`
(Only available on ATmegaX809) | | | -| `gen::ccl2_out` | `gen0::pin_pa1` | `gen1::pin_pa1` | `gen2::pin_pc1` | `gen3::pin_pc1` | `gen4::pin_pe1`
(Only available on ATmegaX809) | `gen5::pin_pe1`
(Only available on ATmegaX809) | | | -| `gen::ccl3_out` | `gen0::pin_pa2` | `gen1::pin_pa2` | `gen2::pin_pc2` | `gen3::pin_pc2` | `gen4::pin_pe2`
(Only available on ATmegaX809) | `gen5::pin_pe2`
(Only available on ATmegaX809) | | | -| `gen::ac0_out` | `gen0::pin_pa3` | `gen1::pin_pa3` | `gen2::pin_pc3` | `gen3::pin_pc3` | `gen4::pin_pe3`
(Only available on ATmegaX809) | `gen5::pin_pe3`
(Only available on ATmegaX809) | | | -| `gen::adc0_ready` | `gen0::pin_pa4` | `gen1::pin_pa4` | `gen2::pin_pc4`
(Only available on ATmegaX809) | `gen3::pin_pc4`
(Only available on ATmegaX809) | | | | | -| `gen::usart0_xck` | `gen0::pin_pa5` | `gen1::pin_pa5` | `gen2::pin_pc5`
(Only available on ATmegaX809) | `gen3::pin_pc5`
(Only available on ATmegaX809) | | | | | -| `gen::usart1_xck` | `gen0::pin_pa6` | `gen1::pin_pa6` | `gen2::pin_pc6`
(Only available on ATmegaX809) | `gen3::pin_pc6`
(Only available on ATmegaX809) | | | | | -| `gen::usart2_xck` | `gen0::pin_pa7` | `gen1::pin_pa7` | `gen2::pin_pc7`
(Only available on ATmegaX809) | `gen3::pin_pc7`
(Only available on ATmegaX809) | | | | | -| `gen::usart3_xck` | `gen0::pin_pb0`
(Only available on ATmegaX809) | `gen1::pin_pb0`
(Only available on ATmegaX809) | `gen2::pin_pd0` | `gen3::pin_pd0` | `gen4::pin_pf0` | `gen5::pin_pf0` | | | -| `gen::spi0_sck` | `gen0::pin_pb1`
(Only available on ATmegaX809) | `gen1::pin_pb1`
(Only available on ATmegaX809) | `gen2::pin_pd1` | `gen3::pin_pd1` | `gen4::pin_pf1` | `gen5::pin_pf1` | | | -| `gen::tca0_ovf_lunf` | `gen0::pin_pb2`
(Only available on ATmegaX809) | `gen1::pin_pb2`
(Only available on ATmegaX809) | `gen2::pin_pd2` | `gen3::pin_pd2` | `gen4::pin_pf2`
(Not available on 28-pin parts) | `gen5::pin_pf2`
(Not available on 28-pin parts) | | | -| `gen::tca0_hunf` | `gen0::pin_pb3`
(Only available on ATmegaX809) | `gen1::pin_pb3`
(Only available on ATmegaX809) | `gen2::pin_pd3` | `gen3::pin_pd3` | `gen4::pin_pf3`
(Not available on 28-pin parts) | `gen5::pin_pf3`
(Not available on 28-pin parts) | | | -| `gen::tca0_cmp0` | `gen0::pin_pb4`
(Only available on ATmegaX809) | `gen1::pin_pb4`
(Only available on ATmegaX809) | `gen2::pin_pd4` | `gen3::pin_pd4` | `gen4::pin_pf4`
(Not available on 28-pin parts) | `gen5::pin_pf4`
(Not available on 28-pin parts) | | | -| `gen::tca0_cmp1` | `gen0::pin_pb5`
(Only available on ATmegaX809) | `gen1::pin_pb5`
(Only available on ATmegaX809) | `gen2::pin_pd5` | `gen3::pin_pd5` | `gen4::pin_pf5`
(Not available on 28-pin parts) | `gen5::pin_pf5`
(Not available on 28-pin parts) | | | -| `gen::tca0_cmp2` | | | `gen2::pin_pd6` | `gen3::pin_pd6` | `gen4::pin_pf6` | `gen5::pin_pf6` | | | -| `gen::tcb0_capt` | | | `gen2::pin_pd7` | `gen3::pin_pd7` | | | | | -| `gen::tcb1_capt` | | | | | | | | | -| `gen::tcb2_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | -| `gen::tcb3_capt` | | | | | | | | | - - -### assign_generator(gen::generator_t) +| All event channels | Event0 | Event1 | Event2 | Event3 | Event4 | Event5 | Event6 | Event7 | +|-----------------------------|------------------------------------------------------------|------------------------------------------------------------|------------------------------------------------------------|------------------------------------------------------------|-------------------------------------------------------------|-------------------------------------------------------------|----------------------------|---------------------------| +| `event::gen::disable` | `event::gen0::disable` | `event::gen1::disable` | `event::gen2::disable` | `event::gen3::disable` | `event::gen4::disable` | `event::gen5::disable` | `event::gen6::disable` | `event::gen7::disable` | +| `event::gen::updi_synch` | `event::gen0::rtc_div8192` | `event::gen1::rtc_div512` | `event::gen2::rtc_div8192` | `event::gen3::rtc_div512` | `event::gen4::rtc_div8192` | `event::gen5::rtc_div512` | `event::gen6::rtc_div8192` | `event::gen7::rtc_div512` | +| `event::gen::rtc_ovf` | `event::gen0::rtc_div4096` | `event::gen1::rtc_div256` | `event::gen2::rtc_div4096` | `event::gen3::rtc_div256` | `event::gen4::rtc_div4096` | `event::gen5::rtc_div256` | `event::gen6::rtc_div4096` | `event::gen7::rtc_div256` | +| `event::gen::rtc_cmp` | `event::gen0::rtc_div2048` | `event::gen1::rtc_div128` | `event::gen2::rtc_div2048` | `event::gen3::rtc_div128` | `event::gen4::rtc_div2048` | `event::gen5::rtc_div128` | `event::gen6::rtc_div2048` | `event::gen7::rtc_div128` | +| `event::gen::ccl0_out` | `event::gen0::rtc_div1024` | `event::gen1::rtc_div64` | `event::gen2::rtc_div1024` | `event::gen3::rtc_div64` | `event::gen4::rtc_div1024` | `event::gen5::rtc_div64` | `event::gen6::rtc_div1024` | `event::gen7::rtc_div64` | +| `event::gen::ccl1_out` | `event::gen0::pin_pa0` | `event::gen1::pin_pa0` | `event::gen2::pin_pc0` | `event::gen3::pin_pc0` | `event::gen4::pin_pe0`
(Only available on ATmegaX809) | `event::gen5::pin_pe0`
(Only available on ATmegaX809) | | | +| `event::gen::ccl2_out` | `event::gen0::pin_pa1` | `event::gen1::pin_pa1` | `event::gen2::pin_pc1` | `event::gen3::pin_pc1` | `event::gen4::pin_pe1`
(Only available on ATmegaX809) | `event::gen5::pin_pe1`
(Only available on ATmegaX809) | | | +| `event::gen::ccl3_out` | `event::gen0::pin_pa2` | `event::gen1::pin_pa2` | `event::gen2::pin_pc2` | `event::gen3::pin_pc2` | `event::gen4::pin_pe2`
(Only available on ATmegaX809) | `event::gen5::pin_pe2`
(Only available on ATmegaX809) | | | +| `event::gen::ac0_out` | `event::gen0::pin_pa3` | `event::gen1::pin_pa3` | `event::gen2::pin_pc3` | `event::gen3::pin_pc3` | `event::gen4::pin_pe3`
(Only available on ATmegaX809) | `event::gen5::pin_pe3`
(Only available on ATmegaX809) | | | +| `event::gen::adc0_ready` | `event::gen0::pin_pa4` | `event::gen1::pin_pa4` | `event::gen2::pin_pc4`
(Only available on ATmegaX809) | `event::gen3::pin_pc4`
(Only available on ATmegaX809) | | | | | +| `event::gen::usart0_xck` | `event::gen0::pin_pa5` | `event::gen1::pin_pa5` | `event::gen2::pin_pc5`
(Only available on ATmegaX809) | `event::gen3::pin_pc5`
(Only available on ATmegaX809) | | | | | +| `event::gen::usart1_xck` | `event::gen0::pin_pa6` | `event::gen1::pin_pa6` | `event::gen2::pin_pc6`
(Only available on ATmegaX809) | `event::gen3::pin_pc6`
(Only available on ATmegaX809) | | | | | +| `event::gen::usart2_xck` | `event::gen0::pin_pa7` | `event::gen1::pin_pa7` | `event::gen2::pin_pc7`
(Only available on ATmegaX809) | `event::gen3::pin_pc7`
(Only available on ATmegaX809) | | | | | +| `event::gen::usart3_xck` | `event::gen0::pin_pb0`
(Only available on ATmegaX809) | `event::gen1::pin_pb0`
(Only available on ATmegaX809) | `event::gen2::pin_pd0` | `event::gen3::pin_pd0` | `event::gen4::pin_pf0` | `event::gen5::pin_pf0` | | | +| `event::gen::spi0_sck` | `event::gen0::pin_pb1`
(Only available on ATmegaX809) | `event::gen1::pin_pb1`
(Only available on ATmegaX809) | `event::gen2::pin_pd1` | `event::gen3::pin_pd1` | `event::gen4::pin_pf1` | `event::gen5::pin_pf1` | | | +| `event::gen::tca0_ovf_lunf` | `event::gen0::pin_pb2`
(Only available on ATmegaX809) | `event::gen1::pin_pb2`
(Only available on ATmegaX809) | `event::gen2::pin_pd2` | `event::gen3::pin_pd2` | `event::gen4::pin_pf2`
(Not available on 28-pin parts) | `event::gen5::pin_pf2`
(Not available on 28-pin parts) | | | +| `event::gen::tca0_hunf` | `event::gen0::pin_pb3`
(Only available on ATmegaX809) | `event::gen1::pin_pb3`
(Only available on ATmegaX809) | `event::gen2::pin_pd3` | `event::gen3::pin_pd3` | `event::gen4::pin_pf3`
(Not available on 28-pin parts) | `event::gen5::pin_pf3`
(Not available on 28-pin parts) | | | +| `event::gen::tca0_cmp0` | `event::gen0::pin_pb4`
(Only available on ATmegaX809) | `event::gen1::pin_pb4`
(Only available on ATmegaX809) | `event::gen2::pin_pd4` | `event::gen3::pin_pd4` | `event::gen4::pin_pf4`
(Not available on 28-pin parts) | `event::gen5::pin_pf4`
(Not available on 28-pin parts) | | | +| `event::gen::tca0_cmp1` | `event::gen0::pin_pb5`
(Only available on ATmegaX809) | `event::gen1::pin_pb5`
(Only available on ATmegaX809) | `event::gen2::pin_pd5` | `event::gen3::pin_pd5` | `event::gen4::pin_pf5`
(Not available on 28-pin parts) | `event::gen5::pin_pf5`
(Not available on 28-pin parts) | | | +| `event::gen::tca0_cmp2` | | | `event::gen2::pin_pd6` | `event::gen3::pin_pd6` | `event::gen4::pin_pf6` | `event::gen5::pin_pf6` | | | +| `event::gen::tcb0_capt` | | | `event::gen2::pin_pd7` | `event::gen3::pin_pd7` | | | | | +| `event::gen::tcb1_capt` | | | | | | | | | +| `event::gen::tcb2_capt` | | | | | | | | | +| `event::gen::tcb3_capt` | | | | | | | | | +| `event::gen::tcb3_capt` | | | | | | | | | + + +### assign_generator(event::gen::generator_t) Static function that connects an event generator to a channel. What's different compared to `set_generator()` is that this function returns a reference to the channel object the generator has been assigned to. In other words, you don't need to keep track of the exact channel number, it just assigns an available channel. -Note that this function only accepts generators that are present on all channels (gen::). It will return a reference to the `Event_empty` object if no channel is available. +Note that this function only accepts generators that are present on all channels (event::gen::). It will return a reference to the `Event_empty` object if no channel is available. ### Declaration ``` c++ -static Event& assign_generator(gen::generator_t event_generator); +static Event& assign_generator(event::gen::generator_t event_generator); ``` ### Usage ```c++ -Event& myEvent = Event::assign_generator(gen::ac0_out); // Assign the AC0 out generator to a channel +Event& myEvent = Event::assign_generator(event::gen::ac0_out); // Assign the AC0 out generator to a channel myEvent.start(); ``` @@ -218,17 +218,17 @@ myEvent.start(); ## get_user_channel_number() Static function to get what event channel a user is connected to. Returns -1 if not connected to any channel. -Note that we use `user::` as prefix when we refer to event users. Since this is a static function you don't have to specify an object to determine what channel the user is connected to. An event channel, and hence an event generator, can have as many event users are you want - but an event user can only have one event generator. +Note that we use `event::user::` as prefix when we refer to event users. Since this is a static function you don't have to specify an object to determine what channel the user is connected to. An event channel, and hence an event generator, can have as many event users are you want - but an event user can only have one event generator. You cannot get a list or count of all users connected to a generator except by iterating over the list. ### Declaration ``` c++ -static int8_t get_user_channel_number(user::user_t event_user); +static int8_t get_user_channel_number(event::user::user_t event_user); ``` ### Usage ```c++ -int8_t connected_to = Event::get_user_channel_number(user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to +int8_t connected_to = Event::get_user_channel_number(event::user::ccl0_event_a); // Returns the channel number ccl0_event_a is connected to ``` @@ -237,12 +237,12 @@ Static function that returns the Event channel object a particular user is conne ### Declaration ``` c++ -static Event& get_user_channel(user::user_t event_user); +static Event& get_user_channel(event::user::user_t event_user); ``` ### Usage ```c++ -Event& myEvent = Event::get_user_channel(user::ccl0_event_a); +Event& myEvent = Event::get_user_channel(event::user::ccl0_event_a); ``` @@ -251,49 +251,49 @@ Function to connect an event user to an event generator. Note that a generator c ### Declaration ``` c++ -void set_user(user::user_t event_user); +void set_user(event::user::user_t event_user); ``` ### Usage ```c++ -Event0.set_generator(gen0::pin_pa0); // Set pin PA0` as event generator for Event0 -Event0.set_user(user::evoutc); // Set EVOUTC (pin PC2) as event user -Event0.set_user(user::evoutd); // Set evoutD (pin PD2) as event user +Event0.set_generator(event::gen0::pin_pa0); // Set pin PA0` as event generator for Event0 +Event0.set_user(event::user::evoutc); // Set EVOUTC (pin PC2) as event user +Event0.set_user(event::user::evoutd); // Set evoutD (pin PD2) as event user ``` ### User table Below is a table with all possible event users. Note that `evoutN_pin_pN7` is the same as `evoutN_pin_pN2` but where the pin is swapped from 2 to 7. This means that for instance, `evouta_pin_pa2` can't be used in combination with `evouta_pin_pa7.` -| Event users | Notes | -|-----------------------------------|-----------------------------------------------------------------------| -| `user::ccl0_event_a` | | -| `user::ccl0_event_b` | | -| `user::ccl1_event_a` | | -| `user::ccl1_event_b` | | -| `user::ccl2_event_a` | | -| `user::ccl2_event_b` | | -| `user::ccl3_event_a` | | -| `user::ccl3_event_b` | | -| `user::adc0_start` | | -| `user::evouta_pin_pa2` | | -| `user::evouta_pin_pa7` | Pin swapped variant of `evouta_pin_pa2` | -| `user::evoutb_pin_pb2` | Only available on ATmegaX809 | -| `user::evoutc_pin_pc2` | | -| `user::evoutc_pin_pc7` | Pin swapped variant of `evoutc_pin_pc2`. Only available on ATmegaX809 | -| `user::evoutd_pin_pd2` | | -| `user::evoutd_pin_pd7` | Pin swapped variant of `evoutd_pin_pd2` | -| `user::evoute_pin_pe2` | Only available on ATmegaX809 | -| `user::evoutf_pin_pf2` | Not available on 28-pin parts | -| `user::usart0_irda` | | -| `user::usart1_irda` | | -| `user::usart2_irda` | | -| `user::usart3_irda` | | -| `user::tca0` or `user::tca0_capt` | | -| `user::tcb0` or `user::tcb0_capt` | | -| `user::tcb1` or `user::tcb1_capt` | | -| `user::tcb2` or `user::tcb2_capt` | | -| `user::tcb3` or `user::tcb3_capt` | | +| Event users | Notes | +|-------------------------------------------------|-----------------------------------------------------------------------| +| `event::user::ccl0_event_a` | | +| `event::user::ccl0_event_b` | | +| `event::user::ccl1_event_a` | | +| `event::user::ccl1_event_b` | | +| `event::user::ccl2_event_a` | | +| `event::user::ccl2_event_b` | | +| `event::user::ccl3_event_a` | | +| `event::user::ccl3_event_b` | | +| `event::user::adc0_start` | | +| `event::user::evouta_pin_pa2` | | +| `event::user::evouta_pin_pa7` | Pin swapped variant of `evouta_pin_pa2` | +| `event::user::evoutb_pin_pb2` | Only available on ATmegaX809 | +| `event::user::evoutc_pin_pc2` | | +| `event::user::evoutc_pin_pc7` | Pin swapped variant of `evoutc_pin_pc2`. Only available on ATmegaX809 | +| `event::user::evoutd_pin_pd2` | | +| `event::user::evoutd_pin_pd7` | Pin swapped variant of `evoutd_pin_pd2` | +| `event::user::evoute_pin_pe2` | Only available on ATmegaX809 | +| `event::user::evoutf_pin_pf2` | Not available on 28-pin parts | +| `event::user::usart0_irda` | | +| `event::user::usart1_irda` | | +| `event::user::usart2_irda` | | +| `event::user::usart3_irda` | | +| `event::user::tca0` or `event::user::tca0_capt` | | +| `event::user::tcb0` or `event::user::tcb0_capt` | | +| `event::user::tcb1` or `event::user::tcb1_capt` | | +| `event::user::tcb2` or `event::user::tcb2_capt` | | +| `event::user::tcb3` or `event::user::tcb3_capt` | | ## set_user_pin(uint8_t pin_number) @@ -328,12 +328,12 @@ Function to detach a user from a channel. Note that you don't need to know what ### Declaration ``` c++ -static void clear_user(user::user_t event_user); +static void clear_user(event::user::user_t event_user); ``` ### Usage ```c++ -Event::clear_user(user::evouta); // Remove the user::evouta from whatever event channel it is connected to +Event::clear_user(event::user::evouta); // Remove the event::user::evouta from whatever event channel it is connected to ``` @@ -399,7 +399,7 @@ Event0.stop(); // Stops the Event0 generator channel These two static functions allow you to pass a reference to a peripheral module, and get back the generator or user associated with it. In this context the "Peripheral Modules" are the structs containing the registers, defined in the io headers; for example `TCB0` or `USART1` or `CCL`. This is most useful if you are writing portable (library) code that uses the Event library to interact with the event system. Say you made a library that lets users make one-shot pulses with timerB. You use the Event library to handle that part. You would of course need to know which timer to use - the natural way would be to ask the user to pass a reference or pointer. -But then what? The fact that you've got the pointer to something which, as it happens, is TCB0 (which itself is annoying to determine from an unknown pointer)... though even KNOWING THAT, you're not able to use it with the event library, since it needs user::tcb0 (or user::tcb0_capt). As the function names imply, one gives generators, the other gives users. They take 2 arguments, the first being a pointer to a peripheral struct. +But then what? The fact that you've got the pointer to something which, as it happens, is TCB0 (which itself is annoying to determine from an unknown pointer)... though even KNOWING THAT, you're not able to use it with the event library, since it needs event::user::tcb0 (or event::user::tcb0_capt). As the function names imply, one gives generators, the other gives users. They take 2 arguments, the first being a pointer to a peripheral struct. The second, defaulting to 0, is the "type" of generator or user. Some peripherals have more than one event input or output. These are ordered in the same order as they are in the tables here and in the datasheet listings. ### Usage diff --git a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino index 8cdeedd..1acd561 100644 --- a/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino +++ b/megaavr/libraries/Event/examples/Read_event_settings/Read_event_settings.ino @@ -24,7 +24,7 @@ void print_event_info(Event& my_event) } // Function to print information about the passed event user -void print_user_info(user::user_t my_user) +void print_user_info(event::user::user_t my_user) { // Event::get_user_channel() returns -1 if the user isn't connected to any event generator Serial2.printf("User 0x%02x is connected to event channel no. %d\n\n", my_user, Event::get_user_channel_number(my_user)); @@ -34,13 +34,13 @@ void setup() { Serial2.begin(9600); // Initialize hardware serial port - Event1.set_generator(gen0::pin_pa3); // Set pin PA3 as event generator for event channel 1 - Event2.set_generator(gen2::pin_pc3); // Set pin PC3 as event generator for event channel 2 + Event1.set_generator(event::gen0::pin_pa3); // Set pin PA3 as event generator for event channel 1 + Event2.set_generator(event::gen2::pin_pc3); // Set pin PC3 as event generator for event channel 2 Event& myEvent = Event::assign_generator_pin(PIN_PA2); // Set pin PA2 as event generator for an available channel // For more information about EVOUT, see the PORTMUX section in the datasheet - Event1.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user - Event2.set_user(user::evouta_pin_pa2); // Set EVOUTA as event user + Event1.set_user(event::user::evoutc_pin_pc2); // Set EVOUTC as event user + Event2.set_user(event::user::evouta_pin_pa2); // Set EVOUTA as event user myEvent.set_user_pin(PIN_PD2); // Set pin PD2 (EVOUTD) as event user // Start event channels @@ -53,16 +53,16 @@ void loop() { // Print info about Event4 and its event user print_event_info(Event1); - print_user_info(user::evoutc_pin_pc2); + print_user_info(event::user::evoutc_pin_pc2); // Print info about Event5 and its event user print_event_info(Event2); - print_user_info(user::evouta_pin_pa2); + print_user_info(event::user::evouta_pin_pa2); // Print info about myEvent and its user Event& myEvent = Event::get_generator_channel(PIN_PA2); print_event_info(myEvent); - print_user_info(user::evoutd_pin_pd2); + print_user_info(event::user::evoutd_pin_pd2); delay(5000); } diff --git a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino index 88623a5..223cd40 100644 --- a/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino +++ b/megaavr/libraries/Event/examples/Route_logic_pins/Route_logic_pins.ino @@ -35,18 +35,18 @@ void setup() { // Initialize Event channel 2 and 3 - Event2.set_generator(gen2::pin_pc0); // Set pin PC0 as event generator - Event3.set_generator(gen3::pin_pc1); // Set pin PC1 as event generator - Event2.set_user(user::ccl0_event_a); // Set CCL0 (Logic0) event A as user - Event3.set_user(user::ccl0_event_b); // Set CCL0 (Logic0) event B as user + Event2.set_generator(event::gen2::pin_pc0); // Set pin PC0 as event generator + Event3.set_generator(event::gen3::pin_pc1); // Set pin PC1 as event generator + Event2.set_user(event::user::ccl0_event_a); // Set CCL0 (Logic0) event A as user + Event3.set_user(event::user::ccl0_event_b); // Set CCL0 (Logic0) event B as user // Initialize logic block 0 Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::event_a; // Connect input 0 to ccl0_event_a (PC0 through Event2) - Logic0.input1 = in::event_b; // Connect input 0 to ccl0_event_b (PC1 through Event3) - Logic0.input2 = in::input; // Set PA2 as input - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.truth = 0x80; // Set truth table + Logic0.input0 = logic::in::event_a; // Connect input 0 to ccl0_event_a (PC0 through Event2) + Logic0.input1 = logic::in::event_b; // Connect input 0 to ccl0_event_b (PC1 through Event3) + Logic0.input2 = logic::in::input; // Set PA2 as input + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.truth = 0x80; // Set truth table Logic0.init(); // Start event channels and the logic hardware diff --git a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino index 900b752..68ec388 100644 --- a/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino +++ b/megaavr/libraries/Event/examples/Simple_event/Simple_event.ino @@ -23,11 +23,11 @@ void setup() { // Since pin PE0 is only available on event generator channel 4 and 5, we use Event4 as our object // Note that we use gen4:: to refer to functionality unique to event channel 4 - Event0.set_generator(gen0::pin_pa0); // Set pin PA0 as event generator + Event0.set_generator(event::gen0::pin_pa0); // Set pin PA0 as event generator // For more information about EVOUT, see the PORTMUX section in the datasheet - Event0.set_user(user::evoutc_pin_pc2); // Set EVOUTC as event user - Event0.set_user(user::evoutd_pin_pd2); // Set EVOUTD as event user + Event0.set_user(event::user::evoutc_pin_pc2); // Set EVOUTC as event user + Event0.set_user(event::user::evoutd_pin_pd2); // Set EVOUTD as event user // Start event channel Event0.start(); diff --git a/megaavr/libraries/Event/keywords.txt b/megaavr/libraries/Event/keywords.txt index 5d24f37..0a21fe2 100644 --- a/megaavr/libraries/Event/keywords.txt +++ b/megaavr/libraries/Event/keywords.txt @@ -47,6 +47,7 @@ Event7 KEYWORD2 # Constants (LITERAL1) ####################################### +event LITERAL1 gen LITERAL1 gen0 LITERAL1 gen1 LITERAL1 diff --git a/megaavr/libraries/Event/library.properties b/megaavr/libraries/Event/library.properties index 3a0551c..0f11f66 100644 --- a/megaavr/libraries/Event/library.properties +++ b/megaavr/libraries/Event/library.properties @@ -1,5 +1,5 @@ name=Event System -version=1.2.0 +version=1.2.1 author=MCUdude maintainer=MCUdude and Spence Konde sentence=A library for interfacing with the built-in event system diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index 195013b..bd25ebd 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -128,7 +128,7 @@ Event& Event::get_channel(uint8_t ch_number) { * @param generator Event generator * @return Event& Event channel object used with this event generator */ -Event& Event::get_generator_channel(gen::generator_t generator) { +Event& Event::get_generator_channel(event::gen::generator_t generator) { #if defined(EVSYS_CHANNEL0) if(Event0.generator_type == generator) { return Event0; @@ -268,10 +268,10 @@ uint8_t Event::get_generator() { * @brief Sets a generator for a particular event channel * * @param event_generator Set generator. - * Use gen:: for functionality present on all event channels. + * Use event::gen:: for functionality present on all event channels. * Use genN:: for functionality present on channel N. */ -void Event::set_generator(gen::generator_t event_generator) { +void Event::set_generator(event::gen::generator_t event_generator) { // Store event generator setting for use in start() and stop() generator_type = (uint8_t)event_generator; } @@ -295,7 +295,7 @@ void Event::set_generator(uint8_t pin_number) { generator_type = 0x40 | (port & 0x01) << 3 | port_pin; } else { - generator_type = gen::disable; + generator_type = event::gen::disable; } } @@ -316,42 +316,42 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { #if defined(MEGACOREX) || defined(DXCORE) uint8_t gen = 0x40 | (port & 0x01) << 3 | port_pin; if(port == PA || port == PB) { - if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == event::gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } - else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { + else if(Event1.generator_type == event::gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } } else if(port == PC || port == PD) { - if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { + if(Event2.generator_type == event::gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } - else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { + else if(Event3.generator_type == event::gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } } else if(port == PE || port == PF) { - if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { + if(Event4.generator_type == event::gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } - else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) { + else if(Event5.generator_type == event::gen::disable || Event5.generator_type == gen) { Event5.generator_type = gen; return Event5; } } #if defined(Dx_64_PINS) else if(port == PG) { - if(Event6.generator_type == gen::disable || Event6.generator_type == gen) { + if(Event6.generator_type == event::gen::disable || Event6.generator_type == gen) { Event6.generator_type = gen; return Event6; } - else if(Event7.generator_type == gen::disable || Event7.generator_type == gen) { + else if(Event7.generator_type == event::gen::disable || Event7.generator_type == gen) { Event7.generator_type = gen; return Event7; } @@ -362,22 +362,22 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { #elif defined(TINY_2_SERIES) if(port != PC) { uint8_t gen = port_pin | (port == PB ? 0x40 : 0x48); - if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == event::gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } - else if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { + else if(Event1.generator_type == event::gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } } if(port != PB) { uint8_t gen = port_pin | (port == PA ? 0x40 : 0x48); - if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { + if(Event2.generator_type == event::gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } - else if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { + else if(Event3.generator_type == event::gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } @@ -385,11 +385,11 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { if(port != PA) { uint8_t gen = port_pin | (port == PC ? 0x40 : 0x48); - if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { + if(Event4.generator_type == event::gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } - else if(Event5.generator_type == gen::disable || Event5.generator_type == gen) { + else if(Event5.generator_type == event::gen::disable || Event5.generator_type == gen) { Event5.generator_type = gen; return Event5; } @@ -400,12 +400,12 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { #if !defined(__AVR_ATtinyxy2__) if(port == PA) { #endif - if(Event2.generator_type == gen::disable || Event2.generator_type == gen) { + if(Event2.generator_type == event::gen::disable || Event2.generator_type == gen) { Event2.generator_type = gen; return Event2; } gen += 3; - if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == event::gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } @@ -413,13 +413,13 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { } #endif if(port == PB) { - if(Event3.generator_type == gen::disable || Event3.generator_type == gen) { + if(Event3.generator_type == event::gen::disable || Event3.generator_type == gen) { Event3.generator_type = gen; return Event3; } #if defined(TINY_1_SERIES) // No Event1 on 0-series gen -= 2; - if(Event1.generator_type == gen::disable || Event1.generator_type == gen) { + if(Event1.generator_type == event::gen::disable || Event1.generator_type == gen) { Event1.generator_type = gen; return Event1; } @@ -428,13 +428,13 @@ Event& Event::assign_generator_pin(uint8_t port, uint8_t port_pin) { #if defined(PIN_PC0) // can't test if PORTx is defined - all are defined everywhere) if(port == PC) { #if defined(TINY_1_SERIES) // no event 4 on 0-series - if(Event4.generator_type == gen::disable || Event4.generator_type == gen) { + if(Event4.generator_type == event::gen::disable || Event4.generator_type == gen) { Event4.generator_type = gen; return Event4; } #endif gen -= 3; - if(Event0.generator_type == gen::disable || Event0.generator_type == gen) { + if(Event0.generator_type == event::gen::disable || Event0.generator_type == gen) { Event0.generator_type = gen; return Event0; } @@ -465,7 +465,7 @@ Event& Event::assign_generator_pin(uint8_t pin_number) { /** - * @brief Static member function that takes a gen:: generator as a parameter and + * @brief Static member function that takes a event::gen:: generator as a parameter and * finds an available channel for it. Starts with the highest possible channel * number, 7, and iterate down to 0 * @@ -473,7 +473,7 @@ Event& Event::assign_generator_pin(uint8_t pin_number) { * @return Event& Reference to the event object the generator has been assigned to. * Returns the Event_empty object if no generator has been assigned to a channel */ -Event& Event::assign_generator(gen::generator_t event_generator) { +Event& Event::assign_generator(event::gen::generator_t event_generator) { // Check if generator is already in use Event& channel = Event::get_generator_channel(event_generator); if(channel.get_channel_number() != 255) { @@ -482,70 +482,70 @@ Event& Event::assign_generator(gen::generator_t event_generator) { else { #if defined(EVSYS_CHANNEL9) - if(Event9.get_generator() == gen::disable) { + if(Event9.get_generator() == event::gen::disable) { Event9.set_generator(event_generator); return Event9; } else #endif #if defined(EVSYS_CHANNEL8) - if(Event8.get_generator() == gen::disable) { + if(Event8.get_generator() == event::gen::disable) { Event8.set_generator(event_generator); return Event8; } else #endif #if defined(EVSYS_CHANNEL7) - if(Event7.get_generator() == gen::disable) { + if(Event7.get_generator() == event::gen::disable) { Event7.set_generator(event_generator); return Event7; } else #endif #if defined(EVSYS_CHANNEL6) - if(Event6.get_generator() == gen::disable) { + if(Event6.get_generator() == event::gen::disable) { Event6.set_generator(event_generator); return Event6; } else #endif #if defined(EVSYS_CHANNEL5) - if(Event5.get_generator() == gen::disable) { + if(Event5.get_generator() == event::gen::disable) { Event5.set_generator(event_generator); return Event5; } else #endif #if defined(EVSYS_CHANNEL4) - if(Event4.get_generator() == gen::disable) { + if(Event4.get_generator() == event::gen::disable) { Event4.set_generator(event_generator); return Event4; } else #endif #if defined(EVSYS_CHANNEL3) - if(Event3.get_generator() == gen::disable) { + if(Event3.get_generator() == event::gen::disable) { Event3.set_generator(event_generator); return Event3; } else #endif #if defined(EVSYS_CHANNEL2) - if(Event2.get_generator() == gen::disable) { + if(Event2.get_generator() == event::gen::disable) { Event2.set_generator(event_generator); return Event2; } else #endif #if defined(EVSYS_CHANNEL1) - if(Event1.get_generator() == gen::disable) { + if(Event1.get_generator() == event::gen::disable) { Event1.set_generator(event_generator); return Event1; } else #endif #if defined(EVSYS_CHANNEL0) - if(Event0.get_generator() == gen::disable) { + if(Event0.get_generator() == event::gen::disable) { Event0.set_generator(event_generator); return Event0; } @@ -563,7 +563,7 @@ Event& Event::assign_generator(gen::generator_t event_generator) { * @return int8_t Event channel number. * Returns -1 if not connected to any event channel */ -int8_t Event::get_user_channel_number(user::user_t event_user) { +int8_t Event::get_user_channel_number(event::user::user_t event_user) { // Figure out what user register to read from to based on the passed parameter volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user; @@ -579,7 +579,7 @@ int8_t Event::get_user_channel_number(user::user_t event_user) { * @return Event& Event channel object. Returns the Event_empty object if the * user is not connected to any event channel */ -Event& Event::get_user_channel(user::user_t event_user) { +Event& Event::get_user_channel(event::user::user_t event_user) { int8_t ch_number = get_user_channel_number(event_user); #if defined(EVSYS_CHANNEL0) @@ -646,7 +646,7 @@ Event& Event::get_user_channel(user::user_t event_user) { * * @param event_user The event user to connect to a particular channel */ -void Event::set_user(user::user_t event_user) { +void Event::set_user(event::user::user_t event_user) { // Figure out what user register to write to based on the passed parameter uint8_t event_user_mask = event_user & 0x7F; @@ -683,7 +683,7 @@ void Event::set_user(user::user_t event_user) { * * @param pin_number The Arduino pin number to use as a channel user * @return uint8_t Event channel user enum - (for instance user::evouta_pin_pa2 pin PIN_PA2 is passed) + (for instance event::user::evouta_pin_pa2 pin PIN_PA2 is passed) * Returns -1 if invalid pin is passed */ int8_t Event::set_user_pin(uint8_t pin_number) { @@ -692,20 +692,20 @@ int8_t Event::set_user_pin(uint8_t pin_number) { int8_t event_user = -1; if(port != NOT_A_PIN && port_pin != NOT_A_PIN) { - uint8_t evout_user = (uint8_t)user::evouta_pin_pa2; + uint8_t evout_user = (uint8_t)event::user::evouta_pin_pa2; if(port_pin == 2) { - event_user = (user::user_t)(evout_user + port); + event_user = (event::user::user_t)(evout_user + port); } #if !defined(TINY_0_SERIES) && !defined(TINY_1_SERIES) else if(port_pin == 7) { - event_user = (user::user_t)(evout_user + port); + event_user = (event::user::user_t)(evout_user + port); } #endif else { return -1; } - set_user((user::user_t)event_user); + set_user((event::user::user_t)event_user); } return event_user; } @@ -716,7 +716,7 @@ int8_t Event::set_user_pin(uint8_t pin_number) { * * @param event_user The event user to remove from a particular channel */ -void Event::clear_user(user::user_t event_user) { +void Event::clear_user(event::user::user_t event_user) { // Figure out what user register to write to based on the passed parameter uint8_t event_user_mask = event_user & 0x7F; volatile uint8_t *user_register = &EVSYS_USERCCLLUT0A + (volatile uint8_t&)event_user_mask; @@ -853,30 +853,30 @@ void Event::long_soft_event(uint8_t length) { * comparator peripheral * * @param comp Analog comparator struct - * @return gen::generator_t generator type + * @return event::gen::generator_t generator type */ -gen::generator_t Event::gen_from_peripheral(AC_t& comp) +event::gen::generator_t Event::gen_from_peripheral(AC_t& comp) { #if defined(TINY_1_SERIES) && PROGMEM_SIZE > 8192 badCall("gen_from_peripheral() does not support channel-specific generators. The AC's larger 1-series are."); #else #if defined(AC0) if(&comp == &AC0) { - return gen::ac0_out; + return event::gen::ac0_out; } #if defined(AC1) else if(&comp == &AC1) { - return gen::ac1_out; + return event::gen::ac1_out; } #if defined(AC2) else if(&comp == &AC2) { - return gen::ac2_out; + return event::gen::ac2_out; } #endif #endif #endif #endif - return (gen::generator_t) -1; + return (event::gen::generator_t) -1; } @@ -885,9 +885,9 @@ gen::generator_t Event::gen_from_peripheral(AC_t& comp) * * @param logic CCL struct * @param logic_block Logic block number (0, 1, 2 or 3 for megaAVR-0's) - * @return gen::generator_t generator type + * @return event::gen::generator_t generator type */ -gen::generator_t Event::gen_from_peripheral(CCL_t& logic, uint8_t logic_block) { +event::gen::generator_t Event::gen_from_peripheral(CCL_t& logic, uint8_t logic_block) { uint8_t retval = -1; if(&logic == &CCL) { #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) @@ -898,10 +898,10 @@ gen::generator_t Event::gen_from_peripheral(CCL_t& logic, uint8_t logic_block) { if(logic_block < 4) #endif { - retval = (int8_t)(gen::ccl0_out) + logic_block; + retval = (int8_t)(event::gen::ccl0_out) + logic_block; } } - return (gen::generator_t)retval; + return (event::gen::generator_t)retval; } @@ -911,9 +911,9 @@ gen::generator_t Event::gen_from_peripheral(CCL_t& logic, uint8_t logic_block) { * * @param logic CCL struct * @param user_type - * @return user::user_t CCL user number. + * @return event::user::user_t CCL user number. */ -user::user_t Event::user_from_peripheral(CCL_t& logic, uint8_t user_type) { +event::user::user_t Event::user_from_peripheral(CCL_t& logic, uint8_t user_type) { uint8_t retval = -1; if(&logic == &CCL) { #if !defined(TINY_0_SERIES) && !defined(TINY_1_SERIES) @@ -931,7 +931,7 @@ user::user_t Event::user_from_peripheral(CCL_t& logic, uint8_t user_type) { } #endif } - return (user::user_t)retval; + return (event::user::user_t)retval; } @@ -941,9 +941,9 @@ user::user_t Event::user_from_peripheral(CCL_t& logic, uint8_t user_type) { * @param logic TCA struct * @param event_type TCA has multiple generators. This parameter provides the number, * and ranges from 0 to 4 for megaAVR-0's - * @return gen::generator_t generator type + * @return event::gen::generator_t generator type */ -gen::generator_t Event::gen_from_peripheral(TCA_t& timer, uint8_t event_type) { +event::gen::generator_t Event::gen_from_peripheral(TCA_t& timer, uint8_t event_type) { uint8_t retval = -1; if(event_type < 5) { #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) @@ -959,7 +959,7 @@ gen::generator_t Event::gen_from_peripheral(TCA_t& timer, uint8_t event_type) { #endif #endif } - return (gen::generator_t)retval; + return (event::gen::generator_t)retval; } @@ -969,18 +969,18 @@ gen::generator_t Event::gen_from_peripheral(TCA_t& timer, uint8_t event_type) { * @param timer TCA struct * @param user_type TCA has only has one user on megaAVR-0's. * Leave this parameter unused - * @return user::user_t TCA user number + * @return event::user::user_t TCA user number */ -user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { +event::user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { uint8_t user = -1; #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) || defined(MEGACOREX) if(user_type != 0) { - return (user::user_t) -1; + return (event::user::user_t) -1; } #else if(user_type > 1) { - return (user::user_t) -1; + return (event::user::user_t) -1; } #endif user = user_type; // 0 or 1 for event user a or b (on parts with both, or 0 for parts that only have one @@ -990,7 +990,7 @@ user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { } else #endif if(&timer != &TCA0) { - return (user::user_t) -1; + return (event::user::user_t) -1; } #if defined(__AVR_DA__) user += 0x1B; @@ -1003,7 +1003,7 @@ user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { #else user += 0x10; #endif - return (user::user_t)user; + return (event::user::user_t)user; } @@ -1013,16 +1013,16 @@ user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) { * @param timer TCB struct * @param event_type TCB only has one generators on megaAVR-0's. * Leave this parameter unused - * @return gen::generator_t generator type + * @return event::gen::generator_t generator type */ -gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { +event::gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { int8_t gentype = -1; #if defined(TINY_0_OR_1_SERIES) badCall("gen_from_peripheral() does not support channel-specific generators. The TCBs on 0/1-series are."); #else #if defined(MEGACOREX) // Dx-series and 2-series have ovf event, others don't. if(event_type != 1) { - return (gen::generator_t) -1; + return (event::gen::generator_t) -1; } else { gentype = 0; @@ -1033,33 +1033,33 @@ gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { } #endif if(&timer == &TCB0) { - gentype += (uint8_t)gen::tcb0_capt; + gentype += (uint8_t)event::gen::tcb0_capt; } else #if defined(TCB1) if (&timer == &TCB1) { - gentype += (uint8_t)gen::tcb1_capt; + gentype += (uint8_t)event::gen::tcb1_capt; } else #endif #if defined(TCB2) if (&timer == &TCB2) { - gentype += (uint8_t)gen::tcb2_capt; + gentype += (uint8_t)event::gen::tcb2_capt; } else #endif #if defined(TCB3) if (&timer == &TCB3) { - gentype += (uint8_t)gen::tcb3_capt; + gentype += (uint8_t)event::gen::tcb3_capt; } else #endif #if defined(TCB4) if (&timer == &TCB4) { - gentype += (uint8_t)gen::tcb4_capt; + gentype += (uint8_t)event::gen::tcb4_capt; } else #endif { gentype = -1; } #endif - return (gen::generator_t) gentype; + return (event::gen::generator_t) gentype; } @@ -1068,13 +1068,13 @@ gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { * * @param timer TCB struct * @param user_type - * @return user::user_t TCA user number + * @return event::user::user_t TCA user number */ -user::user_t Event::user_from_peripheral(TCB_t& timer, uint8_t user_type) { +event::user::user_t Event::user_from_peripheral(TCB_t& timer, uint8_t user_type) { uint8_t user = -1; #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) || defined(MEGACOREX) // Dx-series and 2-series have event count input, others don't. if (user_type != 1) { - return (user::user_t) -1; + return (event::user::user_t) -1; } else { user = 0; @@ -1085,32 +1085,32 @@ user::user_t Event::user_from_peripheral(TCB_t& timer, uint8_t user_type) { } #endif if (&timer == &TCB0) { - user += (uint8_t)user::tcb0_capt; + user += (uint8_t)event::user::tcb0_capt; } else #if defined(TCB1) if (&timer == &TCB1) { - user += (uint8_t)user::tcb1_capt; + user += (uint8_t)event::user::tcb1_capt; } else #endif #if defined(TCB2) if (&timer == &TCB2) { - user += (uint8_t)user::tcb2_capt; + user += (uint8_t)event::user::tcb2_capt; } else #endif #if defined(TCB3) if (&timer == &TCB3) { - user += (uint8_t)user::tcb3_capt; + user += (uint8_t)event::user::tcb3_capt; } else #endif #if defined(TCB4) if (&timer == &TCB4) { - user += (uint8_t)user::tcb4_capt; + user += (uint8_t)event::user::tcb4_capt; } else #endif { user = -1; } - return (user::user_t)user; + return (event::user::user_t)user; } @@ -1119,38 +1119,38 @@ user::user_t Event::user_from_peripheral(TCB_t& timer, uint8_t user_type) { * to offer * * @param usart USART struct - * @return user::user_t USART related event channel user + * @return event::user::user_t USART related event channel user */ -user::user_t Event::user_from_peripheral(USART_t& usart) { +event::user::user_t Event::user_from_peripheral(USART_t& usart) { if(&usart == &USART0) { - return user::usart0_irda; + return event::user::usart0_irda; } #if defined(USART1) else if(&usart == &USART1) { - return user::usart1_irda; + return event::user::usart1_irda; } #endif #if defined(USART2) else if(&usart == &USART2) { - return user::usart2_irda; + return event::user::usart2_irda; } #endif #if defined(USART3) else if(&usart == &USART3) { - return user::usart3_irda; + return event::user::usart3_irda; } #endif #if defined(USART4) else if(&usart == &USART4) { - return user::usart4_irda; + return event::user::usart4_irda; } #endif #if defined(USART5) else if(&usart == &USART5) { - return user::usart5_irda; + return event::user::usart5_irda; } #endif - return (user::user_t) -1; + return (event::user::user_t) -1; } @@ -1166,7 +1166,7 @@ void Event::start(bool state) { } else { // Disable event generator - channel_address = gen::disable; + channel_address = event::gen::disable; } } diff --git a/megaavr/libraries/Event/src/Event.h b/megaavr/libraries/Event/src/Event.h index 6e0e505..512391e 100644 --- a/megaavr/libraries/Event/src/Event.h +++ b/megaavr/libraries/Event/src/Event.h @@ -13,461 +13,462 @@ #endif #endif +namespace event { #if defined(MEGACOREX) || defined(DXCORE) -// Features present on all generator channels -namespace gen { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - updi_synch = 0x01, - rtc_ovf = 0x06, - rtc_cmp = 0x07, - ccl0_out = 0x10, - ccl1_out = 0x11, - ccl2_out = 0x12, - ccl3_out = 0x13, - ac0_out = 0x20, + // Features present on all generator channels + namespace gen { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + updi_synch = 0x01, + rtc_ovf = 0x06, + rtc_cmp = 0x07, + ccl0_out = 0x10, + ccl1_out = 0x11, + ccl2_out = 0x12, + ccl3_out = 0x13, + ac0_out = 0x20, #if defined(AC1) - ac1_out = 0x21, + ac1_out = 0x21, #endif #if defined(AC2) - ac2_out = 0x22, + ac2_out = 0x22, #endif - adc0_ready = 0x24, - usart0_xck = 0x60, - usart1_xck = 0x61, - usart2_xck = 0x62, + adc0_ready = 0x24, + usart0_xck = 0x60, + usart1_xck = 0x61, + usart2_xck = 0x62, #if defined(USART3) - usart3_xck = 0x63, -#endif - spi0_sck = 0x68, - tca0_ovf_lunf = 0x80, - tca0_hunf = 0x81, - tca0_cmp0 = 0x84, - tca0_cmp1 = 0x85, - tca0_cmp2 = 0x86, - tcb0_capt = 0xA0, - tcb0 = 0xA0, - tcb1_capt = 0xA2, - tcb1 = 0xA2, - tcb2_capt = 0xA4, - tcb2 = 0xA4, + usart3_xck = 0x63, +#endif + spi0_sck = 0x68, + tca0_ovf_lunf = 0x80, + tca0_hunf = 0x81, + tca0_cmp0 = 0x84, + tca0_cmp1 = 0x85, + tca0_cmp2 = 0x86, + tcb0_capt = 0xA0, + tcb0 = 0xA0, + tcb1_capt = 0xA2, + tcb1 = 0xA2, + tcb2_capt = 0xA4, + tcb2 = 0xA4, #if defined(TCB3) - tcb3_capt = 0xA6, - tcb3 = 0xA6, + tcb3_capt = 0xA6, + tcb3 = 0xA6, #endif #if defined(TCB4) - tcb4_capt = 0xA8, - tcb4 = 0xA8, + tcb4_capt = 0xA8, + tcb4 = 0xA8, #endif #if defined(__AVR_DA__) || defined(__AVR_DB__) - ccl4_out = 0x14, - ccl5_out = 0x15, - zcd0_out = 0x30, - zcd1_out = 0x31, + ccl4_out = 0x14, + ccl5_out = 0x15, + zcd0_out = 0x30, + zcd1_out = 0x31, #if defined(ZCD2) - zcd2_out = 0x32, + zcd2_out = 0x32, #endif #if defined(USART4) - usart4_xck = 0x64, + usart4_xck = 0x64, #endif #if defined(USART5) - usart5_xck = 0x65, + usart5_xck = 0x65, #endif - spi1_sck = 0x69, + spi1_sck = 0x69, #if defined(TCA1) - tca1_ovf_lunf = 0x88, - tca1_hunf = 0x89, - tca1_cmp0 = 0x8C, - tca1_cmp1 = 0x8D, - tca1_cmp2 = 0x8E, + tca1_ovf_lunf = 0x88, + tca1_hunf = 0x89, + tca1_cmp0 = 0x8C, + tca1_cmp1 = 0x8D, + tca1_cmp2 = 0x8E, #endif #endif // defined(__AVR_DA__) || defined(__AVR_DB__) #if defined(DXCORE) // These are present on every modern part released since the 0/1-series and will probably continue to be, so check - tcb0_ovf = 0xA1, - tcb1_ovf = 0xA3, + tcb0_ovf = 0xA1, + tcb1_ovf = 0xA3, #if defined(TCB2) - tcb2_ovf = 0xA5, + tcb2_ovf = 0xA5, #endif #if defined(TCB3) - tcb3_ovf = 0xA7, + tcb3_ovf = 0xA7, #endif #if defined(TCB4) - tcb4_ovf = 0xA9, + tcb4_ovf = 0xA9, #endif #endif #if defined(TCD0) - tcd0_cmpbclr = 0xB0, - tcd0_cmpaset = 0xB1, - tcd0_cmpbset = 0xB2, - tcd0_progev = 0xB3, + tcd0_cmpbclr = 0xB0, + tcd0_cmpaset = 0xB1, + tcd0_cmpbset = 0xB2, + tcd0_progev = 0xB3, #endif #if defined(MVIO) - mvio_ok = 0x05, + mvio_ok = 0x05, #endif #if defined(ZCD3) - zcd3_out = 0x30, // The ZCD is numbered differently, I think just because it's on different pins. Still has the same event channel + zcd3_out = 0x30, // The ZCD is numbered differently, I think just because it's on different pins. Still has the same event channel #endif #if defined(__AVR_DB__) - opamp0_ready = 0x34, - opamp1_ready = 0x35, + opamp0_ready = 0x34, + opamp1_ready = 0x35, #if defined(OPAMP2) - opamp2_ready = 0x36, + opamp2_ready = 0x36, #endif #endif // defined(__AVR_DB__) + }; }; -}; // Features unique to event generator channel 0 #if defined(EVSYS_CHANNEL0) -namespace gen0 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, + namespace gen0 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, #if !defined(DXCORE) || defined(PIN_PA2) - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, #endif #if defined(PIN_PB0) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4D, + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4D, #endif #if defined(PIN_PB6) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, #endif + }; }; -}; #endif // Features unique to event generator channel 1 #if defined(EVSYS_CHANNEL1) -namespace gen1 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, + namespace gen1 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, #if defined(PIN_PA2) - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, #endif #if defined(PIN_PB0) - pin_pb0 = 0x48, - pin_pb1 = 0x49, - pin_pb2 = 0x4A, - pin_pb3 = 0x4B, - pin_pb4 = 0x4C, - pin_pb5 = 0x4D, + pin_pb0 = 0x48, + pin_pb1 = 0x49, + pin_pb2 = 0x4A, + pin_pb3 = 0x4B, + pin_pb4 = 0x4C, + pin_pb5 = 0x4D, #endif #if defined(PIN_PB6) - pin_pb6 = 0x4E, - pin_pb7 = 0x4F, + pin_pb6 = 0x4E, + pin_pb7 = 0x4F, #endif + }; }; -}; #endif // Features unique to event generator channel 2 #if defined(EVSYS_CHANNEL2) -namespace gen2 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, + namespace gen2 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, #if !defined(DD_14_PINS) // Can't just check PIN_PC0 - the 0-pin of any port with any pins present is always defined by DxCore. // I considered both ways, but there are to many reasons we need to have the 0-pin defined. - pin_pc0 = 0x40, + pin_pc0 = 0x40, #endif - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, #endif #if defined(PIN_PD1) // See above for note on PIN_PD0 and why we can't test that, this even impacts DBs. #if !defined(MVIO) || defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pd0 = 0x48, + pin_pd0 = 0x48, #endif - pin_pd1 = 0x49, - pin_pd2 = 0x4A, - pin_pd3 = 0x4B, + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, #endif - pin_pd4 = 0x4C, - pin_pd5 = 0x4D, - pin_pd6 = 0x4E, - pin_pd7 = 0x4F, + pin_pd4 = 0x4C, + pin_pd5 = 0x4D, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, }; }; #endif // Features unique to event generator channel 3 #if defined(EVSYS_CHANNEL3) -namespace gen3 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, + namespace gen3 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, #if !defined(DD_14_PINS) - pin_pc0 = 0x40, + pin_pc0 = 0x40, #endif - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, - pin_pc6 = 0x46, - pin_pc7 = 0x47, + pin_pc4 = 0x44, + pin_pc5 = 0x45, + pin_pc6 = 0x46, + pin_pc7 = 0x47, #endif #if defined(PIN_PD1) // See above for note on PIN_PD0 and why we can't test that, this even impacts DBs. #if !defined(MVIO) || defined(__AVR_ATmegax09__) || defined(Dx_48_PINS) || defined(Dx_64_PINS) - pin_pd0 = 0x48, + pin_pd0 = 0x48, #endif - pin_pd1 = 0x49, - pin_pd2 = 0x4A, - pin_pd3 = 0x4B, + pin_pd1 = 0x49, + pin_pd2 = 0x4A, + pin_pd3 = 0x4B, #endif - pin_pd4 = 0x4C, - pin_pd5 = 0x4D, - pin_pd6 = 0x4E, - pin_pd7 = 0x4F, + pin_pd4 = 0x4C, + pin_pd5 = 0x4D, + pin_pd6 = 0x4E, + pin_pd7 = 0x4F, + }; }; -}; #endif // Features unique to event generator channel 4 #if defined(EVSYS_CHANNEL4) -namespace gen4 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, + namespace gen4 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, #if defined(PIN_PE0) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, #endif #if defined(PIN_PE4) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, #endif - pin_pf0 = 0x48, - pin_pf1 = 0x49, + pin_pf0 = 0x48, + pin_pf1 = 0x49, #if defined(PIN_PF2) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, #endif - pin_pf6 = 0x4E, + pin_pf6 = 0x4E, #if defined(PIN_PF7) - pin_pf7 = 0x4F, + pin_pf7 = 0x4F, #endif + }; }; -}; #endif // Features unique to event generator channel 5 #if defined(EVSYS_CHANNEL5) -namespace gen5 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, + namespace gen5 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, #if defined(PIN_PE0) - pin_pe0 = 0x40, - pin_pe1 = 0x41, - pin_pe2 = 0x42, - pin_pe3 = 0x43, + pin_pe0 = 0x40, + pin_pe1 = 0x41, + pin_pe2 = 0x42, + pin_pe3 = 0x43, #endif #if defined(PIN_PE4) - pin_pe4 = 0x44, - pin_pe5 = 0x45, - pin_pe6 = 0x46, - pin_pe7 = 0x47, + pin_pe4 = 0x44, + pin_pe5 = 0x45, + pin_pe6 = 0x46, + pin_pe7 = 0x47, #endif - pin_pf0 = 0x48, - pin_pf1 = 0x49, + pin_pf0 = 0x48, + pin_pf1 = 0x49, #if defined(PIN_PF2) - pin_pf2 = 0x4A, - pin_pf3 = 0x4B, - pin_pf4 = 0x4C, - pin_pf5 = 0x4D, + pin_pf2 = 0x4A, + pin_pf3 = 0x4B, + pin_pf4 = 0x4C, + pin_pf5 = 0x4D, #endif - pin_pf6 = 0x4E, + pin_pf6 = 0x4E, #if defined(PIN_PF7) - pin_pf7 = 0x4F, + pin_pf7 = 0x4F, #endif + }; }; -}; #endif // Features unique to event generator channel 6 #if defined(EVSYS_CHANNEL6) -namespace gen6 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, + namespace gen6 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, #if defined(PIN_PG0) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, -#endif + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif + }; }; -}; #endif // Features unique to event generator channel 7 #if defined(EVSYS_CHANNEL7) -namespace gen7 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, + namespace gen7 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, #if defined(PIN_PG0) - pin_pg0 = 0x40, - pin_pg1 = 0x41, - pin_pg2 = 0x42, - pin_pg3 = 0x43, - pin_pg4 = 0x44, - pin_pg5 = 0x45, - pin_pg6 = 0x46, - pin_pg7 = 0x47, -#endif + pin_pg0 = 0x40, + pin_pg1 = 0x41, + pin_pg2 = 0x42, + pin_pg3 = 0x43, + pin_pg4 = 0x44, + pin_pg5 = 0x45, + pin_pg6 = 0x46, + pin_pg7 = 0x47, +#endif + }; }; -}; #endif // Features unique to event generator channel 8 #if defined(EVSYS_CHANNEL8) -namespace gen8 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, + namespace gen8 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + }; }; -}; #endif // Features unique to event generator channel 9 #if defined(EVSYS_CHANNEL9) -namespace gen9 { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, + namespace gen9 { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + }; }; -}; #endif // Generator users -namespace user { - enum user_t : uint8_t { + namespace user { + enum user_t : uint8_t { #if defined(MEGACOREX) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - adc0_start = 0x08, - evouta_pin_pa2 = 0x09, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta_pin_pa2 = 0x09, #if defined(PIN_PB2) - evoutb_pin_pb2 = 0x0A, + evoutb_pin_pb2 = 0x0A, #endif - evoutc_pin_pc2 = 0x0B, - evoutd_pin_pd2 = 0x0C, + evoutc_pin_pc2 = 0x0B, + evoutd_pin_pd2 = 0x0C, #if defined(PIN_PE2) - evoute_pin_pe2 = 0x0D, + evoute_pin_pe2 = 0x0D, #endif - evoutf_pin_pf2 = 0x0E, - usart0_irda = 0x0F, - usart1_irda = 0x10, - usart2_irda = 0x11, + evoutf_pin_pf2 = 0x0E, + usart0_irda = 0x0F, + usart1_irda = 0x10, + usart2_irda = 0x11, #if defined(USART3) - usart3_irda = 0x12, -#endif - tca0 = 0x13, - tca0_cnt_a = 0x13, - tcb0 = 0x14, - tcb0_capt = 0x14, - tcb1 = 0x15, - tcb1_capt = 0x15, - tcb2 = 0x16, - tcb2_capt = 0x16, + usart3_irda = 0x12, +#endif + tca0 = 0x13, + tca0_cnt_a = 0x13, + tcb0 = 0x14, + tcb0_capt = 0x14, + tcb1 = 0x15, + tcb1_capt = 0x15, + tcb2 = 0x16, + tcb2_capt = 0x16, #if defined(TCB3) - tcb3 = 0x17, - tcb3_capt = 0x17, + tcb3 = 0x17, + tcb3_capt = 0x17, #endif - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x89, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x89, #if defined(PIN_PC7) - evoutc_pin_pc7 = 0x8B, + evoutc_pin_pc7 = 0x8B, #endif - evoutd_pin_pd7 = 0x8C, + evoutd_pin_pd7 = 0x8C, #endif // defined(MEGACOREX) #if defined(__AVR_DA__) @@ -559,144 +560,144 @@ namespace user { #endif #endif // defined(__AVR_DA__) #if defined(__AVR_DB__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, #if defined(LUT4) - ccl4_event_a = 0x08, - ccl4_event_b = 0x09, - ccl5_event_a = 0x0A, - ccl5_event_b = 0x0B, + ccl4_event_a = 0x08, + ccl4_event_b = 0x09, + ccl5_event_a = 0x0A, + ccl5_event_b = 0x0B, #endif - adc0_start = 0x0C, - evouta_pin_pa2 = 0x0D, + adc0_start = 0x0C, + evouta_pin_pa2 = 0x0D, #if defined(PIN_PB2) - evoutb_pin_pb2 = 0x0E, + evoutb_pin_pb2 = 0x0E, #endif - evoutc_pin_pc2 = 0x0F, - evoutd_pin_pd2 = 0x10, + evoutc_pin_pc2 = 0x0F, + evoutd_pin_pd2 = 0x10, #if defined(PIN_PE2) - evoute_pin_pe2 = 0x11, + evoute_pin_pe2 = 0x11, #endif #if defined(PIN_PF2) - evoutf_pin_pf2 = 0x12, + evoutf_pin_pf2 = 0x12, #endif #if defined(PIN_PG2) - evoutg_pin_pg2 = 0x13, + evoutg_pin_pg2 = 0x13, #endif - usart0_irda = 0x14, - usart1_irda = 0x15, - usart2_irda = 0x16, + usart0_irda = 0x14, + usart1_irda = 0x15, + usart2_irda = 0x16, #if defined(USART3) - usart3_irda = 0x17, + usart3_irda = 0x17, #endif #if defined(USART4) - usart4_irda = 0x18, + usart4_irda = 0x18, #endif #if defined(USART5) - usart5_irda = 0x19, -#endif - tca0 = 0x1A, - tca0_cnt_a = 0x1A, - tca0_cnt_b = 0x1B, - tca1 = 0x1C, - tca1_cnt_a = 0x1C, - tca1_cnt_b = 0x1D, - tcb0_capt = 0x1E, - tcb0_cnt = 0x1F, - tcb1_capt = 0x20, - tcb1_cnt = 0x21, - tcb2_capt = 0x22, - tcb2_cnt = 0x23, + usart5_irda = 0x19, +#endif + tca0 = 0x1A, + tca0_cnt_a = 0x1A, + tca0_cnt_b = 0x1B, + tca1 = 0x1C, + tca1_cnt_a = 0x1C, + tca1_cnt_b = 0x1D, + tcb0_capt = 0x1E, + tcb0_cnt = 0x1F, + tcb1_capt = 0x20, + tcb1_cnt = 0x21, + tcb2_capt = 0x22, + tcb2_cnt = 0x23, #if defined(TCB3) - tcb3_capt = 0x24, - tcb3_cnt = 0x25, + tcb3_capt = 0x24, + tcb3_cnt = 0x25, #endif #if defined(TCB4) - tcb4_capt = 0x26, - tcb4_cnt = 0x27, -#endif - tcd0_in_a = 0x28, - tcd0_in_b = 0x29, - opamp0_enable = 0x2A, - opamp0_disable = 0x2B, - opamp0_dump = 0x2C, - opamp0_drive = 0x2D, - opamp1_enable = 0x2E, - opamp1_disable = 0x2F, - opamp1_dump = 0x30, - opamp1_drive = 0x31, + tcb4_capt = 0x26, + tcb4_cnt = 0x27, +#endif + tcd0_in_a = 0x28, + tcd0_in_b = 0x29, + opamp0_enable = 0x2A, + opamp0_disable = 0x2B, + opamp0_dump = 0x2C, + opamp0_drive = 0x2D, + opamp1_enable = 0x2E, + opamp1_disable = 0x2F, + opamp1_dump = 0x30, + opamp1_drive = 0x31, #if defined(OPAMP2) - opamp2_enable = 0x32, - opamp2_disable = 0x33, - opamp2_dump = 0x34, - opamp2_drive = 0x35, + opamp2_enable = 0x32, + opamp2_disable = 0x33, + opamp2_dump = 0x34, + opamp2_drive = 0x35, #endif - // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX - evouta_pin_pa7 = 0x8D, + // "Unofficial" user generators. Uses EVOUT, but swaps the output pin using PORTMUX + evouta_pin_pa7 = 0x8D, #if defined(PIN_PB7) - evoutb_pin_pb7 = 0x8E, + evoutb_pin_pb7 = 0x8E, #endif #if defined(PIN_PC7) - evoutc_pin_pc7 = 0x8F, + evoutc_pin_pc7 = 0x8F, #endif - evoutd_pin_pd7 = 0x90, + evoutd_pin_pd7 = 0x90, #if defined(PIN_PE7) - evoute_pin_pe7 = 0x91, + evoute_pin_pe7 = 0x91, #endif #if defined(PIN_PG7) - evoutg_pin_pg7 = 0x93, + evoutg_pin_pg7 = 0x93, #endif #endif // defined(__AVR_DB__) #if defined(__AVR_DD__) - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - adc0_start = 0x0C, + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x0C, #if defined(PIN_PA2) // not on 14-pin ones. - evouta_pin_pa2 = 0x0D, + evouta_pin_pa2 = 0x0D, #endif - evoutc_pin_pc2 = 0x0F, + evoutc_pin_pc2 = 0x0F, #if defined(PIN_PD2) // only on 28 or 32 pin ones. - evoutd_pin_pd2 = 0x10, + evoutd_pin_pd2 = 0x10, #endif #if defined(PIN_PF2) // only on 32-pin ones. - evoutf_pin_pf2 = 0x12, -#endif - usart0_irda = 0x14, - usart1_irda = 0x15, - tca0 = 0x1A, - tca0_cnt_a = 0x1A, - tca0_cnt_b = 0x1B, - tcb0 = 0x1E, - tcb0_capt = 0x1E, - tcb0_cnt = 0x1F, - tcb1 = 0x20, - tcb1_capt = 0x20, - tcb1_cnt = 0x21, - tcb2 = 0x22, - tcb2_capt = 0x22, - tcb2_cnt = 0x23, - tcd0_in_a = 0x28, - tcd0_in_b = 0x29, + evoutf_pin_pf2 = 0x12, +#endif + usart0_irda = 0x14, + usart1_irda = 0x15, + tca0 = 0x1A, + tca0_cnt_a = 0x1A, + tca0_cnt_b = 0x1B, + tcb0 = 0x1E, + tcb0_capt = 0x1E, + tcb0_cnt = 0x1F, + tcb1 = 0x20, + tcb1_capt = 0x20, + tcb1_cnt = 0x21, + tcb2 = 0x22, + tcb2_capt = 0x22, + tcb2_cnt = 0x23, + tcd0_in_a = 0x28, + tcd0_in_b = 0x29, #if defined(PIN_PA7) // not on 14-pin ones. - evouta_pin_pa7 = 0x8D, + evouta_pin_pa7 = 0x8D, #endif #if defined(PIN_PC7) - evoutc_pin_pc7 = 0x8F, + evoutc_pin_pc7 = 0x8F, #endif - evoutd_pin_pd7 = 0x90, + evoutd_pin_pd7 = 0x90, #endif // __AVR_DD__ }; }; @@ -705,521 +706,559 @@ namespace user { // tinyAVR-2 definitions #elif defined(TINY_2_SERIES) -namespace gen { - enum generator_t : uint8_t { - disable = 0x00, - updi_synch = 0x1, - rtc_ovf = 0x6, - rtc_cmp = 0x7, - ccl0_out = 0x10, - ccl1_out = 0x11, - ccl2_out = 0x12, - ccl3_out = 0x13, - ac0_out = 0x20, - adc0_ready = 0x24, - adc0_sample = 0x25, - adc0_window = 0x26, - usart0_xck = 0x60, - usart1_xck = 0x61, - spi0_sck = 0x68, - tca0_ovf_lunf = 0x80, - tca0_hunf = 0x81, - tca0_cmp0 = 0x84, - tca0_cmp1 = 0x85, - tca0_cmp2 = 0x86, - tcb0 = 0xA0, - tcb0_capt = 0xA0, - tcb0_ovf = 0xA1, - tcb1 = 0xA2, - tcb1_capt = 0xA2, - tcb1_ovf = 0xA3, + namespace gen { + enum generator_t : uint8_t { + disable = 0x00, + updi_synch = 0x1, + rtc_ovf = 0x6, + rtc_cmp = 0x7, + ccl0_out = 0x10, + ccl1_out = 0x11, + ccl2_out = 0x12, + ccl3_out = 0x13, + ac0_out = 0x20, + adc0_ready = 0x24, + adc0_sample = 0x25, + adc0_window = 0x26, + usart0_xck = 0x60, + usart1_xck = 0x61, + spi0_sck = 0x68, + tca0_ovf_lunf = 0x80, + tca0_hunf = 0x81, + tca0_cmp0 = 0x84, + tca0_cmp1 = 0x85, + tca0_cmp2 = 0x86, + tcb0 = 0xA0, + tcb0_capt = 0xA0, + tcb0_ovf = 0xA1, + tcb1 = 0xA2, + tcb1_capt = 0xA2, + tcb1_ovf = 0xA3, + }; }; -}; -namespace gen0 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, - pin_pb0 = 0x40, - pin_pb1 = 0x41, - pin_pb2 = 0x42, - pin_pb3 = 0x43, + namespace gen0 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, #if defined(PIN_PB4) - pin_pb4 = 0x44, - pin_pb5 = 0x45, + pin_pb4 = 0x44, + pin_pb5 = 0x45, #endif #if defined(PIN_PB6) - pin_pb6 = 0x46, - pin_pb7 = 0x47, + pin_pb6 = 0x46, + pin_pb7 = 0x47, #endif + }; }; -}; -namespace gen1 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, - pin_pb0 = 0x40, - pin_pb1 = 0x41, - pin_pb2 = 0x42, - pin_pb3 = 0x43, + namespace gen1 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, #if defined(PIN_PB4) - pin_pb4 = 0x44, - pin_pb5 = 0x45, + pin_pb4 = 0x44, + pin_pb5 = 0x45, #endif #if defined(PIN_PB6) - pin_pb6 = 0x46, - pin_pb7 = 0x47, + pin_pb6 = 0x46, + pin_pb7 = 0x47, #endif + }; }; -}; -namespace gen2 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, + namespace gen2 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, #if defined(PIN_PC0) - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #endif #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, -#endif - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + }; }; -}; -namespace gen3 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, + namespace gen3 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, #if defined(PIN_PC0) - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #endif #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, -#endif - pin_pa0 = 0x40, - pin_pa1 = 0x41, - pin_pa2 = 0x42, - pin_pa3 = 0x43, - pin_pa4 = 0x44, - pin_pa5 = 0x45, - pin_pa6 = 0x46, - pin_pa7 = 0x47, + pin_pc4 = 0x44, + pin_pc5 = 0x45, +#endif + pin_pa0 = 0x40, + pin_pa1 = 0x41, + pin_pa2 = 0x42, + pin_pa3 = 0x43, + pin_pa4 = 0x44, + pin_pa5 = 0x45, + pin_pa6 = 0x46, + pin_pa7 = 0x47, + }; }; -}; -namespace gen4 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div8192 = 0x08, - rtc_div4096 = 0x09, - rtc_div2048 = 0x0A, - rtc_div1024 = 0x0B, - pin_pb0 = 0x40, - pin_pb1 = 0x41, - pin_pb2 = 0x42, - pin_pb3 = 0x43, + namespace gen4 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div8192 = 0x08, + rtc_div4096 = 0x09, + rtc_div2048 = 0x0A, + rtc_div1024 = 0x0B, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, #if defined(PIN_PB4) - pin_pb4 = 0x44, - pin_pb5 = 0x45, + pin_pb4 = 0x44, + pin_pb5 = 0x45, #endif #if defined(PIN_PB6) - pin_pb6 = 0x46, - pin_pb7 = 0x47, + pin_pb6 = 0x46, + pin_pb7 = 0x47, #endif #if defined(PIN_PC0) - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #endif #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, + pin_pc4 = 0x44, + pin_pc5 = 0x45, #endif + }; }; -}; -namespace gen5 { - enum generator_t : uint8_t { - disable = 0x00, - rtc_div512 = 0x08, - rtc_div256 = 0x09, - rtc_div128 = 0x0A, - rtc_div64 = 0x0B, - pin_pb0 = 0x40, - pin_pb1 = 0x41, - pin_pb2 = 0x42, - pin_pb3 = 0x43, + namespace gen5 { + enum generator_t : uint8_t { + disable = 0x00, + rtc_div512 = 0x08, + rtc_div256 = 0x09, + rtc_div128 = 0x0A, + rtc_div64 = 0x0B, + pin_pb0 = 0x40, + pin_pb1 = 0x41, + pin_pb2 = 0x42, + pin_pb3 = 0x43, #if defined(PIN_PB4) - pin_pb4 = 0x44, - pin_pb5 = 0x45, + pin_pb4 = 0x44, + pin_pb5 = 0x45, #endif #if defined(PIN_PB6) - pin_pb6 = 0x46, - pin_pb7 = 0x47, + pin_pb6 = 0x46, + pin_pb7 = 0x47, #endif #if defined(PIN_PC0) - pin_pc0 = 0x40, - pin_pc1 = 0x41, - pin_pc2 = 0x42, - pin_pc3 = 0x43, + pin_pc0 = 0x40, + pin_pc1 = 0x41, + pin_pc2 = 0x42, + pin_pc3 = 0x43, #endif #if defined(PIN_PC4) - pin_pc4 = 0x44, - pin_pc5 = 0x45, + pin_pc4 = 0x44, + pin_pc5 = 0x45, #endif + }; }; -}; -namespace user { - enum user_t : uint8_t { - ccl0_event_a = 0x00, - ccl0_event_b = 0x01, - ccl1_event_a = 0x02, - ccl1_event_b = 0x03, - ccl2_event_a = 0x04, - ccl2_event_b = 0x05, - ccl3_event_a = 0x06, - ccl3_event_b = 0x07, - adc0_start = 0x08, - evouta_pin_pa2 = 0x09, - evouta_pin_pa7 = 0x89, - evoutb_pin_pb2 = 0x0A, + namespace user { + enum user_t : uint8_t { + ccl0_event_a = 0x00, + ccl0_event_b = 0x01, + ccl1_event_a = 0x02, + ccl1_event_b = 0x03, + ccl2_event_a = 0x04, + ccl2_event_b = 0x05, + ccl3_event_a = 0x06, + ccl3_event_b = 0x07, + adc0_start = 0x08, + evouta_pin_pa2 = 0x09, + evouta_pin_pa7 = 0x89, + evoutb_pin_pb2 = 0x0A, #if defined(PIN_PB7) - evoutb_pin_pb7 = 0x8A, + evoutb_pin_pb7 = 0x8A, #endif #if defined(PIN_PC2) - evoutc_pin_pc2 = 0x0B, -#endif - usart0_irda = 0x0C, - usart1_irda = 0x0D, - tca0 = 0x0E, - tca0_cnt_a = 0x0E, - tca0_cnt_b = 0x0F, - tcb0 = 0x11, - tcb0_capt = 0x11, - tcb0_cnt = 0x12, - tcb1 = 0x13, - tcb1_capt = 0x13, - tcb1_cnt = 0x14, + evoutc_pin_pc2 = 0x0B, +#endif + usart0_irda = 0x0C, + usart1_irda = 0x0D, + tca0 = 0x0E, + tca0_cnt_a = 0x0E, + tca0_cnt_b = 0x0F, + tcb0 = 0x11, + tcb0_capt = 0x11, + tcb0_cnt = 0x12, + tcb1 = 0x13, + tcb1_capt = 0x13, + tcb1_cnt = 0x14, + }; }; -}; // tinyAVR-0/1 definitions #elif defined(TINY_0_SERIES) || defined(TINY_1_SERIES) -namespace gen0 { - enum generator_t : uint8_t { + namespace gen0 { + enum generator_t : uint8_t { #if defined(PIN_PC0) - pin_pc0 = 0x07, - pin_pc1 = 0x08, - pin_pc2 = 0x09, - pin_pc3 = 0x0A, + pin_pc0 = 0x07, + pin_pc1 = 0x08, + pin_pc2 = 0x09, + pin_pc3 = 0x0A, #endif #if defined(PIN_PC4) - pin_pc4 = 0x0B, - pin_pc5 = 0x0C, -#endif - pin_pa0 = 0x0D, - pin_pa1 = 0x0E, - pin_pa2 = 0x0F, - pin_pa3 = 0x10, - pin_pa4 = 0x11, - pin_pa5 = 0x12, - pin_pa6 = 0x13, - pin_pa7 = 0x14, + pin_pc4 = 0x0B, + pin_pc5 = 0x0C, +#endif + pin_pa0 = 0x0D, + pin_pa1 = 0x0E, + pin_pa2 = 0x0F, + pin_pa3 = 0x10, + pin_pa4 = 0x11, + pin_pa5 = 0x12, + pin_pa6 = 0x13, + pin_pa7 = 0x14, #if (PROGMEM_SIZE > 8192 && defined(TINY_1_SERIES)) - tcb1 = 0x15, - tcb1_capt = 0x15, + tcb1 = 0x15, + tcb1_capt = 0x15, #endif + }; }; -}; -namespace gen2 { - enum generator_t : uint8_t { - pin_pa0 = 0x0A, - pin_pa1 = 0x0B, - pin_pa2 = 0x0C, - pin_pa3 = 0x0D, - pin_pa4 = 0x0E, - pin_pa5 = 0x0F, - pin_pa6 = 0x10, - pin_pa7 = 0x11, - updi = 0x12, + namespace gen2 { + enum generator_t : uint8_t { + pin_pa0 = 0x0A, + pin_pa1 = 0x0B, + pin_pa2 = 0x0C, + pin_pa3 = 0x0D, + pin_pa4 = 0x0E, + pin_pa5 = 0x0F, + pin_pa6 = 0x10, + pin_pa7 = 0x11, + updi = 0x12, #if (PROGMEM_SIZE > 8192 && defined(TINY_1_SERIES)) - ac1_out = 0x13, - ac2_out = 0x14, + ac1_out = 0x13, + ac2_out = 0x14, #endif + }; }; -}; // Only on parts with > 8 pins does this have any unique options #if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) -namespace gen3 { - enum generator_t : uint8_t { - pin_pb0 = 0x0A, - pin_pb1 = 0x0B, - pin_pb2 = 0x0C, - pin_pb3 = 0x0D, + namespace gen3 { + enum generator_t : uint8_t { + pin_pb0 = 0x0A, + pin_pb1 = 0x0B, + pin_pb2 = 0x0C, + pin_pb3 = 0x0D, #if defined(PIN_PB4) - pin_pb4 = 0x0E, - pin_pb5 = 0x0F, + pin_pb4 = 0x0E, + pin_pb5 = 0x0F, #endif #if defined(PIN_PB6) - pin_pb6 = 0x10, - pin_pb7 = 0x11, + pin_pb6 = 0x10, + pin_pb7 = 0x11, #endif #if (PROGMEM_SIZE > 8192 && MEGATINYCORE_SERIES == 1) - ac1_out = 0x12, - ac2_out = 0x13, + ac1_out = 0x12, + ac2_out = 0x13, #endif + }; }; -}; #endif #if defined(TINY_1_SERIES) #if defined(__AVR_ATtinyxy4__) || defined(__AVR_ATtinyxy6__) || defined(__AVR_ATtinyxy7__) -// Only 1-series parts have second sync channel. -// Only on parts with > 8 pins does it have any unique options -namespace gen1 { - enum generator_t : uint8_t { - pin_pb0 = 0x08, - pin_pb1 = 0x09, - pin_pb2 = 0x0A, - pin_pb3 = 0x0B, + // Only 1-series parts have second sync channel. + // Only on parts with > 8 pins does it have any unique options + namespace gen1 { + enum generator_t : uint8_t { + pin_pb0 = 0x08, + pin_pb1 = 0x09, + pin_pb2 = 0x0A, + pin_pb3 = 0x0B, #if defined(PIN_PB0) - pin_pb4 = 0x0C, - pin_pb5 = 0x0D, + pin_pb4 = 0x0C, + pin_pb5 = 0x0D, #endif #if defined(PIN_PB6) - pin_pb6 = 0x0E, - pin_pb7 = 0x0F, + pin_pb6 = 0x0E, + pin_pb7 = 0x0F, #endif #if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here - tcb1 = 0x10, - tcb1_capt = 0x10, + tcb1 = 0x10, + tcb1_capt = 0x10, #endif + }; }; -}; #endif -// Only 1-series parts have third and fourth async sync channel. -// and only parts with 20/24 pins, or the 1614 have any items on this list available + // Only 1-series parts have third and fourth async sync channel. + // and only parts with 20/24 pins, or the 1614 have any items on this list available #if !(defined(__AVR_ATtinyxy2__) || (defined(__AVR_ATtinyxy4__) && PROGMEM_SIZE <= 8192)) -namespace gen4 { - enum generator_t : uint8_t { + namespace gen4 { + enum generator_t : uint8_t { #if defined(PIN_PC0) - pin_pc0 = 0x0A, - pin_pc1 = 0x0B, - pin_pc2 = 0x0C, - pin_pc3 = 0x0D, + pin_pc0 = 0x0A, + pin_pc1 = 0x0B, + pin_pc2 = 0x0C, + pin_pc3 = 0x0D, #endif #if defined(PIN_PC4) - pin_pc4 = 0x0E, - pin_pc5 = 0x0F, + pin_pc4 = 0x0E, + pin_pc5 = 0x0F, #endif #if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series, but only 1-series is here - ac1_out = 0x10, - ac2_out = 0x11, + ac1_out = 0x10, + ac2_out = 0x11, #endif + }; }; -}; #endif -namespace gen5 { - enum generator_t : uint8_t { - rtc_div8192 = 0x0A, - rtc_div4096 = 0x0B, - rtc_div2048 = 0x0C, - rtc_div1024 = 0x0D, - rtc_div512 = 0x0E, - rtc_div256 = 0x0F, - rtc_div128 = 0x10, - rtc_div64 = 0x11, + namespace gen5 { + enum generator_t : uint8_t { + rtc_div8192 = 0x0A, + rtc_div4096 = 0x0B, + rtc_div2048 = 0x0C, + rtc_div1024 = 0x0D, + rtc_div512 = 0x0E, + rtc_div256 = 0x0F, + rtc_div128 = 0x10, + rtc_div64 = 0x11, #if (PROGMEM_SIZE > 8192) // Only 16/32k 1-series - ac1_out = 0x12, - ac2_out = 0x13, + ac1_out = 0x12, + ac2_out = 0x13, #endif + }; }; -}; #endif // end of 1-series only part. -namespace gens { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - tcb0 = 0x01, - tcb0_capt = 0x01, - tca0_ovf_lunf = 0x02, - tca0_hunf = 0x03, - tca0_cmp0 = 0x04, - tca0_cmp1 = 0x05, - tca0_cmp2 = 0x06, + namespace gens { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + tcb0 = 0x01, + tcb0_capt = 0x01, + tca0_ovf_lunf = 0x02, + tca0_hunf = 0x03, + tca0_cmp0 = 0x04, + tca0_cmp1 = 0x05, + tca0_cmp2 = 0x06, + }; }; -}; -namespace gen { - enum generator_t : uint8_t { - disable = 0x00, - off = 0x00, - ccl_lut0 = 0x01, - ccl_lut1 = 0x02, - ac0_out = 0x03, + namespace gen { + enum generator_t : uint8_t { + disable = 0x00, + off = 0x00, + ccl_lut0 = 0x01, + ccl_lut1 = 0x02, + ac0_out = 0x03, #if defined(TINY_1_SERIES) - tcd0_cmpbclr = 0x04, - tcd0_cmpaset = 0x05, - tcd0_cmpbset = 0x06, - tcd0_progev = 0x07, -#endif - rtc_ovf = 0x08, - rtc_cmp = 0x09, + tcd0_cmpbclr = 0x04, + tcd0_cmpaset = 0x05, + tcd0_cmpbset = 0x06, + tcd0_progev = 0x07, +#endif + rtc_ovf = 0x08, + rtc_cmp = 0x09, + }; }; -}; -namespace user { - enum user_t : uint8_t { - tcb0 = 0x00, - tcb0_capt = 0x00, - adc0_start = 0x01, - ccl0_event_a = 0x02, - ccl1_event_a = 0x03, - ccl0_event_b = 0x04, - ccl1_event_b = 0x05, - tcd0_in_a = 0x06, - tcd0_in_b = 0x07, - evouta_pin_pa2 = 0x08, - evoutb_pin_pb2 = 0x09, - evoutc_pin_pc2 = 0x0A, - tcb1 = 0x0B, - tcb1_capt = 0x0B, - adc1_start = 0x0c, - tca0 = 0x10, - tca0_cnt_a = 0x10, - usart0_irda = 0x11, + namespace user { + enum user_t : uint8_t { + tcb0 = 0x00, + tcb0_capt = 0x00, + adc0_start = 0x01, + ccl0_event_a = 0x02, + ccl1_event_a = 0x03, + ccl0_event_b = 0x04, + ccl1_event_b = 0x05, + tcd0_in_a = 0x06, + tcd0_in_b = 0x07, + evouta_pin_pa2 = 0x08, + evoutb_pin_pb2 = 0x09, + evoutc_pin_pc2 = 0x0A, + tcb1 = 0x0B, + tcb1_capt = 0x0B, + adc1_start = 0x0c, + tca0 = 0x10, + tca0_cnt_a = 0x10, + usart0_irda = 0x11, + }; }; -}; #endif // TINY_0_SERIES || TINY_1_SERIES +}; + +// Legacy definitions +namespace user { using namespace event::user; }; +namespace gen { using namespace event::gen; }; +#if defined(EVSYS_CHANNEL0) +namespace gen0 { using namespace event::gen0; }; +#endif +#if defined(EVSYS_CHANNEL1) +namespace gen1 { using namespace event::gen1; }; +#endif +#if defined(EVSYS_CHANNEL2) +namespace gen2 { using namespace event::gen2; }; +#endif +#if defined(EVSYS_CHANNEL3) +namespace gen3 { using namespace event::gen3; }; +#endif +#if defined(EVSYS_CHANNEL4) +namespace gen4 { using namespace event::gen4; }; +#endif +#if defined(EVSYS_CHANNEL5) +namespace gen5 { using namespace event::gen5; }; +#endif +#if defined(EVSYS_CHANNEL6) +namespace gen6 { using namespace event::gen6; }; +#endif +#if defined(EVSYS_CHANNEL7) +namespace gen7 { using namespace event::gen7; }; +#endif +#if defined(EVSYS_CHANNEL8) +namespace gen8 { using namespace event::gen8; }; +#endif +#if defined(EVSYS_CHANNEL9) +namespace gen9 { using namespace event::gen9; }; +#endif +#if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) +namespace gens { using namespace event::gens; }; +#endif class Event { public: Event(uint8_t channel_num, volatile uint8_t &channel_addr); uint8_t get_channel_number(); static Event& get_channel(uint8_t channel_number); - static Event& get_generator_channel(gen::generator_t generator); + static Event& get_generator_channel(event::gen::generator_t generator); static Event& get_generator_channel(uint8_t generator_pin); uint8_t get_generator(); - void set_generator(gen::generator_t generator); - static Event& assign_generator(gen::generator_t event_generator); + void set_generator(event::gen::generator_t generator); + static Event& assign_generator(event::gen::generator_t event_generator); void set_generator(uint8_t pin_number); static Event& assign_generator_pin(uint8_t port, uint8_t port_pin); static Event& assign_generator_pin(uint8_t pin_number); - static int8_t get_user_channel_number(user::user_t event_user); - static Event& get_user_channel(user::user_t event_user); - void set_user(user::user_t event_user); + static int8_t get_user_channel_number(event::user::user_t event_user); + static Event& get_user_channel(event::user::user_t event_user); + void set_user(event::user::user_t event_user); int8_t set_user_pin(uint8_t pin_number); - static void clear_user(user::user_t event_user); + static void clear_user(event::user::user_t event_user); void soft_event(); void long_soft_event(uint8_t length); // event_types: They start from 0x00 for inputs, outputs start at 0x40 - static gen::generator_t gen_from_peripheral(AC_t& comp); - static gen::generator_t gen_from_peripheral(CCL_t& logic, uint8_t event_type = 0); - static user::user_t user_from_peripheral(CCL_t& logic, uint8_t user_type = 0); - static gen::generator_t gen_from_peripheral(TCA_t& timer, uint8_t event_type = 0); - static user::user_t user_from_peripheral(TCA_t& timer, uint8_t user_type = 0); - static gen::generator_t gen_from_peripheral(TCB_t& timer, uint8_t event_type = 0); - static user::user_t user_from_peripheral(TCB_t& timer, uint8_t user_type = 0); - static user::user_t user_from_peripheral(USART_t& usart); + static event::gen::generator_t gen_from_peripheral(AC_t& comp); + static event::gen::generator_t gen_from_peripheral(CCL_t& logic, uint8_t event_type = 0); + static event::user::user_t user_from_peripheral(CCL_t& logic, uint8_t user_type = 0); + static event::gen::generator_t gen_from_peripheral(TCA_t& timer, uint8_t event_type = 0); + static event::user::user_t user_from_peripheral(TCA_t& timer, uint8_t user_type = 0); + static event::gen::generator_t gen_from_peripheral(TCB_t& timer, uint8_t event_type = 0); + static event::user::user_t user_from_peripheral(TCB_t& timer, uint8_t user_type = 0); + static event::user::user_t user_from_peripheral(USART_t& usart); void start(bool state = true); void stop(); #if defined(EVSYS_CHANNEL0) - void get_generator_channel(gen0::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen0::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen0::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen0::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL1) - void get_generator_channel(gen1::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen1::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen1::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen1::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL2) - void get_generator_channel(gen2::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen2::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen2::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen2::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL3) - void get_generator_channel(gen3::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen3::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen3::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen3::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL4) - void get_generator_channel(gen4::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen4::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen4::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen4::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL5) - void get_generator_channel(gen5::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen5::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen5::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen5::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL6) - void get_generator_channel(gen6::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen6::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen6::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen6::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL7) - void get_generator_channel(gen7::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen7::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen7::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen7::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL8) - void get_generator_channel(gen8::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen8::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen8::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen8::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(EVSYS_CHANNEL9) - void get_generator_channel(gen9::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen9::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gen9::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen9::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif #if defined(TINY_0_SERIES) || defined(TINY_1_SERIES) - void get_generator_channel(gens::generator_t generator) { get_generator_channel((gen::generator_t)generator); } - void set_generator(gen::generator_t generator) { set_generator((gen::generator_t)generator); } + void get_generator_channel(event::gens::generator_t generator) { get_generator_channel((event::gen::generator_t)generator); } + void set_generator(event::gen::generator_t generator) { set_generator((event::gen::generator_t)generator); } #endif private: From 15e38ae7744fc3154eaafcf1e95dd7768d21b88b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 15 Jun 2022 20:37:58 +0200 Subject: [PATCH 303/351] Add extra namespace to Logic constants #150 related --- megaavr/libraries/Logic/README.md | 130 +++--- .../Five_input_NOR/Five_input_NOR.ino | 32 +- .../Logic/examples/Interrupt/Interrupt.ino | 16 +- .../Three_input_AND/Three_input_AND.ino | 16 +- .../Three_input_NAND/Three_input_NAND.ino | 16 +- .../Three_input_OR/Three_input_OR.ino | 16 +- .../examples/Two_input_AND/Two_input_AND.ino | 14 +- .../Two_input_NAND/Two_input_NAND.ino | 14 +- .../examples/Two_input_OR/Two_input_OR.ino | 14 +- megaavr/libraries/Logic/keywords.txt | 1 + megaavr/libraries/Logic/library.properties | 2 +- megaavr/libraries/Logic/src/Logic.cpp | 34 +- megaavr/libraries/Logic/src/Logic.h | 424 +++++++++--------- 13 files changed, 370 insertions(+), 359 deletions(-) diff --git a/megaavr/libraries/Logic/README.md b/megaavr/libraries/Logic/README.md index bd66c2f..c2fc999 100644 --- a/megaavr/libraries/Logic/README.md +++ b/megaavr/libraries/Logic/README.md @@ -37,25 +37,25 @@ Variable for setting what mode input 0..2 on a logic block should have. Accepted values for megaAVR 0-series parts: ``` c++ -in::masked; // Pin not in use -in::unused; // Pin not in use -in::disable; // Pin not in use -in::feedback; // Connect output of sequencer (if used) or even-numbered logic block (n or n-1) to this input -in::link; // Connect output of logic block n+1 to this input -in::event_0; // Connect input to event a -in::event_a; // Connect input to event a -in::event_1; // Connect input to event b -in::event_b; // Connect input to event b -in::pin; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, do not change pinMode -in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup on -in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off -in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off -in::ac; // Connect input to the output of the internal analog comparator (input 0,1,2 from AC0,1,2) -in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX -in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK -in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 -in::tca; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 -in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO. +logic::in::masked; // Pin not in use +logic::in::unused; // Pin not in use +logic::in::disable; // Pin not in use +logic::in::feedback; // Connect output of sequencer (if used) or even-numbered logic block (n or n-1) to this input +logic::in::link; // Connect output of logic block n+1 to this input +logic::in::event_0; // Connect input to event a +logic::in::event_a; // Connect input to event a +logic::in::event_1; // Connect input to event b +logic::in::event_b; // Connect input to event b +logic::in::pin; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, do not change pinMode +logic::in::input_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup on +logic::in::input; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +logic::in::input_no_pullup; // Connect input to CCL IN0, IN1, IN2 for input 0, 1, 2, set input, pullup off +logic::in::ac; // Connect input to the output of the internal analog comparator (input 0,1,2 from AC0,1,2) +logic::in::uart; // Connect input to UART TX. Input 0 connects to UART0 TX, input 1 to UART1 TX, and input 2 to UART2 TX +logic::in::spi; // Connect input to SPI. Input 0 and 1 connects to MOSI, and input 2 connects to SCK +logic::in::tca0; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 +logic::in::tca; // Connect input to TCA0. Input 0 connects to WO0, input 1 to WO1 and input2 to WO2 +logic::in::tcb; // Connect input to TCB. Input 0 connects to TCB0 W0, input 1 to TCB1 WO, and input 2 to TCB2 WO. ``` Notes specific to ATmega parts @@ -67,47 +67,47 @@ Notes specific to ATmega parts ##### Usage ``` c++ -Logic0.input0 = in::link; // Connect output from block 1 to input 0 of block 0 -Logic0.input1 = in::input; // Connect the input 1 from block 0 to its GPIO -Logic0.input2 = in::input_pullup; // Connect the input 2 from block 0 to its GPIO, with pullup on +Logic0.input0 = logic::in::link; // Connect output from block 1 to input 0 of block 0 +Logic0.input1 = logic::in::input; // Connect the input 1 from block 0 to its GPIO +Logic0.input2 = logic::in::input_pullup; // Connect the input 2 from block 0 to its GPIO, with pullup on ``` ##### Default state -`LogicN.inputN` defaults to `in::unused` if not specified in the user program. +`LogicN.inputN` defaults to `logic::in::unused` if not specified in the user program. ### output Variable for changing the logic block output pin behavior. Note that the output of the logic block still can be used internally if the output pin is disabled. Accepted values: ```c++ -out::disable; // Disable the output GPIO pin. Useful when triggering an interrupt instead. -out::enable; // Enable the output GPIO pin +logic::out::disable; // Disable the output GPIO pin. Useful when triggering an interrupt instead. +logic::out::enable; // Enable the output GPIO pin ``` ##### Usage ```c++ -Logic0.output = out::disable; // Disable the output GPIO pin. +Logic0.output = logic::out::disable; // Disable the output GPIO pin. ``` ##### Default state -`LogicN.output` defaults to `out::disable` if not specified in the user program. +`LogicN.output` defaults to `logic::out::disable` if not specified in the user program. ### output_swap Variable for pin swapping the physical output pin to its alternative position. See the pinout diagrams in the main MegaCoreX README for detailed info. Accepted values: ```c++ -out::no_swap; // Use default pin position, pin 3 on the port -out::pin_swap; // Use alternative position, pin 6 on the port +logic::out::no_swap; // Use default pin position, pin 3 on the port +logic::out::pin_swap; // Use alternative position, pin 6 on the port ``` ##### Usage ```c++ -Logic0.output_swap = out::no_swap; // No pin swap for output of block0 +Logic0.output_swap = logic::out::no_swap; // No pin swap for output of block0 ``` ##### Default state -`LogicN.output_swap` defaults to `out::no_swap` if not specified in the user program. +`LogicN.output_swap` defaults to `logic::out::no_swap` if not specified in the user program. ### filter @@ -117,20 +117,20 @@ Alternately, the delay itself may be desirable, or it can be combined with a con Either filter or synchronizer is required for edge detector, below. Accepted values: ```c++ -filter::disable; // No filter used, asynchronous output. -filter::synchronizer; // Connect synchronizer to output; delays output by 2 clock cycles. -filter::synch; // Syntactic sugar for synchronizer -filter::sync; // Syntactic sugar for synchronizer -filter::filter; // Connect filter to output; delays output by 4 clock cycles, only passes output that is stable for >2 clock cycles. +logic::filter::disable; // No filter used, asynchronous output. +logic::filter::synchronizer; // Connect synchronizer to output; delays output by 2 clock cycles. +logic::filter::synch; // Syntactic sugar for synchronizer +logic::filter::sync; // Syntactic sugar for synchronizer +logic::filter::filter; // Connect filter to output; delays output by 4 clock cycles, only passes output that is stable for >2 clock cycles. ``` ##### Usage ```c++ -Logic0.filter = filter::filter; // Enable filter on output of block 0 +Logic0.filter = logic::filter::filter; // Enable filter on output of block 0 ``` ##### Default state -`LogicN.filter` defaults to `filter::disable` if not specified in the user program. +`LogicN.filter` defaults to `logic::filter::disable` if not specified in the user program. ### clocksource @@ -138,34 +138,34 @@ Variable to set the clock source for the logic block; this is used for the synch If sequential logic is used, it is clocked from the clock source used by the even-numbered logic block. Accepted values: ```c++ -clocksource::clk_per; // Clock from the peripheral clock (ie, system clock) -clocksource::in2; // Clock from the selected input2; it is treated as a 0 in the truth table. +logic::clocksource::clk_per; // Clock from the peripheral clock (ie, system clock) +logic::clocksource::in2; // Clock from the selected input2; it is treated as a 0 in the truth table. ``` ##### Usage ```c++ -Logic0.clocksource = clocksource::clk_per; +Logic0.clocksource = logic::clocksource::clk_per; ``` ##### Default state -`LogicN.clocksource` defaults to `clocksource::clk_per` if not specified in the user program. +`LogicN.clocksource` defaults to `logic::clocksource::clk_per` if not specified in the user program. ### edgedetect Variable for controlling use of the edge detector. The edge detector can be used to generate a pulse when detecting a rising edge on its input. To detect a falling edge, the TRUTH table should be programmed to provide inverted output. In order to avoid unpredictable behavior, a valid filter option must be enabled. Note that this is likely only of use when the output is being used for sequential logic or as the input to another logic block; it looks particularly useful on the odd LUT input to a J-K flip-flop sequential logic unit. ```c++ -edgedetect::disable; // No edge detection used -edgedetect::enable; // Edge detection used +logic::edgedetect::disable; // No edge detection used +logic::edgedetect::enable; // Edge detection used ``` #### Usage ```c++ -Logic0.edgedetect = edgedetect::enable; +Logic0.edgedetect = logic::edgedetect::enable; ``` ##### Default state -`LogicN.edgedetect` defaults to `edgedetect::disable` if not specified in the user program. +`LogicN.edgedetect` defaults to `logic::edgedetect::disable` if not specified in the user program. ### sequencer @@ -173,20 +173,20 @@ Variable for connecting a "sequencer" to the logic block output - these are latc Accepted values: ```c++ -sequencer::disable; // No sequencer connected -sequencer::d_flip_flop; // D flip flop sequencer connected -sequencer::jk_flip_flop; // JK flip flop sequencer connected -sequencer::d_latch; // Gated D latch sequencer connected - note that on most megaAVR parts, this doesn't work. See the Errata. -sequencer::rs_latch; // RS latch sequencer connected +logic::sequencer::disable; // No sequencer connected +logic::sequencer::d_flip_flop; // D flip flop sequencer connected +logic::sequencer::jk_flip_flop; // JK flip flop sequencer connected +logic::sequencer::d_latch; // Gated D latch sequencer connected - note that on most megaAVR parts, this doesn't work. See the Errata. +logic::sequencer::rs_latch; // RS latch sequencer connected ``` ##### Usage ```c++ -Logic0.sequencer = sequencer::disable; // Disable sequencer +Logic0.sequencer = logic::sequencer::disable; // Disable sequencer ``` ##### Default state -`LogicN.sequencer` defaults to `sequencer::disable` if not specified in the user program. +`LogicN.sequencer` defaults to `logic::sequencer::disable` if not specified in the user program. ### truth @@ -231,24 +231,24 @@ Logic::stop(); // Stop CCL ``` ## Reconfiguring -There are TWO levels of "enable protection" on the CCL hardware. According to the Silicon Errata, only one of these is intended. -As always, it's anyone's guess when or if this issue will be corrected in a future silicon revision. -The intended enable-protection is that a given logic block cannot be reconfigured while enabled. +There are TWO levels of "enable protection" on the CCL hardware. According to the Silicon Errata, only one of these is intended. +As always, it's anyone's guess when or if this issue will be corrected in a future silicon revision. +The intended enable-protection is that a given logic block cannot be reconfigured while enabled. This is handled by `init()` - you can write your new setting to a logic block, call `LogicN.init()` and it will briefly disable the logic block, make the changes, and reenable it. -The unintended layer is that no logic block can be reconfigured without also disabling the whole CCL system. -Changes can be freely made to the `Logic` classes, however, only the `init()` method will apply those changes, and you must call `Logic::stop()` before calling them, and `Logic::start()` afterwards. +The unintended layer is that no logic block can be reconfigured without also disabling the whole CCL system. +Changes can be freely made to the `Logic` classes, however, only the `init()` method will apply those changes, and you must call `Logic::stop()` before calling them, and `Logic::start()` afterwards. ##### Example ```c++ // logic blocks 0, 1 configured, initialized, and in use -Logic1.truth=0x55; // new truth table -Logic1.input2=tca0; // and different input 2 -Logic3.enabled=true; // enable another LUT -Logic3.input0=in::link; // Use link from LUT0 -Logic3.input1=in::ac; // and the analog comparator -Logic3.input2=in::pin; // and the LUT3 IN2 pin -Logic3.truth=0x79; // truth table for LUT3 +Logic1.truth=0x55; // new truth table +Logic1.input2=logic::in::tca0; // and different input 2 +Logic3.enabled=true; // enable another LUT +Logic3.input0=logic::in::link; // Use link from LUT0 +Logic3.input1=logic::in::ac; // and the analog comparator +Logic3.input2=logic::in::pin; // and the LUT3 IN2 pin +Logic3.truth=0x79; // truth table for LUT3 Logic3.attachInterrupt(RISING,interruptFunction); diff --git a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino index cf9ef8d..71fd7ef 100644 --- a/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino +++ b/megaavr/libraries/Logic/examples/Five_input_NOR/Five_input_NOR.ino @@ -22,25 +22,25 @@ void setup() // Initialize logic block 1 // Logic block 1 has three inputs, PC0, PC1 and PC2. // It's output, PC3 is disabled because we connect the output signal to block 0 internally - Logic1.enable = true; // Enable logic block 1 - Logic1.input0 = in::input_pullup; // Set PC0 as input with pullup - Logic1.input1 = in::input_pullup; // Set PC1 as input with pullup - Logic1.input2 = in::input_pullup; // Set PC2 as input with pullup - Logic1.output = out::disable; // No output on PC3 - Logic1.filter = filter::disable; // No output filter enabled - Logic1.truth = 0xFE; // Set truth table - + Logic1.enable = true; // Enable logic block 1 + Logic1.input0 = logic::in::input_pullup; // Set PC0 as input with pullup + Logic1.input1 = logic::in::input_pullup; // Set PC1 as input with pullup + Logic1.input2 = logic::in::input_pullup; // Set PC2 as input with pullup + Logic1.output = logic::out::disable; // No output on PC3 + Logic1.filter = logic::filter::disable; // No output filter enabled + Logic1.truth = 0xFE; // Set truth table + // Initialize logic block 0 - // Logic block 0 has three inputs, PA0, PA1 and PA2. + // Logic block 0 has three inputs, PA0, PA1 and PA2. // input2 is internally connected to the output of block1 (which means PA2 is freed up) // Block 0 output on PA3 - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic0.input2 = in::link; // Route output from block 1 to this input internally - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0x01; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = logic::in::link; // Route output from block 1 to this input internally + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0x01; // Set truth table // Initialize logic block 0 and 1 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino index d381bb9..12993ef 100644 --- a/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino +++ b/megaavr/libraries/Logic/examples/Interrupt/Interrupt.ino @@ -33,17 +33,17 @@ void setup() { // Modify the serial port to match your hardware Serial.begin(9600); - + // Initialize logic block 2 // Logic block 2 has three inputs, PA0, PA1 and PA2. // It has one output, but this is disabled because we're using an interrupt instead. - Logic2.enable = true; // Enable logic block 2 - Logic2.input0 = in::input_pullup; // Set PD0 as input with pullup - Logic2.input1 = in::input_pullup; // Set PD1 as input with pullup - Logic2.input2 = in::input_pullup; // Set PD2 as input with pullup - Logic2.output = out::disable; // Disable output on PD3 (we don't have to though) - Logic2.filter = filter::disable; // No output filter enabled - Logic2.truth = 0x01; // Set truth table + Logic2.enable = true; // Enable logic block 2 + Logic2.input0 = logic::in::input_pullup; // Set PD0 as input with pullup + Logic2.input1 = logic::in::input_pullup; // Set PD1 as input with pullup + Logic2.input2 = logic::in::input_pullup; // Set PD2 as input with pullup + Logic2.output = logic::out::disable; // Disable output on PD3 (we don't have to though) + Logic2.filter = logic::filter::disable; // No output filter enabled + Logic2.truth = 0x01; // Set truth table // Initialize logic block 2 Logic2.init(); diff --git a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino index fbf2534..9f74d2e 100644 --- a/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_AND/Three_input_AND.ino @@ -34,14 +34,14 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0x80; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = logic::in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0x80; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino index 36a39a1..652dc2a 100644 --- a/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Three_input_NAND/Three_input_NAND.ino @@ -34,14 +34,14 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0x7F; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = logic::in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0x7F; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino index 1fd8a2f..0c9b473 100644 --- a/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Three_input_OR/Three_input_OR.ino @@ -34,14 +34,14 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup - Logic0.input2 = in::input_pullup; // Set PA2 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0xFE; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup + Logic0.input2 = logic::in::input_pullup; // Set PA2 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0xFE; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino index 961f703..c7ed698 100644 --- a/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_AND/Two_input_AND.ino @@ -36,13 +36,13 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0x08; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0x08; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino index 3266d2a..5f5e529 100644 --- a/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino +++ b/megaavr/libraries/Logic/examples/Two_input_NAND/Two_input_NAND.ino @@ -36,13 +36,13 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0xF7; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0xF7; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino index fb5f539..de622bb 100644 --- a/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino +++ b/megaavr/libraries/Logic/examples/Two_input_OR/Two_input_OR.ino @@ -36,13 +36,13 @@ void setup() // Initialize logic block 0 // Logic block 0 has three inputs, PA0, PA1 and PA2. // It has one output, PA3, but can be swapped to PA6 if needed - Logic0.enable = true; // Enable logic block 0 - Logic0.input0 = in::input_pullup; // Set PA0 as input with pullup - Logic0.input1 = in::input_pullup; // Set PA1 as input with pullup -//Logic0.output_swap = out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 - Logic0.output = out::enable; // Enable logic block 0 output pin (PA3) - Logic0.filter = filter::disable; // No output filter enabled - Logic0.truth = 0xFE; // Set truth table + Logic0.enable = true; // Enable logic block 0 + Logic0.input0 = logic::in::input_pullup; // Set PA0 as input with pullup + Logic0.input1 = logic::in::input_pullup; // Set PA1 as input with pullup +//Logic0.output_swap = logic::out::pin_swap; // Uncomment this line to route the output to PA6 instead of PA3 + Logic0.output = logic::out::enable; // Enable logic block 0 output pin (PA3) + Logic0.filter = logic::filter::disable; // No output filter enabled + Logic0.truth = 0xFE; // Set truth table // Initialize logic block 0 Logic0.init(); diff --git a/megaavr/libraries/Logic/keywords.txt b/megaavr/libraries/Logic/keywords.txt index 8e167c1..6ad19d5 100644 --- a/megaavr/libraries/Logic/keywords.txt +++ b/megaavr/libraries/Logic/keywords.txt @@ -31,6 +31,7 @@ Logic3 KEYWORD2 # Constants (LITERAL1) ####################################### +logic LITERAL1 in LITERAL1 out LITERAL1 filter LITERAL1 diff --git a/megaavr/libraries/Logic/library.properties b/megaavr/libraries/Logic/library.properties index c57d9d9..d796a6d 100644 --- a/megaavr/libraries/Logic/library.properties +++ b/megaavr/libraries/Logic/library.properties @@ -1,5 +1,5 @@ name=Logic -version=1.1.1 +version=1.2.0 author=MCUdude and Spence Konde maintainer=MCUdude and Spence Konde sentence=A library for interfacing with the customizable logic in megaAVR 0-series, tinyAVR 0/1-series, and Dx-series chips. MegaCoreX version of documentation and examples. diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index dbf7614..0f52dd2 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -372,16 +372,16 @@ static const struct Logic::CCLBlock blocks[] = { Logic::Logic(const uint8_t block_number) : enable(false), - input0(in::masked), - input1(in::masked), - input2(in::masked), - output(out::disable), - output_swap(out::no_swap), - filter(filter::disable), - edgedetect(edgedetect::disable), + input0(logic::in::masked), + input1(logic::in::masked), + input2(logic::in::masked), + output(logic::out::disable), + output_swap(logic::out::no_swap), + filter(logic::filter::disable), + edgedetect(logic::edgedetect::disable), truth(0x00), - sequencer(sequencer::disable), - clocksource(clocksource::clk_per), + sequencer(logic::sequencer::disable), + clocksource(logic::clocksource::clk_per), block(blocks[block_number]) { } @@ -421,11 +421,11 @@ static volatile register8_t &PINCTRL(PORT_t &port, const uint8_t pin_bm) { return port.PIN7CTRL; } -void Logic::initInput(in::input_t &input, PORT_t &port, const uint8_t pin_bm) { +void Logic::initInput(logic::in::input_t &input, PORT_t &port, const uint8_t pin_bm) { if ((input & 0x30) && pin_bm) { // Input pin is either set to input or input with pullup port.DIRCLR = pin_bm; - if (input == in::input) { + if (input == logic::in::input) { PINCTRL(port, pin_bm) &= ~PORT_PULLUPEN_bm; } else { PINCTRL(port, pin_bm) |= PORT_PULLUPEN_bm; @@ -437,27 +437,27 @@ void Logic::init() { // Clear LUTCTRLA in case the CCL block gets reinitialized block.LUTCTRLA = 0x00; - + // Configure input pins initInput(input0, block.PORT_IN, block.input0_bm); initInput(input1, block.PORT_IN, block.input1_bm); initInput(input2, block.PORT_IN, block.input2_bm); - + // Set output pin state and output pin swap - if (output == out::enable) { - if (output_swap == out::pin_swap && block.output_alt_bm) { + if (output == logic::out::enable) { + if (output_swap == logic::out::pin_swap && block.output_alt_bm) { #if defined(PORTMUX_CCL) PORTMUX_CCL |= PORTMUX_ALTOUT_bm; #endif block.PORT_OUT.DIRSET = block.output_alt_bm; - } else if (output_swap == out::no_swap && block.output_bm) { + } else if (output_swap == logic::out::no_swap && block.output_bm) { #if defined(PORTMUX_CCL) PORTMUX_CCL &= ~PORTMUX_ALTOUT_bm; #endif block.PORT_ALT_OUT.DIRSET = block.output_bm; } } - + // Set inputs modes block.LUTCTRLB = ((input1 & 0xf0) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); block.LUTCTRLC = ((input2 & 0x0f) << CCL_INSEL2_gp); diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 48c8cc3..70d6eb3 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -3,217 +3,227 @@ #include -namespace in { - enum input_t : uint8_t { - #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ - defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ - defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ - defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ - defined(__AVR_ATtiny3227__) || defined(__AVR_ATtiny3226__) || \ - defined(__AVR_ATtiny3224__) || defined(__AVR_ATtiny1627__) || \ - defined(__AVR_ATtiny1626__) || defined(__AVR_ATtiny1624__) || \ - defined(__AVR_ATtiny827__) || defined(__AVR_ATtiny826__) || \ - defined(__AVR_ATtiny824__) || defined(__AVR_ATtiny427__) || \ - defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny424__) - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_0 = 0x03, - event_a = 0x03, - event_1 = 0x04, - event_b = 0x04, - pin = 0x05, - ac = 0x06, - uart = 0x08, - usart = 0x08, - spi = 0x09, - tca0 = 0x0A, - tca = 0x0A, - tcb = 0x0C, - input_pullup = 0x15, - input = 0x25, - input_no_pullup = 0x25, - #elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA32__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ - defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ - defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ - defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB32__) || \ - defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ - defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ - defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ - defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_0 = 0x03, - event_a = 0x03, - event_1 = 0x04, - event_b = 0x04, - pin = 0x05, - ac = 0x06, - zcd = 0x07, - usart = 0x08, - spi = 0x09, - tca0 = 0x0A, - tca = 0x0A, - tca1 = 0x0B, - tcb = 0x0C, - tcd = 0x0D, - input_pullup = 0x15, - input = 0x25, - input_no_pullup = 0x25, - #elif defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ - defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ - defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) || \ - defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ - defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ - defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) - // educated guess - these have at least one of everything the rest of DA-series has, - // and these lists have been super consistent since v1.0 (tinyAVR 0/1-series) - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_0 = 0x03, - event_a = 0x03, - event_1 = 0x04, - event_b = 0x04, - pin = 0x05, - ac = 0x06, - zcd = 0x07, - usart = 0x08, - spi = 0x09, - tca0 = 0x0A, - tca = 0x0A, - tcb = 0x0C, - tcd = 0x0D, - input_pullup = 0x15, - input = 0x25, - input_no_pullup = 0x25, - #elif defined(__AVR_AVR64EA28__) || defined(__AVR_AVR32EA28__) || \ - defined(__AVR_AVR16EA28__) || defined(__AVR_AVR8EA28__) || \ - defined(__AVR_AVR64EA32__) || defined(__AVR_AVR32EA32__) || \ - defined(__AVR_AVR16EA32__) || defined(__AVR_AVR8EA32__) || \ - defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ - defined(__AVR_AVR16EA48__) - // educated guess based on recent consistency and which peripherals they have - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_0 = 0x03, - event_a = 0x03, - event_1 = 0x04, - event_b = 0x04, - pin = 0x05, - ac = 0x06, - usart = 0x08, - spi = 0x09, - tca0 = 0x0A, - tca = 0x0A, - tca1 = 0x0B, - tcb = 0x0C, - input_pullup = 0x15, - input = 0x25, - input_no_pullup = 0x25, +namespace logic { + namespace in { + enum input_t : uint8_t { + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ + defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ + defined(__AVR_ATtiny3227__) || defined(__AVR_ATtiny3226__) || \ + defined(__AVR_ATtiny3224__) || defined(__AVR_ATtiny1627__) || \ + defined(__AVR_ATtiny1626__) || defined(__AVR_ATtiny1624__) || \ + defined(__AVR_ATtiny827__) || defined(__AVR_ATtiny826__) || \ + defined(__AVR_ATtiny824__) || defined(__AVR_ATtiny427__) || \ + defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny424__) + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + uart = 0x08, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tcb = 0x0C, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + #elif defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA32__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB32__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + zcd = 0x07, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tca1 = 0x0B, + tcb = 0x0C, + tcd = 0x0D, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + #elif defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ + defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ + defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) + // educated guess - these have at least one of everything the rest of DA-series has, + // and these lists have been super consistent since v1.0 (tinyAVR 0/1-series) + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + zcd = 0x07, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tcb = 0x0C, + tcd = 0x0D, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + #elif defined(__AVR_AVR64EA28__) || defined(__AVR_AVR32EA28__) || \ + defined(__AVR_AVR16EA28__) || defined(__AVR_AVR8EA28__) || \ + defined(__AVR_AVR64EA32__) || defined(__AVR_AVR32EA32__) || \ + defined(__AVR_AVR16EA32__) || defined(__AVR_AVR8EA32__) || \ + defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ + defined(__AVR_AVR16EA48__) + // educated guess based on recent consistency and which peripherals they have + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + usart = 0x08, + spi = 0x09, + tca0 = 0x0A, + tca = 0x0A, + tca1 = 0x0B, + tcb = 0x0C, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, - #else //tinyAVR 0/1-series - masked = 0x00, - unused = 0x00, - disable = 0x00, - feedback = 0x01, - link = 0x02, - event_0 = 0x03, - event_a = 0x03, - event_1 = 0x04, - event_b = 0x04, - pin = 0x05, - ac = 0x06, - ac0 = 0x06, - tcb0 = 0x07, - tcb = 0x07, - tca = 0x08, - tca0 = 0x08, - tcd0 = 0x09, - usart = 0x0A, - usart0 = 0x0A, - spi = 0x0B, - spi0 = 0x0B, - ac1 = 0x0C, - tcb1 = 0x0D, - ac2 = 0x0E, - input_pullup = 0x15, - input = 0x25, - input_no_pullup = 0x25, - #endif + #else //tinyAVR 0/1-series + masked = 0x00, + unused = 0x00, + disable = 0x00, + feedback = 0x01, + link = 0x02, + event_0 = 0x03, + event_a = 0x03, + event_1 = 0x04, + event_b = 0x04, + pin = 0x05, + ac = 0x06, + ac0 = 0x06, + tcb0 = 0x07, + tcb = 0x07, + tca = 0x08, + tca0 = 0x08, + tcd0 = 0x09, + usart = 0x0A, + usart0 = 0x0A, + spi = 0x0B, + spi0 = 0x0B, + ac1 = 0x0C, + tcb1 = 0x0D, + ac2 = 0x0E, + input_pullup = 0x15, + input = 0x25, + input_no_pullup = 0x25, + #endif + }; }; -}; -// Use out:: when working with logic outputs -namespace out { - enum output_t : uint8_t { - disable = 0x00, - enable = 0x01, - }; - enum pinswap_t : uint8_t { - no_swap = 0x00, - pin_swap = 0x01, + // Use out:: when working with logic outputs + namespace out { + enum output_t : uint8_t { + disable = 0x00, + enable = 0x01, + }; + enum pinswap_t : uint8_t { + no_swap = 0x00, + pin_swap = 0x01, + }; }; -}; -// Use filter:: when working with logic output filter -namespace filter { - enum filter_t : uint8_t { - disable = 0x00, - synchronizer = 0x01, - synch = 0x01, - sync = 0x01, - filter = 0x02, + // Use filter:: when working with logic output filter + namespace filter { + enum filter_t : uint8_t { + disable = 0x00, + synchronizer = 0x01, + synch = 0x01, + sync = 0x01, + filter = 0x02, + }; }; -}; -// Use clocksource:: when working with logic clock source -namespace clocksource { - enum clocksource_t : uint8_t { - clk_per = 0x00, - in2 = 0x01, - #ifdef CCL_CLKSEL_gm - oschf = 0x04, - osc32k = 0x05, - osc1k = 0x06, - #endif + // Use clocksource:: when working with logic clock source + namespace clocksource { + enum clocksource_t : uint8_t { + clk_per = 0x00, + in2 = 0x01, + #ifdef CCL_CLKSEL_gm + oschf = 0x04, + osc32k = 0x05, + osc1k = 0x06, + #endif + }; }; -}; -// Use edgedetect:: when using edge detection with filter -namespace edgedetect { - enum edgedet_t : uint8_t { - disable = 0x00, - enable = 0x01 + // Use edgedetect:: when using edge detection with filter + namespace edgedetect { + enum edgedet_t : uint8_t { + disable = 0x00, + enable = 0x01 + }; }; -}; -// Use sequencer:: when working with LUT sequencer -namespace sequencer { - enum sequencer_t : uint8_t { - disable = 0x00, - d_flip_flop = 0x01, - jk_flip_flop = 0x02, - d_latch = 0x03, - sr_latch = 0x04, - rs_latch = 0x04, + // Use sequencer:: when working with LUT sequencer + namespace sequencer { + enum sequencer_t : uint8_t { + disable = 0x00, + d_flip_flop = 0x01, + jk_flip_flop = 0x02, + d_latch = 0x03, + sr_latch = 0x04, + rs_latch = 0x04, + }; }; }; +// Legacy definitions +namespace in { using namespace logic::in; }; +namespace out { using namespace logic::out; }; +namespace filter { using namespace logic::filter; }; +namespace clocksource { using namespace logic::clocksource; }; +namespace edgedetect { using namespace logic::edgedetect; }; +namespace sequencer { using namespace logic::sequencer; }; + class Logic { public: static void start(bool state = true); @@ -227,23 +237,23 @@ class Logic { #endif bool enable; - in::input_t input0; - in::input_t input1; - in::input_t input2; - out::output_t output; - out::pinswap_t output_swap; - filter::filter_t filter; - edgedetect::edgedet_t edgedetect; + logic::in::input_t input0; + logic::in::input_t input1; + logic::in::input_t input2; + logic::out::output_t output; + logic::out::pinswap_t output_swap; + logic::filter::filter_t filter; + logic::edgedetect::edgedet_t edgedetect; uint8_t truth; - sequencer::sequencer_t sequencer; - clocksource::clocksource_t clocksource; + logic::sequencer::sequencer_t sequencer; + logic::clocksource::clocksource_t clocksource; struct CCLBlock; private: const struct CCLBlock █ - void initInput(in::input_t &input, PORT_t &port, const uint8_t pin_bm); + void initInput(logic::in::input_t &input, PORT_t &port, const uint8_t pin_bm); }; #if defined(CCL_TRUTH0) From 41b09f2106ba4d554a8e9ca0d8cabe9e4c0c40fb Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 18 Jun 2022 20:57:43 +0200 Subject: [PATCH 304/351] Move attach/detachInterrupt and ISR to separate cpp file This makes it possible for the dot_a_linkage to optimize away the file when the ISR is not in use, saving about 200 bytes for every sketch that includes Logic.h --- megaavr/libraries/Logic/library.properties | 1 + megaavr/libraries/Logic/src/Logic.cpp | 450 --------------------- megaavr/libraries/Logic/src/Logic.h | 351 ++++++++++++++++ megaavr/libraries/Logic/src/Logic_ISR.cpp | 104 +++++ 4 files changed, 456 insertions(+), 450 deletions(-) create mode 100644 megaavr/libraries/Logic/src/Logic_ISR.cpp diff --git a/megaavr/libraries/Logic/library.properties b/megaavr/libraries/Logic/library.properties index d796a6d..5c1249b 100644 --- a/megaavr/libraries/Logic/library.properties +++ b/megaavr/libraries/Logic/library.properties @@ -6,4 +6,5 @@ sentence=A library for interfacing with the customizable logic in megaAVR 0-seri paragraph= category=Signal Input/Output url=https://github.com/MCUdude/MegaCoreX +dot_a_linkage=true architectures=megaavr diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index 0f52dd2..fce2d26 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -1,355 +1,5 @@ #include "Logic.h" -// Array for storing ISR function pointers -#if defined(CCL_CCL_vect) - #if defined(TRUTH5) - static volatile voidFuncPtr intFuncCCL[6]; - #else - static volatile voidFuncPtr intFuncCCL[4]; - #endif -#endif - -struct Logic::CCLBlock { - const uint8_t number; - const uint8_t input0_bm; - const uint8_t input1_bm; - const uint8_t input2_bm; - const uint8_t output_bm; - const uint8_t output_alt_bm; - PORT_t &PORT_IN; - PORT_t &PORT_OUT; - PORT_t &PORT_ALT_OUT; - volatile register8_t &SEQCTRL; - volatile register8_t &LUTCTRLA; - volatile register8_t &LUTCTRLB; - volatile register8_t &LUTCTRLC; - volatile register8_t &TRUTH; -}; - -static const struct Logic::CCLBlock blocks[] = { - #if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ - defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ - defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ - defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ - defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ - defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - 0, 0, 0, PIN7_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - #endif - #if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ - defined(__AVR_ATtiny1606__) || \ - defined(__AVR_ATtiny416__) || defined(__AVR_ATtiny816__) || \ - defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) - #define PORTMUX_CCL PORTMUX.CTRLA - #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - #endif - #if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ - defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ - defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) - #define PORTMUX_CCL PORTMUX.CTRLA - #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - #endif - #if defined(__AVR_ATtiny424__) || defined(__AVR_ATtiny824__) || \ - defined(__AVR_ATtiny1624__) || defined(__AVR_ATtiny3224__) - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - 0, 0, 0, PIN7_bm, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTB, PORTB, PORTA, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - 0, 0, 0, 0, PIN5_bm, - PORTC, PORTA, PORTA, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #if defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny826__) || \ - defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTB, PORTB, PORTA, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, 0, PIN5_bm, - PORTC, PORTA, PORTA, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #if defined(__AVR_ATtiny427__) || defined(__AVR_ATtiny827__) || \ - defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, - PORTA, PORTA, PORTB, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, - PORTC, PORTA, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTB, PORTB, PORTB, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN4_bm, PIN5_bm, - PORTC, PORTC, PORTA, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #if defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ - defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ - defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) - - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - 0, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTC, PORTC, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - 0, 0, 0, 0, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - 0, 0, 0, 0, 0, - PORTA, PORTA, PORTA, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ - defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ - defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) || \ - defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ - defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ - defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ - defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ - defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ - defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ - defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ - defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) || \ - defined(__AVR_AVR64EA32__) || defined(__AVR_AVR64EA28__) || \ - defined(__AVR_AVR32EA32__) || defined(__AVR_AVR32EA28__) || \ - defined(__AVR_AVR16EA32__) || defined(__AVR_AVR16EA28__) || \ - defined(__AVR_AVR8EA32__) || defined(__AVR_AVR8EA28__) - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - 1, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTC, PORTC, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - #if defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ - defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ - defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ - defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ - defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ - defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) - // These have no PD0, because it was sacrificed for VDDIO2 - { - 2, - 0, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - #else - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - #endif - #if defined(__AVR_AVR128DA28__)|| defined(__AVR_AVR64DA28__) || \ - defined(__AVR_AVR32DA28__) || defined(__AVR_AVR64EA28__) || \ - defined(__AVR_AVR32EA28__) || defined(__AVR_AVR16EA28__) || \ - defined(__AVR_AVR8EA28__) || defined(__AVR_AVR64DD28__) || \ - defined(__AVR_AVR32DD28__) || defined(__AVR_AVR16DD28__) - // only has PF0, PF1, and even if RESET set GPIO, is input only - { - 3, - PIN0_bm, PIN1_bm, 0, 0, 0, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #elif defined(__AVR_AVR128DA32__)|| defined(__AVR_AVR64DA32__) || \ - defined(__AVR_AVR32DA32__) || defined(__AVR_AVR64EA32__) || \ - defined(__AVR_AVR32EA32__) || defined(__AVR_AVR16EA32__) || \ - defined(__AVR_AVR8EA32__) || defined(__AVR_AVR64DD32__) || \ - defined(__AVR_AVR32DD32__) || defined(__AVR_AVR16DD32__) - // even if RESET set GPIO, is input only - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #else - // megaAVR 0-series with 32-pins - // Note that PF6 is Reset, which must be set as GPIO to use as alt output. - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #endif - #if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ - defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ - defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ - defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ - defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ - defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ - defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ - defined(__AVR_AVR16EA48__) - #define PORTMUX_CCL PORTMUX.CCLROUTEA - #define PORTMUX_ALTOUT_bm (1 << block.number) - { - 0, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTA, PORTA, PORTA, - CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, - }, - { - // Note: 40-Pin version doesn't have output_alt, but the parts cannot - // be programmatically distinguished - it's a 48-pin die in 40-pin package - 1, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTC, PORTC, PORTC, - CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, - }, - { - 2, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTD, PORTD, PORTD, - CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, - }, - { - 3, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTF, PORTF, PORTF, - CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, - }, - #endif - #if defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ - defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ - defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ - defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ - defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ - defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) - { - 4, - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTB, PORTB, PORTB, - CCL.SEQCTRL2, CCL.LUT4CTRLA, CCL.LUT4CTRLB, CCL.LUT4CTRLC, CCL.TRUTH4, - }, - { - 5, - #ifdef PORTG - PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, - PORTG, PORTG, PORTG, - #else - 0,0,0,0,0, - PORTA,PORTA,PORTA, - #endif - CCL.SEQCTRL2, CCL.LUT5CTRLA, CCL.LUT5CTRLB, CCL.LUT5CTRLC, CCL.TRUTH5, - }, - #endif -}; #if defined(CCL_TRUTH0) Logic Logic0(0); @@ -481,103 +131,3 @@ void Logic::init() #endif | (enable ? CCL_ENABLE_bm : 0); } - -#if defined(CCL_CCL_vect) -void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) { - CCL_INTMODE0_t intmode; - switch (mode) { - // Set RISING, FALLING or CHANGE interrupt trigger for a block output - case RISING: - intmode = CCL_INTMODE0_RISING_gc; - break; - case FALLING: - intmode = CCL_INTMODE0_FALLING_gc; - break; - case CHANGE: - intmode = CCL_INTMODE0_BOTH_gc; - break; - default: - // Only RISING, FALLING and CHANGE is supported - return; - } - #if defined(CCL_TRUTH4) - if (block.number > 3) { - const int16_t intmode_bp = (block.number & 0x03) * 2; - CCL.INTCTRL1 = (CCL.INTCTRL1 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); - } else { - const int16_t intmode_bp = (block.number & 0x03) * 2; - CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); - } - #else - const int16_t intmode_bp = block.number * 2; - CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); - #endif - // Store function pointer - intFuncCCL[block.number] = userFunc; -} - -void Logic::detachInterrupt() { - // Disable interrupt for a given block output - #if defined(CCL_TRUTH4) - if (block.number > 4) { - CCL.INTCTRL1 &= ~(CCL_INTMODE1_gm << ((block.number & 3) * 2)); - } else { - CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); - } - #else - CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); - #endif -} - -// CCL interrupt service routine -// Use attachIntterupt to activate this. -ISR(CCL_CCL_vect) { - // Check for block 0 interrupt - if (CCL.INTFLAGS & CCL_INT0_bm) { - // Run user function - intFuncCCL[CCL_INT0_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT0_bm; - } - // Check for block 1 interrupt - if (CCL.INTFLAGS & CCL_INT1_bm) { - // Run user function - intFuncCCL[CCL_INT1_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT1_bm; - } - // Check for block 2 interrupt - if (CCL.INTFLAGS & CCL_INT2_bm) { - // Run user function - intFuncCCL[CCL_INT2_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT2_bm; - } - // Check for block 3 interrupt - if (CCL.INTFLAGS & CCL_INT3_bm) { - // Run user function - intFuncCCL[CCL_INT3_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT3_bm; - } - #if defined(TRUTH4) - // Check for block 4 interrupt - if (CCL.INTFLAGS & CCL_INT4_bm) { - // Run user function - intFuncCCL[CCL_INT4_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT4_bm; - } - #endif - #if defined(TRUTH5) - // Check for block 5 interrupt - if (CCL.INTFLAGS & CCL_INT5_bm) { - // Run user function - intFuncCCL[CCL_INT5_bp](); - // Clear flag - CCL.INTFLAGS |= CCL_INT5_bm; - } -#endif // CCL_CCL_vect -} - -#endif diff --git a/megaavr/libraries/Logic/src/Logic.h b/megaavr/libraries/Logic/src/Logic.h index 70d6eb3..958c83c 100644 --- a/megaavr/libraries/Logic/src/Logic.h +++ b/megaavr/libraries/Logic/src/Logic.h @@ -256,6 +256,357 @@ class Logic { void initInput(logic::in::input_t &input, PORT_t &port, const uint8_t pin_bm); }; +// Array for storing ISR function pointers +#if defined(CCL_CCL_vect) + #if defined(TRUTH5) + static volatile voidFuncPtr intFuncCCL[6]; + #else + static volatile voidFuncPtr intFuncCCL[4]; + #endif +#endif + +struct Logic::CCLBlock { + const uint8_t number; + const uint8_t input0_bm; + const uint8_t input1_bm; + const uint8_t input2_bm; + const uint8_t output_bm; + const uint8_t output_alt_bm; + PORT_t &PORT_IN; + PORT_t &PORT_OUT; + PORT_t &PORT_ALT_OUT; + volatile register8_t &SEQCTRL; + volatile register8_t &LUTCTRLA; + volatile register8_t &LUTCTRLB; + volatile register8_t &LUTCTRLC; + volatile register8_t &TRUTH; +}; + +static const struct Logic::CCLBlock blocks[] = { + #if defined(__AVR_ATtiny202__) || defined(__AVR_ATtiny402__) || \ + defined(__AVR_ATtiny204__) || defined(__AVR_ATtiny404__) || \ + defined(__AVR_ATtiny804__) || defined(__AVR_ATtiny1604__) || \ + defined(__AVR_ATtiny212__) || defined(__AVR_ATtiny412__) || \ + defined(__AVR_ATtiny214__) || defined(__AVR_ATtiny414__) || \ + defined(__AVR_ATtiny814__) || defined(__AVR_ATtiny1614__) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, 0, 0, PIN7_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + #endif + #if defined(__AVR_ATtiny406__) || defined(__AVR_ATtiny806__) || \ + defined(__AVR_ATtiny1606__) || \ + defined(__AVR_ATtiny416__) || defined(__AVR_ATtiny816__) || \ + defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) + #define PORTMUX_CCL PORTMUX.CTRLA + #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + #endif + #if defined(__AVR_ATtiny807__) || defined(__AVR_ATtiny1607__) || \ + defined(__AVR_ATtiny417__) || defined(__AVR_ATtiny817__) || \ + defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) + #define PORTMUX_CCL PORTMUX.CTRLA + #define PORTMUX_ALTOUT_bm (1 << (block.number + 4)) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + #endif + #if defined(__AVR_ATtiny424__) || defined(__AVR_ATtiny824__) || \ + defined(__AVR_ATtiny1624__) || defined(__AVR_ATtiny3224__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, 0, 0, PIN7_bm, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTB, PORTB, PORTA, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + 0, 0, 0, 0, PIN5_bm, + PORTC, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATtiny426__) || defined(__AVR_ATtiny826__) || \ + defined(__AVR_ATtiny1616__) || defined(__AVR_ATtiny3216__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, 0, 0, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTB, PORTB, PORTA, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, 0, PIN5_bm, + PORTC, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATtiny427__) || defined(__AVR_ATtiny827__) || \ + defined(__AVR_ATtiny1617__) || defined(__AVR_ATtiny3217__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN6_bm, PIN4_bm, + PORTA, PORTA, PORTB, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN3_bm, PIN4_bm, PIN5_bm, PIN7_bm, PIN1_bm, + PORTC, PORTA, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTB, PORTB, PORTB, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN4_bm, PIN5_bm, + PORTC, PORTC, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_AVR64DD20__) || defined(__AVR_AVR64DD14__) || \ + defined(__AVR_AVR32DD20__) || defined(__AVR_AVR32DD14__) || \ + defined(__AVR_AVR16DD20__) || defined(__AVR_AVR16DD14__) + + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + 0, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + 0, 0, 0, 0, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + 0, 0, 0, 0, 0, + PORTA, PORTA, PORTA, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_ATmega808__) || defined(__AVR_ATmega1608__) || \ + defined(__AVR_ATmega3208__) || defined(__AVR_ATmega4808__) || \ + defined(__AVR_AVR128DA32__) || defined(__AVR_AVR128DA28__) || \ + defined(__AVR_AVR64DA32__) || defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR32DA28__) || \ + defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) || \ + defined(__AVR_AVR64EA32__) || defined(__AVR_AVR64EA28__) || \ + defined(__AVR_AVR32EA32__) || defined(__AVR_AVR32EA28__) || \ + defined(__AVR_AVR16EA32__) || defined(__AVR_AVR16EA28__) || \ + defined(__AVR_AVR8EA32__) || defined(__AVR_AVR8EA28__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + #if defined(__AVR_AVR128DB32__) || defined(__AVR_AVR128DB28__) || \ + defined(__AVR_AVR64DB32__) || defined(__AVR_AVR64DB28__) || \ + defined(__AVR_AVR32DB32__) || defined(__AVR_AVR32DB28__) || \ + defined(__AVR_AVR64DD32__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR32DD28__) || \ + defined(__AVR_AVR16DD32__) || defined(__AVR_AVR16DD28__) + // These have no PD0, because it was sacrificed for VDDIO2 + { + 2, + 0, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + #else + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + #endif + #if defined(__AVR_AVR128DA28__)|| defined(__AVR_AVR64DA28__) || \ + defined(__AVR_AVR32DA28__) || defined(__AVR_AVR64EA28__) || \ + defined(__AVR_AVR32EA28__) || defined(__AVR_AVR16EA28__) || \ + defined(__AVR_AVR8EA28__) || defined(__AVR_AVR64DD28__) || \ + defined(__AVR_AVR32DD28__) || defined(__AVR_AVR16DD28__) + // only has PF0, PF1, and even if RESET set GPIO, is input only + { + 3, + PIN0_bm, PIN1_bm, 0, 0, 0, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #elif defined(__AVR_AVR128DA32__)|| defined(__AVR_AVR64DA32__) || \ + defined(__AVR_AVR32DA32__) || defined(__AVR_AVR64EA32__) || \ + defined(__AVR_AVR32EA32__) || defined(__AVR_AVR16EA32__) || \ + defined(__AVR_AVR8EA32__) || defined(__AVR_AVR64DD32__) || \ + defined(__AVR_AVR32DD32__) || defined(__AVR_AVR16DD32__) + // even if RESET set GPIO, is input only + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, 0, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #else + // megaAVR 0-series with 32-pins + // Note that PF6 is Reset, which must be set as GPIO to use as alt output. + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #endif + #if defined(__AVR_ATmega809__) || defined(__AVR_ATmega1609__) || \ + defined(__AVR_ATmega3209__) || defined(__AVR_ATmega4809__) || \ + defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) || \ + defined(__AVR_AVR64EA48__) || defined(__AVR_AVR32EA48__) || \ + defined(__AVR_AVR16EA48__) + #define PORTMUX_CCL PORTMUX.CCLROUTEA + #define PORTMUX_ALTOUT_bm (1 << block.number) + { + 0, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTA, PORTA, PORTA, + CCL.SEQCTRL0, CCL.LUT0CTRLA, CCL.LUT0CTRLB, CCL.LUT0CTRLC, CCL.TRUTH0, + }, + { + // Note: 40-Pin version doesn't have output_alt, but the parts cannot + // be programmatically distinguished - it's a 48-pin die in 40-pin package + 1, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTC, PORTC, PORTC, + CCL.SEQCTRL0, CCL.LUT1CTRLA, CCL.LUT1CTRLB, CCL.LUT1CTRLC, CCL.TRUTH1, + }, + { + 2, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTD, PORTD, PORTD, + CCL.SEQCTRL1, CCL.LUT2CTRLA, CCL.LUT2CTRLB, CCL.LUT2CTRLC, CCL.TRUTH2, + }, + { + 3, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTF, PORTF, PORTF, + CCL.SEQCTRL1, CCL.LUT3CTRLA, CCL.LUT3CTRLB, CCL.LUT3CTRLC, CCL.TRUTH3, + }, + #endif + #if defined(__AVR_AVR128DA64__) || defined(__AVR_AVR128DA48__) || \ + defined(__AVR_AVR64DA64__) || defined(__AVR_AVR64DA48__) || \ + defined(__AVR_AVR32DA64__) || defined(__AVR_AVR32DA48__) || \ + defined(__AVR_AVR128DB64__) || defined(__AVR_AVR128DB48__) || \ + defined(__AVR_AVR64DB64__) || defined(__AVR_AVR64DB48__) || \ + defined(__AVR_AVR32DB64__) || defined(__AVR_AVR32DB48__) + { + 4, + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTB, PORTB, PORTB, + CCL.SEQCTRL2, CCL.LUT4CTRLA, CCL.LUT4CTRLB, CCL.LUT4CTRLC, CCL.TRUTH4, + }, + { + 5, + #ifdef PORTG + PIN0_bm, PIN1_bm, PIN2_bm, PIN3_bm, PIN6_bm, + PORTG, PORTG, PORTG, + #else + 0,0,0,0,0, + PORTA,PORTA,PORTA, + #endif + CCL.SEQCTRL2, CCL.LUT5CTRLA, CCL.LUT5CTRLB, CCL.LUT5CTRLC, CCL.TRUTH5, + }, + #endif +}; + #if defined(CCL_TRUTH0) extern Logic Logic0; #endif diff --git a/megaavr/libraries/Logic/src/Logic_ISR.cpp b/megaavr/libraries/Logic/src/Logic_ISR.cpp new file mode 100644 index 0000000..5fe697b --- /dev/null +++ b/megaavr/libraries/Logic/src/Logic_ISR.cpp @@ -0,0 +1,104 @@ +// This file will be optimized away if attachInterrupt or detachInterrupt isn't used in +// user program, thanks to dot_a_linkage set in library.properties + +#include "Logic.h" + +#if defined(CCL_CCL_vect) +void Logic::attachInterrupt(void (*userFunc)(void), uint8_t mode) { + CCL_INTMODE0_t intmode; + switch (mode) { + // Set RISING, FALLING or CHANGE interrupt trigger for a block output + case RISING: + intmode = CCL_INTMODE0_RISING_gc; + break; + case FALLING: + intmode = CCL_INTMODE0_FALLING_gc; + break; + case CHANGE: + intmode = CCL_INTMODE0_BOTH_gc; + break; + default: + // Only RISING, FALLING and CHANGE is supported + return; + } + #if defined(CCL_TRUTH4) + if (block.number > 3) { + const int16_t intmode_bp = (block.number & 0x03) * 2; + CCL.INTCTRL1 = (CCL.INTCTRL1 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); + } else { + const int16_t intmode_bp = (block.number & 0x03) * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); + } + #else + const int16_t intmode_bp = block.number * 2; + CCL.INTCTRL0 = (CCL.INTCTRL0 & ~(CCL_INTMODE0_gm << intmode_bp)) | (intmode << intmode_bp); + #endif + // Store function pointer + intFuncCCL[block.number] = userFunc; +} + +void Logic::detachInterrupt() { + // Disable interrupt for a given block output + #if defined(CCL_TRUTH4) + if (block.number > 4) { + CCL.INTCTRL1 &= ~(CCL_INTMODE1_gm << ((block.number & 3) * 2)); + } else { + CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); + } + #else + CCL.INTCTRL0 &= ~(CCL_INTMODE0_gm << (block.number * 2)); + #endif +} + +// CCL interrupt service routine +// Use attachIntterupt to activate this. +ISR(CCL_CCL_vect) { + // Check for block 0 interrupt + if (CCL.INTFLAGS & CCL_INT0_bm) { + // Run user function + intFuncCCL[CCL_INT0_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT0_bm; + } + // Check for block 1 interrupt + if (CCL.INTFLAGS & CCL_INT1_bm) { + // Run user function + intFuncCCL[CCL_INT1_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT1_bm; + } + // Check for block 2 interrupt + if (CCL.INTFLAGS & CCL_INT2_bm) { + // Run user function + intFuncCCL[CCL_INT2_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT2_bm; + } + // Check for block 3 interrupt + if (CCL.INTFLAGS & CCL_INT3_bm) { + // Run user function + intFuncCCL[CCL_INT3_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT3_bm; + } + #if defined(TRUTH4) + // Check for block 4 interrupt + if (CCL.INTFLAGS & CCL_INT4_bm) { + // Run user function + intFuncCCL[CCL_INT4_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT4_bm; + } + #endif + #if defined(TRUTH5) + // Check for block 5 interrupt + if (CCL.INTFLAGS & CCL_INT5_bm) { + // Run user function + intFuncCCL[CCL_INT5_bp](); + // Clear flag + CCL.INTFLAGS |= CCL_INT5_bm; + } +#endif // CCL_CCL_vect +} + +#endif \ No newline at end of file From 38d58d26baeef0bcd497977c71f974d8998cb532 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 18 Jun 2022 21:47:06 +0200 Subject: [PATCH 305/351] Move comparator attach/detachInterrupt and ISR to separate cpp file This makes it possible for the dot_a_linkage to optimize away the file when the ISR is not in use, saving about 200 bytes for every sketch that includes Logic.h --- .../libraries/Comparator/library.properties | 3 +- .../libraries/Comparator/src/Comparator.cpp | 79 ------------------- megaavr/libraries/Comparator/src/Comparator.h | 11 +++ .../Comparator/src/Comparator_ISR.cpp | 71 +++++++++++++++++ 4 files changed, 84 insertions(+), 80 deletions(-) create mode 100644 megaavr/libraries/Comparator/src/Comparator_ISR.cpp diff --git a/megaavr/libraries/Comparator/library.properties b/megaavr/libraries/Comparator/library.properties index d06fc20..858879d 100644 --- a/megaavr/libraries/Comparator/library.properties +++ b/megaavr/libraries/Comparator/library.properties @@ -1,9 +1,10 @@ name=Comparator -version=1.1.0 +version=1.1.1 author=MCUdude maintainer=MCUdude sentence=A library for interfacing with the built-in analog comparator paragraph= category=Signal Input/Output url=https://github.com/MCUdude/MegaCoreX +dot_a_linkage=true architectures=megaavr diff --git a/megaavr/libraries/Comparator/src/Comparator.cpp b/megaavr/libraries/Comparator/src/Comparator.cpp index 90796e8..eb5326b 100644 --- a/megaavr/libraries/Comparator/src/Comparator.cpp +++ b/megaavr/libraries/Comparator/src/Comparator.cpp @@ -2,18 +2,6 @@ AnalogComparator Comparator(0, AC0); -// Array for storing ISR function pointers -#if defined(AC2_AC_vect) -static volatile voidFuncPtr intFuncAC[3]; -#elif defined(AC1_AC_vect) -static volatile voidFuncPtr intFuncAC[2]; -#elif defined(AC0_AC_vect) -static volatile voidFuncPtr intFuncAC[1]; -#else -#error target does not have an analog comparator! -#endif - - AnalogComparator::AnalogComparator(const uint8_t comp_number, AC_t& ac) : comparator_number(comp_number), AC(ac) { } @@ -78,70 +66,3 @@ bool AnalogComparator::read() { return !!(AC0.STATUS & AC_STATE_bm); } - -void AnalogComparator::attachInterrupt(void (*userFunc)(void), uint8_t mode) -{ - AC_INTMODE_t intmode; - switch (mode) - { - // Set RISING, FALLING or CHANGE interrupt trigger for the comparator output - case RISING: - intmode = AC_INTMODE_POSEDGE_gc; - break; - case FALLING: - intmode = AC_INTMODE_NEGEDGE_gc; - break; - case CHANGE: - intmode = AC_INTMODE_BOTHEDGE_gc; - break; - default: - // Only RISING, FALLING and CHANGE is supported - return; - } - AC.CTRLA = (AC.CTRLA & ~AC_INTMODE_POSEDGE_gc) | intmode; - - // Store function pointer - intFuncAC[comparator_number] = userFunc; - - // Enable interrupt - AC.INTCTRL |= AC_CMP_bm; -} - -void AnalogComparator::detachInterrupt() -{ - // Disable interrupt - AC.INTCTRL &= ~AC_CMP_bm; -} - -#ifdef AC0_AC_vect -ISR(AC0_AC_vect) -{ - // Run user function - intFuncAC[0](); - - // Clear flag - AC0.STATUS = AC_CMP_bm; -} -#endif - -#ifdef AC1_AC_vect -ISR(AC1_AC_vect) -{ - // Run user function - intFuncAC[1](); - - // Clear flag - AC1.STATUS = AC_CMP_bm; -} -#endif - -#ifdef AC2_AC_vect -ISR(AC2_AC_vect) -{ - // Run user function - intFuncAC[2](); - - // Clear flag - AC2.STATUS = AC_CMP_bm; -} -#endif diff --git a/megaavr/libraries/Comparator/src/Comparator.h b/megaavr/libraries/Comparator/src/Comparator.h index 956bff0..699eec6 100644 --- a/megaavr/libraries/Comparator/src/Comparator.h +++ b/megaavr/libraries/Comparator/src/Comparator.h @@ -96,6 +96,17 @@ class AnalogComparator bool enable = false; }; +// Array for storing ISR function pointers +#if defined(AC2_AC_vect) +static volatile voidFuncPtr intFuncAC[3]; +#elif defined(AC1_AC_vect) +static volatile voidFuncPtr intFuncAC[2]; +#elif defined(AC0_AC_vect) +static volatile voidFuncPtr intFuncAC[1]; +#else +#error target does not have an analog comparator! +#endif + #if defined(AC0_AC_vect) extern AnalogComparator Comparator0; #define Comparator Comparator0 diff --git a/megaavr/libraries/Comparator/src/Comparator_ISR.cpp b/megaavr/libraries/Comparator/src/Comparator_ISR.cpp new file mode 100644 index 0000000..21af638 --- /dev/null +++ b/megaavr/libraries/Comparator/src/Comparator_ISR.cpp @@ -0,0 +1,71 @@ +// This file will be optimized away if attachInterrupt or detachInterrupt isn't used in +// user program, thanks to dot_a_linkage set in library.properties + +#include "Comparator.h" + +void AnalogComparator::attachInterrupt(void (*userFunc)(void), uint8_t mode) +{ + AC_INTMODE_t intmode; + switch (mode) + { + // Set RISING, FALLING or CHANGE interrupt trigger for the comparator output + case RISING: + intmode = AC_INTMODE_POSEDGE_gc; + break; + case FALLING: + intmode = AC_INTMODE_NEGEDGE_gc; + break; + case CHANGE: + intmode = AC_INTMODE_BOTHEDGE_gc; + break; + default: + // Only RISING, FALLING and CHANGE is supported + return; + } + AC.CTRLA = (AC.CTRLA & ~AC_INTMODE_POSEDGE_gc) | intmode; + + // Store function pointer + intFuncAC[comparator_number] = userFunc; + + // Enable interrupt + AC.INTCTRL |= AC_CMP_bm; +} + +void AnalogComparator::detachInterrupt() +{ + // Disable interrupt + AC.INTCTRL &= ~AC_CMP_bm; +} + +#ifdef AC0_AC_vect +ISR(AC0_AC_vect) +{ + // Run user function + intFuncAC[0](); + + // Clear flag + AC0.STATUS = AC_CMP_bm; +} +#endif + +#ifdef AC1_AC_vect +ISR(AC1_AC_vect) +{ + // Run user function + intFuncAC[1](); + + // Clear flag + AC1.STATUS = AC_CMP_bm; +} +#endif + +#ifdef AC2_AC_vect +ISR(AC2_AC_vect) +{ + // Run user function + intFuncAC[2](); + + // Clear flag + AC2.STATUS = AC_CMP_bm; +} +#endif From 4ad400b5b263613379942246d2960c4d447a6c04 Mon Sep 17 00:00:00 2001 From: Hans Date: Sat, 18 Jun 2022 23:08:04 +0200 Subject: [PATCH 306/351] Add SerialUPDI section to README --- README.md | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 7f03110..d1a6a55 100644 --- a/README.md +++ b/README.md @@ -15,6 +15,7 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB * [Supported microcontrollers](#supported-microcontrollers) * [Programming](#programming) - [Using a UPDI programmer](#using-a-updi-programmer) + - [SerialUPDI](#serialupdi) - [Using a bootloader](#using-a-bootloader) * [Supported clock frequencies](#supported-clock-frequencies) * [BOD option](#bod-option) @@ -66,9 +67,12 @@ If you're looking for a sleek, reliable UPDI programmer that also acts as a USB ## Programming ### Using a UPDI programmer -Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) or an official Atmel/Microchip UPDI compatible programmer. +Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) SerialUPDI or an official Atmel/Microchip UPDI compatible programmer. -Unlike the Arduino UNO WiFi Rev2 boards package MegaCoreX does not auto-detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. +Unlike the *Arduino megaAVR boards* package, MegaCoreX does not auto-detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. + +#### SerialUPDI +SerialUPDI is a programmer that utilize a simple serial connection. It uses a USB serial adapter which can be turned into a UPDI programmer by adding a few passive components. You can read more about the details on how the SerualUPDI works [here](https://github.com/SpenceKonde/AVR-Guidance/blob/master/UPDI/jtag2updi.md). ### Using a bootloader Programming can also be done using the [Optiboot bootloader](https://github.com/optiboot/Optiboot). It is available for all megaAVR-0 chips and can be used with all hardware serial ports including alternative pin positions. Simply select what UART number to use, default/alternative pin position and click "Burn bootloader". The bootloader will flash an LED connected to PA7 (digital pin 7 on most pinouts) twice when a hardware reset occurs. The upload speed is 115200 baud. Note that that the reset pin cannot be used as a GPIO when using a bootloader. It doesn't matter if you have set the reset pin as GPIO in the tools menu or not; the bootloader option will override this setting. From a58e5fa3a349076f4a537bc32b66ef0b1ef4b422 Mon Sep 17 00:00:00 2001 From: Hans Date: Wed, 29 Jun 2022 13:54:27 +0200 Subject: [PATCH 307/351] Add info about the SerialUPDI programmer I sell on Tindie --- README.md | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index d1a6a55..539767a 100644 --- a/README.md +++ b/README.md @@ -7,9 +7,14 @@ Compared to older AVR families they also have more advanced and accurate interna For programming, these chips use a UPDI programming interface. This is a bi-directional single wire interface and requires a programmer that supports UPDI. If you rather prefer uploading using a USB to serial adapter there is an option to use the Optiboot bootloader. Read more about UPDI and bootloaders in the [Programming](#programming) section below. -If you're looking for a sleek, reliable UPDI programmer that also acts as a USB to serial adapter, check out the microUPDI programmer! It's a small breakout board where you add your own Arduino Pro Micro board, and flash it with the right firmware using Arduino IDE. You can buy the microUPDI programmer over at my [Tindie store](https://www.tindie.com/products/MCUdude/microupdi-programmer/), and you can flash your Arduino Pro Micro with the correct firmware by installing [microUPDIcore](https://github.com/MCUdude/microUPDI). - - +#### UPDI programmers +If you're looking for well-designed, reliable UPDI programmers that also acts as a USB to serial adapters, check out the [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) and the [SerialUPDI](https://www.tindie.com/products/mcudude/serialupdi-programmer/) programmers I sell on [Tindie](https://www.tindie.com/stores/mcudude/)! +They're small programmers with excellent software support, and can be used with Arduino IDE or PlatformIO. The SerialUPDI programmer comes fully assembled (except for the 6-pin programming connector), but the microUPDI needs to be soldered to an Arduino Pro Micro board. + +| [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) | [SerialUPDI](https://www.tindie.com/products/mcudude/serialupdi-programmer/) | Pinout | +|----------------------------------------------------------------------------|------------------------------------------------------------------------------|----------------------------------------------------------| +| | | | +| | | | # Table of contents * [Supported microcontrollers](#supported-microcontrollers) From 5881d1ee88089fa71316aa5f6aa785b45dbbd19a Mon Sep 17 00:00:00 2001 From: per1234 Date: Sun, 18 Sep 2022 08:49:08 -0700 Subject: [PATCH 308/351] Prevent corruption of disassembler listing command for paths w/ spaces MegaCoreX uses a build hook to save a disassembler listing to the build folder when compiling sketches. Due to the use of a redirection operator in the command, it was necessary to execute it via the Windows command interpreter by passing it as an argument to `cmd /c`. Although paths with spaces can be used without difficulty in pattern generated commands executed directly by the Arduino framework, things are more complicated when it comes to executing commands indirectly via `cmd /c`. The `cmd /c` command has an odd handling of quotes: https://learn.microsoft.com/en-us/windows-server/administration/windows-commands/cmd#remarks Under certain conditions, the first and last quotation mark of the command passed via the argument to `/c` are stripped. These conditions occur for the command generated via the platform's `recipe.hooks.objcopy.postobjcopy.1.pattern.windows` property when the both the path to `avr-objdump` and the temporary build path contain a space. The removal of the essential quotes from the start and end of the command executed by `cmd /c` causes an error. for example, if the `avr-objdump` path was: ``` C:\Users\username with spaces\AppData\Local\\Arduino15\packages\arduino\tools\avr-gcc\7.3.0-atmel3.6.1-arduino7\bin\avr-objdump ``` The command will fail with the error: 'C:\Users\username' is not recognized as an internal or external command, operable program or batch file. One of the required conditions for the unwanted quote stripping is that the first character of the argument to `cmd /c` is a double quote. So this unwanted behavior can be avoided by ensuring the first character is not a double quote. That is accomplished here by adding a dummy command that does not require quoting at the start of the argument. It might seem that a less hacky approach would be to simply wrap the entire argument to `cmd /c` in an extra layer of sacrificial quotes, leaving the essential quotes intact in the command that is finally executed. While that does indeed work when running the command directly from the command line, it does not work when used in a pattern in the Arduino platform configuration framework. The problem is that the string generated from the platform pattern can not be executed as is. It must be split into arguments. The list of arguments space separated, with quoting where an argument contains a space. These arguments may contain quote characters, which must be escaped. This escaping is where the simple approach of extra quotes becomes unusable. The `os/exec` Go package used to handle the escaping does that in a way that is compatible with directly executing a command, but is not compatible with the legacy escaping system used by cmd. It seems this problem of the command having paths with spaces did not occur in Arduino IDE 1.x due to it using a Windows "8.3" format instead. Arduino CLI (and thus Arduino IDE 2.x) use the full path format instead. `recipe.hooks.savehex.presavehex.2.pattern.windows` also uses `cmd /C`. However, this command is not subject to the quote stripping because it does not ever have a double quote as the first character of the argument. --- megaavr/platform.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 5e99cdc..5859ce0 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -75,7 +75,8 @@ recipe.objcopy.eep.pattern="{compiler.path}{compiler.objcopy.cmd}" {compiler.obj recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.hex" ## Save disassembler listing -recipe.hooks.objcopy.postobjcopy.1.pattern.windows=cmd /C "{compiler.path}{compiler.objdump.cmd}" {compiler.objdump.flags} "{build.path}/{build.project_name}.elf" > "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" +# Dummy initial `echo.` command prevents unwanted stripping of quotes by `cmd /C` which would cause the command to fail for paths with spaces +recipe.hooks.objcopy.postobjcopy.1.pattern.windows=cmd /C echo. && "{compiler.path}{compiler.objdump.cmd}" {compiler.objdump.flags} "{build.path}/{build.project_name}.elf" > "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" recipe.hooks.objcopy.postobjcopy.1.pattern.linux=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" recipe.hooks.objcopy.postobjcopy.1.pattern.macosx=chmod +x "{runtime.platform.path}/scripts/create_disassembler_listing.sh" recipe.hooks.objcopy.postobjcopy.2.pattern.linux="{runtime.platform.path}/scripts/create_disassembler_listing.sh" "{compiler.path}{compiler.objdump.cmd}" "{compiler.objdump.flags}" "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}_{build.mcu}_{build.f_cpu}.lst" From d3d5aa744d1e9e7532604013bd21b02a42d9e73e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 27 Dec 2022 10:27:54 +0100 Subject: [PATCH 309/351] Use template functions by default --- megaavr/cores/coreX-corefiles/api/Common.h | 104 +++++++++++++++------ 1 file changed, 74 insertions(+), 30 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index e0d9d6c..f7e85f2 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -31,36 +31,6 @@ void yield(void); #define SERIAL 0 #define DISPLAY 1 -#ifndef min -#define min(a,b) \ - ({ __typeof__ (a) _a = (a); \ - __typeof__ (b) _b = (b); \ - _a < _b ? _a : _b; }) -#endif - -#ifndef max -#define max(a,b) \ - ({ __typeof__ (a) _a = (a); \ - __typeof__ (b) _b = (b); \ - _a > _b ? _a : _b; }) -#endif - -#ifndef constrain -#define constrain(amt,low,high) ((amt)<(low)?(low):((amt)>(high)?(high):(amt))) -#endif - -#ifndef radians -#define radians(deg) ((deg)*DEG_TO_RAD) -#endif - -#ifndef degrees -#define degrees(rad) ((rad)*RAD_TO_DEG) -#endif - -#ifndef sq -#define sq(x) ((x)*(x)) -#endif - typedef void (*voidFuncPtr)(void); // interrupts() / noInterrupts() must be defined by the core @@ -134,6 +104,80 @@ inline __attribute__((always_inline)) void check_constant_pin(pin_size_t pin) } // extern "C" #endif +#ifdef __cplusplus +#ifndef min + template + auto min(const T& a, const L& b) -> decltype((b < a) ? b : a) { + return (b < a) ? b : a; + } +#endif + +#ifndef max + template + auto max(const T& a, const L& b) -> decltype((b < a) ? b : a) { + return (a < b) ? b : a; + } +#endif + +#ifndef round + template + long round(const T& x) { + return (long)(x >= 0 ? (x + 0.5) : (x - 0.5)); + } +#endif + +#ifndef max + template + auto sq(const T& x) -> decltype(x * x) { + return x * x; + } +#endif + +#ifndef radians + template + auto radians(const T& deg) -> decltype(deg * DEG_TO_RAD) { + return deg * DEG_TO_RAD; + } +#endif + +#ifndef degrees + template + auto degrees(const T& rad) -> decltype(rad * RAD_TO_DEG) { + return rad * RAD_TO_DEG; + } +#endif +#ifndef constrain + template + auto constrain(const T& x, const L& l, const H& h) -> decltype((x < l) ? l : (x > h) ? h : x) { + return (x < l) ? l : (x > h) ? h : x; + } +#endif + +#else + #ifndef min + #define min(a,b) ({ typeof (a) _a = (a); typeof (b) _b = (b); _a < _b ? _a : _b; }) + #endif + #ifndef max + #define max(a,b) ({ typeof (a) _a = (a); typeof (b) _b = (b); _a > _b ? _a : _b; }) + #endif + #ifndef sq + #define sq(x) ({ typeof (x) _x = (x); _x * _x; }) + #endif + #ifndef radians + #define radians(deg) ((deg) * DEG_TO_RAD) + #endif + #ifndef degrees + #define degrees(rad) ((rad) * RAD_TO_DEG) + #endif + #ifndef constrain + #define constrain(x,low,high) ({ \ + typeof (x) _x = (x); \ + typeof (low) _l = (low); \ + typeof (high) _h = (high); \ + _x < _l ? _l : _x > _h ? _h : _x; }) + #endif +#endif // __cplusplus + #ifdef __cplusplus /* C++ prototypes */ From b74211c1e77de3d80a7a301e29f588d3b830ec61 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Jan 2023 20:40:26 +0100 Subject: [PATCH 310/351] Fix Servo library include issue Resolves issue #167 --- megaavr/libraries/Servo/src/ServoMegaCoreX.h | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 megaavr/libraries/Servo/src/ServoMegaCoreX.h diff --git a/megaavr/libraries/Servo/src/ServoMegaCoreX.h b/megaavr/libraries/Servo/src/ServoMegaCoreX.h new file mode 100644 index 0000000..44144c1 --- /dev/null +++ b/megaavr/libraries/Servo/src/ServoMegaCoreX.h @@ -0,0 +1,3 @@ +// Dummy file to deal with issue https://github.com/MCUdude/MegaCoreX/issues/167 + +#include From dabd52d4bf78f91b96acbec94c9fd8f7449ed09c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Jan 2023 20:44:24 +0100 Subject: [PATCH 311/351] No need to "Burn Bootloader" to set/ the EEPROM retain fuse This is done automatically as long as the user program is uploaded using a UPDI programmer, and not a bootloader --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 539767a..4941830 100644 --- a/README.md +++ b/README.md @@ -124,7 +124,7 @@ Brownout detection or BOD for short lets the microcontroller sense the input vol ## EEPROM option -If you want the EEPROM to be erased every time you burn the bootloader or upload using a programmer, you can turn off this option. You'll have to connect a UPDI programmer and hit "Burn bootloader" to enable or disable EEPROM retain. Note that when uploading using a bootloader, the EEPROM will always be retained. +If you want the EEPROM to be erased every time you burn the bootloader or upload using a programmer, you can turn off this option. A UPDI programmer is needed to enable or disable EEPROM retain. Note that when uploading using a bootloader, the EEPROM will always be retained. ## Reset pin From 8dca088f6f287fa83e43d2a85b883e3838c5318b Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 10 Jan 2023 21:58:17 +0100 Subject: [PATCH 312/351] Update README.md --- README.md | 27 +++++++++++++++++++++++---- 1 file changed, 23 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 4941830..99cb94f 100644 --- a/README.md +++ b/README.md @@ -32,6 +32,7 @@ They're small programmers with excellent software support, and can be used with * [Write to own flash](#write-to-own-flash) * [Memory-mapped flash](#memory-mapped-flash) * [Identifying MegaCoreX](#identifying-megacorex) +* [Timer used for millis and micros](#timer-used-for-millis-and-micros) * [Pinout](#pinout) * [Hardware features](#hardware-features) - [PWM output](#pwm-output) @@ -192,6 +193,22 @@ Usage: #endif ``` + +# Timer used for millis and micros +The 28 and 32 pin part have a total of three TCB timers, while the 40 and 48 pin parts have four. In order to create default pinouts with as may PWM output pins as possible, different pinout uses different timers for millis and micros. +The default timer can be changed by adding `-DMILLIS_USE_TIMERBx` to the platformio.ini build flags, where *x* represents the TCB timer number from 0 to 3. Alternativey, the respective *pins_arduino.h* file can be modified if using Arduino IDE. + +| Pinout | Timer used for millis and micros | +|-----------------|----------------------------------| +| 48 pin standard | TCB3 | +| 40 pin standard | TCB2 | +| 32 pin standard | TCB2 | +| 28 pin standard | TCB2 | +| Uno WiFi | TCB3 | +| Nano Every | TCB3 | +| Nano Every 4808 | TCB2 | + + ## Pinout This core provides several different Arduino pin mappings based on your current hardware - **48 pin standard**: This pinout is much closer to the actual hardware than the Uno WiFi pinout. It will not be compatible with shields or anything like that, but it's much cleaner and elegant from a hardware point of view. The only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. Note that this pinout is only available on ATmega3209/ATmega4809. @@ -200,6 +217,7 @@ This core provides several different Arduino pin mappings based on your current - **28 pin standard**: This is the pinout for the 28 pin version of the ATmega3208/4808. It will not be compatible with shields or anything like that, but it's still clean and elegant from a hardware point of view. Only pin swap done by default is the PWM output pins. This is done to prevent them from "colliding" with other peripherals. - **Uno WiFi**: This pinout is 100% compatible with the Arduino Uno WiFi Rev2 hardware. If you have code that's written for the Uno WiFi Rev2 it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. Note that this pinout is only available on ATmega3209/ATmega4809. - **Nano Every**: This pinout is 100% compatible with the Arduino Nano Every. If you have code that's written for the Nano Every it will work without any modifications if you choose this pinout. Note that this pinout does pin swapping on serial interfaces and PWM pins by default, and some peripherals are renamed to match the original 328P Uno hardware better. This pinout is only available when ATmega4809 is selected. +- **Nano Every 4808**: This matches the "official" Thinary Nano Every pinout, and is compatible with the Thinary Nano Every Arduino core. Note that this pinout does pin swapping on serial interfaces and PWM pins by default. This pinout is only available when ATmega4808 is selected. Please have a look at the pins_arduino.h files for detailed info.

Click to enlarge: @@ -231,6 +249,7 @@ PWM output, `analogWrite()`, is available for the following pins: | *48 pin standard* | 9 | 13, 14, 15, 16, 17, 18, 19, 38, 39 | | *Uno WiFi* | 6 | 3, 5, 6, 9, 10, 27 | | *Nano Every* | 5 | 3, 5, 6, 9, 10 | +| *Nano Every 4808* | 8 | 4, 5, 14, 15, 16, 17, 22, 23 | The repeat frequency for the pulses on all PWM outputs can be changed with the new function `analogWriteFrequency(kHz)`, where `kHz` values of 1 (default), 4, 8, 16, 32 and 64 are supported. Note that these values are very approximate. The best effort within the constraints of the hardware will be made to match the request. @@ -289,7 +308,7 @@ Here are some simple schematics that show a minimal setup. The straight 6-pin he ## Getting your hardware working ### Arduino Uno WiFi Rev2 -[The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **Atmel mEDBG (ATmega32u4)** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. +[The Arduino Uno WiFi Rev2](https://store.arduino.cc/arduino-uno-wifi-rev2) is one of the few megaAVR-0 based boards that's officially supported by Arduino. It uses an ATmega4809 and the recommended pinout is *Uno WiFi*. Printing to the serial monitor on your PC is done by initializing `Serial.begin(baud)`. You'll also have to choose **microUPDI/Uno Wifi** as your programmer to upload code. Uno WiFi Rev2 does not support a bootloader, so select *No bootloader* in the tools menu. For more information about this board please see the product page and its schematic. Click to enlarge: @@ -309,21 +328,21 @@ Click to enlarge: ### Curiosity Nano -[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. +[The Curiosity Nano](https://www.microchip.com/developmenttools/ProductDetails/DM320115) uses an ATmega4809 but has a different pinout than the Uno Wifi Rev2. The recommended pinout for this board is *48 pin standard*. The on-board LED is connected t pin PF5 (digital pin 39). Note that UART3 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial3.begin(baud)` to print to the serial monitor. You'll also have to choose **Curiosity Nano** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: ### AVR-IOT WG -[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel nEDBG (ATSAMD21E18)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. +[The AVR-IOT WG](https://www.microchip.com/developmenttools/ProductDetails/AC164160) uses the ATmega4808 in a 32 pin package. *32 pin standard* is the correct pinout for this board. Note that UART2 is connected to the nEDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial2.begin(baud)` to print to the serial monitor. You'll also have to choose **Curiosity Nano** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: ### ATmega4809 Xplained Pro -[The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Atmel EDBG (AT32UC3A4256)** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. +[The ATmega4809 Xplained Pro](https://www.microchip.com/developmenttools/ProductDetails/atmega4809-xpro) uses an ATmega4809. The recommended pinout for this board is *48 pin standard*. Note that the UART1 is connected to the EDBG chip (often referred to as the debug serial port). This means you'll have to use `Serial1.begin(baud)` to print to the serial monitor. You'll also have to choose **Xplained Pro** as your programmer to upload code. For more information about this board please refer to the user guide and its schematic. Click to enlarge: From 7afbf43cc2999aaa238f086182282255715c028e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Jan 2023 22:04:53 +0100 Subject: [PATCH 313/351] Add another function overloaded requestFrom function Closes issue #146 --- megaavr/libraries/Wire/src/Wire.cpp | 5 +++++ megaavr/libraries/Wire/src/Wire.h | 1 + 2 files changed, 6 insertions(+) diff --git a/megaavr/libraries/Wire/src/Wire.cpp b/megaavr/libraries/Wire/src/Wire.cpp index 8bc3ead..68b62cf 100644 --- a/megaavr/libraries/Wire/src/Wire.cpp +++ b/megaavr/libraries/Wire/src/Wire.cpp @@ -195,6 +195,11 @@ uint8_t TwoWire::requestFrom(int address, int quantity, int sendStop) return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); } +uint8_t TwoWire::requestFrom(uint8_t address, uint8_t quantity, uint8_t sendStop) +{ + return requestFrom((uint8_t)address, (size_t)quantity, (bool)sendStop); +} + uint8_t TwoWire::requestFrom(uint8_t address, size_t quantity) { return requestFrom(address, quantity, true); diff --git a/megaavr/libraries/Wire/src/Wire.h b/megaavr/libraries/Wire/src/Wire.h index 45db79e..ff5c9bc 100644 --- a/megaavr/libraries/Wire/src/Wire.h +++ b/megaavr/libraries/Wire/src/Wire.h @@ -75,6 +75,7 @@ class TwoWire : public Stream uint8_t endTransmission(bool sendStop); uint8_t requestFrom(uint8_t address, size_t quantity, bool sendStop); uint8_t requestFrom(int address, int quantity, int sendStop); + uint8_t requestFrom(uint8_t address, uint8_t quantity, uint8_t sendStop); uint8_t requestFrom(uint8_t address, size_t quantity); uint8_t requestFrom(uint8_t address, uint8_t quantity); uint8_t requestFrom(int address, int quantity); From 4e32ed6fa60dd2dde73297e4c7aa7213276d73b1 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Jan 2023 22:05:16 +0100 Subject: [PATCH 314/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 5859ce0..a42227f 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.0.10 +version=1.1.1 # AVR compile variables # --------------------- From a9f9455b88d89d94c7d95b25c6589a11cb141f24 Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 10 Jan 2023 22:14:28 +0100 Subject: [PATCH 315/351] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 99cb94f..5f7de6c 100644 --- a/README.md +++ b/README.md @@ -75,7 +75,7 @@ They're small programmers with excellent software support, and can be used with ### Using a UPDI programmer Programming must be done with a UPDI compatible programmer, such as the [microUPDI](https://github.com/MCUdude/microUPDI), [JTAG2UPDI](https://github.com/ElTangas/jtag2updi) SerialUPDI or an official Atmel/Microchip UPDI compatible programmer. -Unlike the *Arduino megaAVR boards* package, MegaCoreX does not auto-detect the programmer you're using. You'll have to select the correct programmer in the *Programmers*. If you're using an Arduino Uno Wifi Rev2 board, a Curiosity Nano or an Xplained Pro board you'll have to choose mEDBG, nEDBG or EDBG. +Unlike the *Arduino megaAVR boards* package, MegaCoreX does not auto-detect the programmer you're using. You'll have to select the correct programmer in the *Programmers* menu. #### SerialUPDI SerialUPDI is a programmer that utilize a simple serial connection. It uses a USB serial adapter which can be turned into a UPDI programmer by adding a few passive components. You can read more about the details on how the SerualUPDI works [here](https://github.com/SpenceKonde/AVR-Guidance/blob/master/UPDI/jtag2updi.md). From be87c765ca7d66d3d7e927834b50860937ef0602 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 10 Jan 2023 22:53:25 +0100 Subject: [PATCH 316/351] Prepare for Avrdude 7.1 --- megaavr/avrdude.conf | 26410 +++++++++++++++++--------------------- megaavr/platform.txt | 38 +- megaavr/programmers.txt | 65 +- 3 files changed, 11888 insertions(+), 14625 deletions(-) diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf index 36c62ce..ade0ddb 100644 --- a/megaavr/avrdude.conf +++ b/megaavr/avrdude.conf @@ -12,68 +12,91 @@ # # DO NOT MODIFY THIS FILE. Modifications will be overwritten the next # time a "make install" is run. For user-specific additions, use the -# "-C +filename" commandline option. +# "-C +filename" command line option. # # Possible entry formats are: # # programmer -# parent # optional parent -# id = [, [, ] ...] ; # are quoted strings -# desc = ; # quoted string -# type = ; # programmer type, quoted string -# # supported programmer types can be listed by "-c ?type" -# connection_type = parallel | serial | usb -# baudrate = ; # baudrate for avr910-programmer -# vcc = [, ... ] ; # pin number(s) -# buff = [, ... ] ; # pin number(s) -# reset = ; # pin number -# sck = ; # pin number -# mosi = ; # pin number -# miso = ; # pin number -# errled = ; # pin number -# rdyled = ; # pin number -# pgmled = ; # pin number -# vfyled = ; # pin number -# usbvid = ; # USB VID (Vendor ID) -# usbpid = [, ...] # USB PID (Product ID) (1) -# usbdev = ; # USB interface or other device info -# usbvendor = ; # USB Vendor Name -# usbproduct = ; # USB Product Name -# usbsn = ; # USB Serial Number +# parent # optional parent +# id = [, ... ] ; # are quoted strings +# desc = ; # quoted string +# type = ; # programmer type, quoted string +# # supported types can be listed by "-c ?type" +# prog_modes = PM_ {| PM_} # interfaces, eg, PM_SPM|PM_PDI (1) +# connection_type = parallel | serial | usb | spi +# baudrate = ; # baudrate for avr910-programmer +# vcc = [, ... ] ; # pin number(s) +# buff = [, ... ] ; # pin number(s) +# reset = ; # pin number +# sck = ; # pin number +# sdo = ; # pin number +# sdi = ; # pin number +# errled = ; # pin number +# rdyled = ; # pin number +# pgmled = ; # pin number +# vfyled = ; # pin number +# usbvid = ; # USB VID (Vendor ID) +# usbpid = [, ...] ; # USB PID (Product ID) (2) +# usbdev = ; # USB interface or other device info +# usbvendor = ; # USB Vendor Name +# usbproduct = ; # USB Product Name +# usbsn = ; # USB Serial Number +# hvupdi_support = [, , ... ] ; # UPDI HV Variants Support +# ; # -# To invert a bit, use = ~ , the spaces are important. -# For a pin list all pins must be inverted. -# A single pin can be specified as usual = ~ , for lists -# specify it as follows = ~ ( [, ... ] ) . -# -# (1) Not all programmer types can process a list of PIDs. -# ; +# # To invert a pin use = ~ +# # To invert a pin list (all pins get inverted) use ~ ( [, ... ] ) +# # +# # (1) The following program modes are known: +# # - PM_SPM: Bootloaders, self-programming with SPM opcodes or NVM Controllers +# # - PM_TPI: Tiny Programming Interface (t4, t5, t9, t10, t20, t40, t102, t104) +# # - PM_ISP: SPI programming for In-System Programming (almost all classic parts) +# # - PM_PDI: Program and Debug Interface (xmega parts) +# # - PM_UPDI: Unified Program and Debug Interface +# # - PM_HVSP: High Voltage Serial Programming (some classic parts) +# # - PM_HVPP: High Voltage Parallel Programming (most non-HVSP classic parts) +# # - PM_debugWIRE: Simpler alternative to JTAG (a subset of HVPP/HVSP parts) +# # - PM_JTAG: Joint Test Action Group standard (some classic parts) +# # - PM_JTAGmkI: Subset of PM_JTAG, older parts, Atmel ICE mkI +# # - PM_XMEGAJTAG: JTAG, some XMEGA parts +# # - PM_AVR32JTAG: JTAG for 32-bit AVRs +# # - PM_aWire: AVR32 parts +# # +# # (2) Not all programmer types can process a list of PIDs # # part -# id = ; # quoted string # desc = ; # quoted string -# has_jtag = ; # part has JTAG i/f -# has_debugwire = ; # part has debugWire i/f -# has_pdi = ; # part has PDI i/f -# has_updi = ; # part has UPDI i/f -# has_tpi = ; # part has TPI i/f -# devicecode = ; # deprecated, use stk500_devcode +# id = ; # quoted string +# family_id = ; # quoted string, eg, "megaAVR" or "tinyAVR" +# prog_modes = PM_ {| PM_} # interfaces, eg, PM_SPM|PM_ISP|PM_HVPP|PM_debugWIRE +# mcuid = ; # unique id in 0..2039 for 8-bit AVRs +# n_interrupts = ; # number of interrupts, used for vector bootloaders +# n_page_erase = ; # if set, number of pages erased during SPM erase +# n_boot_sections = ; # Number of boot sections +# boot_section_size = ; # Size of (smallest) boot section, if any +# hvupdi_variant = ; # numeric -1 (n/a) or 0..2 +# devicecode = ; # deprecated, use stk500_devcode # stk500_devcode = ; # numeric # avr910_devcode = ; # numeric +# has_jtag = ; # part has JTAG i/f (deprecated, use prog_modes) +# has_debugwire = ; # part has debugWire i/f (deprecated, use prog_modes) +# has_pdi = ; # part has PDI i/f (deprecated, use prog_modes) +# has_updi = ; # part has UPDI i/f (deprecated, use prog_modes) +# has_tpi = ; # part has TPI i/f (deprecated, use prog_modes) +# is_avr32 = ; # AVR32 part (deprecated, use prog_modes) +# is_at90s1200 = ; # AT90S1200 part # signature = ; # signature bytes # usbpid = ; # DFU USB PID # chip_erase_delay = ; # micro-seconds -# reset = dedicated | io; -# retry_pulse = reset | sck; -# pgm_enable = ; -# chip_erase = ; +# reset = dedicated | io ; +# retry_pulse = reset | sck ; # chip_erase_delay = ; # chip erase delay (us) # # STK500 parameters (parallel programming IO lines) # pagel = ; # pin name in hex, i.e., 0xD7 # bs2 = ; # pin name in hex, i.e., 0xA0 # serial = ; # can use serial downloading -# parallel = ; # can use par. programming -# # STK500v2 parameters, to be taken from Atmel's XML files +# parallel = ; # can use par. programming +# # STK500v2 parameters, to be taken from Atmel's ATDF files # timeout = ; # stabdelay = ; # cmdexedelay = ; @@ -84,52 +107,63 @@ # predelay = ; # postdelay = ; # pollmethod = ; -# mode = ; -# delay = ; -# blocksize = ; -# readsize = ; # hvspcmdexedelay = ; -# # STK500v2 HV programming parameters, from XML -# pp_controlstack = , , ...; # PP only -# hvsp_controlstack = , , ...; # HVSP only -# hventerstabdelay = ; -# progmodedelay = ; # PP only -# latchcycles = ; -# togglevtg = ; -# poweroffdelay = ; -# resetdelayms = ; -# resetdelayus = ; -# hvleavestabdelay = ; -# resetdelay = ; -# synchcycles = ; # HVSP only -# chiperasepulsewidth = ; # PP only -# chiperasepolltimeout = ; -# chiperasetime = ; # HVSP only -# programfusepulsewidth = ; # PP only -# programfusepolltimeout = ; -# programlockpulsewidth = ; # PP only -# programlockpolltimeout = ; -# # JTAG ICE mkII parameters, also from XML files +# # STK500v2 HV programming parameters, from ATDFs +# pp_controlstack = , , ... ; # PP only +# hvsp_controlstack = , , ... ; # HVSP only +# flash_instr = , , ; +# eeprom_instr = , , ... ; +# hventerstabdelay = ; +# progmodedelay = ; # PP only +# latchcycles = ; +# togglevtg = ; +# poweroffdelay = ; +# resetdelayms = ; +# resetdelayus = ; +# hvleavestabdelay = ; +# resetdelay = ; +# synchcycles = ; # HVSP only +# chiperasepulsewidth = ; # PP only +# chiperasepolltimeout = ; +# chiperasetime = ; # HVSP only +# programfusepulsewidth = ; # PP only +# programfusepolltimeout = ; +# programlockpulsewidth = ; # PP only +# programlockpolltimeout = ; +# # debugWIRE and/or JTAG ICE mkII parameters, also from ATDF files # allowfullpagebitstream = ; # enablepageprogramming = ; -# idr = ; # IO addr of IDR (OCD) reg. -# rampz = ; # IO addr of RAMPZ reg. -# spmcr = ; # mem addr of SPMC[S]R reg. -# eecr = ; # mem addr of EECR reg. -# # (only when != 0x3c) -# is_at90s1200 = ; # AT90S1200 part -# is_avr32 = ; # AVR32 part +# idr = ; # IO addr of IDR (OCD) reg +# rampz = ; # IO addr of RAMPZ reg +# spmcr = ; # mem addr of SPMC[S]R reg +# eecr = ; # mem addr of EECR reg only when != 0x3f +# eind = ; # mem addr of EIND reg +# mcu_base = ; +# nvm_base = ; +# ocd_base = ; +# ocdrev = ; +# pgm_enable = ; +# chip_erase = ; +# # parameters for bootloaders +# autobaud_sync = ; # autobaud detection byte, default 0x30 # # memory -# paged = ; # yes / no +# paged = ; # yes/no (flash only, do not use for EEPROM) +# offset = ; # memory offset # size = ; # bytes # page_size = ; # bytes # num_pages = ; # numeric +# n_word_writes = ; # TPI only: if set, number of words to write # min_write_delay = ; # micro-seconds # max_write_delay = ; # micro-seconds -# readback_p1 = ; # byte value -# readback_p2 = ; # byte value -# pwroff_after_write = ; # yes / no +# readback = ; # pair of byte values +# readback_p1 = ; # byte value (first component) +# readback_p2 = ; # byte value (second component) +# pwroff_after_write = ; # yes/no +# mode = ; # STK500 v2 file parameter from ATDF files +# delay = ; # " +# blocksize = ; # " +# readsize = ; # " # read = ; # write = ; # read_lo = ; @@ -139,19 +173,29 @@ # loadpage_lo = ; # loadpage_hi = ; # writepage = ; -# ; -# ; +# ; +# ; # # If any of the above parameters are not specified, the default value -# of 0 is used for numerics or the empty string ("") for string -# values. If a required parameter is left empty, AVRDUDE will -# complain. +# of 0 is used for numerics (except for mcuid, hvupdi_variant and +# ocdrev, where the default value is -1, and for autobaud_sync which +# defaults to 0x30), or the empty string "" for string values. If a +# required parameter is left empty, AVRDUDE will complain. Almost all +# occurrences of numbers (with the exception of pin numbers and where +# they are separated by space, eg, in signature and readback) can also +# be given as simple expressions involving arithemtic and bitwise +# operators. # # Parts can also inherit parameters from previously defined parts # using the following syntax. In this case specified integer and # string values override parameter values from the parent part. New # memory definitions are added to the definitions inherited from the -# parent. +# parent. If, however, a new memory definition refers to an existing +# one of the same name for that part then, from v7.1, the existing +# memory definition is extended, and components overwritten with new +# values. Assigning NULL removes an inherited SPI instruction format, +# memory definition, control stack, eeprom or flash instruction, eg, +# as in memory "efuse" = NULL; # # part parent # quoted string # id = ; # quoted string @@ -161,16 +205,16 @@ # NOTES: # * 'devicecode' is the device code used by the STK500 (see codes # listed below) -# * Not all memory types will implement all instructions. -# * AVR Fuse bits and Lock bits are implemented as a type of memory. +# * Not all memory types will implement all instructions +# * AVR Fuse bits and Lock bits are implemented as a type of memory # * Example memory types are: # "flash", "eeprom", "fuse", "lfuse" (low fuse), "hfuse" (high # fuse), "signature", "calibration", "lock" # * The memory type specified on the avrdude command line must match -# one of the memory types defined for the specified chip. +# one of the memory types defined for the specified chip # * The pwroff_after_write flag causes avrdude to attempt to # power the device off and back on after an unsuccessful write to -# the affected memory area if VCC programmer pins are defined. If +# the affected memory area if VCC programmer pins are defined. If # VCC pins are not defined for the programmer, a message # indicating that the device needs a power-cycle is printed out. # This flag was added to work around a problem with the @@ -180,7 +224,7 @@ # # INSTRUCTION FORMATS # -# Instruction formats are specified as a comma seperated list of +# Instruction formats are specified as a comma separated list of # string values containing information (bit specifiers) about each # of the 32 bits of the instruction. Bit specifiers may be one of # the following formats: @@ -189,10 +233,11 @@ # # '0' = the bit is always clear on input as well as output # -# 'x' = the bit is ignored on input and output +# 'x' = the bit is ignored on input and output and set as 0 # -# 'a' = the bit is an address bit, the bit-number matches this bit -# specifier's position within the current instruction byte +# 'a' = the bit is an address bit; from v 7.1 the bit-number +# is set to match the right bit position for the +# instruction to "just work" # # 'aN' = the bit is the Nth address bit, bit-number = N, i.e., a12 # is address bit 12 on input, a0 is address bit 0. @@ -201,11 +246,28 @@ # # 'o' = the bit is an output data bit # -# Each instruction must be composed of 32 bit specifiers. The +# Each instruction must be composed of 32 bit specifiers. The # instruction specification closely follows the instruction data -# provided in Atmel's data sheets for their parts. +# provided in Atmel's data sheets for their parts. Note that flash +# addresses always refer to *word* addresses whilst all other +# memory types specify *byte* addresses. +# +# Example for signature read on the ATmega328P: +# read = "0 0 1 1 0 0 0 0", "0 0 0 x x x x x", +# "x x x x x x a1 a0", "o o o o o o o o"; # -# See below for some examples. +# As the address bit numbers in the SPI opcodes are highly +# systematic, they don't really need to be specified. A compact +# version of the format specification neither uses bit-numbers for +# address lines nor spaces. If such a string is longer than 7 +# characters, then the characters 0, 1, x, a, i and o will be +# recognised as the corresponding bit, whilst any of the characters +# ., -, _ or / can act as arbitrary visual separators, which are +# ignored. Examples: +# +# loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; +# +# loadpage_lo = "0100.0000", "000x.xxxx", "xxaa.aaaa", "iiii.iiii"; # # # The following are STK500 part device codes to use for the @@ -213,7 +275,7 @@ # section avr061.zip which accompanies the application note # AVR061 available from: # -# http://www.atmel.com/dyn/resources/prod_documents/doc2525.pdf +# https://ww1.microchip.com/downloads/en/Appnotes/doc2525.pdf # #define ATTINY10 0x10 /* the _old_ one that never existed! */ @@ -269,8 +331,8 @@ #define AT86RF401 0xD0 #define AT89START 0xE0 -#define AT89S51 0xE0 -#define AT89S52 0xE1 +#define AT89S51 0xE0 +#define AT89S52 0xE1 # The following table lists the devices in the original AVR910 # appnote: @@ -322,51 +384,90 @@ # in the Internet. These add the following codes (only devices that # actually exist are listed): -# ATmega8515 0x3A -# ATmega128 0x43 -# ATmega64 0x45 -# ATtiny26 0x5E -# ATmega8535 0x69 -# ATmega32 0x72 -# ATmega16 0x74 -# ATmega8 0x76 -# ATmega169 0x78 +# ATmega8515 0x3A +# ATmega128 0x43 +# ATmega64 0x45 +# ATtiny26 0x5E +# ATmega8535 0x69 +# ATmega32 0x72 +# ATmega16 0x74 +# ATmega8 0x76 +# ATmega169 0x78 # -# Overall avrdude defaults; suitable for ~/.avrduderc +# Overall avrdude defaults; suitable for ~/.config/avrdude/avrdude.rc # -default_parallel = "unknown"; -default_serial = "unknown"; +default_parallel = "/dev/parport0"; +default_serial = "/dev/ttyS0"; +default_spi = ""; # default_bitclock = 2.5; + + + + + + # # PROGRAMMER DEFINITIONS # +#------------------------------------------------------------ +# wiring +#------------------------------------------------------------ + # http://wiring.org.co/ -# Basically STK500v2 protocol, with some glue to trigger the -# bootloader. +# Basically STK500v2 protocol, with some glue to trigger the bootloader + programmer - id = "wiring"; - desc = "Wiring"; - type = "wiring"; - connection_type = serial; + id = "wiring"; + desc = "Wiring for bootloader using STK500 v2 protocol"; + type = "wiring"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# arduino +#------------------------------------------------------------ + +programmer + id = "arduino"; + desc = "Arduino for bootloader using STK500 v1 protocol"; + type = "arduino"; + prog_modes = PM_SPM; + connection_type = serial; +; + +#------------------------------------------------------------ +# urclock +#------------------------------------------------------------ + +# See https://github.com/stefanrueger/urboot programmer - id = "arduino"; - desc = "Arduino"; - type = "arduino"; - connection_type = serial; + id = "urclock"; + desc = "Urclock programmer for urboot bootloaders using urprotocol"; + type = "urclock"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# xbee +#------------------------------------------------------------ + programmer - id = "xbee"; - desc = "XBee Series 2 Over-The-Air (XBeeBoot)"; - type = "xbee"; - connection_type = serial; + id = "xbee"; + desc = "XBee for Series 2 Over-The-Air (XBeeBoot) bootloader using STK500 v1 protocol"; + type = "xbee"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# ft2232h +#------------------------------------------------------------ + # this will interface with the chips on these programmers: # # http://real.kiev.ua/old/avreal/en/adapters @@ -383,137 +484,172 @@ programmer # And fill that in here. # # Note that the pin numbers for the main ISP signals (reset, sck, -# mosi, miso) are fixed and cannot be changed, since they must match +# sdo, sdi) are fixed and cannot be changed, since they must match # the way the Multi-Protocol Synchronous Serial Engine (MPSSE) of # these FTDI ICs has been designed. programmer - id = "avrftdi"; - desc = "FT2232D based generic programmer"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x6010; - usbvendor = ""; - usbproduct = ""; - usbdev = "A"; - usbsn = ""; -#ISP-signals - lower ADBUS-Nibble (default) - reset = 3; - sck = 0; - mosi = 1; - miso = 2; -#LED SIGNALs - higher ADBUS-Nibble -# errled = 4; -# rdyled = 5; -# pgmled = 6; -# vfyled = 7; -#Buffer Signal - ACBUS - Nibble -# buff = 8; + id = "ft2232h"; + desc = "FT2232H based generic programmer"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0x6010; + usbdev = "A"; +# ISP-signals - lower ADBUS-Nibble (default) + reset = 3; # AD3 (TMS) + sck = 0; # AD0 (TCK) + sdo = 1; # AD1 (TDI) + sdi = 2; # AD2 (TDO) +; + +#------------------------------------------------------------ +# avrftdi +#------------------------------------------------------------ + +programmer parent "ft2232h" + id = "avrftdi"; + desc = "FT2232D based generic programmer"; ; + +#------------------------------------------------------------ +# 2232HIO +#------------------------------------------------------------ + # This is an implementation of the above with a buffer IC (74AC244) and # 4 LEDs directly attached, all active low. -programmer - id = "2232HIO"; - desc = "FT2232H based generic programmer"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; -# Note: This PID is reserved for generic H devices and -# should be programmed into the EEPROM -# usbpid = 0x8A48; - usbpid = 0x6010; - usbdev = "A"; - usbvendor = ""; - usbproduct = ""; - usbsn = ""; -#ISP-signals - reset = 3; - sck = 0; - mosi = 1; - miso = 2; - buff = ~4; -#LED SIGNALs - errled = ~ 11; - rdyled = ~ 14; - pgmled = ~ 13; - vfyled = ~ 12; + +programmer parent "ft2232h" + id = "2232hio"; + desc = "2232hio based on FT2232H with buffer and LEDs"; + buff = ~4; +# LED SIGNALs + errled = ~11; + rdyled = ~14; + pgmled = ~13; + vfyled = ~12; +; + +#------------------------------------------------------------ +# tigard +#------------------------------------------------------------ + +# Tigard - FT2232H based multi-protocol tool for hardware hacking +# https://github.com/tigard-tools/tigard + +programmer parent "ft2232h" + id = "tigard"; + desc = "Tigard interface board"; + usbdev = "B"; +# Reset is different to the FT2232H; sck, sdo, sdi remain at 0, 1, 2 + reset = 5; # BD5 (GPIOL1) ; +#------------------------------------------------------------ +# ft4232h +#------------------------------------------------------------ + #The FT4232H can be treated as FT2232H, but it has a different USB #device ID of 0x6011. -programmer parent "avrftdi" - id = "4232h"; - desc = "FT4232H based generic programmer"; - usbpid = 0x6011; + +programmer parent "ft2232h" + id = "ft4232h"; + desc = "FT4232H based generic programmer"; + usbpid = 0x6011; ; -programmer - id = "jtagkey"; - desc = "Amontec JTAGKey, JTAGKey-Tiny and JTAGKey2"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; -# Note: This PID is used in all JTAGKey variants - usbpid = 0xCFF8; - usbdev = "A"; - usbvendor = ""; - usbproduct = ""; - usbsn = ""; -#ISP-signals => 20 - Pin connector on JTAGKey - reset = 3; # TMS 7 violet - sck = 0; # TCK 9 white - mosi = 1; # TDI 5 green - miso = 2; # TDO 13 orange - buff = ~4; -# VTG VREF 1 brown with red tip -# GND GND 20 black -# The colors are on the 20 pin breakout cable -# from Amontec +#------------------------------------------------------------ +# 4232h +#------------------------------------------------------------ + +programmer parent "ft4232h" + id = "4232h"; ; +#------------------------------------------------------------ +# jtagkey +#------------------------------------------------------------ + +programmer + id = "jtagkey"; + desc = "Amontec JTAGKey, JTAGKey-Tiny and JTAGKey2"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; +# Note: This PID is used in all JTAGKey variants + usbpid = 0xcff8; + usbdev = "A"; + buff = ~4; +# ISP-signals => 20 - Pin connector on JTAGKey + reset = 3; # TMS 7 violet + sck = 0; # TCK 9 white + sdo = 1; # TDI 5 green + sdi = 2; # TDO 13 orange +# VTG VREF 1 brown with red tip +# GND GND 20 black +# The colors are on the 20 pin breakout cable from Amontec +; + +#------------------------------------------------------------ +# ft232h +#------------------------------------------------------------ + programmer - id = "ft232h"; - desc = "FT232H in MPSSE mode"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x6014; - usbdev = "A"; - usbvendor = ""; - usbproduct = ""; - usbsn = ""; -#ISP-signals - sck = 0; # AD0 (TCK) - mosi = 1; # AD1 (TDI) - miso = 2; # AD2 (TDO) - reset = 3; # AD3 (TMS) + id = "ft232h"; + desc = "FT232H based generic programmer"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0x6014; + usbdev = "A"; +# ISP-signals + reset = 3; # AD3 (TMS) + sck = 0; # AD0 (TCK) + sdo = 1; # AD1 (TDI) + sdi = 2; # AD2 (TDO) ; +#------------------------------------------------------------ +# um232h +#------------------------------------------------------------ + # Pin J2-7 (AD0) is SCK -# Pin J2-8 (AD1) is MOSI -# Pin J2-9 (AD2) is MISO +# Pin J2-8 (AD1) is SDO +# Pin J2-9 (AD2) is SDI # Pin J2-10 (AD3) is RESET # Pin J2-6 is GND # Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get # a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. + programmer parent "ft232h" - id = "um232h"; - desc = "UM232H module from FTDI"; + id = "um232h"; + desc = "UM232H module from FTDI"; ; +#------------------------------------------------------------ +# c232hm +#------------------------------------------------------------ + # Orange (Pin 2) is SCK -# Yellow (Pin 3) is MOSI -# Green (Pin 4) is MISO +# Yellow (Pin 3) is SDO +# Green (Pin 4) is SDI # Brown (Pin 5) is RESET # Black (Pin 10) is GND # Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get # a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. + programmer parent "ft232h" - id = "c232hm"; - desc = "C232HM cable from FTDI"; + id = "c232hm"; + desc = "C232HM cable from FTDI"; ; +#------------------------------------------------------------ +# o-link +#------------------------------------------------------------ + # On the adapter you can read "O-Link". On the PCB is printed "OpenJTAG v3.1" # You can find it as "OpenJTAG ARM JTAG USB" in the internet. # (But there are also several projects called Open JTAG, eg. @@ -527,859 +663,1530 @@ programmer parent "ft232h" # http://armwerks.com/catalog/o-link-debugger-copy/ # or just have a look at ebay ... # It is basically the same entry as jtagkey with different usb ids. + programmer parent "jtagkey" - id = "o-link"; - desc = "O-Link, OpenJTAG from www.100ask.net"; - usbvid = 0x1457; - usbpid = 0x5118; - usbvendor = "www.100ask.net"; - usbproduct = "USB<=>JTAG&RS232"; + id = "o-link"; + desc = "O-Link, OpenJTAG from www.100ask.net"; + usbvid = 0x1457; + usbpid = 0x5118; + usbvendor = "www.100ask.net"; + usbproduct = "USB<=>JTAG&RS232"; ; +#------------------------------------------------------------ +# openmoko +#------------------------------------------------------------ + # http://wiki.openmoko.org/wiki/Debug_Board_v3 + programmer - id = "openmoko"; - desc = "Openmoko debug board (v3)"; - type = "avrftdi"; - usbvid = 0x1457; - usbpid = 0x5118; - usbdev = "A"; - usbvendor = ""; - usbproduct = ""; - usbsn = ""; - reset = 3; # TMS 7 - sck = 0; # TCK 9 - mosi = 1; # TDI 5 - miso = 2; # TDO 13 + id = "openmoko"; + desc = "Openmoko debug board (v3)"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + usbvid = 0x1457; + usbpid = 0x5118; + usbdev = "A"; + reset = 3; # TMS 7 + sck = 0; # TCK 9 + sdo = 1; # TDI 5 + sdi = 2; # TDO 13 ; +#------------------------------------------------------------ +# lm3s811 +#------------------------------------------------------------ + # Only Rev. A boards. # Schematic and user manual: http://www.cs.put.poznan.pl/wswitala/download/pdf/811EVBK.pdf + programmer - id = "lm3s811"; - desc = "Luminary Micro LM3S811 Eval Board (Rev. A)"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0xbcd9; - usbvendor = "LMI"; - usbproduct = "LM3S811 Evaluation Board"; - usbdev = "A"; - usbsn = ""; -#ISP-signals - lower ACBUS-Nibble (default) - reset = 3; - sck = 0; - mosi = 1; - miso = 2; + id = "lm3s811"; + desc = "Luminary Micro LM3S811 Eval Board (Rev. A)"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0xbcd9; + usbdev = "A"; + usbvendor = "LMI"; + usbproduct = "LM3S811 Evaluation Board"; # Enable correct buffers - buff = 7; + buff = 7; +# ISP-signals - lower ACBUS-Nibble (default) + reset = 3; + sck = 0; + sdo = 1; + sdi = 2; ; +#------------------------------------------------------------ +# tumpa +#------------------------------------------------------------ + # submitted as bug #46020 + +programmer + id = "tumpa"; + desc = "TIAO USB Multi-Protocol Adapter"; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0x8a98; + usbdev = "A"; + usbvendor = "TIAO"; + reset = 3; # TMS 7 + sck = 0; # TCK 9 + sdo = 1; # TDI 5 + sdi = 2; # TDO 13 +; + +#------------------------------------------------------------ +# ktlink +#------------------------------------------------------------ + +# Kristech KT-LINK FT2232H interface with IO switching and voltage buffers. +# Created on 20220410 by CeDeROM Tomasz CEDRO (www.cederom.io). +# Interface DataSheet: https://kristech.pl/files/KT-LINK-UM-ENG.pdf +# AVRDUDE FT2232H PIN NUMBER DECODE: +# | 0 | 1 | .. | 7 | 8 | 9 | .. | 15 | +# | ADBUS0 | ADBUS1 | .. | ADBUS7 | ACBUS0 | ACBUS1 | .. | ACBUS7 | +# KT-LINK JTAG CONN: +# 1=Vsense(->EXT13), 19=5V(EXT1->EXT3), 20=GND, 3=TPIRST, 9=TPICLK, 7=TPIDATA. +# INTERNALS CONFIGURATION ("~" MEANS ACTIVE LOW): +# ~TRST_EN=10(ACBUS2), ~CLK_EN=14(ACBUS6), ~SDO_EN=13(ACBUS5), +# TMS_SEL=5(ADBUS5), ~TMS_EN=12(ACBUS4), LED=~15(ACBUS7). +# CONNECTION NOTES: +# * Connect EXT connector pin 1 with 3 to get 5V on JTAG connector pin 19. +# * Connect JTAG connector pin 1 to 5V (i.e. EXT pin 13 or JTAG pin 19). +# * For TPI connection use resistors: TDO --[470R]-- TPIDATA --[470R]-- TDI. +# * Powering target from JTAG pin 19 allows KT-LINK current measurement. + programmer - id = "tumpa"; - desc = "TIAO USB Multi-Protocol Adapter"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x8A98; - usbdev = "A"; - usbvendor = "TIAO"; - usbproduct = ""; - usbsn = ""; - sck = 0; # TCK 9 - mosi = 1; # TDI 5 - miso = 2; # TDO 13 - reset = 3; # TMS 7 + id = "ktlink"; + desc = "KT-LINK FT2232H interface with IO switching and voltage buffers."; + type = "avrftdi"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0xbbe2; + usbdev = "A"; + buff = 5, ~10, ~13, ~14; + reset = 8; + sck = 0; + sdo = 1; + sdi = 2; + rdyled = ~15; ; +#------------------------------------------------------------ +# digilent-hs2 +#------------------------------------------------------------ + +# Digilent JTAG HS2 programmer. FT232H-based dongle with buffers. +# https://digilent.com/reference/_media/reference/programmers/jtag-hs2/jtag-hs2_rm.pdf + +programmer + id = "digilent-hs2"; + desc = "Digilient JTAG HS2 (MPSSE)"; + type = "avrftdi"; + connection_type = usb; + usbvid = 0x0403; + usbpid = 0x6014; + usbdev = "A"; + buff = 5, 6, 7; + reset = 3; + sck = 0; + sdo = 1; + sdi = 2; +; + +#------------------------------------------------------------ +# serialupdi +#------------------------------------------------------------ + programmer - id = "serialupdi"; - desc = "SerialUPDI"; - type = "serialupdi"; - connection_type = serial; + id = "serialupdi"; + desc = "SerialUPDI"; + type = "serialupdi"; + prog_modes = PM_UPDI; + connection_type = serial; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# avrisp +#------------------------------------------------------------ + programmer - id = "avrisp"; - desc = "Atmel AVR ISP"; - type = "stk500"; - connection_type = serial; + id = "avrisp"; + desc = "Atmel AVR ISP"; + type = "stk500"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# avrispv2 +#------------------------------------------------------------ + programmer - id = "avrispv2"; - desc = "Atmel AVR ISP V2"; - type = "stk500v2"; - connection_type = serial; + id = "avrispv2"; + desc = "Atmel AVR ISP v2"; + type = "stk500v2"; + prog_modes = PM_TPI | PM_ISP | PM_PDI; + connection_type = serial; ; +#------------------------------------------------------------ +# avrispmkII +#------------------------------------------------------------ + programmer - id = "avrispmkII"; - desc = "Atmel AVR ISP mkII"; - type = "stk500v2"; - connection_type = usb; + id = "avrispmkII"; + desc = "Atmel AVR ISP mkII"; + type = "stk500v2"; + prog_modes = PM_TPI | PM_ISP | PM_PDI; + connection_type = usb; ; +#------------------------------------------------------------ +# avrisp2 +#------------------------------------------------------------ + programmer parent "avrispmkII" - id = "avrisp2"; + id = "avrisp2"; ; +#------------------------------------------------------------ +# buspirate +#------------------------------------------------------------ + programmer - id = "buspirate"; - desc = "The Bus Pirate"; - type = "buspirate"; - connection_type = serial; + id = "buspirate"; + desc = "The Bus Pirate"; + type = "buspirate"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# buspirate_bb +#------------------------------------------------------------ + programmer - id = "buspirate_bb"; - desc = "The Bus Pirate (bitbang interface, supports TPI)"; - type = "buspirate_bb"; - connection_type = serial; + id = "buspirate_bb"; + desc = "The Bus Pirate (bitbang interface, supports TPI)"; + type = "buspirate_bb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; # pins are bits in bitbang byte (numbers are 87654321) - # 1|POWER|PULLUP|AUX|MOSI|CLK|MISO|CS - reset = 1; - sck = 3; - mosi = 4; - miso = 2; - #vcc = 7; This is internally set independent of this setting. + # 1|POWER|PULLUP|AUX|SDO|CLK|SDI|CS + reset = 1; + sck = 3; + sdo = 4; + sdi = 2; + # vcc = 7; # Internally set independent of this setting ; +#------------------------------------------------------------ +# stk500 +#------------------------------------------------------------ + # This is supposed to be the "default" STK500 entry. # Attempts to select the correct firmware version # by probing for it. Better use one of the entries # below instead. + programmer - id = "stk500"; - desc = "Atmel STK500"; - type = "stk500generic"; - connection_type = serial; + id = "stk500"; + desc = "Atmel STK500"; + type = "stk500generic"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# stk500v1 +#------------------------------------------------------------ + programmer - id = "stk500v1"; - desc = "Atmel STK500 Version 1.x firmware"; - type = "stk500"; - connection_type = serial; + id = "stk500v1"; + desc = "Atmel STK500 version 1.x firmware"; + type = "stk500"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# mib510 +#------------------------------------------------------------ + programmer - id = "mib510"; - desc = "Crossbow MIB510 programming board"; - type = "stk500"; - connection_type = serial; + id = "mib510"; + desc = "Crossbow MIB510 programming board"; + type = "stk500"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# stk500v2 +#------------------------------------------------------------ + programmer - id = "stk500v2"; - desc = "Atmel STK500 Version 2.x firmware"; - type = "stk500v2"; - connection_type = serial; + id = "stk500v2"; + desc = "Atmel STK500 version 2.x firmware"; + type = "stk500v2"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# stk500pp +#------------------------------------------------------------ + programmer - id = "stk500pp"; - desc = "Atmel STK500 V2 in parallel programming mode"; - type = "stk500pp"; - connection_type = serial; + id = "stk500pp"; + desc = "Atmel STK500 v2 in parallel programming mode"; + type = "stk500pp"; + prog_modes = PM_HVPP; + connection_type = serial; ; +#------------------------------------------------------------ +# stk500hvsp +#------------------------------------------------------------ + programmer - id = "stk500hvsp"; - desc = "Atmel STK500 V2 in high-voltage serial programming mode"; - type = "stk500hvsp"; - connection_type = serial; + id = "stk500hvsp"; + desc = "Atmel STK500 v2 in high-voltage serial programming mode"; + type = "stk500hvsp"; + prog_modes = PM_HVSP; + connection_type = serial; ; +#------------------------------------------------------------ +# stk600 +#------------------------------------------------------------ + programmer - id = "stk600"; - desc = "Atmel STK600"; - type = "stk600"; - connection_type = usb; + id = "stk600"; + desc = "Atmel STK600"; + type = "stk600"; + prog_modes = PM_TPI | PM_ISP | PM_PDI; + connection_type = usb; ; +#------------------------------------------------------------ +# stk600pp +#------------------------------------------------------------ + programmer - id = "stk600pp"; - desc = "Atmel STK600 in parallel programming mode"; - type = "stk600pp"; - connection_type = usb; + id = "stk600pp"; + desc = "Atmel STK600 in parallel programming mode"; + type = "stk600pp"; + prog_modes = PM_HVPP; + connection_type = usb; ; +#------------------------------------------------------------ +# stk600hvsp +#------------------------------------------------------------ + programmer - id = "stk600hvsp"; - desc = "Atmel STK600 in high-voltage serial programming mode"; - type = "stk600hvsp"; - connection_type = usb; + id = "stk600hvsp"; + desc = "Atmel STK600 in high-voltage serial programming mode"; + type = "stk600hvsp"; + prog_modes = PM_HVSP; + connection_type = usb; ; +#------------------------------------------------------------ +# avr910 +#------------------------------------------------------------ + programmer - id = "avr910"; - desc = "Atmel Low Cost Serial Programmer"; - type = "avr910"; - connection_type = serial; + id = "avr910"; + desc = "Atmel Low Cost Serial Programmer"; + type = "avr910"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# ft245r +#------------------------------------------------------------ + programmer - id = "ft245r"; - desc = "FT245R Synchronous BitBang"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 1; # D1 - sck = 0; # D0 - mosi = 2; # D2 - reset = 4; # D4 + id = "ft245r"; + desc = "FT245R based generic programmer"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 4; # D4 + sck = 0; # D0 + sdo = 2; # D2 + sdi = 1; # D1 ; +#------------------------------------------------------------ +# ft232r +#------------------------------------------------------------ + programmer - id = "ft232r"; - desc = "FT232R Synchronous BitBang"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 1; # RxD - sck = 0; # TxD - mosi = 2; # RTS - reset = 4; # DTR + id = "ft232r"; + desc = "FT232R based generic programmer"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 4; # DTR + sck = 0; # TxD + sdo = 2; # RTS + sdi = 1; # RxD ; +#------------------------------------------------------------ +# bwmega +#------------------------------------------------------------ + # see http://www.bitwizard.nl/wiki/index.php/FTDI_ATmega + programmer - id = "bwmega"; - desc = "BitWizard ftdi_atmega builtin programmer"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 5; # DSR - sck = 6; # DCD - mosi = 3; # CTS - reset = 7; # RI + id = "bwmega"; + desc = "BitWizard ftdi_atmega builtin programmer"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 7; # RI + sck = 6; # DCD + sdo = 3; # CTS + sdi = 5; # DSR ; +#------------------------------------------------------------ +# arduino-ft232r +#------------------------------------------------------------ + # see http://www.geocities.jp/arduino_diecimila/bootloader/index_en.html # Note: pins are numbered from 1! + programmer - id = "arduino-ft232r"; - desc = "Arduino: FT232R connected to ISP"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 3; # CTS X3(1) - sck = 5; # DSR X3(2) - mosi = 6; # DCD X3(3) - reset = 7; # RI X3(4) + id = "arduino-ft232r"; + desc = "Arduino: FT232R connected to ISP"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 7; # RI X3(4) + sck = 5; # DSR X3(2) + sdo = 6; # DCD X3(3) + sdi = 3; # CTS X3(1) ; +#------------------------------------------------------------ +# tc2030 +#------------------------------------------------------------ + programmer - id = "tc2030"; - desc = "Tag-Connect TC2030"; - type = "ftdi_syncbb"; - connection_type = usb; + id = "tc2030"; + desc = "Tag-Connect TC2030"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; # FOR TPI devices: - mosi = 0; # TxD = D0 (wire to TPIDATA via 1k resistor) - miso = 1; # RxD = D1 (wire to TPIDATA directly) - sck = 2; # RTS = D2 (wire to SCK) - reset = 3; # CTS = D3 (wire to ~RESET) + reset = 3; # CTS = D3 (wire to ~RESET) + sck = 2; # RTS = D2 (wire to SCK) + sdo = 0; # TxD = D0 (wire to TPIDATA via 1k resistor) + sdi = 1; # RxD = D1 (wire to TPIDATA directly) ; +#------------------------------------------------------------ +# diecimila +#------------------------------------------------------------ + # website mentioned above uses this id + programmer parent "arduino-ft232r" - id = "diecimila"; - desc = "alias for arduino-ft232r"; + id = "diecimila"; + desc = "alias for arduino-ft232r"; ; +#------------------------------------------------------------ +# uncompatino +#------------------------------------------------------------ + # There is a ATmega328P kit PCB called "uncompatino". # This board allows ISP via its on-board FT232R. # This is designed like Arduino Duemilanove but has no standard ICPS header. # Its 4 pairs of pins are shorted to enable ftdi_syncbb. # http://akizukidenshi.com/catalog/g/gP-07487/ # http://akizukidenshi.com/download/ds/akizuki/k6096_manual_20130816.pdf + programmer - id = "uncompatino"; - desc = "uncompatino with all pairs of pins shorted"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 3; # cts - sck = 5; # dsr - mosi = 6; # dcd - reset = 7; # ri + id = "uncompatino"; + desc = "uncompatino with all pairs of pins shorted"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 7; # ri + sck = 5; # dsr + sdo = 6; # dcd + sdi = 3; # cts ; +#------------------------------------------------------------ +# ttl232r +#------------------------------------------------------------ + # FTDI USB to serial cable TTL-232R-5V with a custom adapter for ICSP # http://www.ftdichip.com/Products/Cables/USBTTLSerial.htm # http://www.ftdichip.com/Support/Documents/DataSheets/Cables/DS_TTL-232R_CABLES.pdf # For ICSP pinout see for example http://www.atmel.com/images/doc2562.pdf # (Figure 1. ISP6PIN header pinout and Table 1. Connections required for ISP ...) # TTL-232R GND 1 Black -> ICPS GND (pin 6) -# TTL-232R CTS 2 Brown -> ICPS MOSI (pin 4) +# TTL-232R CTS 2 Brown -> ICPS SDO (pin 4) # TTL-232R VCC 3 Red -> ICPS VCC (pin 2) # TTL-232R TXD 4 Orange -> ICPS RESET (pin 5) # TTL-232R RXD 5 Yellow -> ICPS SCK (pin 3) -# TTL-232R RTS 6 Green -> ICPS MISO (pin 1) +# TTL-232R RTS 6 Green -> ICPS SDI (pin 1) # Except for VCC and GND, you can connect arbitual pairs as long as # the following table is adjusted. + programmer - id = "ttl232r"; - desc = "FTDI TTL232R-5V with ICSP adapter"; - type = "ftdi_syncbb"; - connection_type = usb; - miso = 2; # rts - sck = 1; # rxd - mosi = 3; # cts - reset = 0; # txd + id = "ttl232r"; + desc = "FTDI TTL232R-5V with ICSP adapter"; + type = "ftdi_syncbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + reset = 0; # txd + sck = 1; # rxd + sdo = 3; # cts + sdi = 2; # rts ; -programmer - id = "usbasp"; - desc = "USBasp, http://www.fischl.de/usbasp/"; - type = "usbasp"; - connection_type = usb; - usbvid = 0x16C0; # VOTI - usbpid = 0x05DC; # Obdev's free shared PID - usbvendor = "www.fischl.de"; - usbproduct = "USBasp"; +#------------------------------------------------------------ +# usbasp +#------------------------------------------------------------ +programmer + id = "usbasp"; + desc = "USBasp, http://www.fischl.de/usbasp/"; + type = "usbasp"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x16c0; # VOTI + usbpid = 0x05dc; # Obdev's free shared PID + usbvendor = "www.fischl.de"; + usbproduct = "USBasp"; # following variants are autodetected for id "usbasp" # original usbasp from fischl.de # see above "usbasp" # old usbasp from fischl.de - #usbvid = 0x03EB; # ATMEL - #usbpid = 0xC7B4; # (unoffical) USBasp - #usbvendor = "www.fischl.de"; - #usbproduct = "USBasp"; + # usbvid = 0x03EB; # ATMEL + # usbpid = 0xC7B4; # (unoffical) USBasp + # usbvendor = "www.fischl.de"; + # usbproduct = "USBasp"; # NIBObee (only if -P nibobee is given on command line) # see below "nibobee" ; +#------------------------------------------------------------ +# nibobee +#------------------------------------------------------------ + programmer - id = "nibobee"; - desc = "NIBObee"; - type = "usbasp"; - connection_type = usb; - usbvid = 0x16C0; # VOTI - usbpid = 0x092F; # NIBObee PID - usbvendor = "www.nicai-systems.com"; - usbproduct = "NIBObee"; + id = "nibobee"; + desc = "NIBObee"; + type = "usbasp"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x16c0; # VOTI + usbpid = 0x092f; # NIBObee PID + usbvendor = "www.nicai-systems.com"; + usbproduct = "NIBObee"; ; +#------------------------------------------------------------ +# usbasp-clone +#------------------------------------------------------------ + programmer - id = "usbasp-clone"; - desc = "Any usbasp clone with correct VID/PID"; - type = "usbasp"; - connection_type = usb; - usbvid = 0x16C0; # VOTI - usbpid = 0x05DC; # Obdev's free shared PID - #usbvendor = ""; - #usbproduct = ""; + id = "usbasp-clone"; + desc = "Any usbasp clone with correct VID/PID"; + type = "usbasp"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x16c0; # VOTI + usbpid = 0x05dc; # Obdev's free shared PID ; +#------------------------------------------------------------ +# usbtiny +#------------------------------------------------------------ + # USBtiny can also be used for TPI programming. -# In that case, a resistor of 1 kOhm is needed between MISO and MOSI -# pins of the connector, and MISO (pin 1 of the 6-pin connector) +# In that case, a resistor of 1 kOhm is needed between SDI and SDO +# pins of the connector, and SDI (pin 1 of the 6-pin connector) # connects to TPIDATA. + +programmer + id = "usbtiny"; + desc = "USBtiny simple USB programmer, https://learn.adafruit.com/usbtinyisp"; + type = "usbtiny"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x1781; + usbpid = 0x0c9f; +; + +#------------------------------------------------------------ +# arduino_gemma +#------------------------------------------------------------ + +# https://github.com/arduino/ArduinoCore-avr/tree/master/bootloaders/gemma + +programmer + id = "arduino_gemma"; + desc = "Arduino Gemma bootloader disguised as USBtiny"; + type = "usbtiny"; + prog_modes = PM_SPM; + connection_type = usb; + usbvid = 0x2341; + usbpid = 0x0c9f; +; + +#------------------------------------------------------------ +# adafruit_gemma +#------------------------------------------------------------ + +# https://github.com/adafruit/Adafruit-Trinket-Gemma-Bootloader + programmer - id = "usbtiny"; - desc = "USBtiny simple USB programmer, https://learn.adafruit.com/usbtinyisp"; - type = "usbtiny"; - connection_type = usb; - usbvid = 0x1781; - usbpid = 0x0c9f; + id = "adafruit_gemma"; + desc = "Adafruit Trinket Gemma bootloader disguised as USBtiny"; + type = "usbtiny"; + prog_modes = PM_SPM; + connection_type = usb; + usbvid = 0x1781; + usbpid = 0x0c9f; ; +#------------------------------------------------------------ +# arduinoisp +#------------------------------------------------------------ + programmer - id = "arduinoisp"; - desc = "Arduino ISP Programmer"; - type = "usbtiny"; - connection_type = usb; - usbvid = 0x2341; - usbpid = 0x0049; + id = "arduinoisp"; + desc = "Arduino ISP Programmer"; + type = "usbtiny"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x2341; + usbpid = 0x0049; ; +#------------------------------------------------------------ +# arduinoisporg +#------------------------------------------------------------ + programmer - id = "arduinoisporg"; - desc = "Arduino ISP Programmer"; - type = "usbtiny"; - connection_type = usb; - usbvid = 0x2A03; - usbpid = 0x0049; + id = "arduinoisporg"; + desc = "Arduino ISP Programmer"; + type = "usbtiny"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x2a03; + usbpid = 0x0049; ; +#------------------------------------------------------------ +# ehajo-isp +#------------------------------------------------------------ + # commercial version of USBtiny, using a separate VID/PID + programmer - id = "ehajo-isp"; - desc = "avr-isp-programmer from eHaJo, http://www.eHaJo.de"; - type = "usbtiny"; - connection_type = usb; - usbvid = 0x16D0; - usbpid = 0x0BA5; + id = "ehajo-isp"; + desc = "avr-isp-programmer from eHaJo, http://www.eHaJo.de"; + type = "usbtiny"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x16d0; + usbpid = 0x0ba5; ; +#------------------------------------------------------------ +# iseavrprog +#------------------------------------------------------------ + # commercial version of USBtiny, using a separate VID/PID +# https://github.com/IowaScaledEngineering/ckt-avrprogrammer + programmer - id = "iseavrprog"; - desc = "USBtiny-based USB programmer, https://github.com/IowaScaledEngineering/ckt-avrprogrammer"; - type = "usbtiny"; - connection_type = usb; - usbvid = 0x1209; - usbpid = 0x6570; + id = "iseavrprog"; + desc = "USBtiny-based programmer, https://iascaled.com"; + type = "usbtiny"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + usbvid = 0x1209; + usbpid = 0x6570; ; +#------------------------------------------------------------ +# micronucleus +#------------------------------------------------------------ + programmer - id = "micronucleus"; - desc = "Micronucleus Bootloader"; - type = "micronucleus"; - connection_type = usb; - usbvid = 0x16D0; - usbpid = 0x0753; + id = "micronucleus"; + desc = "Micronucleus for bootloader"; + type = "micronucleus"; + prog_modes = PM_SPM; + connection_type = usb; + usbvid = 0x16d0; + usbpid = 0x0753; ; +#------------------------------------------------------------ +# teensy +#------------------------------------------------------------ + programmer - id = "teensy"; - desc = "Teensy Bootloader"; - type = "teensy"; - connection_type = usb; - usbvid = 0x16C0; - usbpid = 0x0478; + id = "teensy"; + desc = "Teensy for bootloader"; + type = "teensy"; + prog_modes = PM_SPM; + connection_type = usb; + usbvid = 0x16c0; + usbpid = 0x0478; ; +#------------------------------------------------------------ +# butterfly +#------------------------------------------------------------ + programmer - id = "butterfly"; - desc = "Atmel Butterfly Development Board"; - type = "butterfly"; - connection_type = serial; + id = "butterfly"; + desc = "Atmel for bootloader (Butterfly Development Board)"; + type = "butterfly"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# avr109 +#------------------------------------------------------------ + programmer - id = "avr109"; - desc = "Atmel AppNote AVR109 Boot Loader"; - type = "butterfly"; - connection_type = serial; + id = "avr109"; + desc = "Atmel for bootloader using AppNote AVR109"; + type = "butterfly"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# avr911 +#------------------------------------------------------------ + programmer - id = "avr911"; - desc = "Atmel AppNote AVR911 AVROSP"; - type = "butterfly"; - connection_type = serial; + id = "avr911"; + desc = "Atmel for bootloader using AppNote AVR911 AVROSP"; + type = "butterfly"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# mkbutterfly +#------------------------------------------------------------ + # suggested in http://forum.mikrokopter.de/topic-post48317.html + programmer - id = "mkbutterfly"; - desc = "Mikrokopter.de Butterfly"; - type = "butterfly_mk"; - connection_type = serial; + id = "mkbutterfly"; + desc = "Mikrokopter.de Butterfly for bootloader"; + type = "butterfly_mk"; + prog_modes = PM_SPM; + connection_type = serial; ; +#------------------------------------------------------------ +# butterfly_mk +#------------------------------------------------------------ + programmer parent "mkbutterfly" - id = "butterfly_mk"; + id = "butterfly_mk"; ; +#------------------------------------------------------------ +# jtagmkI +#------------------------------------------------------------ + programmer - id = "jtagmkI"; - desc = "Atmel JTAG ICE (mkI)"; - baudrate = 115200; # default is 115200 - type = "jtagmki"; - connection_type = serial; + id = "jtagmkI"; + desc = "Atmel JTAG ICE (mkI)"; + type = "jtagmki"; + prog_modes = PM_JTAGmkI; + connection_type = serial; + baudrate = 115200; # default is 115200 ; +#------------------------------------------------------------ +# jtag1 +#------------------------------------------------------------ + # easier to type + programmer parent "jtagmkI" - id = "jtag1"; + id = "jtag1"; ; -# easier to type +#------------------------------------------------------------ +# jtag1slow +#------------------------------------------------------------ + +# easier to type + programmer parent "jtag1" - id = "jtag1slow"; - baudrate = 19200; + id = "jtag1slow"; + baudrate = 19200; ; +#------------------------------------------------------------ +# jtagmkII +#------------------------------------------------------------ + # The JTAG ICE mkII has both, serial and USB connectivity. As it is # mostly used through USB these days (AVR Studio 5 only supporting it # that way), we make connection_type = usb the default. Users are # still free to use a serial port with the -P option. programmer - id = "jtagmkII"; - desc = "Atmel JTAG ICE mkII"; - baudrate = 19200; # default is 19200 - type = "jtagmkii"; - connection_type = usb; + id = "jtagmkII"; + desc = "Atmel JTAG ICE mkII"; + type = "jtagmkii"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + baudrate = 19200; # default is 19200 ; +#------------------------------------------------------------ +# jtag2slow +#------------------------------------------------------------ + # easier to type + programmer parent "jtagmkII" - id = "jtag2slow"; + id = "jtag2slow"; ; +#------------------------------------------------------------ +# jtag2fast +#------------------------------------------------------------ + # JTAG ICE mkII @ 115200 Bd + programmer parent "jtag2slow" - id = "jtag2fast"; - baudrate = 115200; + id = "jtag2fast"; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtag2 +#------------------------------------------------------------ + # make the fast one the default, people will love that + programmer parent "jtag2fast" - id = "jtag2"; + id = "jtag2"; ; +#------------------------------------------------------------ +# jtag2isp +#------------------------------------------------------------ + # JTAG ICE mkII in ISP mode + programmer - id = "jtag2isp"; - desc = "Atmel JTAG ICE mkII in ISP mode"; - baudrate = 115200; - type = "jtagmkii_isp"; - connection_type = usb; + id = "jtag2isp"; + desc = "Atmel JTAG ICE mkII in ISP mode"; + type = "jtagmkii_isp"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtag2dw +#------------------------------------------------------------ + # JTAG ICE mkII in debugWire mode + programmer - id = "jtag2dw"; - desc = "Atmel JTAG ICE mkII in debugWire mode"; - baudrate = 115200; - type = "jtagmkii_dw"; - connection_type = usb; + id = "jtag2dw"; + desc = "Atmel JTAG ICE mkII in debugWire mode"; + type = "jtagmkii_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtagmkII_avr32 +#------------------------------------------------------------ + # JTAG ICE mkII in AVR32 mode + programmer - id = "jtagmkII_avr32"; - desc = "Atmel JTAG ICE mkII im AVR32 mode"; - baudrate = 115200; - type = "jtagmkii_avr32"; - connection_type = usb; + id = "jtagmkII_avr32"; + desc = "Atmel JTAG ICE mkII in AVR32 mode"; + type = "jtagmkii_avr32"; + prog_modes = PM_aWire; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtag2avr32 +#------------------------------------------------------------ + # JTAG ICE mkII in AVR32 mode + programmer - id = "jtag2avr32"; - desc = "Atmel JTAG ICE mkII im AVR32 mode"; - baudrate = 115200; - type = "jtagmkii_avr32"; - connection_type = usb; + id = "jtag2avr32"; + desc = "Atmel JTAG ICE mkII in AVR32 mode"; + type = "jtagmkii_avr32"; + prog_modes = PM_aWire; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtag2pdi +#------------------------------------------------------------ + # JTAG ICE mkII in PDI mode + programmer - id = "jtag2pdi"; - desc = "Atmel JTAG ICE mkII PDI mode"; - baudrate = 115200; - type = "jtagmkii_pdi"; - connection_type = usb; + id = "jtag2pdi"; + desc = "Atmel JTAG ICE mkII in PDI mode"; + type = "jtagmkii_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_jtag +#------------------------------------------------------------ + # AVR Dragon in JTAG mode + programmer - id = "dragon_jtag"; - desc = "Atmel AVR Dragon in JTAG mode"; - baudrate = 115200; - type = "dragon_jtag"; - connection_type = usb; + id = "dragon_jtag"; + desc = "Atmel AVR Dragon in JTAG mode"; + type = "dragon_jtag"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_isp +#------------------------------------------------------------ + # AVR Dragon in ISP mode + programmer - id = "dragon_isp"; - desc = "Atmel AVR Dragon in ISP mode"; - baudrate = 115200; - type = "dragon_isp"; - connection_type = usb; + id = "dragon_isp"; + desc = "Atmel AVR Dragon in ISP mode"; + type = "dragon_isp"; + prog_modes = PM_TPI | PM_ISP; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_pp +#------------------------------------------------------------ + # AVR Dragon in PP mode + programmer - id = "dragon_pp"; - desc = "Atmel AVR Dragon in PP mode"; - baudrate = 115200; - type = "dragon_pp"; - connection_type = usb; + id = "dragon_pp"; + desc = "Atmel AVR Dragon in PP mode"; + type = "dragon_pp"; + prog_modes = PM_HVPP; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_hvsp +#------------------------------------------------------------ + # AVR Dragon in HVSP mode + programmer - id = "dragon_hvsp"; - desc = "Atmel AVR Dragon in HVSP mode"; - baudrate = 115200; - type = "dragon_hvsp"; - connection_type = usb; + id = "dragon_hvsp"; + desc = "Atmel AVR Dragon in HVSP mode"; + type = "dragon_hvsp"; + prog_modes = PM_HVSP; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_dw +#------------------------------------------------------------ + # AVR Dragon in debugWire mode + programmer - id = "dragon_dw"; - desc = "Atmel AVR Dragon in debugWire mode"; - baudrate = 115200; - type = "dragon_dw"; - connection_type = usb; + id = "dragon_dw"; + desc = "Atmel AVR Dragon in debugWire mode"; + type = "dragon_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# dragon_pdi +#------------------------------------------------------------ + # AVR Dragon in PDI mode + programmer - id = "dragon_pdi"; - desc = "Atmel AVR Dragon in PDI mode"; - baudrate = 115200; - type = "dragon_pdi"; - connection_type = usb; + id = "dragon_pdi"; + desc = "Atmel AVR Dragon in PDI mode"; + type = "dragon_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + baudrate = 115200; ; +#------------------------------------------------------------ +# jtag3 +#------------------------------------------------------------ + +programmer + id = "jtag3"; + desc = "Atmel AVR JTAGICE3 in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + usbpid = 0x2110, 0x2140; +; + +#------------------------------------------------------------ +# jtag3pdi +#------------------------------------------------------------ + +programmer + id = "jtag3pdi"; + desc = "Atmel AVR JTAGICE3 in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2110, 0x2140; +; + +#------------------------------------------------------------ +# jtag3updi +#------------------------------------------------------------ + +programmer + id = "jtag3updi"; + desc = "Atmel AVR JTAGICE3 in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2110, 0x2140; + hvupdi_support = 1; +; + +#------------------------------------------------------------ +# jtag3dw +#------------------------------------------------------------ + +programmer + id = "jtag3dw"; + desc = "Atmel AVR JTAGICE3 in debugWIRE mode"; + type = "jtagice3_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + usbpid = 0x2110, 0x2140; +; + +#------------------------------------------------------------ +# jtag3isp +#------------------------------------------------------------ + +programmer + id = "jtag3isp"; + desc = "Atmel AVR JTAGICE3 in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2110, 0x2140; +; + +#------------------------------------------------------------ +# xplainedpro +#------------------------------------------------------------ + programmer - id = "jtag3"; - desc = "Atmel AVR JTAGICE3 in JTAG mode"; - type = "jtagice3"; - connection_type = usb; - usbpid = 0x2110, 0x2140; + id = "xplainedpro"; + desc = "Atmel AVR XplainedPro in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + usbpid = 0x2111; ; +#------------------------------------------------------------ +# xplainedpro_pdi +#------------------------------------------------------------ + programmer - id = "jtag3pdi"; - desc = "Atmel AVR JTAGICE3 in PDI mode"; - type = "jtagice3_pdi"; - connection_type = usb; - usbpid = 0x2110, 0x2140; + id = "xplainedpro_pdi"; + desc = "Atmel AVR XplainedPro in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2111; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# xplainedpro_updi +#------------------------------------------------------------ + programmer - id = "jtag3updi"; - desc = "Atmel AVR JTAGICE3 in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2110, 0x2140; + id = "xplainedpro_updi"; + desc = "Atmel AVR XplainedPro in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2111; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# xplainedmini +#------------------------------------------------------------ + programmer - id = "jtag3dw"; - desc = "Atmel AVR JTAGICE3 in debugWIRE mode"; - type = "jtagice3_dw"; - connection_type = usb; - usbpid = 0x2110, 0x2140; + id = "xplainedmini"; + desc = "Atmel AVR XplainedMini in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2145; ; +#------------------------------------------------------------ +# xplainedmini_dw +#------------------------------------------------------------ + programmer - id = "jtag3isp"; - desc = "Atmel AVR JTAGICE3 in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x2110, 0x2140; + id = "xplainedmini_dw"; + desc = "Atmel AVR XplainedMini in debugWIRE mode"; + type = "jtagice3_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + usbpid = 0x2145; ; +#------------------------------------------------------------ +# xplainedmini_updi +#------------------------------------------------------------ + programmer - id = "xplainedpro"; - desc = "Atmel AVR XplainedPro in JTAG mode"; - type = "jtagice3"; - connection_type = usb; - usbpid = 0x2111; + id = "xplainedmini_updi"; + desc = "Atmel AVR XplainedMini in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2145; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# xplainedmini_tpi +#------------------------------------------------------------ + programmer - id = "xplainedpro_updi"; - desc = "Atmel AVR XplainedPro in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2111; + id = "xplainedmini_tpi"; + desc = "Atmel AVR XplainedMini in TPI mode"; + type = "jtagice3_tpi"; + prog_modes = PM_TPI; + connection_type = usb; + usbpid = 0x2145; ; +#------------------------------------------------------------ +# atmelice +#------------------------------------------------------------ + programmer - id = "xplainedmini"; - desc = "Atmel AVR XplainedMini in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x2145; + id = "atmelice"; + desc = "Atmel-ICE (ARM/AVR) in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + usbpid = 0x2141; ; +#------------------------------------------------------------ +# atmelice_pdi +#------------------------------------------------------------ + programmer - id = "xplainedmini_dw"; - desc = "Atmel AVR XplainedMini in debugWIRE mode"; - type = "jtagice3_dw"; - connection_type = usb; - usbpid = 0x2145; + id = "atmelice_pdi"; + desc = "Atmel-ICE (ARM/AVR) in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2141; ; +#------------------------------------------------------------ +# atmelice_updi +#------------------------------------------------------------ + programmer - id = "xplainedmini_updi"; - desc = "Atmel AVR XplainedMini in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2145; + id = "atmelice_updi"; + desc = "Atmel-ICE (ARM/AVR) in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2141; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# atmelice_dw +#------------------------------------------------------------ + programmer - id = "atmelice"; - desc = "Atmel-ICE (ARM/AVR) in JTAG mode"; - type = "jtagice3"; - connection_type = usb; - usbpid = 0x2141; + id = "atmelice_dw"; + desc = "Atmel-ICE (ARM/AVR) in debugWIRE mode"; + type = "jtagice3_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + usbpid = 0x2141; ; +#------------------------------------------------------------ +# atmelice_isp +#------------------------------------------------------------ + programmer - id = "atmelice_pdi"; - desc = "Atmel-ICE (ARM/AVR) in PDI mode"; - type = "jtagice3_pdi"; - connection_type = usb; - usbpid = 0x2141; + id = "atmelice_isp"; + desc = "Atmel-ICE (ARM/AVR) in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2141; ; +#------------------------------------------------------------ +# atmelice_tpi +#------------------------------------------------------------ + programmer - id = "atmelice_updi"; - desc = "Atmel-ICE (ARM/AVR) in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2141; + id = "atmelice_tpi"; + desc = "Atmel-ICE (ARM/AVR) in TPI mode"; + type = "jtagice3_tpi"; + prog_modes = PM_TPI; + connection_type = usb; + usbpid = 0x2141; ; +#------------------------------------------------------------ +# powerdebugger +#------------------------------------------------------------ + programmer - id = "atmelice_dw"; - desc = "Atmel-ICE (ARM/AVR) in debugWIRE mode"; - type = "jtagice3_dw"; - connection_type = usb; - usbpid = 0x2141; + id = "powerdebugger"; + desc = "Atmel PowerDebugger (ARM/AVR) in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; + connection_type = usb; + usbpid = 0x2144; ; +#------------------------------------------------------------ +# powerdebugger_pdi +#------------------------------------------------------------ + programmer - id = "atmelice_isp"; - desc = "Atmel-ICE (ARM/AVR) in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x2141; + id = "powerdebugger_pdi"; + desc = "Atmel PowerDebugger (ARM/AVR) in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2144; ; +#------------------------------------------------------------ +# powerdebugger_updi +#------------------------------------------------------------ + programmer - id = "powerdebugger"; - desc = "Atmel PowerDebugger (ARM/AVR) in JTAG mode"; - type = "jtagice3"; - connection_type = usb; - usbpid = 0x2144; + id = "powerdebugger_updi"; + desc = "Atmel PowerDebugger (ARM/AVR) in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2144; + hvupdi_support = 0, 1; ; +#------------------------------------------------------------ +# powerdebugger_dw +#------------------------------------------------------------ + programmer - id = "powerdebugger_pdi"; - desc = "Atmel PowerDebugger (ARM/AVR) in PDI mode"; - type = "jtagice3_pdi"; - connection_type = usb; - usbpid = 0x2144; + id = "powerdebugger_dw"; + desc = "Atmel PowerDebugger (ARM/AVR) in debugWire mode"; + type = "jtagice3_dw"; + prog_modes = PM_debugWIRE; + connection_type = usb; + usbpid = 0x2144; ; +#------------------------------------------------------------ +# powerdebugger_isp +#------------------------------------------------------------ + programmer - id = "powerdebugger_updi"; - desc = "Atmel PowerDebugger (ARM/AVR) in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2144; + id = "powerdebugger_isp"; + desc = "Atmel PowerDebugger (ARM/AVR) in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2144; ; +#------------------------------------------------------------ +# powerdebugger_tpi +#------------------------------------------------------------ + programmer - id = "powerdebugger_dw"; - desc = "Atmel PowerDebugger (ARM/AVR) in debugWire mode"; - type = "jtagice3_dw"; - connection_type = usb; - usbpid = 0x2144; + id = "powerdebugger_tpi"; + desc = "Atmel PowerDebugger (ARM/AVR) in TPI mode"; + type = "jtagice3_tpi"; + prog_modes = PM_TPI; + connection_type = usb; + usbpid = 0x2144; ; +#------------------------------------------------------------ +# pickit4 +#------------------------------------------------------------ + programmer - id = "powerdebugger_isp"; - desc = "Atmel PowerDebugger (ARM/AVR) in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x2144; + id = "pickit4"; + desc = "MPLAB(R) PICkit 4 in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; ; +#------------------------------------------------------------ +# pickit4_updi +#------------------------------------------------------------ + programmer - id = "pickit4_updi"; - desc = "MPLAB(R) PICkit 4 in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; + id = "pickit4_updi"; + desc = "MPLAB(R) PICkit 4 in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; + hvupdi_support = 0, 1, 2; ; +#------------------------------------------------------------ +# pickit4_pdi +#------------------------------------------------------------ + programmer - id = "pickit4_pdi"; - desc = "MPLAB(R) PICkit 4 in PDI mode"; - type = "jtagice3_pdi"; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; + id = "pickit4_pdi"; + desc = "MPLAB(R) PICkit 4 in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; ; +#------------------------------------------------------------ +# pickit4_isp +#------------------------------------------------------------ + programmer - id = "pickit4_isp"; - desc = "MPLAB(R) PICkit 4 in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179, 0x9018; + id = "pickit4_isp"; + desc = "MPLAB(R) PICkit 4 in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; ; +#------------------------------------------------------------ +# pickit4_tpi +#------------------------------------------------------------ + programmer - id = "snap_updi"; - desc = "MPLAB(R) SNAP in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x217F, 0x2180, 0x2181; + id = "pickit4_tpi"; + desc = "MPLAB(R) PICkit 4 in TPI mode"; + type = "jtagice3_tpi"; + prog_modes = PM_TPI; + connection_type = usb; + usbpid = 0x2177, 0x2178, 0x2179; ; +#------------------------------------------------------------ +# snap +#------------------------------------------------------------ + programmer - id = "snap_pdi"; - desc = "MPLAB(R) SNAP in PDI mode"; - type = "jtagice3_pdi"; - connection_type = usb; - usbpid = 0x217F, 0x2180, 0x2181; + id = "snap"; + desc = "MPLAB(R) Snap in JTAG mode"; + type = "jtagice3"; + prog_modes = PM_JTAG | PM_XMEGAJTAG; + connection_type = usb; + usbpid = 0x2180, 0x217f, 0x2181; ; +#------------------------------------------------------------ +# snap_updi +#------------------------------------------------------------ + programmer - id = "snap_isp"; - desc = "MPLAB(R) SNAP in ISP mode"; - type = "jtagice3_isp"; - connection_type = usb; - usbpid = 0x217F, 0x2180, 0x2181; + id = "snap_updi"; + desc = "MPLAB(R) SNAP in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2180, 0x217f, 0x2181; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# snap_pdi +#------------------------------------------------------------ + programmer - id = "pkobn_updi"; - desc = "Curiosity nano (nEDBG) in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2175; + id = "snap_pdi"; + desc = "MPLAB(R) SNAP in PDI mode"; + type = "jtagice3_pdi"; + prog_modes = PM_PDI; + connection_type = usb; + usbpid = 0x2180, 0x217f, 0x2181; ; +#------------------------------------------------------------ +# snap_isp +#------------------------------------------------------------ + programmer - id = "curiosity_updi"; - desc = "Curiosity in UPDI mode"; - type = "jtagice3_updi"; - connection_type = usb; - usbpid = 0x2175; + id = "snap_isp"; + desc = "MPLAB(R) SNAP in ISP mode"; + type = "jtagice3_isp"; + prog_modes = PM_ISP; + connection_type = usb; + usbpid = 0x2180, 0x217f, 0x2181; ; +#------------------------------------------------------------ +# snap_tpi +#------------------------------------------------------------ + programmer - id = "pavr"; - desc = "Jason Kyle's pAVR Serial Programmer"; - type = "avr910"; - connection_type = serial; + id = "snap_tpi"; + desc = "MPLAB(R) SNAP in TPI mode"; + type = "jtagice3_tpi"; + prog_modes = PM_TPI; + connection_type = usb; + usbpid = 0x2180, 0x217f, 0x2181; ; +#------------------------------------------------------------ +# pkobn_updi +#------------------------------------------------------------ + programmer - id = "pickit2"; - desc = "MicroChip's PICkit2 Programmer"; - type = "pickit2"; - connection_type = usb; + id = "pkobn_updi"; + desc = "Curiosity nano (nEDBG) in UPDI mode"; + type = "jtagice3_updi"; + prog_modes = PM_UPDI; + connection_type = usb; + usbpid = 0x2175; + hvupdi_support = 1; ; +#------------------------------------------------------------ +# pavr +#------------------------------------------------------------ + programmer - id = "flip1"; - desc = "FLIP USB DFU protocol version 1 (doc7618)"; - type = "flip1"; - connection_type = usb; + id = "pavr"; + desc = "Jason Kyle's pAVR Serial Programmer"; + type = "avr910"; + prog_modes = PM_ISP; + connection_type = serial; ; +#------------------------------------------------------------ +# pickit2 +#------------------------------------------------------------ + programmer - id = "flip2"; - desc = "FLIP USB DFU protocol version 2 (AVR4023)"; - type = "flip2"; - connection_type = usb; + id = "pickit2"; + desc = "MicroChip's PICkit2 Programmer"; + type = "pickit2"; + prog_modes = PM_ISP; + connection_type = usb; ; +#------------------------------------------------------------ +# flip1 +#------------------------------------------------------------ + +programmer + id = "flip1"; + desc = "FLIP for bootloader using USB DFU protocol version 1 (doc7618)"; + type = "flip1"; + prog_modes = PM_SPM; + connection_type = usb; +; +#------------------------------------------------------------ +# flip2 +#------------------------------------------------------------ +programmer + id = "flip2"; + desc = "FLIP for bootloader using USB DFU protocol version 2 (AVR4023)"; + type = "flip2"; + prog_modes = PM_SPM; + connection_type = usb; +; +#------------------------------------------------------------ +# ponyser +#------------------------------------------------------------ -# some ultra cheap programmers use bitbanging on the -# serialport. +# some ultra cheap programmers use bitbanging on the serialport # # PC - DB9 - Pins for RS232: # @@ -1397,78 +2204,104 @@ programmer # Using RI is not supported under Win32 but is supported under Posix. # serial ponyprog design (dasa2 in uisp) -# reset=!txd sck=rts mosi=dtr miso=cts +# reset=!txd sck=rts sdo=dtr sdi=cts programmer - id = "ponyser"; - desc = "design ponyprog serial, reset=!txd sck=rts mosi=dtr miso=cts"; - type = "serbb"; - connection_type = serial; - reset = ~3; - sck = 7; - mosi = 4; - miso = 8; + id = "ponyser"; + desc = "design ponyprog serial, reset=!txd sck=rts sdo=dtr sdi=cts"; + type = "serbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; + reset = ~3; + sck = 7; + sdo = 4; + sdi = 8; ; +#------------------------------------------------------------ +# siprog +#------------------------------------------------------------ + # Same as above, different name -# reset=!txd sck=rts mosi=dtr miso=cts +# reset=!txd sck=rts sdo=dtr sdi=cts programmer parent "ponyser" - id = "siprog"; - desc = "Lancos SI-Prog "; + id = "siprog"; + desc = "Lancos SI-Prog "; ; +#------------------------------------------------------------ +# dasa +#------------------------------------------------------------ + # unknown (dasa in uisp) -# reset=rts sck=dtr mosi=txd miso=cts +# reset=rts sck=dtr sdo=txd sdi=cts programmer - id = "dasa"; - desc = "serial port banging, reset=rts sck=dtr mosi=txd miso=cts"; - type = "serbb"; - connection_type = serial; - reset = 7; - sck = 4; - mosi = 3; - miso = 8; + id = "dasa"; + desc = "serial port banging, reset=rts sck=dtr sdo=txd sdi=cts"; + type = "serbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; + reset = 7; + sck = 4; + sdo = 3; + sdi = 8; ; +#------------------------------------------------------------ +# dasa3 +#------------------------------------------------------------ + # unknown (dasa3 in uisp) -# reset=!dtr sck=rts mosi=txd miso=cts +# reset=!dtr sck=rts sdo=txd sdi=cts programmer - id = "dasa3"; - desc = "serial port banging, reset=!dtr sck=rts mosi=txd miso=cts"; - type = "serbb"; - connection_type = serial; - reset = ~4; - sck = 7; - mosi = 3; - miso = 8; + id = "dasa3"; + desc = "serial port banging, reset=!dtr sck=rts sdo=txd sdi=cts"; + type = "serbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; + reset = ~4; + sck = 7; + sdo = 3; + sdi = 8; ; +#------------------------------------------------------------ +# C2N232i +#------------------------------------------------------------ + # C2N232i (jumper configuration "auto") -# reset=dtr sck=!rts mosi=!txd miso=!cts +# reset=dtr sck=!rts sdo=!txd sdi=!cts programmer - id = "c2n232i"; - desc = "serial port banging, reset=dtr sck=!rts mosi=!txd miso=!cts"; - type = "serbb"; - connection_type = serial; - reset = 4; - sck = ~7; - mosi = ~3; - miso = ~8; + id = "c2n232i"; + desc = "serial port banging, reset=dtr sck=!rts sdo=!txd sdi=!cts"; + type = "serbb"; + prog_modes = PM_TPI | PM_ISP; + connection_type = serial; + reset = 4; + sck = ~7; + sdo = ~3; + sdi = ~8; ; +#------------------------------------------------------------ +# jtag2updi +#------------------------------------------------------------ + # JTAG2UPDI # https://github.com/ElTangas/jtag2updi programmer - id = "jtag2updi"; - desc = "JTAGv2 to UPDI bridge"; - type = "jtagmkii_pdi"; - connection_type = serial; - baudrate = 115200; + id = "jtag2updi"; + desc = "JTAGv2 to UPDI bridge"; + type = "jtagmkii_updi"; + prog_modes = PM_UPDI; + connection_type = serial; + baudrate = 115200; + hvupdi_support = 1; ; # @@ -1482,62 +2315,61 @@ programmer # This is an HVSP-only device. part - id = "t11"; - desc = "ATtiny11"; - stk500_devcode = 0x11; - signature = 0x1e 0x90 0x04; - chip_erase_delay = 20000; - - timeout = 200; - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x00, + desc = "ATtiny11"; + id = "t11"; + prog_modes = PM_HVSP; + mcuid = 8; + n_interrupts = 5; + stk500_devcode = 0x11; + chip_erase_delay = 20000; + signature = 0x1e 0x90 0x04; + serial = no; + timeout = 200; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 50; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; memory "eeprom" - size = 64; - blocksize = 64; - readsize = 256; - delay = 5; + size = 64; + delay = 5; + blocksize = 64; + readsize = 256; ; memory "flash" - size = 1024; - blocksize = 128; - readsize = 256; - delay = 3; + size = 1024; + delay = 3; + blocksize = 128; + readsize = 256; ; - memory "signature" - size = 3; + memory "fuse" + size = 1; ; memory "lock" - size = 1; + size = 1; ; - memory "calibration" - size = 1; + memory "signature" + size = 3; ; - memory "fuse" - size = 1; + memory "calibration" + size = 1; ; ; @@ -1546,131 +2378,94 @@ part #------------------------------------------------------------ part - id = "t12"; - desc = "ATtiny12"; - stk500_devcode = 0x12; - avr910_devcode = 0x55; - signature = 0x1e 0x90 0x05; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x00, + desc = "ATtiny12"; + id = "t12"; + prog_modes = PM_ISP | PM_HVSP; + mcuid = 9; + n_interrupts = 6; + stk500_devcode = 0x12; + avr910_devcode = 0x55; + chip_erase_delay = 20000; + signature = 0x1e 0x90 0x05; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 50; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; - - memory "eeprom" - size = 64; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 8; - blocksize = 64; - readsize = 256; - ; - - memory "flash" - size = 1024; - min_write_delay = 4500; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 5; - blocksize = 128; - readsize = 256; + synchcycles = 6; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 64; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 8; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + ; + + memory "flash" + size = 1024; + min_write_delay = 4500; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 5; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "fuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--101x.xxxx--xxxx.xxxx--iiii.iiii"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; ; - memory "fuse" - size = 1; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 x x x x x", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; + memory "calibration" + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -1679,172 +2474,118 @@ part #------------------------------------------------------------ part - id = "t13"; - desc = "ATtiny13"; - has_debugwire = yes; - flash_instr = 0xB4, 0x0E, 0x1E; - eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x0E, 0xB4, 0x0E, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x14; - signature = 0x1e 0x90 0x07; - chip_erase_delay = 4000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 90; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - - ocdrev = 0; - - memory "eeprom" - size = 64; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x x a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x x a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 1024; - page_size = 32; - num_pages = 32; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 0 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 0 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 0 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; + desc = "ATtiny13"; + id = "t13"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 10; + n_interrupts = 10; + stk500_devcode = 0x14; + chip_erase_delay = 4000; + signature = 0x1e 0x90 0x07; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; + flash_instr = 0xb4, 0x0e, 0x1e; + eeprom_instr = + 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x0e, 0xb4, 0x0e, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 90; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; + programfusepolltimeout = 25; + programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 0; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 64; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4000; + readback = 0xff 0xff; + mode = 65; + delay = 5; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--xxaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xxaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 1024; + page_size = 32; + num_pages = 32; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.000a--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.000a--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.000a--aaaa.xxxx--xxxx.xxxx"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + memory "lock" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; ; memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; + size = 2; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - ; ; #------------------------------------------------------------ @@ -1852,140 +2593,105 @@ part #------------------------------------------------------------ part parent "t13" - id = "t13a"; - desc = "ATtiny13A"; - ; + desc = "ATtiny13A"; + id = "t13a"; + mcuid = 11; +; #------------------------------------------------------------ # ATtiny15 #------------------------------------------------------------ part - id = "t15"; - desc = "ATtiny15"; - stk500_devcode = 0x13; - avr910_devcode = 0x56; - signature = 0x1e 0x90 0x06; - chip_erase_delay = 8200; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x00, + desc = "ATtiny15"; + id = "t15"; + prog_modes = PM_ISP | PM_HVSP; + mcuid = 12; + n_interrupts = 9; + stk500_devcode = 0x13; + avr910_devcode = 0x56; + chip_erase_delay = 8200; + signature = 0x1e 0x90 0x06; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 5; - synchcycles = 6; - latchcycles = 16; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + hventerstabdelay = 100; + latchcycles = 16; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 50; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; - - memory "eeprom" - size = 64; - min_write_delay = 8200; - max_write_delay = 8200; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 10; - blocksize = 64; - readsize = 256; - ; - - memory "flash" - size = 1024; - min_write_delay = 4100; - max_write_delay = 4100; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 5; - blocksize = 128; - readsize = 256; + synchcycles = 6; + hvspcmdexedelay = 5; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 64; + min_write_delay = 8200; + max_write_delay = 8200; + readback = 0xff 0xff; + mode = 4; + delay = 10; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + ; + + memory "flash" + size = 1024; + min_write_delay = 4100; + max_write_delay = 4100; + readback = 0xff 0xff; + mode = 4; + delay = 5; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "fuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--oooo.xxoo"; + write = "1010.1100--101x.xxxx--xxxx.xxxx--iiii.11ii"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; ; - memory "fuse" - size = 1; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x o o o o x x o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 x x x x x", - "x x x x x x x x i i i i 1 1 i i"; - min_write_delay = 9000; - max_write_delay = 9000; + memory "calibration" + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -1994,5024 +2700,3514 @@ part #------------------------------------------------------------ part - id = "1200"; - desc = "AT90S1200"; - is_at90s1200 = yes; - stk500_devcode = 0x33; - avr910_devcode = 0x13; - signature = 0x1e 0x90 0x01; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 1; - bytedelay = 0; - pollindex = 0; - pollvalue = 0xFF; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S1200"; + id = "1200"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 183; + n_interrupts = 4; + stk500_devcode = 0x33; + avr910_devcode = 0x13; + chip_erase_delay = 20000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x90 0x01; + is_at90s1200 = yes; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 1; + pollvalue = 0xff; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 64; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x x a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 20; - blocksize = 32; - readsize = 256; - ; + size = 64; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x00 0xff; + mode = 4; + delay = 20; + blocksize = 32; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + ; + memory "flash" - size = 1024; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x02; - delay = 15; - blocksize = 128; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 1024; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 2; + delay = 15; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + memory "fuse" - size = 1; - ; + size = 1; + ; + memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - ; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; + + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s4414 #------------------------------------------------------------ part - id = "4414"; - desc = "AT90S4414"; - stk500_devcode = 0x50; - avr910_devcode = 0x28; - signature = 0x1e 0x92 0x01; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S4414"; + id = "4414"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 190; + n_interrupts = 13; + stk500_devcode = 0x50; + avr910_devcode = 0x28; + chip_erase_delay = 20000; + signature = 0x1e 0x92 0x01; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x80; - readback_p2 = 0x7f; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; + size = 256; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x80 0x7f; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x7f; - readback_p2 = 0x7f; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 4096; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x7f 0x7f; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; + memory "fuse" - size = 1; - ; + size = 1; + ; + memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; + + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s2313 #------------------------------------------------------------ part - id = "2313"; - desc = "AT90S2313"; - stk500_devcode = 0x40; - avr910_devcode = 0x20; - signature = 0x1e 0x91 0x01; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S2313"; + id = "2313"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 186; + n_interrupts = 11; + stk500_devcode = 0x40; + avr910_devcode = 0x20; + chip_erase_delay = 20000; + signature = 0x1e 0x91 0x01; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 128; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x80; - readback_p2 = 0x7f; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; + size = 128; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x80 0x7f; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + ; + memory "flash" - size = 2048; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x7f; - readback_p2 = 0x7f; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 2048; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x7f 0x7f; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + ; + memory "fuse" - size = 1; - ; + size = 1; + ; + memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x i i x", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + write = "1010.1100--111x.xiix--xxxx.xxxx--xxxx.xxxx"; + ; + + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s2333 #------------------------------------------------------------ part - id = "2333"; ##### WARNING: No XML file for device 'AT90S2333'! ##### - desc = "AT90S2333"; - stk500_devcode = 0x42; - avr910_devcode = 0x34; - signature = 0x1e 0x91 0x05; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S2333"; + id = "2333"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 188; + n_interrupts = 14; + stk500_devcode = 0x42; + avr910_devcode = 0x34; + chip_erase_delay = 20000; + signature = 0x1e 0x91 0x05; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; + size = 128; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x00 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + ; memory "flash" - size = 2048; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; + size = 2048; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; pwroff_after_write = yes; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x x x o o o o o o"; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; + write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 i i i i i", - "x x x x x x x x x x x x x x x x"; - ; memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - ; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s2343 (also AT90s2323 and ATtiny22) #------------------------------------------------------------ part - id = "2343"; - desc = "AT90S2343"; - stk500_devcode = 0x43; - avr910_devcode = 0x4c; - signature = 0x1e 0x91 0x03; - chip_erase_delay = 18000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x00, + desc = "AT90S2343"; + id = "2343"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP; + mcuid = 189; + n_interrupts = 3; + stk500_devcode = 0x43; + avr910_devcode = 0x4c; + chip_erase_delay = 18000; + signature = 0x1e 0x91 0x03; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 0; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + hventerstabdelay = 100; + latchcycles = 1; + poweroffdelay = 25; + resetdelayus = 50; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x00 0xff; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read = "1010.0000--0000.0000--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.0000--xaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + size = 2048; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 128; + read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + ; - memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; - memory "flash" - size = 2048; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 128; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x o o o x x x x o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 1 1 1 1 i", - "x x x x x x x x x x x x x x x x"; - ; - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x o o o x x x x o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooox.xxxo"; + write = "1010.1100--1011.111i--xxxx.xxxx--xxxx.xxxx"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - ; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooox.xxxo"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s4433 #------------------------------------------------------------ part - id = "4433"; - desc = "AT90S4433"; - stk500_devcode = 0x51; - avr910_devcode = 0x30; - signature = 0x1e 0x92 0x03; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S4433"; + id = "4433"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 191; + n_interrupts = 14; + stk500_devcode = 0x51; + avr910_devcode = 0x30; + chip_erase_delay = 20000; + signature = 0x1e 0x92 0x03; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; + size = 256; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x00 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; + ; + memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 4096; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + ; + memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; pwroff_after_write = yes; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x x x o o o o o o"; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; + write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 i i i i i", - "x x x x x x x x x x x x x x x x"; - ; memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s4434 #------------------------------------------------------------ part - id = "4434"; ##### WARNING: No XML file for device 'AT90S4434'! ##### - desc = "AT90S4434"; - stk500_devcode = 0x52; - avr910_devcode = 0x6c; - signature = 0x1e 0x92 0x02; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; + desc = "AT90S4434"; + id = "4434"; + prog_modes = PM_SPM | PM_ISP; + mcuid = 192; + n_interrupts = 17; + stk500_devcode = 0x52; + avr910_devcode = 0x6c; + chip_erase_delay = 20000; + signature = 0x1e 0x92 0x02; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x00 0xff; + read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + size = 4096; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + ; - memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - ; - memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x x x o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 i i i i i", - "x x x x x x x x x x x x x x x x"; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; + write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; + ; + memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; + size = 1; + min_write_delay = 9000; + max_write_delay = 20000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90s8515 #------------------------------------------------------------ part - id = "8515"; - desc = "AT90S8515"; - stk500_devcode = 0x60; - avr910_devcode = 0x38; - signature = 0x1e 0x93 0x01; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; + desc = "AT90S8515"; + id = "8515"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 193; + n_interrupts = 13; + stk500_devcode = 0x60; + avr910_devcode = 0x38; + chip_erase_delay = 20000; + signature = 0x1e 0x93 0x01; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; programlockpolltimeout = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 512; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x80; - readback_p2 = 0x7f; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; + size = 512; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x80 0x7f; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + memory "flash" - size = 8192; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x7f; - readback_p2 = 0x7f; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "fuse" - size = 1; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - ; + size = 8192; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x7f 0x7f; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; -#------------------------------------------------------------ -# AT90s8535 -#------------------------------------------------------------ + memory "fuse" + size = 1; + ; -part - id = "8535"; - desc = "AT90S8535"; - stk500_devcode = 0x61; - avr910_devcode = 0x68; - signature = 0x1e 0x93 0x03; - chip_erase_delay = 20000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; - programlockpolltimeout = 1; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0x00; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; - memory "flash" - size = 8192; - min_write_delay = 9000; - max_write_delay = 20000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write_lo = " 0 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - write_hi = " 0 1 0 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 128; - readsize = 256; - ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "fuse" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x x x o"; - write = "1 0 1 0 1 1 0 0 1 0 1 1 1 1 1 i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x o o x x x x x x"; - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ -# ATmega103 +# AT90s8535 #------------------------------------------------------------ part - id = "m103"; - desc = "ATmega103"; - stk500_devcode = 0xB1; - avr910_devcode = 0x41; - signature = 0x1e 0x97 0x01; - chip_erase_delay = 112000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x8E, 0x9E, 0x2E, 0x3E, 0xAE, 0xBE, - 0x4E, 0x5E, 0xCE, 0xDE, 0x6E, 0x7E, 0xEE, 0xDE, - 0x66, 0x76, 0xE6, 0xF6, 0x6A, 0x7A, 0xEA, 0x7A, - 0x7F, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - chiperasepolltimeout = 0; - programfusepulsewidth = 2; - programfusepolltimeout = 0; - programlockpulsewidth = 0; - programlockpolltimeout = 10; + desc = "AT90S8535"; + id = "8535"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 195; + n_interrupts = 17; + stk500_devcode = 0x61; + avr910_devcode = 0x68; + chip_erase_delay = 20000; + signature = 0x1e 0x93 0x03; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; + programlockpolltimeout = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; memory "eeprom" - size = 4096; - min_write_delay = 4000; - max_write_delay = 9000; - readback_p1 = 0x80; - readback_p2 = 0x7f; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; + size = 512; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0x00 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 22000; - max_write_delay = 56000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x11; - delay = 70; - blocksize = 256; - readsize = 256; - ; + size = 8192; + min_write_delay = 9000; + max_write_delay = 20000; + readback = 0xff 0xff; + mode = 4; + delay = 12; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; memory "fuse" - size = 1; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x x x o x o 1 o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 1 i 1 i i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxxo"; + write = "1010.1100--1011.111i--xxxx.xxxx--xxxx.xxxx"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x o o x"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 i i 1", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooxx.xxxx"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; - + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ -# ATmega64 +# ATmega103 #------------------------------------------------------------ part - id = "m64"; - desc = "ATmega64"; - has_jtag = yes; - stk500_devcode = 0xA0; - avr910_devcode = 0x45; - signature = 0x1e 0x96 0x02; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; - programfusepolltimeout = 5; - programlockpulsewidth = 0; - programlockpolltimeout = 5; - - idr = 0x22; - spmcr = 0x68; - allowfullpagebitstream = yes; + desc = "ATmega103"; + id = "m103"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 84; + n_interrupts = 24; + stk500_devcode = 0xb1; + avr910_devcode = 0x41; + chip_erase_delay = 112000; + signature = 0x1e 0x97 0x01; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x8e, 0x9e, 0x2e, 0x3e, 0xae, 0xbe, + 0x4e, 0x5e, 0xce, 0xde, 0x6e, 0x7e, 0xee, 0xde, + 0x66, 0x76, 0xe6, 0xf6, 0x6a, 0x7a, 0xea, 0x7a, + 0x7f, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepulsewidth = 15; + programfusepulsewidth = 2; + programlockpolltimeout = 10; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + min_write_delay = 4000; + max_write_delay = 9000; + readback = 0x80 0x7f; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 22000; + max_write_delay = 56000; + readback = 0xff 0xff; + mode = 17; + delay = 70; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; - ocdrev = 2; + memory "fuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxox.o1oo"; + write = "1010.1100--1011.i1ii--xxxx.xxxx--xxxx.xxxx"; + ; - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 20; - blocksize = 64; - readsize = 256; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; + write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; + ; - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 128; - readsize = 256; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; +#------------------------------------------------------------ +# ATmega64 +#------------------------------------------------------------ - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; +part + desc = "ATmega64"; + id = "m64"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 72; + n_interrupts = 35; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xa0; + avr910_devcode = 0x45; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x96 0x02; + reset = io; + allowfullpagebitstream = yes; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; + programfusepolltimeout = 5; + programlockpolltimeout = 5; + idr = 0x22; + spmcr = 0x68; + ocdrev = 2; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 20; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 4; + read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega64A #------------------------------------------------------------ part parent "m64" - id = "m64a"; - desc = "ATmega64A"; - ; + desc = "ATmega64A"; + id = "m64a"; + mcuid = 73; +; #------------------------------------------------------------ # ATmega128 #------------------------------------------------------------ part - id = "m128"; - desc = "ATmega128"; - has_jtag = yes; - stk500_devcode = 0xB2; - avr910_devcode = 0x43; - signature = 0x1e 0x97 0x02; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega128"; + id = "m128"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 85; + n_interrupts = 35; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xb2; + avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x97 0x02; + reset = io; + allowfullpagebitstream = yes; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x22; - spmcr = 0x68; - rampz = 0x3b; - allowfullpagebitstream = yes; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 12; - blocksize = 64; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 128; - readsize = 256; - ; + idr = 0x22; + rampz = 0x3b; + spmcr = 0x68; + ocdrev = 1; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 12; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 4; + read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega128A #------------------------------------------------------------ part parent "m128" - id = "m128a"; - desc = "ATmega128A"; - ; + desc = "ATmega128A"; + id = "m128a"; + mcuid = 86; +; #------------------------------------------------------------ # AT90CAN128 #------------------------------------------------------------ part - id = "c128"; - desc = "AT90CAN128"; - has_jtag = yes; - stk500_devcode = 0xB3; -# avr910_devcode = 0x43; - signature = 0x1e 0x97 0x81; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90CAN128"; + id = "c128"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 176; + n_interrupts = 37; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xb3; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; +# avr910_devcode = 0x43; + signature = 0x1e 0x97 0x81; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - eecr = 0x3f; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - - mode = 0x41; - delay = 20; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 8; + readsize = 256; + read = "1010.0000--000x.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90CAN64 #------------------------------------------------------------ part - id = "c64"; - desc = "AT90CAN64"; - has_jtag = yes; - stk500_devcode = 0xB3; -# avr910_devcode = 0x43; - signature = 0x1e 0x96 0x81; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90CAN64"; + id = "c64"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 172; + n_interrupts = 37; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xb3; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; +# avr910_devcode = 0x43; + signature = 0x1e 0x96 0x81; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - eecr = 0x3f; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - - mode = 0x41; - delay = 20; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 8; + readsize = 256; + read = "1010.0000--000x.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90CAN32 #------------------------------------------------------------ part - id = "c32"; - desc = "AT90CAN32"; - has_jtag = yes; - stk500_devcode = 0xB3; -# avr910_devcode = 0x43; - signature = 0x1e 0x95 0x81; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90CAN32"; + id = "c32"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 171; + n_interrupts = 37; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xb3; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; +# avr910_devcode = 0x43; + signature = 0x1e 0x95 0x81; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - eecr = 0x3f; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - - mode = 0x41; - delay = 20; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 256; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 8; + readsize = 256; + read = "1010.0000--000x.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 256; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega16 #------------------------------------------------------------ part - id = "m16"; - desc = "ATmega16"; - has_jtag = yes; - stk500_devcode = 0x82; - avr910_devcode = 0x74; - signature = 0x1e 0x94 0x03; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 100; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega16"; + id = "m16"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 49; + n_interrupts = 21; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x82; + avr910_devcode = 0x74; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x03; + reset = io; + allowfullpagebitstream = yes; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + progmodedelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + idr = 0x31; + spmcr = 0x57; + ocdrev = 2; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 10; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = yes; - - ocdrev = 2; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x04; - delay = 10; - blocksize = 128; - readsize = 256; - ; + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 128; - readsize = 256; - ; + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "calibration" - size = 4; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; - ; + memory "calibration" + size = 4; + read = "0011.1000--000x.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega16A #------------------------------------------------------------ part parent "m16" - id = "m16a"; - desc = "ATmega16A"; - ; + desc = "ATmega16A"; + id = "m16a"; + mcuid = 50; +; #------------------------------------------------------------ # ATmega324P #------------------------------------------------------------ part - id = "m324p"; - desc = "ATmega324P"; - has_jtag = yes; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - signature = 0x1e 0x95 0x08; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 55000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega324P"; + id = "m324p"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 111; + n_interrupts = 31; + n_boot_sections = 4; + boot_section_size = 512; + stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one + avr910_devcode = 0x74; + chip_erase_delay = 55000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x95 0x08; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 256; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--0aaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega164P #------------------------------------------------------------ part parent "m324p" - id = "m164p"; - desc = "ATmega164P"; - signature = 0x1e 0x94 0x0a; + desc = "ATmega164P"; + id = "m164p"; + mcuid = 93; + boot_section_size = 256; + signature = 0x1e 0x94 0x0a; memory "eeprom" - size = 512; - page_size = 4; - ; + size = 512; + ; memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - ; - ; + size = 0x4000; + num_pages = 128; + ; +; #------------------------------------------------------------ # ATmega164PA #------------------------------------------------------------ part parent "m164p" - id = "m164pa"; - desc = "ATmega164PA"; - ; + desc = "ATmega164PA"; + id = "m164pa"; + mcuid = 94; +; #------------------------------------------------------------ # ATmega164A #------------------------------------------------------------ part parent "m164p" - id = "m164a"; - desc = "ATmega164A"; - signature = 0x1e 0x94 0x0f; - ; + desc = "ATmega164A"; + id = "m164a"; + mcuid = 92; + signature = 0x1e 0x94 0x0f; +; #------------------------------------------------------------ # ATmega324PB #------------------------------------------------------------ part parent "m324p" - id = "m324pb"; - desc = "ATmega324PB"; - signature = 0x1e 0x95 0x17; - ; + desc = "ATmega324PB"; + id = "m324pb"; + mcuid = 113; + n_interrupts = 51; + signature = 0x1e 0x95 0x17; +; #------------------------------------------------------------ # ATmega324PA #------------------------------------------------------------ part parent "m324p" - id = "m324pa"; - desc = "ATmega324PA"; - signature = 0x1e 0x95 0x11; - ; + desc = "ATmega324PA"; + id = "m324pa"; + mcuid = 112; + signature = 0x1e 0x95 0x11; +; #------------------------------------------------------------ # ATmega324A #------------------------------------------------------------ part parent "m324p" - id = "m324a"; - desc = "ATmega324A"; - signature = 0x1e 0x95 0x15; - ; + desc = "ATmega324A"; + id = "m324a"; + mcuid = 110; + signature = 0x1e 0x95 0x15; +; #------------------------------------------------------------ # ATmega644 #------------------------------------------------------------ part - id = "m644"; - desc = "ATmega644"; - has_jtag = yes; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - signature = 0x1e 0x96 0x09; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 55000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega644"; + id = "m644"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 127; + n_interrupts = 28; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one + avr910_devcode = 0x74; + chip_erase_delay = 55000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x96 0x09; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 256; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega644A #------------------------------------------------------------ part parent "m644" - id = "m644a"; - desc = "ATmega644A"; - ; + desc = "ATmega644A"; + id = "m644a"; + mcuid = 128; + n_interrupts = 31; +; #------------------------------------------------------------ # ATmega644P #------------------------------------------------------------ part parent "m644" - id = "m644p"; - desc = "ATmega644P"; - signature = 0x1e 0x96 0x0a; - ; + desc = "ATmega644P"; + id = "m644p"; + mcuid = 129; + n_interrupts = 31; + signature = 0x1e 0x96 0x0a; +; #------------------------------------------------------------ # ATmega644PA #------------------------------------------------------------ part parent "m644" - id = "m644pa"; - desc = "ATmega644PA"; - signature = 0x1e 0x96 0x0a; - ; + desc = "ATmega644PA"; + id = "m644pa"; + mcuid = 130; + n_interrupts = 31; + signature = 0x1e 0x96 0x0a; +; #------------------------------------------------------------ # ATmega1284 #------------------------------------------------------------ part - id = "m1284"; - desc = "ATmega1284"; - has_jtag = yes; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - signature = 0x1e 0x97 0x06; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 55000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega1284"; + id = "m1284"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 140; + n_interrupts = 35; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one + avr910_devcode = 0x74; + chip_erase_delay = 55000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x97 0x06; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; + hventerstabdelay = 100; + latchcycles = 6; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 256; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega1284P #------------------------------------------------------------ part parent "m1284" - id = "m1284p"; - desc = "ATmega1284P"; - signature = 0x1e 0x97 0x05; - ; + desc = "ATmega1284P"; + id = "m1284p"; + mcuid = 141; + signature = 0x1e 0x97 0x05; +; #------------------------------------------------------------ # ATmega162 #------------------------------------------------------------ part - id = "m162"; - desc = "ATmega162"; - has_jtag = yes; - stk500_devcode = 0x83; - avr910_devcode = 0x63; - signature = 0x1e 0x94 0x04; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - - idr = 0x04; - spmcr = 0x57; + desc = "ATmega162"; + id = "m162"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 90; + n_interrupts = 28; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x83; + avr910_devcode = 0x63; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x04; + reset = io; allowfullpagebitstream = yes; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - ocdrev = 2; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - - ; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; + idr = 0x04; + spmcr = 0x57; + ocdrev = 2; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 16000; + max_write_delay = 16000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 16000; + max_write_delay = 16000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - ; + size = 1; + min_write_delay = 16000; + max_write_delay = 16000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; + ; memory "lock" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 16000; + max_write_delay = 16000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - - read = "0 0 1 1 0 0 0 0 0 0 x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--00xx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + size = 1; + read = "0011.1000--00xx.xxxx--0000.0000--oooo.oooo"; + ; ; - - #------------------------------------------------------------ # ATmega163 #------------------------------------------------------------ part - id = "m163"; - desc = "ATmega163"; - stk500_devcode = 0x81; - avr910_devcode = 0x64; - signature = 0x1e 0x94 0x02; - chip_erase_delay = 32000; - pagel = 0xd7; - bs2 = 0xa0; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 30; - programfusepulsewidth = 0; + desc = "ATmega163"; + id = "m163"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 91; + n_interrupts = 18; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x81; + avr910_devcode = 0x64; + chip_erase_delay = 32000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x02; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepolltimeout = 30; programfusepolltimeout = 2; - programlockpulsewidth = 0; programlockpolltimeout = 2; - - - memory "eeprom" - size = 512; - min_write_delay = 4000; - max_write_delay = 4000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 16000; - max_write_delay = 16000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x11; - delay = 20; - blocksize = 128; - readsize = 256; - ; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + min_write_delay = 4000; + max_write_delay = 4000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 16000; + max_write_delay = 16000; + readback = 0xff 0xff; + mode = 17; + delay = 20; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o x x o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i 1 1 i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.0000--xxxx.xxxx--ooxx.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--ii11.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x x x x x 1 o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x 1 1 1 1 1 i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.1000--xxxx.xxxx--xxxx.1ooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--1111.1iii"; + ; memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x 0 x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.0xxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega169 #------------------------------------------------------------ part - id = "m169"; - desc = "ATmega169"; - has_jtag = yes; - stk500_devcode = 0x85; - avr910_devcode = 0x78; - signature = 0x1e 0x94 0x05; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega169"; + id = "m169"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 104; + n_interrupts = 23; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x85; + avr910_devcode = 0x78; + chip_erase_delay = 9000; + signature = 0x1e 0x94 0x05; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - - ocdrev = 2; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 2; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega169A #------------------------------------------------------------ part parent "m169" - id = "m169a"; - desc = "ATmega169A"; - signature = 0x1E 0x94 0x11; - ; + desc = "ATmega169A"; + id = "m169a"; + mcuid = 105; + signature = 0x1e 0x94 0x11; + reset = io; +; #------------------------------------------------------------ # ATmega169P #------------------------------------------------------------ part parent "m169" - id = "m169p"; - desc = "ATmega169P"; - signature = 0x1E 0x94 0x05; - ; + desc = "ATmega169P"; + id = "m169p"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 106; + reset = io; +; #------------------------------------------------------------ # ATmega169PA #------------------------------------------------------------ part parent "m169" - id = "m169pa"; - desc = "ATmega169PA"; - signature = 0x1E 0x94 0x05; - ; + desc = "ATmega169PA"; + id = "m169pa"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 107; + reset = io; +; #------------------------------------------------------------ # ATmega329 #------------------------------------------------------------ part - id = "m329"; - desc = "ATmega329"; - has_jtag = yes; -# stk500_devcode = 0x85; # no STK500 support, only STK500v2 -# avr910_devcode = 0x?; # try the ATmega169 one: - avr910_devcode = 0x75; - signature = 0x1e 0x95 0x03; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega329"; + id = "m329"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 121; + n_interrupts = 23; + n_boot_sections = 4; + boot_section_size = 512; +# stk500_devcode = 0x85; # no STK500 support, only STK500v2 +# avr910_devcode = 0x?; # try the ATmega169 one: + avr910_devcode = 0x75; + chip_erase_delay = 9000; + signature = 0x1e 0x95 0x03; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega329A #------------------------------------------------------------ part parent "m329" - id = "m329a"; - desc = "ATmega329A"; - ; + desc = "ATmega329A"; + id = "m329a"; + mcuid = 122; +; #------------------------------------------------------------ # ATmega329P #------------------------------------------------------------ part parent "m329" - id = "m329p"; - desc = "ATmega329P"; - signature = 0x1e 0x95 0x0b; - ; + desc = "ATmega329P"; + id = "m329p"; + mcuid = 123; + signature = 0x1e 0x95 0x0b; +; #------------------------------------------------------------ # ATmega329PA #------------------------------------------------------------ part parent "m329" - id = "m329pa"; - desc = "ATmega329PA"; - signature = 0x1e 0x95 0x0b; - ; + desc = "ATmega329PA"; + id = "m329pa"; + mcuid = 124; + signature = 0x1e 0x95 0x0b; +; #------------------------------------------------------------ # ATmega3290 #------------------------------------------------------------ part parent "m329" - id = "m3290"; - desc = "ATmega3290"; - signature = 0x1e 0x95 0x04; - ; + desc = "ATmega3290"; + id = "m3290"; + mcuid = 150; + n_interrupts = 25; + signature = 0x1e 0x95 0x04; +; #------------------------------------------------------------ # ATmega3290A #------------------------------------------------------------ part parent "m329" - id = "m3290a"; - desc = "ATmega3290A"; - signature = 0x1e 0x95 0x04; - ; + desc = "ATmega3290A"; + id = "m3290a"; + mcuid = 151; + n_interrupts = 25; + signature = 0x1e 0x95 0x04; +; #------------------------------------------------------------ # ATmega3290P #------------------------------------------------------------ part parent "m329" - id = "m3290p"; - desc = "ATmega3290P"; - signature = 0x1e 0x95 0x0c; - ; + desc = "ATmega3290P"; + id = "m3290p"; + mcuid = 152; + n_interrupts = 25; + signature = 0x1e 0x95 0x0c; +; #------------------------------------------------------------ # ATmega3290PA #------------------------------------------------------------ part parent "m329" - id = "m3290pa"; - desc = "ATmega3290PA"; - signature = 0x1e 0x95 0x0c; - ; + desc = "ATmega3290PA"; + id = "m3290pa"; + mcuid = 153; + n_interrupts = 25; + signature = 0x1e 0x95 0x0c; +; #------------------------------------------------------------ # ATmega649 #------------------------------------------------------------ part - id = "m649"; - desc = "ATmega649"; - has_jtag = yes; -# stk500_devcode = 0x85; # no STK500 support, only STK500v2 -# avr910_devcode = 0x?; # try the ATmega169 one: - avr910_devcode = 0x75; - signature = 0x1e 0x96 0x03; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega649"; + id = "m649"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 135; + n_interrupts = 23; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0x85; # no STK500 support, only STK500v2 +# avr910_devcode = 0x?; # try the ATmega169 one: + avr910_devcode = 0x75; + chip_erase_delay = 9000; + signature = 0x1e 0x96 0x03; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega649A #------------------------------------------------------------ part parent "m649" - id = "m649a"; - desc = "ATmega649A"; - ; + desc = "ATmega649A"; + id = "m649a"; + mcuid = 136; +; #------------------------------------------------------------ # ATmega649P #------------------------------------------------------------ part parent "m649" - id = "m649p"; - desc = "ATmega649P"; - signature = 0x1e 0x96 0x0b; - ; + desc = "ATmega649P"; + id = "m649p"; + mcuid = 137; + signature = 0x1e 0x96 0x0b; +; #------------------------------------------------------------ # ATmega6490 #------------------------------------------------------------ part parent "m649" - id = "m6490"; - desc = "ATmega6490"; - signature = 0x1e 0x96 0x04; - ; + desc = "ATmega6490"; + id = "m6490"; + mcuid = 157; + n_interrupts = 25; + signature = 0x1e 0x96 0x04; +; #------------------------------------------------------------ # ATmega6490A #------------------------------------------------------------ part parent "m649" - id = "m6490a"; - desc = "ATmega6490A"; - signature = 0x1e 0x96 0x04; - ; + desc = "ATmega6490A"; + id = "m6490a"; + mcuid = 158; + n_interrupts = 25; + signature = 0x1e 0x96 0x04; +; #------------------------------------------------------------ # ATmega6490P #------------------------------------------------------------ part parent "m649" - id = "m6490p"; - desc = "ATmega6490P"; - signature = 0x1e 0x96 0x0C; - ; + desc = "ATmega6490P"; + id = "m6490p"; + mcuid = 159; + n_interrupts = 25; + signature = 0x1e 0x96 0x0c; +; #------------------------------------------------------------ # ATmega32 #------------------------------------------------------------ part - id = "m32"; - desc = "ATmega32"; - has_jtag = yes; - stk500_devcode = 0x91; - avr910_devcode = 0x72; - signature = 0x1e 0x95 0x02; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega32"; + id = "m32"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; + mcuid = 58; + n_interrupts = 21; + n_boot_sections = 4; + boot_section_size = 512; + stk500_devcode = 0x91; + avr910_devcode = 0x72; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x95 0x02; + reset = io; + allowfullpagebitstream = yes; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = yes; - - ocdrev = 2; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x04; - delay = 10; - blocksize = 64; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 64; - readsize = 256; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 2; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 10; + blocksize = 64; + readsize = 256; + read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; - - memory "efuse" - size = 0; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 0 0 x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; - ; + size = 4; + read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega161 #------------------------------------------------------------ part - id = "m161"; - desc = "ATmega161"; - stk500_devcode = 0x80; - avr910_devcode = 0x60; - signature = 0x1e 0x94 0x01; - chip_erase_delay = 28000; - pagel = 0xd7; - bs2 = 0xa0; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 30; - programfusepulsewidth = 0; + desc = "ATmega161"; + id = "m161"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 89; + n_interrupts = 21; + n_boot_sections = 1; + boot_section_size = 1024; + stk500_devcode = 0x80; + avr910_devcode = 0x60; + chip_erase_delay = 28000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x01; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + chiperasepolltimeout = 30; programfusepolltimeout = 2; - programlockpulsewidth = 0; programlockpolltimeout = 2; - - memory "eeprom" - size = 512; - min_write_delay = 3400; - max_write_delay = 3400; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 5; - blocksize = 128; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 14000; - max_write_delay = 14000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 16; - blocksize = 128; - readsize = 256; - ; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + min_write_delay = 3400; + max_write_delay = 3400; + readback = 0xff 0xff; + mode = 4; + delay = 5; + blocksize = 128; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 14000; + max_write_delay = 14000; + readback = 0xff 0xff; + mode = 33; + delay = 16; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "fuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 x x x x x x x x", - "x x x x x x x x x o x o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 x x x x x", - "x x x x x x x x 1 i 1 i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xoxo.oooo"; + write = "1010.1100--101x.xxxx--xxxx.xxxx--1i1i.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; + memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega32A #------------------------------------------------------------ part parent "m32" - id = "m32a"; - desc = "ATmega32A"; - ; + desc = "ATmega32A"; + id = "m32a"; + mcuid = 59; +; #------------------------------------------------------------ # ATmega8 #------------------------------------------------------------ part - id = "m8"; - desc = "ATmega8"; - stk500_devcode = 0x70; - avr910_devcode = 0x76; - signature = 0x1e 0x93 0x07; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 10000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega8"; + id = "m8"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 45; + n_interrupts = 19; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x70; + avr910_devcode = 0x76; + chip_erase_delay = 10000; + pagel = 0xd7; + bs2 = 0xc2; + signature = 0x1e 0x93 0x07; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 2; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 20; - blocksize = 128; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 10; - blocksize = 64; - readsize = 256; - ; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 20; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0x00; + mode = 33; + delay = 10; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; - - memory "efuse" - size = 0; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 0 0 x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + memory "lock" + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; - + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; + memory "calibration" + size = 4; + read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega8A #------------------------------------------------------------ part parent "m8" - id = "m8a"; - desc = "ATmega8A"; - ; + desc = "ATmega8A"; + id = "m8a"; + mcuid = 46; +; #------------------------------------------------------------ # ATmega8515 #------------------------------------------------------------ part - id = "m8515"; - desc = "ATmega8515"; - stk500_devcode = 0x63; - avr910_devcode = 0x3A; - signature = 0x1e 0x93 0x06; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega8515"; + id = "m8515"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 160; + n_interrupts = 17; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x63; + avr910_devcode = 0x3a; + chip_erase_delay = 9000; + signature = 0x1e 0x93 0x06; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 20; - blocksize = 128; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 64; - readsize = 256; - ; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 20; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; - - memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 0 0 x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; - - + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; + memory "calibration" + size = 4; + read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega8535 #------------------------------------------------------------ part - id = "m8535"; - desc = "ATmega8535"; - stk500_devcode = 0x64; - avr910_devcode = 0x69; - signature = 0x1e 0x93 0x08; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega8535"; + id = "m8535"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP; + mcuid = 161; + n_interrupts = 21; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x64; + avr910_devcode = 0x69; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x93 0x08; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 6; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - mode = 0x04; - delay = 20; - blocksize = 128; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 64; - readsize = 256; - ; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 20; + blocksize = 128; + readsize = 256; + read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; - - memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 0 0 x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + size = 1; + min_write_delay = 2000; + max_write_delay = 2000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; + memory "calibration" + size = 4; + read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny26 #------------------------------------------------------------ part - id = "t26"; - desc = "ATtiny26"; - stk500_devcode = 0x21; - avr910_devcode = 0x5e; - signature = 0x1e 0x91 0x09; - pagel = 0xb3; - bs2 = 0xb2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0xC4, 0xE4, 0xC4, 0xE4, 0xCC, 0xEC, 0xCC, 0xEC, - 0xD4, 0xF4, 0xD4, 0xF4, 0xDC, 0xFC, 0xDC, 0xFC, - 0xC8, 0xE8, 0xD8, 0xF8, 0x4C, 0x6C, 0x5C, 0x7C, - 0xEC, 0xBC, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny26"; + id = "t26"; + prog_modes = PM_ISP | PM_HVPP; + mcuid = 17; + n_interrupts = 12; + stk500_devcode = 0x21; + avr910_devcode = 0x5e; + chip_erase_delay = 9000; + pagel = 0xb3; + bs2 = 0xb2; + signature = 0x1e 0x91 0x09; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, + 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, + 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, + 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 2; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - mode = 0x04; - delay = 10; - blocksize = 64; - readsize = 256; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 4; + delay = 10; + blocksize = 64; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + ; + + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 33; + delay = 6; + blocksize = 16; + readsize = 256; + read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxx.xxaa--aaaa.xxxx--xxxx.xxxx"; ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 16; - readsize = 256; + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--xxxi.iiii"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x x o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 1 i i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 9000; - max_write_delay = 9000; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; + write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x x x x i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 4; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + size = 4; + read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; ; ; @@ -7020,186 +6216,126 @@ part #------------------------------------------------------------ part - id = "t261"; - desc = "ATtiny261"; - has_debugwire = yes; - flash_instr = 0xB4, 0x00, 0x10; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x00, 0xB4, 0x00, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x91 0x0c; - pagel = 0xb3; - bs2 = 0xb2; - chip_erase_delay = 4000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0xC4, 0xE4, 0xC4, 0xE4, 0xCC, 0xEC, 0xCC, 0xEC, - 0xD4, 0xF4, 0xD4, 0xF4, 0xDC, 0xFC, 0xDC, 0xFC, - 0xC8, 0xE8, 0xD8, 0xF8, 0x4C, 0x6C, 0x5C, 0x7C, - 0xEC, 0xBC, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny261"; + id = "t261"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 30; + n_interrupts = 19; + chip_erase_delay = 4000; + pagel = 0xb3; + bs2 = 0xb2; +# stk500_devcode = 0x21; +# avr910_devcode = 0x5e; + signature = 0x1e 0x91 0x0c; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, + 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, + 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, + 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb4, 0x00, 0x10; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 2; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + page_size = 4; + num_pages = 32; + min_write_delay = 4000; + max_write_delay = 4000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxx.xxaa--aaaa.xxxx--xxxx.xxxx"; + ; - ocdrev = 1; - - memory "eeprom" - paged = no; - size = 128; - page_size = 4; - num_pages = 32; - min_write_delay = 4000; - max_write_delay = 4000; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read = "1 0 1 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 x x x x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x x x x a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x x o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 1 i i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 4500; - max_write_delay = 4500; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; + write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -7208,195 +6344,136 @@ part #------------------------------------------------------------ part parent "t261" - id = "t261a"; - desc = "ATtiny261A"; - ; + desc = "ATtiny261A"; + id = "t261a"; + mcuid = 31; +; #------------------------------------------------------------ # ATtiny461 #------------------------------------------------------------ part - id = "t461"; - desc = "ATtiny461"; - has_debugwire = yes; - flash_instr = 0xB4, 0x00, 0x10; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x00, 0xB4, 0x00, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x92 0x08; - pagel = 0xb3; - bs2 = 0xb2; - chip_erase_delay = 4000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0xC4, 0xE4, 0xC4, 0xE4, 0xCC, 0xEC, 0xCC, 0xEC, - 0xD4, 0xF4, 0xD4, 0xF4, 0xDC, 0xFC, 0xDC, 0xFC, - 0xC8, 0xE8, 0xD8, 0xF8, 0x4C, 0x6C, 0x5C, 0x7C, - 0xEC, 0xBC, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny461"; + id = "t461"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 33; + n_interrupts = 19; + chip_erase_delay = 4000; + pagel = 0xb3; + bs2 = 0xb2; +# stk500_devcode = 0x21; +# avr910_devcode = 0x5e; + signature = 0x1e 0x92 0x08; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, + 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, + 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, + 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb4, 0x00, 0x10; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 2; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + num_pages = 64; + min_write_delay = 4000; + max_write_delay = 4000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxx.xaaa--aaax.xxxx--xxxx.xxxx"; + ; - ocdrev = 1; - - memory "eeprom" - paged = no; - size = 256; - page_size = 4; - num_pages = 64; - min_write_delay = 4000; - max_write_delay = 4000; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read = " 1 0 1 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x x o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 1 i i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 4500; - max_write_delay = 4500; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; + write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -7405,195 +6482,136 @@ part #------------------------------------------------------------ part parent "t461" - id = "t461a"; - desc = "ATtiny461A"; - ; + desc = "ATtiny461A"; + id = "t461a"; + mcuid = 34; +; #------------------------------------------------------------ # ATtiny861 #------------------------------------------------------------ part - id = "t861"; - desc = "ATtiny861"; - has_debugwire = yes; - flash_instr = 0xB4, 0x00, 0x10; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x00, 0xB4, 0x00, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x93 0x0d; - pagel = 0xb3; - bs2 = 0xb2; - chip_erase_delay = 4000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0xC4, 0xE4, 0xC4, 0xE4, 0xCC, 0xEC, 0xCC, 0xEC, - 0xD4, 0xF4, 0xD4, 0xF4, 0xDC, 0xFC, 0xDC, 0xFC, - 0xC8, 0xE8, 0xD8, 0xF8, 0x4C, 0x6C, 0x5C, 0x7C, - 0xEC, 0xBC, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny861"; + id = "t861"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 38; + n_interrupts = 19; + chip_erase_delay = 4000; + pagel = 0xb3; + bs2 = 0xb2; +# stk500_devcode = 0x21; +# avr910_devcode = 0x5e; + signature = 0x1e 0x93 0x0d; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, + 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, + 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, + 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb4, 0x00, 0x10; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 2; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 4000; + max_write_delay = 4000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxx.aaaa--aaax.xxxx--xxxx.xxxx"; + ; - ocdrev = 1; - - memory "eeprom" - paged = no; - size = 512; - num_pages = 128; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4000; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read = " 1 0 1 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0 x x x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read_lo = " 0 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 x x x x x x x x", - "x x x x x x x x x x x x x x o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 1 1 1 i i", - "x x x x x x x x x x x x x x x x"; - min_write_delay = 4500; - max_write_delay = 4500; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; + write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; ; - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -7602,9 +6620,10 @@ part #------------------------------------------------------------ part parent "t861" - id = "t861a"; - desc = "ATtiny861A"; - ; + desc = "ATtiny861A"; + id = "t861a"; + mcuid = 39; +; #------------------------------------------------------------ # ATtiny28 @@ -7613,701 +6632,532 @@ part parent "t861" # This is an HVPP-only device. part - id = "t28"; - desc = "ATtiny28"; - stk500_devcode = 0x22; - avr910_devcode = 0x5c; - signature = 0x1e 0x91 0x07; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny28"; + id = "t28"; + prog_modes = PM_HVPP; + mcuid = 18; + n_interrupts = 6; + stk500_devcode = 0x22; + avr910_devcode = 0x5c; + signature = 0x1e 0x91 0x07; + serial = no; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; memory "flash" - size = 2048; - page_size = 2; - readsize = 256; - delay = 5; + size = 2048; + page_size = 2; + delay = 5; + readsize = 256; ; - memory "signature" - size = 3; + memory "fuse" + size = 1; ; memory "lock" - size = 1; + size = 1; ; - memory "calibration" - size = 1; + memory "signature" + size = 3; ; - memory "fuse" - size = 1; + memory "calibration" + size = 1; ; ; - - #------------------------------------------------------------ # ATmega48 #------------------------------------------------------------ part - id = "m48"; - desc = "ATmega48"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x59; -# avr910_devcode = 0x; - signature = 0x1e 0x92 0x05; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 45000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega48"; + id = "m48"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 67; + n_interrupts = 26; + stk500_devcode = 0x59; + chip_erase_delay = 45000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x92 0x05; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 256; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x x", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega48A #------------------------------------------------------------ part parent "m48" - id = "m48a"; - desc = "ATmega48A"; - ; + desc = "ATmega48A"; + id = "m48a"; + mcuid = 68; +; #------------------------------------------------------------ # ATmega48P #------------------------------------------------------------ part parent "m48" - id = "m48p"; - desc = "ATmega48P"; - signature = 0x1e 0x92 0x0a; - ; + desc = "ATmega48P"; + id = "m48p"; + mcuid = 69; + signature = 0x1e 0x92 0x0a; +; #------------------------------------------------------------ # ATmega48PA #------------------------------------------------------------ part parent "m48" - id = "m48pa"; - desc = "ATmega48PA"; - signature = 0x1e 0x92 0x0a; - ; + desc = "ATmega48PA"; + id = "m48pa"; + mcuid = 70; + signature = 0x1e 0x92 0x0a; +; #------------------------------------------------------------ # ATmega48PB #------------------------------------------------------------ part parent "m48" - id = "m48pb"; - desc = "ATmega48PB"; - signature = 0x1e 0x92 0x10; - ; + desc = "ATmega48PB"; + id = "m48pb"; + mcuid = 71; + n_interrupts = 27; + chip_erase_delay = 10500; + signature = 0x1e 0x92 0x10; +; #------------------------------------------------------------ # ATmega88 #------------------------------------------------------------ part - id = "m88"; - desc = "ATmega88"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x73; -# avr910_devcode = 0x; - signature = 0x1e 0x93 0x0a; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega88"; + id = "m88"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 79; + n_interrupts = 26; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x73; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x93 0x0a; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 512; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega88A #------------------------------------------------------------ part parent "m88" - id = "m88a"; - desc = "ATmega88A"; - ; + desc = "ATmega88A"; + id = "m88a"; + mcuid = 80; +; #------------------------------------------------------------ # ATmega88P #------------------------------------------------------------ part parent "m88" - id = "m88p"; - desc = "ATmega88P"; - signature = 0x1e 0x93 0x0f; - ; + desc = "ATmega88P"; + id = "m88p"; + mcuid = 81; + signature = 0x1e 0x93 0x0f; +; #------------------------------------------------------------ # ATmega88PA #------------------------------------------------------------ part parent "m88" - id = "m88pa"; - desc = "ATmega88PA"; - signature = 0x1e 0x93 0x0f; - ; + desc = "ATmega88PA"; + id = "m88pa"; + mcuid = 82; + signature = 0x1e 0x93 0x0f; +; #------------------------------------------------------------ # ATmega88PB #------------------------------------------------------------ part parent "m88" - id = "m88pb"; - desc = "ATmega88PB"; - signature = 0x1e 0x93 0x16; - ; + desc = "ATmega88PB"; + id = "m88pb"; + mcuid = 83; + n_interrupts = 27; + chip_erase_delay = 10500; + signature = 0x1e 0x93 0x16; +; #------------------------------------------------------------ # ATmega168 #------------------------------------------------------------ part - id = "m168"; - desc = "ATmega168"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x94 0x06; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega168"; + id = "m168"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 99; + n_interrupts = 26; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x86; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x94 0x06; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 512; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - - ; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--000a.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; ; #------------------------------------------------------------ @@ -8315,226 +7165,175 @@ part #------------------------------------------------------------ part parent "m168" - id = "m168a"; - desc = "ATmega168A"; - ; + desc = "ATmega168A"; + id = "m168a"; + mcuid = 100; +; #------------------------------------------------------------ # ATmega168P #------------------------------------------------------------ part parent "m168" - id = "m168p"; - desc = "ATmega168P"; - signature = 0x1e 0x94 0x0b; - ; + desc = "ATmega168P"; + id = "m168p"; + mcuid = 101; + signature = 0x1e 0x94 0x0b; +; #------------------------------------------------------------ # ATmega168PA #------------------------------------------------------------ part parent "m168" - id = "m168pa"; - desc = "ATmega168PA"; - signature = 0x1e 0x94 0x0b; - ; + desc = "ATmega168PA"; + id = "m168pa"; + mcuid = 102; + signature = 0x1e 0x94 0x0b; +; #------------------------------------------------------------ # ATmega168PB #------------------------------------------------------------ part parent "m168" - id = "m168pb"; - desc = "ATmega168PB"; - signature = 0x1e 0x94 0x15; - ; + desc = "ATmega168PB"; + id = "m168pb"; + mcuid = 103; + n_interrupts = 27; + chip_erase_delay = 10500; + signature = 0x1e 0x94 0x15; +; #------------------------------------------------------------ # ATtiny828 #------------------------------------------------------------ part - id = "t828"; - desc = "ATtiny828"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x93 0x14; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 15000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny828"; + id = "t828"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 35; + n_interrupts = 26; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x86; + chip_erase_delay = 15000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x93 0x14; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - paged = no; - page_size = 4; - size = 256; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - -writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - - ; + spmcr = 0x57; + eecr = 0x3f; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 5; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--111i.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; ; #------------------------------------------------------------ @@ -8542,946 +7341,655 @@ writepage = " 1 1 0 0 0 0 1 0", #------------------------------------------------------------ part parent "t828" - id = "t828r"; - desc = "ATtiny828R"; - ; + desc = "ATtiny828R"; + id = "t828r"; + mcuid = 36; +; #------------------------------------------------------------ # ATtiny87 #------------------------------------------------------------ part - id = "t87"; - desc = "ATtiny87"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, - 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, - 0xBF, 0x99, 0xF9, 0xBB, 0xAF; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x93 0x87; - reset = io; - chip_erase_delay = 15000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x06, 0x16, 0x46, 0x56, 0x0A, 0x1A, 0x4A, 0x5A, - 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny87"; + id = "t87"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 27; + n_interrupts = 20; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 15000; + signature = 0x1e 0x93 0x87; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, + 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 20; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3f; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - idr = 0x00; - spmcr = 0x57; - allowfullpagebitstream = no; - - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 x x x x x a8", - "a8 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " 0 0 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 64; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; + ; # ATtiny87 has Signature Bytes: 0x1E 0x93 0x87. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny167 #------------------------------------------------------------ part - id = "t167"; - desc = "ATtiny167"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, - 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, - 0xBF, 0x99, 0xF9, 0xBB, 0xAF; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x94 0x87; - reset = io; - chip_erase_delay = 15000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 0; - - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x06, 0x16, 0x46, 0x56, 0x0A, 0x1A, 0x4A, 0x5A, - 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny167"; + id = "t167"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 29; + n_interrupts = 20; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = 0x??; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 15000; + signature = 0x1e 0x94 0x87; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, + 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 20; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3f; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--000a.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - idr = 0x00; - spmcr = 0x57; - allowfullpagebitstream = no; - - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 x x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 x x x x x a8", - "a8 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " 0 0 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 64; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; + ; # ATtiny167 has Signature Bytes: 0x1E 0x94 0x87. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny48 #------------------------------------------------------------ part - id = "t48"; - desc = "ATtiny48"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x73; -# avr910_devcode = 0x; - signature = 0x1e 0x92 0x09; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 15000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny48"; + id = "t48"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 23; + n_interrupts = 20; + stk500_devcode = 0x73; + chip_erase_delay = 15000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x92 0x09; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 64; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 64; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 64; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 64; + read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x 1 1 1 1 1 1 1 i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.111i"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny88 #------------------------------------------------------------ part - id = "t88"; - desc = "ATtiny88"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x73; -# avr910_devcode = 0x; - signature = 0x1e 0x93 0x11; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny88"; + id = "t88"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 28; + n_interrupts = 20; + stk500_devcode = 0x73; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x93 0x11; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 64; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 64; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 64; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 64; + read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega328 #------------------------------------------------------------ part - id = "m328"; - desc = "ATmega328"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x95 0x14; - pagel = 0xd7; - bs2 = 0xc2; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega328"; + id = "m328"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 118; + n_interrupts = 26; + n_boot_sections = 4; + boot_section_size = 512; + stk500_devcode = 0x86; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc2; +# avr910_devcode = 0x??; + signature = 0x1e 0x95 0x14; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; - page_size = 4; - size = 1024; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - + spmcr = 0x57; + eecr = 0x3f; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; ; - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; ; ; @@ -9490,9 +7998,10 @@ part #------------------------------------------------------------ part parent "m328" - id = "m328p"; - desc = "ATmega328P"; - signature = 0x1e 0x95 0x0f; + desc = "ATmega328P"; + id = "m328p"; + mcuid = 119; + signature = 0x1e 0x95 0x0f; ; #------------------------------------------------------------ @@ -9500,19 +8009,15 @@ part parent "m328" #------------------------------------------------------------ part parent "m328" - id = "m328pb"; - desc = "ATmega328PB"; - signature = 0x1e 0x95 0x16; + desc = "ATmega328PB"; + id = "m328pb"; + mcuid = 120; + n_interrupts = 45; + chip_erase_delay = 10500; + signature = 0x1e 0x95 0x16; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; ; ; @@ -9521,19 +8026,17 @@ part parent "m328" #------------------------------------------------------------ part parent "m328" - id = "m32m1"; - desc = "ATmega32M1"; - # stk500_devcode = 0x; - # avr910_devcode = 0x; - signature = 0x1e 0x95 0x84; - bs2 = 0xe2; + desc = "ATmega32M1"; + id = "m32m1"; + mcuid = 63; + n_interrupts = 31; + bs2 = 0xe2; +# stk500_devcode = 0x??; +# avr910_devcode = 0x??; + signature = 0x1e 0x95 0x84; memory "efuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x i i i i i i"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxii.iiii"; ; ; @@ -9542,34 +8045,37 @@ part parent "m328" #------------------------------------------------------------ part parent "m328" - id = "m64m1"; - desc = "ATmega64M1"; - # stk500_devcode = 0x; - # avr910_devcode = 0x; - signature = 0x1e 0x96 0x84; - bs2 = 0xe2; + desc = "ATmega64M1"; + id = "m64m1"; + mcuid = 76; + n_interrupts = 31; + boot_section_size = 1024; + bs2 = 0xe2; +# stk500_devcode = 0x??; +# avr910_devcode = 0x??; + signature = 0x1e 0x96 0x84; memory "eeprom" - size = 2048; - page_size = 8; + size = 2048; + page_size = 8; + read = "1010.0000--000x.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; ; memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; + size = 0x10000; + page_size = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x i i i i i i"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxii.iiii"; ; ; @@ -9578,564 +8084,406 @@ part parent "m328" #------------------------------------------------------------ part - id = "t2313"; - desc = "ATtiny2313"; - has_debugwire = yes; - flash_instr = 0xB2, 0x0F, 0x1F; - eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x23; -## Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - signature = 0x1e 0x91 0x0a; - pagel = 0xD4; - bs2 = 0xD6; - reset = io; - chip_erase_delay = 9000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny2313"; + id = "t2313"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 42; + n_interrupts = 19; + stk500_devcode = 0x23; +# Use the ATtiny26 devcode: + avr910_devcode = 0x5e; + chip_erase_delay = 9000; + pagel = 0xd4; + bs2 = 0xd6; + signature = 0x1e 0x91 0x0a; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, + 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb2, 0x0f, 0x1f; + eeprom_instr = + 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xba, 0x0f, 0xb2, 0x0f, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 0; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; +# The information in the data sheet of April/2004 is wrong, this works: + loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; +# The information in the data sheet of April/2004 is wrong, this works: + loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; +# The information in the data sheet of April/2004 is wrong, this works: + writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; + ; - ocdrev = 0; - - memory "eeprom" - size = 128; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; -# The information in the data sheet of April/2004 is wrong, this works: - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; -# The information in the data sheet of April/2004 is wrong, this works: - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; -# The information in the data sheet of April/2004 is wrong, this works: - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # ATtiny2313 has Signature Bytes: 0x1E 0x91 0x0A. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; # The Tiny2313 has calibration data for both 4 MHz and 8 MHz. # The information in the data sheet of April/2004 is wrong, this works: - memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "calibration" + size = 2; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny2313A #------------------------------------------------------------ part parent "t2313" - id = "t2313a"; - desc = "ATtiny2313A"; - ; + desc = "ATtiny2313A"; + id = "t2313a"; + mcuid = 43; + n_interrupts = 21; +; #------------------------------------------------------------ # ATtiny4313 #------------------------------------------------------------ part - id = "t4313"; - desc = "ATtiny4313"; - has_debugwire = yes; - flash_instr = 0xB2, 0x0F, 0x1F; - eeprom_instr = 0xBB, 0xFE, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBA, 0x0F, 0xB2, 0x0F, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x23; -## Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - signature = 0x1e 0x92 0x0d; - pagel = 0xD4; - bs2 = 0xD6; - reset = io; - chip_erase_delay = 9000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny4313"; + id = "t4313"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 44; + n_interrupts = 21; + stk500_devcode = 0x23; +# Use the ATtiny26 devcode: + avr910_devcode = 0x5e; + chip_erase_delay = 9000; + pagel = 0xd4; + bs2 = 0xd6; + signature = 0x1e 0x92 0x0d; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, + 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb2, 0x0f, 0x1f; + eeprom_instr = + 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xba, 0x0f, 0xb2, 0x0f, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 0; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - ocdrev = 0; - - memory "eeprom" - size = 256; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # ATtiny4313 has Signature Bytes: 0x1E 0x92 0x0D. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 2; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90PWM2 #------------------------------------------------------------ part - id = "pwm2"; - desc = "AT90PWM2"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x65; -## avr910_devcode = ?; - signature = 0x1e 0x93 0x81; - pagel = 0xD8; - bs2 = 0xE2; - reset = io; - chip_erase_delay = 9000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90PWM2"; + id = "pwm2"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 167; + n_interrupts = 32; + n_boot_sections = 4; + boot_section_size = 256; + stk500_devcode = 0x65; + chip_erase_delay = 9000; + pagel = 0xd8; + bs2 = 0xe2; +# avr910_devcode = ?; + signature = 0x1e 0x93 0x81; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; + spmcr = 0x57; + eecr = 0x3f; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; + + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 64; - readsize = 256; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # AT90PWM2 has Signature Bytes: 0x1E 0x93 0x81. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--00xx.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90PWM3 @@ -10144,9 +8492,10 @@ part # Completely identical to AT90PWM2 (including the signature!) part parent "pwm2" - id = "pwm3"; - desc = "AT90PWM3"; - ; + desc = "AT90PWM3"; + id = "pwm3"; + mcuid = 169; +; #------------------------------------------------------------ # AT90PWM2B @@ -10154,12 +8503,12 @@ part parent "pwm2" # Same as AT90PWM2 but different signature. part parent "pwm2" - id = "pwm2b"; - desc = "AT90PWM2B"; - signature = 0x1e 0x93 0x83; - - ocdrev = 1; - ; + desc = "AT90PWM2B"; + id = "pwm2b"; + mcuid = 168; + signature = 0x1e 0x93 0x83; + ocdrev = 1; +; #------------------------------------------------------------ # AT90PWM3B @@ -10168,11 +8517,10 @@ part parent "pwm2" # Completely identical to AT90PWM2B (including the signature!) part parent "pwm2b" - id = "pwm3b"; - desc = "AT90PWM3B"; - - ocdrev = 1; - ; + desc = "AT90PWM3B"; + id = "pwm3b"; + mcuid = 170; +; #------------------------------------------------------------ # AT90PWM316 @@ -10181,52 +8529,24 @@ part parent "pwm2b" # Similar to AT90PWM3B, but with 16 kiB flash, 512 B EEPROM, and 1024 B SRAM. part parent "pwm3b" - id = "pwm316"; - desc = "AT90PWM316"; - signature = 0x1e 0x94 0x83; - - ocdrev = 1; + desc = "AT90PWM316"; + id = "pwm316"; + mcuid = 180; + boot_section_size = 512; + signature = 0x1e 0x94 0x83; memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x21; - delay = 6; - blocksize = 128; - readsize = 256; - ; - ; + size = 0x4000; + page_size = 128; + mode = 33; + blocksize = 128; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; +; #------------------------------------------------------------ # AT90PWM216 @@ -10234,560 +8554,405 @@ part parent "pwm3b" # Completely identical to AT90PWM316 (including the signature!) part parent "pwm316" - id = "pwm216"; - desc = "AT90PWM216"; - ; + desc = "AT90PWM216"; + id = "pwm216"; + mcuid = 179; +; #------------------------------------------------------------ # ATtiny25 #------------------------------------------------------------ part - id = "t25"; - desc = "ATtiny25"; - has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x91 0x08; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + desc = "ATtiny25"; + id = "t25"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 16; + n_interrupts = 15; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x91 0x08; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + flash_instr = 0xb4, 0x02, 0x12; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayms = 1; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; - ocdrev = 1; - - memory "eeprom" - size = 128; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; + + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # ATtiny25 has Signature Bytes: 0x1E 0x91 0x08. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny45 #------------------------------------------------------------ part - id = "t45"; - desc = "ATtiny45"; - has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x06; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + desc = "ATtiny45"; + id = "t45"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 22; + n_interrupts = 15; + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x92 0x06; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + flash_instr = 0xb4, 0x02, 0x12; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayms = 1; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - ocdrev = 1; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # ATtiny45 has Signature Bytes: 0x1E 0x92 0x08. (Data sheet 2586C-AVR-06/05 (doc2586.pdf) indicates otherwise!) - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny85 #------------------------------------------------------------ part - id = "t85"; - desc = "ATtiny85"; - has_debugwire = yes; - flash_instr = 0xB4, 0x02, 0x12; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x02, 0xB4, 0x02, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x93 0x0b; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, + desc = "ATtiny85"; + id = "t85"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 26; + n_interrupts = 15; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x93 0x0b; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + flash_instr = 0xb4, 0x02, 0x12; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayms = 1; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; + + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; - ocdrev = 1; - - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; # ATtiny85 has Signature Bytes: 0x1E 0x93 0x08. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega640 @@ -10795,380 +8960,250 @@ part # Almost same as ATmega1280, except for different memory sizes part - id = "m640"; - desc = "ATmega640"; - signature = 0x1e 0x96 0x08; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega640"; + id = "m640"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 126; + n_interrupts = 57; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x96 0x08; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 10; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega1280 #------------------------------------------------------------ part - id = "m1280"; - desc = "ATmega1280"; - signature = 0x1e 0x97 0x03; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega1280"; + id = "m1280"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 138; + n_interrupts = 57; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x97 0x03; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 10; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega1281 @@ -11176,219 +9211,148 @@ part # Identical to ATmega1280 part parent "m1280" - id = "m1281"; - desc = "ATmega1281"; - signature = 0x1e 0x97 0x04; - - ocdrev = 3; - ; + desc = "ATmega1281"; + id = "m1281"; + mcuid = 139; + signature = 0x1e 0x97 0x04; +; #------------------------------------------------------------ # ATmega2560 #------------------------------------------------------------ part - id = "m2560"; - desc = "ATmega2560"; - signature = 0x1e 0x98 0x01; - has_jtag = yes; - stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega2560"; + id = "m2560"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 143; + n_interrupts = 57; + n_boot_sections = 4; + boot_section_size = 1024; + stk500_devcode = 0xb2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x98 0x01; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 4; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 262144; - page_size = 256; - num_pages = 1024; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - load_ext_addr = " 0 1 0 0 1 1 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 a16", - " 0 0 0 0 0 0 0 0"; - - mode = 0x41; - delay = 10; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 4; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x40000; + page_size = 256; + num_pages = 1024; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 10; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + load_ext_addr = "0100.1101--0000.0000--0000.000a--0000.0000"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega2561 #------------------------------------------------------------ part parent "m2560" - id = "m2561"; - desc = "ATmega2561"; - signature = 0x1e 0x98 0x02; - - ocdrev = 4; - ; + desc = "ATmega2561"; + id = "m2561"; + mcuid = 144; + signature = 0x1e 0x98 0x02; +; #------------------------------------------------------------ # ATmega128RFA1 @@ -11396,875 +9360,572 @@ part parent "m2560" # Identical to ATmega2561 but half the ROM part parent "m2561" - id = "m128rfa1"; - desc = "ATmega128RFA1"; - signature = 0x1e 0xa7 0x01; - chip_erase_delay = 55000; - bs2 = 0xE2; - - ocdrev = 3; + desc = "ATmega128RFA1"; + id = "m128rfa1"; + mcuid = 87; + n_interrupts = 72; + chip_erase_delay = 55000; + bs2 = 0xe2; + signature = 0x1e 0xa7 0x01; + ocdrev = 3; memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 50000; - max_write_delay = 50000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 256; - readsize = 256; - ; - ; + size = 0x20000; + num_pages = 512; + min_write_delay = 50000; + max_write_delay = 50000; + delay = 20; + load_ext_addr = NULL; + ; +; #------------------------------------------------------------ # ATmega256RFR2 #------------------------------------------------------------ part parent "m2561" - id = "m256rfr2"; - desc = "ATmega256RFR2"; - signature = 0x1e 0xa8 0x02; - chip_erase_delay = 18500; - bs2 = 0xE2; + desc = "ATmega256RFR2"; + id = "m256rfr2"; + mcuid = 108; + n_interrupts = 77; + chip_erase_delay = 18500; + bs2 = 0xe2; + signature = 0x1e 0xa8 0x02; memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 8192; - min_write_delay = 13000; - max_write_delay = 13000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - - ocdrev = 4; - ; + size = 8192; + min_write_delay = 13000; + max_write_delay = 13000; + read = "1010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxa.aaaa--aaaa.aaaa--iiii.iiii"; + writepage = "1100.0010--00xa.aaaa--aaaa.a000--xxxx.xxxx"; + ; +; #------------------------------------------------------------ # ATmega128RFR2 #------------------------------------------------------------ part parent "m128rfa1" - id = "m128rfr2"; - desc = "ATmega128RFR2"; - signature = 0x1e 0xa7 0x02; - - - ocdrev = 3; - ; + desc = "ATmega128RFR2"; + id = "m128rfr2"; + mcuid = 88; + n_interrupts = 77; + signature = 0x1e 0xa7 0x02; +; #------------------------------------------------------------ # ATmega64RFR2 #------------------------------------------------------------ part parent "m128rfa1" - id = "m64rfr2"; - desc = "ATmega64RFR2"; - signature = 0x1e 0xa6 0x02; + desc = "ATmega64RFR2"; + id = "m64rfr2"; + mcuid = 78; + n_interrupts = 77; + signature = 0x1e 0xa6 0x02; - - ocdrev = 3; + memory "eeprom" + size = 2048; + min_write_delay = 13000; + max_write_delay = 13000; + read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; + ; memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 50000; - max_write_delay = 50000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 256; - readsize = 256; - ; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 13000; - max_write_delay = 13000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - - ; + size = 0x10000; + num_pages = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; +; #------------------------------------------------------------ # ATmega2564RFR2 #------------------------------------------------------------ part parent "m256rfr2" - id = "m2564rfr2"; - desc = "ATmega2564RFR2"; - signature = 0x1e 0xa8 0x03; - ; + desc = "ATmega2564RFR2"; + id = "m2564rfr2"; + mcuid = 145; + signature = 0x1e 0xa8 0x03; +; #------------------------------------------------------------ # ATmega1284RFR2 #------------------------------------------------------------ part parent "m128rfr2" - id = "m1284rfr2"; - desc = "ATmega1284RFR2"; - signature = 0x1e 0xa7 0x03; - ; + desc = "ATmega1284RFR2"; + id = "m1284rfr2"; + mcuid = 142; + signature = 0x1e 0xa7 0x03; +; #------------------------------------------------------------ # ATmega644RFR2 #------------------------------------------------------------ part parent "m64rfr2" - id = "m644rfr2"; - desc = "ATmega644RFR2"; - signature = 0x1e 0xa6 0x03; - ; + desc = "ATmega644RFR2"; + id = "m644rfr2"; + mcuid = 131; + signature = 0x1e 0xa6 0x03; +; #------------------------------------------------------------ # ATtiny24 #------------------------------------------------------------ part - id = "t24"; - desc = "ATtiny24"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x91 0x0b; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + desc = "ATtiny24"; + id = "t24"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 14; + n_interrupts = 17; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x91 0x0b; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; + flash_instr = 0xb4, 0x07, 0x17; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 128; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 2048; + page_size = 32; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - ocdrev = 1; - - memory "eeprom" - size = 128; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "x a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; + ; # ATtiny24 has Signature Bytes: 0x1E 0x91 0x0B. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny24A #------------------------------------------------------------ part parent "t24" - id = "t24a"; - desc = "ATtiny24A"; - ; + desc = "ATtiny24A"; + id = "t24a"; + mcuid = 15; +; #------------------------------------------------------------ # ATtiny44 #------------------------------------------------------------ part - id = "t44"; - desc = "ATtiny44"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x07; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + desc = "ATtiny44"; + id = "t44"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 20; + n_interrupts = 17; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x92 0x07; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; + flash_instr = 0xb4, 0x07, 0x17; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; + + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; - ocdrev = 1; - - memory "eeprom" - size = 256; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; + ; # ATtiny44 has Signature Bytes: 0x1E 0x92 0x07. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny44A #------------------------------------------------------------ part parent "t44" - id = "t44a"; - desc = "ATtiny44A"; - ; + desc = "ATtiny44A"; + id = "t44a"; + mcuid = 21; +; #------------------------------------------------------------ # ATtiny84 #------------------------------------------------------------ part - id = "t84"; - desc = "ATtiny84"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; -## no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x93 0x0c; - reset = io; - chip_erase_delay = 4500; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - hvsp_controlstack = - 0x4C, 0x0C, 0x1C, 0x2C, 0x3C, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7A, 0x6A, 0x68, 0x78, - 0x78, 0x7D, 0x6D, 0x0C, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0F; - hventerstabdelay = 100; - hvspcmdexedelay = 0; - synchcycles = 6; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 0; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - chiperasetime = 0; + desc = "ATtiny84"; + id = "t84"; + prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; + mcuid = 24; + n_interrupts = 17; +# no STK500 devcode in XML file, use the ATtiny45 one + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 4500; + signature = 0x1e 0x93 0x0c; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + hvsp_controlstack = + 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, + 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, + 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, + 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; + flash_instr = 0xb4, 0x07, 0x17; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 1; + togglevtg = 1; + poweroffdelay = 25; + resetdelayus = 70; + hvleavestabdelay = 100; + resetdelay = 25; + chiperasepolltimeout = 40; programfusepolltimeout = 25; programlockpolltimeout = 25; + synchcycles = 6; + spmcr = 0x57; + eecr = 0x3c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 64; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 32; + readsize = 256; + read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; - ocdrev = 1; - - memory "eeprom" - size = 512; - paged = no; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x a8", - "a7 a6 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " x a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 32; - readsize = 256; - ; + memory "efuse" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; + ; # ATtiny84 has Signature Bytes: 0x1E 0x93 0x0C. - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - - memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x x x x x x x i i"; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; - - memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; - ; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATtiny84A #------------------------------------------------------------ part parent "t84" - id = "t84a"; - desc = "ATtiny84A"; - ; + desc = "ATtiny84A"; + id = "t84a"; + mcuid = 25; +; #------------------------------------------------------------ # ATtiny441 #------------------------------------------------------------ part parent "t44" - id = "t441"; - desc = "ATtiny441"; - signature = 0x1e 0x92 0x15; - - memory "flash" - paged = yes; - size = 4096; - page_size = 16; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 16; - readsize = 256; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + desc = "ATtiny441"; + id = "t441"; + mcuid = 32; + n_interrupts = 30; + n_page_erase = 4; + signature = 0x1e 0x92 0x15; + + memory "flash" + page_size = 16; + num_pages = 256; + blocksize = 16; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.xaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.xaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaaa.axxx--xxxx.xxxx"; + ; + + memory "efuse" + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; ; #------------------------------------------------------------ @@ -12272,60 +9933,25 @@ part parent "t44" #------------------------------------------------------------ part parent "t84" - id = "t841"; - desc = "ATtiny841"; - signature = 0x1e 0x93 0x15; - - memory "flash" - paged = yes; - size = 8192; - page_size = 16; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x x x a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 16; - readsize = 256; - ; - - memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + desc = "ATtiny841"; + id = "t841"; + mcuid = 37; + n_interrupts = 30; + n_page_erase = 4; + signature = 0x1e 0x93 0x15; + + memory "flash" + page_size = 16; + num_pages = 512; + blocksize = 16; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.xaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.xaaa--iiii.iiii"; + writepage = "0100.1100--0000.aaaa--aaaa.axxx--xxxx.xxxx"; + ; + + memory "efuse" + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; ; #------------------------------------------------------------ @@ -12333,177 +9959,255 @@ part parent "t84" #------------------------------------------------------------ part - id = "t43u"; - desc = "ATtiny43U"; - has_debugwire = yes; - flash_instr = 0xB4, 0x07, 0x17; - eeprom_instr = 0xBB, 0xFF, 0xBB, 0xEE, 0xBB, 0xCC, 0xB2, 0x0D, - 0xBC, 0x07, 0xB4, 0x07, 0xBA, 0x0D, 0xBB, 0xBC, - 0x99, 0xE1, 0xBB, 0xAC; - stk500_devcode = 0x14; -## avr910_devcode = ?; -## Try the AT90S2313 devcode: - avr910_devcode = 0x20; - signature = 0x1e 0x92 0x0C; - reset = io; - chip_erase_delay = 1000; - - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, 0x4E, 0x5E, - 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, 0x06, 0x16, 0x46, 0x56, - 0x0A, 0x1A, 0x4A, 0x5A, 0x1E, 0x7C, 0x00, 0x01, 0x00, 0x00, - 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - hvspcmdexedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny43U"; + id = "t43u"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 19; + n_interrupts = 16; + stk500_devcode = 0x14; +# avr910_devcode = ?; +# Try the AT90S2313 devcode: + avr910_devcode = 0x20; + chip_erase_delay = 1000; + signature = 0x1e 0x92 0x0c; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, + 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb4, 0x07, 0x17; + eeprom_instr = + 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, + 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, + 0x99, 0xe1, 0xbb, 0xac; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 20; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - memory "eeprom" - size = 64; - paged = yes; - page_size = 4; - num_pages = 16; - min_write_delay = 4000; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = "1 0 1 0 0 0 0 0 0 0 0 x x x x x", - "0 0 a4 a3 a2 a1 a0 o o o o o o o o"; - - write = "1 1 0 0 0 0 0 0 0 0 0 x x x x x", - "0 0 a5 a4 a3 a2 a1 a0 i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x x", - " 0 0 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x x a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 64; - readsize = 256; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; + spmcr = 0x57; + eecr = 0x3c; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + paged = yes; + size = 64; + page_size = 4; + num_pages = 16; + min_write_delay = 4000; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 5; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxx--00aa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxx--00aa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxx--00aa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 4096; + page_size = 64; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 64; + readsize = 256; + read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; + writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; + ; + + memory "lfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; + + memory "hfuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; ; + + memory "efuse" + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; + ; + memory "lock" - size = 1; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 4500; - max_write_delay = 4500; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; + + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; + + memory "calibration" + size = 1; + read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; + ; +; + +#------------------------------------------------------------ +# ATmega16u4 +#------------------------------------------------------------ + +part + desc = "ATmega16U4"; + id = "m16u4"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 57; + n_interrupts = 43; + n_boot_sections = 4; + boot_section_size = 512; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x88; + usbpid = 0x2ff4; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; + programfusepolltimeout = 5; + programlockpolltimeout = 5; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x x x x i"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.iiii"; + ; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 4500; - max_write_delay = 4500; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--00oo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; + + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; ; memory "calibration" - size = 2; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 a0 o o o o o o o o"; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; ; ; @@ -12512,382 +10216,252 @@ part #------------------------------------------------------------ part - id = "m32u4"; - desc = "ATmega32U4"; - signature = 0x1e 0x95 0x87; - usbpid = 0x2ff4; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega32U4"; + id = "m32u4"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 65; + n_interrupts = 43; + n_boot_sections = 4; + boot_section_size = 512; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x95 0x87; + usbpid = 0x2ff4; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--1111.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90USB646 #------------------------------------------------------------ part - id = "usb646"; - desc = "AT90USB646"; - signature = 0x1e 0x96 0x82; - usbpid = 0x2ff9; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90USB646"; + id = "usb646"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 181; + n_interrupts = 38; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x96 0x82; + usbpid = 0x2ff9; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x x a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90USB647 @@ -12895,203 +10469,136 @@ part # identical to AT90USB646 part parent "usb646" - id = "usb647"; - desc = "AT90USB647"; - signature = 0x1e 0x96 0x82; - - ocdrev = 3; - ; + desc = "AT90USB647"; + id = "usb647"; + mcuid = 182; +; #------------------------------------------------------------ # AT90USB1286 #------------------------------------------------------------ part - id = "usb1286"; - desc = "AT90USB1286"; - signature = 0x1e 0x97 0x82; - usbpid = 0x2ffb; - has_jtag = yes; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xD7; - bs2 = 0xA0; - reset = dedicated; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90USB1286"; + id = "usb1286"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 184; + n_interrupts = 38; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0xB2; +# avr910_devcode = 0x43; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x97 0x82; + usbpid = 0x2ffb; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - rampz = 0x3b; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 4096; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " x x x x a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 131072; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 x x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 256; - readsize = 256; - ; + idr = 0x31; + rampz = 0x3b; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 4096; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x20000; + page_size = 256; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 256; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 x x x x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 x x x x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90USB1287 @@ -13099,1721 +10606,1236 @@ part # identical to AT90USB1286 part parent "usb1286" - id = "usb1287"; - desc = "AT90USB1287"; - signature = 0x1e 0x97 0x82; - - ocdrev = 3; - ; + desc = "AT90USB1287"; + id = "usb1287"; + mcuid = 185; +; #------------------------------------------------------------ # AT90USB162 #------------------------------------------------------------ part - id = "usb162"; - desc = "AT90USB162"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x94 0x82; - usbpid = 0x2ffa; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90USB162"; + id = "usb162"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 178; + n_interrupts = 29; + n_boot_sections = 4; + boot_section_size = 512; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc6; + signature = 0x1e 0x94 0x82; + usbpid = 0x2ffa; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + eind = 0x5c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # AT90USB82 #------------------------------------------------------------ -# Changes against AT90USB162 (beside IDs) -# memory "flash" -# size = 8192; -# num_pages = 64; part - id = "usb82"; - desc = "AT90USB82"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x93 0x82; - usbpid = 0x2ff7; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "AT90USB82"; + id = "usb82"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 174; + n_interrupts = 29; + n_boot_sections = 4; + boot_section_size = 512; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc6; + signature = 0x1e 0x93 0x82; + usbpid = 0x2ff7; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + eind = 0x5c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega32U2 #------------------------------------------------------------ -# Changes against AT90USB162 (beside IDs) -# memory "flash" -# size = 32768; -# num_pages = 256; -# memory "eeprom" -# size = 1024; -# num_pages = 256; + part - id = "m32u2"; - desc = "ATmega32U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x95 0x8a; - usbpid = 0x2ff0; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega32U2"; + id = "m32u2"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 64; + n_interrupts = 29; + n_boot_sections = 4; + boot_section_size = 512; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc6; + signature = 0x1e 0x95 0x8a; + usbpid = 0x2ff0; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - num_pages = 256; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + eind = 0x5c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 1024; + page_size = 4; + num_pages = 256; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; + #------------------------------------------------------------ # ATmega16U2 #------------------------------------------------------------ -# Changes against ATmega32U2 (beside IDs) -# memory "flash" -# size = 16384; -# num_pages = 128; -# memory "eeprom" -# size = 512; -# num_pages = 128; + part - id = "m16u2"; - desc = "ATmega16U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x94 0x89; - usbpid = 0x2fef; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega16U2"; + id = "m16u2"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 56; + n_interrupts = 29; + n_boot_sections = 4; + boot_section_size = 512; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc6; + signature = 0x1e 0x94 0x89; + usbpid = 0x2fef; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + eind = 0x5c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega8U2 #------------------------------------------------------------ -# Changes against ATmega16U2 (beside IDs) -# memory "flash" -# size = 8192; -# page_size = 64; -# blocksize = 64; part - id = "m8u2"; - desc = "ATmega8U2"; - has_jtag = no; - has_debugwire = yes; - signature = 0x1e 0x93 0x89; - usbpid = 0x2fee; - chip_erase_delay = 9000; - reset = io; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - pagel = 0xD7; - bs2 = 0xC6; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega8U2"; + id = "m8u2"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 48; + n_interrupts = 29; + n_boot_sections = 4; + boot_section_size = 512; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xc6; + signature = 0x1e 0x93 0x89; + usbpid = 0x2fee; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - ocdrev = 1; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 512; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " x x x x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - "a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - ; + spmcr = 0x57; + eecr = 0x3f; + eind = 0x5c; + ocdrev = 1; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 9000; + max_write_delay = 9000; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 8192; + page_size = 128; + num_pages = 64; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x i i i i i i i i"; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; + ; memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega165 #------------------------------------------------------------ part - id = "m165"; - desc = "ATmega165"; - signature = 0x1e 0x94 0x07; - has_jtag = yes; -# stk500_devcode = 0x??; -# avr910_devcode = 0x??; - chip_erase_delay = 9000; - reset = io; - pagel = 0xd7; - bs2 = 0xa0; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - + desc = "ATmega165"; + id = "m165"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 95; + n_interrupts = 22; + n_boot_sections = 4; + boot_section_size = 256; +# stk500_devcode = 0x??; +# avr910_devcode = 0x??; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x94 0x10; + reset = io; timeout = 200; stabdelay = 100; cmdexedelay = 25; synchloops = 32; - bytedelay = 0; pollindex = 3; pollvalue = 0x53; predelay = 1; postdelay = 1; pollmethod = 1; - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; - progmodedelay = 0; latchcycles = 6; - togglevtg = 0; - poweroffdelay = 0; - resetdelayms = 0; - resetdelayus = 0; hvleavestabdelay = 15; - chiperasepulsewidth = 0; resetdelay = 15; chiperasepolltimeout = 10; - programfusepulsewidth = 0; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - idr = 0x31; spmcr = 0x57; eecr = 0x3f; - allowfullpagebitstream = no; - ocdrev = 3; - - memory "eeprom" - paged = no; - page_size = 4; - size = 512; - num_pages = 128; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0x00; - readback_p2 = 0x00; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 0 0 x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 20; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0x00; - readback_p2 = 0x00; - read_lo = " 0 0 1 0 0 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " x x x a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 512; + page_size = 4; + num_pages = 128; + min_write_delay = 3600; + max_write_delay = 3600; + mode = 65; + delay = 20; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.00xa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.00xa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.00xa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 128; + num_pages = 128; + min_write_delay = 4500; + max_write_delay = 4500; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.xxxx--xxaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.xxxx--xxaa.aaaa--iiii.iiii"; + writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x x i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--0000.0000--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega165A #------------------------------------------------------------ part parent "m165" - id = "m165a"; - desc = "ATmega165A"; - signature = 0x1e 0x94 0x10; - ; + desc = "ATmega165A"; + id = "m165a"; + mcuid = 96; +; #------------------------------------------------------------ # ATmega165P #------------------------------------------------------------ part parent "m165" - id = "m165p"; - desc = "ATmega165P"; - signature = 0x1e 0x94 0x07; - ; + desc = "ATmega165P"; + id = "m165p"; + mcuid = 97; + signature = 0x1e 0x94 0x07; +; #------------------------------------------------------------ # ATmega165PA #------------------------------------------------------------ part parent "m165" - id = "m165pa"; - desc = "ATmega165PA"; - signature = 0x1e 0x94 0x07; - ; + desc = "ATmega165PA"; + id = "m165pa"; + mcuid = 98; + signature = 0x1e 0x94 0x07; +; #------------------------------------------------------------ # ATmega325 #------------------------------------------------------------ part - id = "m325"; - desc = "ATmega325"; - signature = 0x1e 0x95 0x05; - has_jtag = yes; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega325"; + id = "m325"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 114; + n_interrupts = 22; + n_boot_sections = 4; + boot_section_size = 512; +# stk500_devcode = 0x??; # No STK500v1 support? +# avr910_devcode = 0x??; # Try the ATmega16 one + avr910_devcode = 0x74; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x95 0x05; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 4; /* for parallel programming */ - size = 1024; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 0 0 a9 a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 32768; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--0000.0000--0000.0000"; + pgm_enable = "1010.1100--0101.0011--0000.0000--0000.0000"; + + memory "eeprom" + size = 1024; + page_size = 4; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 4; + readsize = 256; + read = "1010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.00aa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--0000.00aa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x8000; + page_size = 128; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.0000--aaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.0000--aaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--0aaa.aaaa--aaaa.aaaa--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.0000--0000.0000--iiii.iiii"; + ; memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.1000--0000.0000--iiii.iiii"; + ; memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.0100--0000.0000--1111.1iii"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1110.0000--0000.0000--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--0000.0000--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--0000.0000--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega325A #------------------------------------------------------------ part parent "m325" - id = "m325a"; - desc = "ATmega325A"; - ; + desc = "ATmega325A"; + id = "m325a"; + mcuid = 115; +; #------------------------------------------------------------ # ATmega325P #------------------------------------------------------------ part parent "m325" - id = "m325p"; - desc = "ATmega325P"; - signature = 0x1e 0x95 0x0d; - ; + desc = "ATmega325P"; + id = "m325p"; + mcuid = 116; + signature = 0x1e 0x95 0x0d; +; #------------------------------------------------------------ # ATmega325PA #------------------------------------------------------------ part parent "m325" - id = "m325pa"; - desc = "ATmega325PA"; - signature = 0x1e 0x95 0x0d; - ; + desc = "ATmega325PA"; + id = "m325pa"; + mcuid = 117; + signature = 0x1e 0x95 0x0d; +; #------------------------------------------------------------ # ATmega645 #------------------------------------------------------------ part - id = "m645"; - desc = "ATmega645"; - signature = 0x1E 0x96 0x05; - has_jtag = yes; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - pagel = 0xd7; - bs2 = 0xa0; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, - 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, - 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, - 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATmega645"; + id = "m645"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; + mcuid = 132; + n_interrupts = 22; + n_boot_sections = 4; + boot_section_size = 1024; +# stk500_devcode = 0x??; # No STK500v1 support? +# avr910_devcode = 0x??; # Try the ATmega16 one + avr910_devcode = 0x74; + chip_erase_delay = 9000; + pagel = 0xd7; + bs2 = 0xa0; + signature = 0x1e 0x96 0x05; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + hventerstabdelay = 100; + latchcycles = 5; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - idr = 0x31; - spmcr = 0x57; - allowfullpagebitstream = no; - - ocdrev = 3; - - memory "eeprom" - paged = no; /* leave this "no" */ - page_size = 8; /* for parallel programming */ - size = 2048; - min_write_delay = 9000; - max_write_delay = 9000; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 0 0 0 a10 a9 a8", - " a7 a6 a5 a4 a3 0 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 10; - blocksize = 8; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 65536; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 0 0 0 0 0", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " a15 a14 a13 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " 0 0 0 0 0 0 0 0"; - - mode = 0x41; - delay = 10; - blocksize = 128; - readsize = 256; - ; - - memory "lock" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 1 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 1 1 i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + idr = 0x31; + spmcr = 0x57; + ocdrev = 3; + chip_erase = "1010.1100--1000.0000--0000.0000--0000.0000"; + pgm_enable = "1010.1100--0101.0011--0000.0000--0000.0000"; + + memory "eeprom" + size = 2048; + page_size = 8; + min_write_delay = 9000; + max_write_delay = 9000; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 8; + readsize = 256; + read = "1010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--0000.0aaa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; + writepage = "1100.0010--0000.0aaa--aaaa.a000--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x10000; + page_size = 256; + num_pages = 256; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 10; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--0000.0000--aaaa.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--0000.0000--aaaa.aaaa--iiii.iiii"; + writepage = "0100.1100--aaaa.aaaa--aaaa.aaaa--0000.0000"; + ; memory "lfuse" - size = 1; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.0000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.0000--0000.0000--iiii.iiii"; + ; memory "hfuse" - size = 1; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "0 0 0 0 0 0 0 0 i i i i i i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.1000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.1000--0000.0000--iiii.iiii"; + ; memory "efuse" - size = 1; - - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.0000--0000.1000--0000.0000--oooo.oooo"; + write = "1010.1100--1010.0100--0000.0000--1111.1iii"; + ; - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "0 0 0 0 0 0 0 0 1 1 1 1 1 i i i"; - min_write_delay = 9000; - max_write_delay = 9000; - ; + memory "lock" + size = 1; + min_write_delay = 9000; + max_write_delay = 9000; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1110.0000--0000.0000--11ii.iiii"; + ; memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 a1 a0 o o o o o o o o"; - ; + size = 3; + read = "0011.0000--0000.0000--0000.00aa--oooo.oooo"; + ; memory "calibration" - size = 1; - - read = "0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - ; + size = 1; + read = "0011.1000--0000.0000--0000.0000--oooo.oooo"; + ; +; #------------------------------------------------------------ # ATmega645A #------------------------------------------------------------ part parent "m645" - id = "m645a"; - desc = "ATmega645A"; - ; + desc = "ATmega645A"; + id = "m645a"; + mcuid = 133; +; #------------------------------------------------------------ # ATmega645P #------------------------------------------------------------ part parent "m645" - id = "m645p"; - desc = "ATmega645P"; - signature = 0x1e 0x96 0x0d; - ; + desc = "ATmega645P"; + id = "m645p"; + mcuid = 134; + signature = 0x1e 0x96 0x0d; +; #------------------------------------------------------------ # ATmega3250 #------------------------------------------------------------ part parent "m325" - id = "m3250"; - desc = "ATmega3250"; - signature = 0x1E 0x95 0x06; - ; + desc = "ATmega3250"; + id = "m3250"; + mcuid = 146; + n_interrupts = 25; + signature = 0x1e 0x95 0x06; +; #------------------------------------------------------------ # ATmega3250A #------------------------------------------------------------ part parent "m325" - id = "m3250a"; - desc = "ATmega3250A"; - signature = 0x1E 0x95 0x06; - ; + desc = "ATmega3250A"; + id = "m3250a"; + mcuid = 147; + n_interrupts = 25; + signature = 0x1e 0x95 0x06; +; #------------------------------------------------------------ # ATmega3250P #------------------------------------------------------------ part parent "m325" - id = "m3250p"; - desc = "ATmega3250P"; - signature = 0x1E 0x95 0x0e; - ; + desc = "ATmega3250P"; + id = "m3250p"; + mcuid = 148; + n_interrupts = 25; + signature = 0x1e 0x95 0x0e; +; #------------------------------------------------------------ # ATmega3250PA #------------------------------------------------------------ part parent "m325" - id = "m3250pa"; - desc = "ATmega3250PA"; - signature = 0x1E 0x95 0x0e; - ; + desc = "ATmega3250PA"; + id = "m3250pa"; + mcuid = 149; + n_interrupts = 25; + signature = 0x1e 0x95 0x0e; +; #------------------------------------------------------------ # ATmega6450 #------------------------------------------------------------ part parent "m645" - id = "m6450"; - desc = "ATmega6450"; - signature = 0x1E 0x96 0x06; - ; + desc = "ATmega6450"; + id = "m6450"; + mcuid = 154; + n_interrupts = 25; + signature = 0x1e 0x96 0x06; +; #------------------------------------------------------------ # ATmega6450A #------------------------------------------------------------ part parent "m645" - id = "m6450a"; - desc = "ATmega6450A"; - signature = 0x1E 0x96 0x06; - ; + desc = "ATmega6450A"; + id = "m6450a"; + mcuid = 155; + n_interrupts = 25; + signature = 0x1e 0x96 0x06; +; #------------------------------------------------------------ # ATmega6450P #------------------------------------------------------------ part parent "m645" - id = "m6450p"; - desc = "ATmega6450P"; - signature = 0x1E 0x96 0x0e; - ; + desc = "ATmega6450P"; + id = "m6450p"; + mcuid = 156; + n_interrupts = 25; + signature = 0x1e 0x96 0x0e; +; #------------------------------------------------------------ # AVR XMEGA family common values #------------------------------------------------------------ part - id = ".xmega"; - desc = "AVR XMEGA family common values"; - has_pdi = yes; - nvm_base = 0x01c0; - mcu_base = 0x0090; - - memory "signature" - size = 3; - offset = 0x1000090; - ; - - memory "prodsig" - size = 0x32; - offset = 0x8e0200; - page_size = 0x32; - readsize = 0x32; - ; + desc = "AVR XMEGA family common values"; + id = ".xmega"; + prog_modes = PM_SPM | PM_PDI; + n_boot_sections = 1; + mcu_base = 0x0090; + nvm_base = 0x01c0; + autobaud_sync = 0x20; memory "fuse1" - size = 1; - offset = 0x8f0021; + size = 1; + offset = 0x8f0021; ; memory "fuse2" - size = 1; - offset = 0x8f0022; + size = 1; + offset = 0x8f0022; ; memory "fuse4" - size = 1; - offset = 0x8f0024; + size = 1; + offset = 0x8f0024; ; memory "fuse5" - size = 1; - offset = 0x8f0025; + size = 1; + offset = 0x8f0025; ; memory "lock" - size = 1; - offset = 0x8f0027; + size = 1; + offset = 0x8f0027; + ; + + memory "signature" + size = 3; + offset = 0x1000090; + ; + + memory "prodsig" + size = 50; + page_size = 50; + offset = 0x8e0200; + readsize = 50; ; memory "data" # SRAM, only used to supply the offset - offset = 0x1000000; + offset = 0x1000000; ; ; @@ -14822,51 +11844,54 @@ part #------------------------------------------------------------ part parent ".xmega" - id = "x16a4u"; - desc = "ATxmega16A4U"; - signature = 0x1e 0x94 0x41; - usbpid = 0x2fe3; + desc = "ATxmega16A4U"; + id = "x16a4u"; + mcuid = 232; + n_interrupts = 127; + boot_section_size = 4096; + signature = 0x1e 0x94 0x41; + usbpid = 0x2fe3; memory "eeprom" - size = 0x400; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 1024; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x5000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x4000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x4000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x803000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x803000; + readsize = 256; ; memory "boot" - size = 0x1000; - offset = 0x804000; - page_size = 0x100; - readsize = 0x100; - ; - - memory "flash" - size = 0x5000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x804000; + readsize = 256; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + size = 256; + page_size = 256; + offset = 0x8e0400; + readsize = 256; ; ; @@ -14875,9 +11900,10 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x16a4u" - id = "x16c4"; - desc = "ATxmega16C4"; - signature = 0x1e 0x94 0x43; + desc = "ATxmega16C4"; + id = "x16c4"; + mcuid = 233; + signature = 0x1e 0x94 0x43; ; #------------------------------------------------------------ @@ -14885,9 +11911,11 @@ part parent "x16a4u" #------------------------------------------------------------ part parent "x16a4u" - id = "x16d4"; - desc = "ATxmega16D4"; - signature = 0x1e 0x94 0x42; + desc = "ATxmega16D4"; + id = "x16d4"; + mcuid = 234; + n_interrupts = 91; + signature = 0x1e 0x94 0x42; ; #------------------------------------------------------------ @@ -14895,14 +11923,14 @@ part parent "x16a4u" #------------------------------------------------------------ part parent "x16a4u" - id = "x16a4"; - desc = "ATxmega16A4"; - signature = 0x1e 0x94 0x41; - has_jtag = yes; + desc = "ATxmega16A4"; + id = "x16a4"; + mcuid = 231; + n_interrupts = 94; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -14911,51 +11939,54 @@ part parent "x16a4u" #------------------------------------------------------------ part parent ".xmega" - id = "x32a4u"; - desc = "ATxmega32A4U"; - signature = 0x1e 0x95 0x41; - usbpid = 0x2fe4; + desc = "ATxmega32A4U"; + id = "x32a4u"; + mcuid = 239; + n_interrupts = 127; + boot_section_size = 4096; + signature = 0x1e 0x95 0x41; + usbpid = 0x2fe4; memory "eeprom" - size = 0x400; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 1024; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x9000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x8000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x8000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x807000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x807000; + readsize = 256; ; memory "boot" - size = 0x1000; - offset = 0x808000; - page_size = 0x100; - readsize = 0x100; - ; - - memory "flash" - size = 0x9000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x808000; + readsize = 256; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + size = 256; + page_size = 256; + offset = 0x8e0400; + readsize = 256; ; ; @@ -14964,9 +11995,10 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x32a4u" - id = "x32c4"; - desc = "ATxmega32C4"; - signature = 0x1e 0x95 0x44; + desc = "ATxmega32C4"; + id = "x32c4"; + mcuid = 240; + signature = 0x1e 0x95 0x44; ; #------------------------------------------------------------ @@ -14974,9 +12006,11 @@ part parent "x32a4u" #------------------------------------------------------------ part parent "x32a4u" - id = "x32d4"; - desc = "ATxmega32D4"; - signature = 0x1e 0x95 0x42; + desc = "ATxmega32D4"; + id = "x32d4"; + mcuid = 241; + n_interrupts = 91; + signature = 0x1e 0x95 0x42; ; #------------------------------------------------------------ @@ -14984,14 +12018,14 @@ part parent "x32a4u" #------------------------------------------------------------ part parent "x32a4u" - id = "x32a4"; - desc = "ATxmega32A4"; - signature = 0x1e 0x95 0x41; - has_jtag = yes; + desc = "ATxmega32A4"; + id = "x32a4"; + mcuid = 238; + n_interrupts = 94; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -15000,51 +12034,54 @@ part parent "x32a4u" #------------------------------------------------------------ part parent ".xmega" - id = "x64a4u"; - desc = "ATxmega64A4U"; - signature = 0x1e 0x96 0x46; - usbpid = 0x2fe5; + desc = "ATxmega64A4U"; + id = "x64a4u"; + mcuid = 252; + n_interrupts = 127; + boot_section_size = 4096; + signature = 0x1e 0x96 0x46; + usbpid = 0x2fe5; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x11000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x10000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x10000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x80f000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x80f000; + readsize = 256; ; memory "boot" - size = 0x1000; - offset = 0x810000; - page_size = 0x100; - readsize = 0x100; - ; - - memory "flash" - size = 0x11000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x810000; + readsize = 256; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + size = 256; + page_size = 256; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15053,10 +12090,11 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x64a4u" - id = "x64c3"; - desc = "ATxmega64C3"; - signature = 0x1e 0x96 0x49; - usbpid = 0x2fd6; + desc = "ATxmega64C3"; + id = "x64c3"; + mcuid = 249; + signature = 0x1e 0x96 0x49; + usbpid = 0x2fd6; ; #------------------------------------------------------------ @@ -15064,9 +12102,11 @@ part parent "x64a4u" #------------------------------------------------------------ part parent "x64a4u" - id = "x64d3"; - desc = "ATxmega64D3"; - signature = 0x1e 0x96 0x4a; + desc = "ATxmega64D3"; + id = "x64d3"; + mcuid = 250; + n_interrupts = 114; + signature = 0x1e 0x96 0x4a; ; #------------------------------------------------------------ @@ -15074,9 +12114,11 @@ part parent "x64a4u" #------------------------------------------------------------ part parent "x64a4u" - id = "x64d4"; - desc = "ATxmega64D4"; - signature = 0x1e 0x96 0x47; + desc = "ATxmega64D4"; + id = "x64d4"; + mcuid = 253; + n_interrupts = 91; + signature = 0x1e 0x96 0x47; ; #------------------------------------------------------------ @@ -15084,14 +12126,16 @@ part parent "x64a4u" #------------------------------------------------------------ part parent "x64a4u" - id = "x64a1"; - desc = "ATxmega64A1"; - signature = 0x1e 0x96 0x4e; - has_jtag = yes; + desc = "ATxmega64A1"; + id = "x64a1"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 243; + n_interrupts = 125; + signature = 0x1e 0x96 0x4e; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -15100,10 +12144,11 @@ part parent "x64a4u" #------------------------------------------------------------ part parent "x64a1" - id = "x64a1u"; - desc = "ATxmega64A1U"; - signature = 0x1e 0x96 0x4e; - usbpid = 0x2fe8; + desc = "ATxmega64A1U"; + id = "x64a1u"; + mcuid = 244; + n_interrupts = 127; + usbpid = 0x2fe8; ; #------------------------------------------------------------ @@ -15111,9 +12156,11 @@ part parent "x64a1" #------------------------------------------------------------ part parent "x64a1" - id = "x64a3"; - desc = "ATxmega64A3"; - signature = 0x1e 0x96 0x42; + desc = "ATxmega64A3"; + id = "x64a3"; + mcuid = 246; + n_interrupts = 122; + signature = 0x1e 0x96 0x42; ; #------------------------------------------------------------ @@ -15121,10 +12168,11 @@ part parent "x64a1" #------------------------------------------------------------ part parent "x64a1" - id = "x64a3u"; - desc = "ATxmega64A3U"; - signature = 0x1e 0x96 0x42; - usbpid = 0x2fe5; + desc = "ATxmega64A3U"; + id = "x64a3u"; + mcuid = 247; + n_interrupts = 127; + signature = 0x1e 0x96 0x42; ; #------------------------------------------------------------ @@ -15132,9 +12180,10 @@ part parent "x64a1" #------------------------------------------------------------ part parent "x64a1" - id = "x64a4"; - desc = "ATxmega64A4"; - signature = 0x1e 0x96 0x46; + desc = "ATxmega64A4"; + id = "x64a4"; + mcuid = 251; + signature = 0x1e 0x96 0x46; ; #------------------------------------------------------------ @@ -15142,10 +12191,12 @@ part parent "x64a1" #------------------------------------------------------------ part parent "x64a1" - id = "x64b1"; - desc = "ATxmega64B1"; - signature = 0x1e 0x96 0x52; - usbpid = 0x2fe1; + desc = "ATxmega64B1"; + id = "x64b1"; + mcuid = 245; + n_interrupts = 81; + signature = 0x1e 0x96 0x52; + usbpid = 0x2fe1; ; #------------------------------------------------------------ @@ -15153,10 +12204,12 @@ part parent "x64a1" #------------------------------------------------------------ part parent "x64a1" - id = "x64b3"; - desc = "ATxmega64B3"; - signature = 0x1e 0x96 0x51; - usbpid = 0x2fdf; + desc = "ATxmega64B3"; + id = "x64b3"; + mcuid = 248; + n_interrupts = 54; + signature = 0x1e 0x96 0x51; + usbpid = 0x2fdf; ; #------------------------------------------------------------ @@ -15164,51 +12217,54 @@ part parent "x64a1" #------------------------------------------------------------ part parent ".xmega" - id = "x128c3"; - desc = "ATxmega128C3"; - signature = 0x1e 0x97 0x52; - usbpid = 0x2fd7; + desc = "ATxmega128C3"; + id = "x128c3"; + mcuid = 261; + n_interrupts = 127; + boot_section_size = 8192; + signature = 0x1e 0x97 0x52; + usbpid = 0x2fd7; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x22000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x2000; - offset = 0x81e000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x81e000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x200; - readsize = 0x100; - ; - - memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x820000; + readsize = 256; ; memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + size = 512; + page_size = 512; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15217,9 +12273,11 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x128c3" - id = "x128d3"; - desc = "ATxmega128D3"; - signature = 0x1e 0x97 0x48; + desc = "ATxmega128D3"; + id = "x128d3"; + mcuid = 262; + n_interrupts = 114; + signature = 0x1e 0x97 0x48; ; #------------------------------------------------------------ @@ -15227,15 +12285,14 @@ part parent "x128c3" #------------------------------------------------------------ part parent "x128c3" - id = "x128d4"; - desc = "ATxmega128D4"; - signature = 0x1e 0x97 0x47; + desc = "ATxmega128D4"; + id = "x128d4"; + mcuid = 265; + n_interrupts = 91; + signature = 0x1e 0x97 0x47; memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + page_size = 256; ; ; @@ -15244,14 +12301,16 @@ part parent "x128c3" #------------------------------------------------------------ part parent "x128c3" - id = "x128a1"; - desc = "ATxmega128A1"; - signature = 0x1e 0x97 0x4c; - has_jtag = yes; + desc = "ATxmega128A1"; + id = "x128a1"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 254; + n_interrupts = 125; + signature = 0x1e 0x97 0x4c; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -15260,9 +12319,10 @@ part parent "x128c3" #------------------------------------------------------------ part parent "x128a1" - id = "x128a1d"; - desc = "ATxmega128A1revD"; - signature = 0x1e 0x97 0x41; + desc = "ATxmega128A1revD"; + id = "x128a1d"; + mcuid = 255; + signature = 0x1e 0x97 0x41; ; #------------------------------------------------------------ @@ -15270,10 +12330,11 @@ part parent "x128a1" #------------------------------------------------------------ part parent "x128a1" - id = "x128a1u"; - desc = "ATxmega128A1U"; - signature = 0x1e 0x97 0x4c; - usbpid = 0x2fed; + desc = "ATxmega128A1U"; + id = "x128a1u"; + mcuid = 256; + n_interrupts = 127; + usbpid = 0x2fed; ; #------------------------------------------------------------ @@ -15281,9 +12342,11 @@ part parent "x128a1" #------------------------------------------------------------ part parent "x128a1" - id = "x128a3"; - desc = "ATxmega128A3"; - signature = 0x1e 0x97 0x42; + desc = "ATxmega128A3"; + id = "x128a3"; + mcuid = 258; + n_interrupts = 122; + signature = 0x1e 0x97 0x42; ; #------------------------------------------------------------ @@ -15291,10 +12354,12 @@ part parent "x128a1" #------------------------------------------------------------ part parent "x128a1" - id = "x128a3u"; - desc = "ATxmega128A3U"; - signature = 0x1e 0x97 0x42; - usbpid = 0x2fe6; + desc = "ATxmega128A3U"; + id = "x128a3u"; + mcuid = 259; + n_interrupts = 127; + signature = 0x1e 0x97 0x42; + usbpid = 0x2fe6; ; #------------------------------------------------------------ @@ -15302,56 +12367,57 @@ part parent "x128a1" #------------------------------------------------------------ part parent ".xmega" - id = "x128a4"; - desc = "ATxmega128A4"; - signature = 0x1e 0x97 0x46; - has_jtag = yes; + desc = "ATxmega128A4"; + id = "x128a4"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 263; + signature = 0x1e 0x97 0x46; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x22000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x81f000; - page_size = 0x200; - readsize = 0x100; + size = 4096; + page_size = 512; + offset = 0x81f000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x820000; + readsize = 256; ; - memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "fuse0" + size = 1; + offset = 0x8f0020; ; memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; - ; - - memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 512; + page_size = 512; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15360,51 +12426,54 @@ part parent ".xmega" #------------------------------------------------------------ part parent ".xmega" - id = "x128a4u"; - desc = "ATxmega128A4U"; - signature = 0x1e 0x97 0x46; - usbpid = 0x2fde; + desc = "ATxmega128A4U"; + id = "x128a4u"; + mcuid = 264; + n_interrupts = 127; + boot_section_size = 8192; + signature = 0x1e 0x97 0x46; + usbpid = 0x2fde; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x22000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x20000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x81f000; - page_size = 0x100; - readsize = 0x100; + size = 4096; + page_size = 256; + offset = 0x81f000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x100; - readsize = 0x100; - ; - - memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 8192; + page_size = 256; + offset = 0x820000; + readsize = 256; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; + size = 256; + page_size = 256; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15413,57 +12482,60 @@ part parent ".xmega" #------------------------------------------------------------ part parent ".xmega" - id = "x128b1"; - desc = "ATxmega128B1"; - signature = 0x1e 0x97 0x4d; - usbpid = 0x2fea; - has_jtag = yes; + desc = "ATxmega128B1"; + id = "x128b1"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 257; + n_interrupts = 81; + boot_section_size = 8192; + signature = 0x1e 0x97 0x4d; + usbpid = 0x2fea; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x22000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x20000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + size = 0x20000; + page_size = 256; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x2000; - offset = 0x81e000; - page_size = 0x100; - readsize = 0x100; + size = 8192; + page_size = 256; + offset = 0x81e000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x820000; - page_size = 0x100; - readsize = 0x100; + size = 8192; + page_size = 256; + offset = 0x820000; + readsize = 256; ; - memory "flash" - size = 0x22000; - offset = 0x800000; - page_size = 0x100; - readsize = 0x100; + memory "fuse0" + size = 1; + offset = 0x8f0020; ; memory "usersig" - size = 0x100; - offset = 0x8e0400; - page_size = 0x100; - readsize = 0x100; - ; - - memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 256; + page_size = 256; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15472,10 +12544,12 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x128b1" - id = "x128b3"; - desc = "ATxmega128B3"; - signature = 0x1e 0x97 0x4b; - usbpid = 0x2fe0; + desc = "ATxmega128B3"; + id = "x128b3"; + mcuid = 260; + n_interrupts = 54; + signature = 0x1e 0x97 0x4b; + usbpid = 0x2fe0; ; #------------------------------------------------------------ @@ -15483,51 +12557,54 @@ part parent "x128b1" #------------------------------------------------------------ part parent ".xmega" - id = "x192c3"; - desc = "ATxmega192C3"; - signature = 0x1e 0x97 0x51; - # usbpid = 0x2f??; + desc = "ATxmega192C3"; + id = "x192c3"; + mcuid = 269; + n_interrupts = 127; + boot_section_size = 8192; + signature = 0x1e 0x97 0x51; +# usbpid = 0x2f??; memory "eeprom" - size = 0x800; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 2048; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x32000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x30000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x30000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x2000; - offset = 0x82e000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x82e000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x830000; - page_size = 0x200; - readsize = 0x100; - ; - - memory "flash" - size = 0x32000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x830000; + readsize = 256; ; memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + size = 512; + page_size = 512; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15536,9 +12613,11 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x192c3" - id = "x192d3"; - desc = "ATxmega192D3"; - signature = 0x1e 0x97 0x49; + desc = "ATxmega192D3"; + id = "x192d3"; + mcuid = 270; + n_interrupts = 114; + signature = 0x1e 0x97 0x49; ; #------------------------------------------------------------ @@ -15546,14 +12625,15 @@ part parent "x192c3" #------------------------------------------------------------ part parent "x192c3" - id = "x192a1"; - desc = "ATxmega192A1"; - signature = 0x1e 0x97 0x4e; - has_jtag = yes; + desc = "ATxmega192A1"; + id = "x192a1"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 266; + signature = 0x1e 0x97 0x4e; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -15562,9 +12642,11 @@ part parent "x192c3" #------------------------------------------------------------ part parent "x192a1" - id = "x192a3"; - desc = "ATxmega192A3"; - signature = 0x1e 0x97 0x44; + desc = "ATxmega192A3"; + id = "x192a3"; + mcuid = 267; + n_interrupts = 122; + signature = 0x1e 0x97 0x44; ; #------------------------------------------------------------ @@ -15572,10 +12654,11 @@ part parent "x192a1" #------------------------------------------------------------ part parent "x192a1" - id = "x192a3u"; - desc = "ATxmega192A3U"; - signature = 0x1e 0x97 0x44; - usbpid = 0x2fe7; + desc = "ATxmega192A3U"; + id = "x192a3u"; + mcuid = 268; + signature = 0x1e 0x97 0x44; + usbpid = 0x2fe7; ; #------------------------------------------------------------ @@ -15583,51 +12666,54 @@ part parent "x192a1" #------------------------------------------------------------ part parent ".xmega" - id = "x256c3"; - desc = "ATxmega256C3"; - signature = 0x1e 0x98 0x46; - usbpid = 0x2fda; + desc = "ATxmega256C3"; + id = "x256c3"; + mcuid = 276; + n_interrupts = 127; + boot_section_size = 8192; + signature = 0x1e 0x98 0x46; + usbpid = 0x2fda; memory "eeprom" - size = 0x1000; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 4096; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x42000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x40000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x40000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x2000; - offset = 0x83e000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x83e000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x840000; - page_size = 0x200; - readsize = 0x100; - ; - - memory "flash" - size = 0x42000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x840000; + readsize = 256; ; memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + size = 512; + page_size = 512; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15636,9 +12722,11 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x256c3" - id = "x256d3"; - desc = "ATxmega256D3"; - signature = 0x1e 0x98 0x44; + desc = "ATxmega256D3"; + id = "x256d3"; + mcuid = 277; + n_interrupts = 114; + signature = 0x1e 0x98 0x44; ; #------------------------------------------------------------ @@ -15646,14 +12734,14 @@ part parent "x256c3" #------------------------------------------------------------ part parent "x256c3" - id = "x256a1"; - desc = "ATxmega256A1"; - signature = 0x1e 0x98 0x46; - has_jtag = yes; + desc = "ATxmega256A1"; + id = "x256a1"; + prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; + mcuid = 271; memory "fuse0" - size = 1; - offset = 0x8f0020; + size = 1; + offset = 0x8f0020; ; ; @@ -15662,9 +12750,11 @@ part parent "x256c3" #------------------------------------------------------------ part parent "x256a1" - id = "x256a3"; - desc = "ATxmega256A3"; - signature = 0x1e 0x98 0x42; + desc = "ATxmega256A3"; + id = "x256a3"; + mcuid = 272; + n_interrupts = 122; + signature = 0x1e 0x98 0x42; ; #------------------------------------------------------------ @@ -15672,10 +12762,11 @@ part parent "x256a1" #------------------------------------------------------------ part parent "x256a1" - id = "x256a3u"; - desc = "ATxmega256A3U"; - signature = 0x1e 0x98 0x42; - usbpid = 0x2fec; + desc = "ATxmega256A3U"; + id = "x256a3u"; + mcuid = 275; + signature = 0x1e 0x98 0x42; + usbpid = 0x2fec; ; #------------------------------------------------------------ @@ -15683,9 +12774,11 @@ part parent "x256a1" #------------------------------------------------------------ part parent "x256a1" - id = "x256a3b"; - desc = "ATxmega256A3B"; - signature = 0x1e 0x98 0x43; + desc = "ATxmega256A3B"; + id = "x256a3b"; + mcuid = 273; + n_interrupts = 122; + signature = 0x1e 0x98 0x43; ; #------------------------------------------------------------ @@ -15693,10 +12786,11 @@ part parent "x256a1" #------------------------------------------------------------ part parent "x256a1" - id = "x256a3bu"; - desc = "ATxmega256A3BU"; - signature = 0x1e 0x98 0x43; - usbpid = 0x2fe2; + desc = "ATxmega256A3BU"; + id = "x256a3bu"; + mcuid = 274; + signature = 0x1e 0x98 0x43; + usbpid = 0x2fe2; ; #------------------------------------------------------------ @@ -15704,51 +12798,54 @@ part parent "x256a1" #------------------------------------------------------------ part parent ".xmega" - id = "x384c3"; - desc = "ATxmega384C3"; - signature = 0x1e 0x98 0x45; - usbpid = 0x2fdb; + desc = "ATxmega384C3"; + id = "x384c3"; + mcuid = 278; + n_interrupts = 127; + boot_section_size = 8192; + signature = 0x1e 0x98 0x45; + usbpid = 0x2fdb; memory "eeprom" - size = 0x1000; - offset = 0x8c0000; - page_size = 0x20; - readsize = 0x100; + size = 4096; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x62000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x60000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 0x60000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x2000; - offset = 0x85e000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x85e000; + readsize = 256; ; memory "boot" - size = 0x2000; - offset = 0x860000; - page_size = 0x200; - readsize = 0x100; - ; - - memory "flash" - size = 0x62000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + size = 8192; + page_size = 512; + offset = 0x860000; + readsize = 256; ; memory "usersig" - size = 0x200; - offset = 0x8e0400; - page_size = 0x200; - readsize = 0x100; + size = 512; + page_size = 512; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15757,9 +12854,11 @@ part parent ".xmega" #------------------------------------------------------------ part parent "x384c3" - id = "x384d3"; - desc = "ATxmega384D3"; - signature = 0x1e 0x98 0x47; + desc = "ATxmega384D3"; + id = "x384d3"; + mcuid = 279; + n_interrupts = 114; + signature = 0x1e 0x98 0x47; ; #------------------------------------------------------------ @@ -15767,50 +12866,53 @@ part parent "x384c3" #------------------------------------------------------------ part parent ".xmega" - id = "x8e5"; - desc = "ATxmega8E5"; - signature = 0x1e 0x93 0x41; + desc = "ATxmega8E5"; + id = "x8e5"; + mcuid = 230; + n_interrupts = 43; + boot_section_size = 2048; + signature = 0x1e 0x93 0x41; memory "eeprom" - size = 0x0200; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + size = 512; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x2800; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x2000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 8192; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x800; - offset = 0x00801800; - page_size = 0x80; - readsize = 0x100; + size = 2048; + page_size = 128; + offset = 0x801800; + readsize = 256; ; memory "boot" - size = 0x800; - offset = 0x00802000; - page_size = 0x80; - readsize = 0x100; - ; - - memory "flash" - size = 0x2800; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 2048; + page_size = 128; + offset = 0x802000; + readsize = 256; ; memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + size = 128; + page_size = 128; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15819,50 +12921,53 @@ part parent ".xmega" #------------------------------------------------------------ part parent ".xmega" - id = "x16e5"; - desc = "ATxmega16E5"; - signature = 0x1e 0x94 0x45; + desc = "ATxmega16E5"; + id = "x16e5"; + mcuid = 235; + n_interrupts = 43; + boot_section_size = 4096; + signature = 0x1e 0x94 0x45; memory "eeprom" - size = 0x0200; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + size = 512; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x5000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x4000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 0x4000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x00803000; - page_size = 0x80; - readsize = 0x100; + size = 4096; + page_size = 128; + offset = 0x803000; + readsize = 256; ; memory "boot" - size = 0x1000; - offset = 0x00804000; - page_size = 0x80; - readsize = 0x100; - ; - - memory "flash" - size = 0x5000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 4096; + page_size = 128; + offset = 0x804000; + readsize = 256; ; memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + size = 128; + page_size = 128; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15871,50 +12976,53 @@ part parent ".xmega" #------------------------------------------------------------ part parent ".xmega" - id = "x32e5"; - desc = "ATxmega32E5"; - signature = 0x1e 0x95 0x4c; + desc = "ATxmega32E5"; + id = "x32e5"; + mcuid = 242; + n_interrupts = 43; + boot_section_size = 4096; + signature = 0x1e 0x95 0x4c; memory "eeprom" - size = 0x0400; - offset = 0x08c0000; - page_size = 0x20; - readsize = 0x100; + size = 1024; + page_size = 32; + offset = 0x8c0000; + readsize = 256; + ; + + memory "flash" + size = 0x9000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "application" - size = 0x8000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 0x8000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; memory "apptable" - size = 0x1000; - offset = 0x00807000; - page_size = 0x80; - readsize = 0x100; + size = 4096; + page_size = 128; + offset = 0x807000; + readsize = 256; ; memory "boot" - size = 0x1000; - offset = 0x00808000; - page_size = 0x80; - readsize = 0x100; - ; - - memory "flash" - size = 0x9000; - offset = 0x0800000; - page_size = 0x80; - readsize = 0x100; + size = 4096; + page_size = 128; + offset = 0x808000; + readsize = 256; ; memory "usersig" - size = 0x80; - offset = 0x8e0400; - page_size = 0x80; - readsize = 0x100; + size = 128; + page_size = 128; + offset = 0x8e0400; + readsize = 256; ; ; @@ -15923,25 +13031,28 @@ part parent ".xmega" #------------------------------------------------------------ part - id = "uc3a0512"; - desc = "AT32UC3A0512"; - signature = 0xED 0xC0 0x3F; - has_jtag = yes; - is_avr32 = yes; + desc = "AT32UC3A0512"; + id = "uc3a0512"; + prog_modes = PM_AVR32JTAG | PM_aWire; + signature = 0xed 0xc0 0x3f; memory "flash" - paged = yes; - page_size = 512; # bytes - readsize = 512; # bytes - num_pages = 1024; # could be set dynamicly - size = 0x00080000; # could be set dynamicly - offset = 0x80000000; + paged = yes; + size = 0x80000; # could be set dynamicly + page_size = 512; # bytes + num_pages = 1024; # could be set dynamicly + offset = 0x80000000; + readsize = 512; # bytes ; ; +#------------------------------------------------------------ +# deprecated, use 'uc3a0512' +#------------------------------------------------------------ + part parent "uc3a0512" - id = "ucr2"; - desc = "deprecated, use 'uc3a0512'"; + desc = "deprecated, use 'uc3a0512'"; + id = "ucr2"; ; #------------------------------------------------------------ @@ -15949,188 +13060,128 @@ part parent "uc3a0512" #------------------------------------------------------------ part - id = "t1634"; - desc = "ATtiny1634"; - has_debugwire = yes; - flash_instr = 0xB6, 0x01, 0x11; - eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, - 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, - 0x99, 0xF9, 0xBB, 0xAF; - stk500_devcode = 0x86; - # avr910_devcode = 0x; - signature = 0x1e 0x94 0x12; - pagel = 0xB3; - bs2 = 0xB1; - reset = io; - chip_erase_delay = 9000; - pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", - "x x x x x x x x x x x x x x x x"; - - chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", - "x x x x x x x x x x x x x x x x"; - - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - bytedelay = 0; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - - pp_controlstack = - 0x0E, 0x1E, 0x0E, 0x1E, 0x2E, 0x3E, 0x2E, 0x3E, - 0x4E, 0x5E, 0x4E, 0x5E, 0x6E, 0x7E, 0x6E, 0x7E, - 0x26, 0x36, 0x66, 0x76, 0x2A, 0x3A, 0x6A, 0x7A, - 0x2E, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 0; - latchcycles = 0; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - resetdelayus = 0; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 0; - chiperasepolltimeout = 10; - programfusepulsewidth = 0; + desc = "ATtiny1634"; + id = "t1634"; + prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; + mcuid = 40; + n_interrupts = 28; + n_page_erase = 4; + stk500_devcode = 0x86; + chip_erase_delay = 9000; + pagel = 0xb3; + bs2 = 0xb1; +# avr910_devcode = 0x??; + signature = 0x1e 0x94 0x12; + reset = io; + timeout = 200; + stabdelay = 100; + cmdexedelay = 25; + synchloops = 32; + pollindex = 3; + pollvalue = 0x53; + predelay = 1; + postdelay = 1; + pollmethod = 1; + pp_controlstack = + 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, + 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, + 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, + 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + flash_instr = 0xb6, 0x01, 0x11; + eeprom_instr = + 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, + 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, + 0x99, 0xf9, 0xbb, 0xaf; + hventerstabdelay = 100; + togglevtg = 1; + poweroffdelay = 15; + resetdelayms = 1; + hvleavestabdelay = 15; + resetdelay = 15; + chiperasepolltimeout = 10; programfusepolltimeout = 5; - programlockpulsewidth = 0; programlockpolltimeout = 5; - - memory "eeprom" - paged = no; - page_size = 4; - size = 256; - min_write_delay = 3600; - max_write_delay = 3600; - readback_p1 = 0xff; - readback_p2 = 0xff; - read = " 1 0 1 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - write = " 1 1 0 0 0 0 0 0", - " 0 0 0 x x x x a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_lo = " 1 1 0 0 0 0 0 1", - " 0 0 0 0 0 0 0 0", - " 0 0 0 0 0 0 a1 a0", - " i i i i i i i i"; - - writepage = " 1 1 0 0 0 0 1 0", - " 0 0 x x x x x a8", - " a7 a6 a5 a4 a3 a2 0 0", - " x x x x x x x x"; - - mode = 0x41; - delay = 5; - blocksize = 4; - readsize = 256; - ; - - memory "flash" - paged = yes; - size = 16384; - page_size = 32; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback_p1 = 0xff; - readback_p2 = 0xff; - read_lo = " 0 0 1 0 0 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - read_hi = " 0 0 1 0 1 0 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 a5 a4 a3 a2 a1 a0", - " o o o o o o o o"; - - loadpage_lo = " 0 1 0 0 0 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - loadpage_hi = " 0 1 0 0 1 0 0 0", - " 0 0 0 x x x x x", - " x x a5 a4 a3 a2 a1 a0", - " i i i i i i i i"; - - writepage = " 0 1 0 0 1 1 0 0", - " 0 0 0 a12 a11 a10 a9 a8", - " a7 a6 x x x x x x", - " x x x x x x x x"; - - mode = 0x41; - delay = 6; - blocksize = 128; - readsize = 256; - - ; + spmcr = 0x57; + eecr = 0x3c; + chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; + pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; + + memory "eeprom" + size = 256; + page_size = 4; + min_write_delay = 3600; + max_write_delay = 3600; + readback = 0xff 0xff; + mode = 65; + delay = 5; + blocksize = 4; + readsize = 256; + read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; + write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; + loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; + writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; + ; + + memory "flash" + paged = yes; + size = 0x4000; + page_size = 32; + num_pages = 512; + min_write_delay = 4500; + max_write_delay = 4500; + readback = 0xff 0xff; + mode = 65; + delay = 6; + blocksize = 128; + readsize = 256; + read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; + loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; + writepage = "0100.1100--00aa.aaaa--aaaa.xxxx--xxxx.xxxx"; + ; memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; + ; memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", - "x x x x x x x x i i i i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; + ; memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", - "x x x x x x x x o o o o o o o o"; - - write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", - "x x x x x x x x x x x i i i i i"; - ; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--1010.0100--xxxx.xxxx--xxxi.iiii"; + ; memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", - "x x x x x x x x o o o o o o o o"; + size = 1; + min_write_delay = 4500; + max_write_delay = 4500; + read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; + write = "1010.1100--111x.xxxx--xxxx.xxxx--1111.11ii"; + ; - write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", - "x x x x x x x x 1 1 1 1 1 1 i i"; - ; + memory "signature" + size = 3; + read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; + ; memory "calibration" - size = 1; - read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", - "0 0 0 0 0 0 0 0 o o o o o o o o"; - ; - - memory "signature" - size = 3; - read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", - "x x x x x x a1 a0 o o o o o o o o"; - ; + size = 1; + read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; + ; ; #------------------------------------------------------------ @@ -16138,42 +13189,43 @@ part #------------------------------------------------------------ part parent "t1634" - id = "t1634r"; - desc = "ATtiny1634R"; - ; + desc = "ATtiny1634R"; + id = "t1634r"; + mcuid = 41; +; #------------------------------------------------------------ # Common values for reduced core tinys (4/5/9/10/20/40) #------------------------------------------------------------ part - id = ".reduced_core_tiny"; - desc = "Common values for reduced core tinys"; - has_tpi = yes; + desc = "Common values for reduced core tinys"; + id = ".reduced_core_tiny"; + prog_modes = PM_TPI; - memory "signature" - size = 3; - offset = 0x3fc0; - page_size = 16; + memory "fuse" + size = 1; + page_size = 16; + offset = 0x3f40; + blocksize = 4; ; - memory "fuse" - size = 1; - offset = 0x3f40; - page_size = 16; - blocksize = 4; + memory "lockbits" + size = 1; + page_size = 16; + offset = 0x3f00; ; - memory "calibration" - size = 1; - offset = 0x3f80; - page_size = 16; + memory "signature" + size = 3; + page_size = 16; + offset = 0x3fc0; ; - memory "lockbits" - size = 1; - offset = 0x3f00; - page_size = 16; + memory "calibration" + size = 1; + page_size = 16; + offset = 0x3f80; ; ; @@ -16182,15 +13234,17 @@ part #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t4"; - desc = "ATtiny4"; - signature = 0x1e 0x8f 0x0a; + desc = "ATtiny4"; + id = "t4"; + mcuid = 0; + n_interrupts = 10; + signature = 0x1e 0x8f 0x0a; memory "flash" - size = 512; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 512; + page_size = 16; + offset = 0x4000; + blocksize = 128; ; ; @@ -16199,9 +13253,11 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part parent "t4" - id = "t5"; - desc = "ATtiny5"; - signature = 0x1e 0x8f 0x09; + desc = "ATtiny5"; + id = "t5"; + mcuid = 1; + n_interrupts = 11; + signature = 0x1e 0x8f 0x09; ; #------------------------------------------------------------ @@ -16209,15 +13265,17 @@ part parent "t4" #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t9"; - desc = "ATtiny9"; - signature = 0x1e 0x90 0x08; + desc = "ATtiny9"; + id = "t9"; + mcuid = 2; + n_interrupts = 10; + signature = 0x1e 0x90 0x08; memory "flash" - size = 1024; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 1024; + page_size = 16; + offset = 0x4000; + blocksize = 128; ; ; @@ -16226,9 +13284,11 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part parent "t9" - id = "t10"; - desc = "ATtiny10"; - signature = 0x1e 0x90 0x03; + desc = "ATtiny10"; + id = "t10"; + mcuid = 3; + n_interrupts = 11; + signature = 0x1e 0x90 0x03; ; #------------------------------------------------------------ @@ -16236,15 +13296,22 @@ part parent "t9" #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t20"; - desc = "ATtiny20"; - signature = 0x1e 0x91 0x0F; + desc = "ATtiny20"; + id = "t20"; + mcuid = 4; + n_interrupts = 17; + signature = 0x1e 0x91 0x0f; memory "flash" - size = 2048; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 2048; + page_size = 16; + n_word_writes = 2; + offset = 0x4000; + blocksize = 128; + ; + + memory "fuse" + n_word_writes = 2; ; ; @@ -16253,15 +13320,22 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t40"; - desc = "ATtiny40"; - signature = 0x1e 0x92 0x0E; + desc = "ATtiny40"; + id = "t40"; + mcuid = 5; + n_interrupts = 18; + signature = 0x1e 0x92 0x0e; memory "flash" - size = 4096; - offset = 0x4000; - page_size = 64; - blocksize = 128; + size = 4096; + page_size = 64; + n_word_writes = 4; + offset = 0x4000; + blocksize = 128; + ; + + memory "fuse" + n_word_writes = 4; ; ; @@ -16270,15 +13344,23 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t102"; - desc = "ATtiny102"; - signature = 0x1e 0x90 0x0C; + desc = "ATtiny102"; + id = "t102"; + mcuid = 6; + n_interrupts = 16; + signature = 0x1e 0x90 0x0c; memory "flash" - size = 1024; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 1024; + page_size = 16; + offset = 0x4000; + blocksize = 128; + ; + + memory "sigrow" + size = 16; + page_size = 16; + offset = 0x3fc6; ; ; @@ -16287,15 +13369,23 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part parent ".reduced_core_tiny" - id = "t104"; - desc = "ATtiny104"; - signature = 0x1e 0x90 0x0B; + desc = "ATtiny104"; + id = "t104"; + mcuid = 7; + n_interrupts = 16; + signature = 0x1e 0x90 0x0b; memory "flash" - size = 1024; - offset = 0x4000; - page_size = 16; - blocksize = 128; + size = 1024; + page_size = 16; + offset = 0x4000; + blocksize = 128; + ; + + memory "sigrow" + size = 16; + page_size = 16; + offset = 0x3fc6; ; ; @@ -16304,63 +13394,60 @@ part parent ".reduced_core_tiny" #------------------------------------------------------------ part - id = "m406"; - desc = "ATmega406"; - has_jtag = yes; - signature = 0x1e 0x95 0x07; - + desc = "ATmega406"; + id = "m406"; + prog_modes = PM_SPM | PM_HVPP | PM_JTAG; + mcuid = 125; + n_interrupts = 23; + n_boot_sections = 4; + boot_section_size = 512; # STK500 parameters (parallel programming IO lines) - pagel = 0xa7; - bs2 = 0xa0; - serial = no; - parallel = yes; - + pagel = 0xa7; + bs2 = 0xa0; + signature = 0x1e 0x95 0x07; + reset = io; + serial = no; # STK500v2 HV programming parameters, from XML - pp_controlstack = 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - - # JTAG ICE mkII parameters, also from XML files - allowfullpagebitstream = no; - enablepageprogramming = yes; - idr = 0x51; - rampz = 0x00; - spmcr = 0x57; - eecr = 0x3f; + pp_controlstack = + 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, + 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, + 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, + 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; + idr = 0x51; + spmcr = 0x57; + eecr = 0x3f; memory "eeprom" - paged = no; - size = 512; - page_size = 4; - blocksize = 4; - readsize = 4; - num_pages = 128; + size = 512; + page_size = 4; + num_pages = 128; + blocksize = 4; + readsize = 4; ; memory "flash" - paged = yes; - size = 40960; - page_size = 128; - blocksize = 128; - readsize = 128; - num_pages = 320; + paged = yes; + size = 0xa000; + page_size = 128; + num_pages = 320; + blocksize = 128; + readsize = 128; ; - memory "hfuse" - size = 1; + memory "lfuse" + size = 1; ; - memory "lfuse" - size = 1; + memory "hfuse" + size = 1; ; memory "lockbits" - size = 1; + size = 1; ; memory "signature" - size = 3; + size = 3; ; ; @@ -16369,72 +13456,17 @@ part #------------------------------------------------------------ part - id = ".avr8x"; - desc = "AVR8X family common values"; - has_updi = yes; - nvm_base = 0x1000; - ocd_base = 0x0F80; - - memory "signature" - size = 3; - offset = 0x1100; - readsize = 0x3; - ; - - memory "prodsig" - size = 0x3D; - offset = 0x1103; - page_size = 0x3D; - readsize = 0x3D; - ; - - memory "sernum" - size = 10; - offset = 0x1104; - readsize = 1; - ; - - memory "osccal16" - size = 2; - offset = 0x1118; - readsize = 1; - ; - - memory "osccal20" - size = 2; - offset = 0x111A; - readsize = 1; - ; - - memory "tempsense" - size = 2; - offset = 0x1120; - readsize = 1; - ; - - memory "osc16err" - size = 2; - offset = 0x1122; - readsize = 1; - ; - - memory "osc20err" - size = 2; - offset = 0x1124; - readsize = 1; - ; - - memory "fuses" - size = 9; - offset = 0x1280; - page_size = 0x0A; - readsize = 0x0A; - ; + desc = "AVR8X family common values"; + id = ".avr8x"; + prog_modes = PM_SPM | PM_UPDI; + n_boot_sections = 1; + nvm_base = 0x1000; + ocd_base = 0x0f80; memory "fuse0" - size = 1; - offset = 0x1280; - readsize = 1; + size = 1; + offset = 0x1280; + readsize = 1; ; memory "wdtcfg" @@ -16442,9 +13474,9 @@ part ; memory "fuse1" - size = 1; - offset = 0x1281; - readsize = 1; + size = 1; + offset = 0x1281; + readsize = 1; ; memory "bodcfg" @@ -16452,9 +13484,9 @@ part ; memory "fuse2" - size = 1; - offset = 0x1282; - readsize = 1; + size = 1; + offset = 0x1282; + readsize = 1; ; memory "osccfg" @@ -16462,9 +13494,9 @@ part ; memory "fuse4" - size = 1; - offset = 0x1284; - readsize = 1; + size = 1; + offset = 0x1284; + readsize = 1; ; memory "tcd0cfg" @@ -16472,9 +13504,9 @@ part ; memory "fuse5" - size = 1; - offset = 0x1285; - readsize = 1; + size = 1; + offset = 0x1285; + readsize = 1; ; memory "syscfg0" @@ -16482,9 +13514,9 @@ part ; memory "fuse6" - size = 1; - offset = 0x1286; - readsize = 1; + size = 1; + offset = 0x1286; + readsize = 1; ; memory "syscfg1" @@ -16492,9 +13524,9 @@ part ; memory "fuse7" - size = 1; - offset = 0x1287; - readsize = 1; + size = 1; + offset = 0x1287; + readsize = 1; ; memory "append" @@ -16506,9 +13538,9 @@ part ; memory "fuse8" - size = 1; - offset = 0x1288; - readsize = 1; + size = 1; + offset = 0x1288; + readsize = 1; ; memory "bootend" @@ -16519,15 +13551,71 @@ part alias "fuse8"; ; + memory "fuses" + size = 9; + page_size = 10; + offset = 0x1280; + readsize = 10; + ; + memory "lock" - size = 1; - offset = 0x128a; - readsize = 1; + size = 1; + offset = 0x128a; + readsize = 1; + ; + + memory "tempsense" + size = 2; + offset = 0x1120; + readsize = 1; + ; + + memory "signature" + size = 3; + offset = 0x1100; + readsize = 3; + ; + + memory "prodsig" + size = 61; + page_size = 61; + offset = 0x1103; + readsize = 61; + ; + + memory "sernum" + size = 10; + offset = 0x1104; + readsize = 1; + ; + + memory "osccal16" + size = 2; + offset = 0x1118; + readsize = 1; + ; + + memory "osccal20" + size = 2; + offset = 0x111a; + readsize = 1; + ; + + memory "osc16err" + size = 2; + offset = 0x1122; + readsize = 1; + ; + + memory "osc20err" + size = 2; + offset = 0x1124; + readsize = 1; ; memory "data" # SRAM, only used to supply the offset - offset = 0x1000000; + offset = 0x1000000; ; ; @@ -16535,16 +13623,18 @@ part # AVR8X tiny family common values #------------------------------------------------------------ -part parent ".avr8x" - id = ".avr8x_tiny"; - desc = "AVR8X tiny family common values"; - family_id = "tinyAVR"; +part parent ".avr8x" + desc = "AVR8X tiny family common values"; + id = ".avr8x_tiny"; + family_id = "tinyAVR"; + # Shared UPDI pin, HV on UPDI pin + hvupdi_variant = 0; memory "userrow" - size = 0x20; - offset = 0x1300; - page_size = 0x20; - readsize = 0x100; + size = 32; + page_size = 32; + offset = 0x1300; + readsize = 256; ; memory "usersig" @@ -16556,16 +13646,18 @@ part parent ".avr8x" # AVR8X mega family common values #------------------------------------------------------------ -part parent ".avr8x" - id = ".avr8x_mega"; - desc = "AVR8X mega family common values"; - family_id = "megaAVR"; +part parent ".avr8x" + desc = "AVR8X mega family common values"; + id = ".avr8x_mega"; + family_id = "megaAVR"; + # Dedicated UPDI pin, no HV + hvupdi_variant = 1; memory "userrow" - size = 0x40; - offset = 0x1300; - page_size = 0x40; - readsize = 0x100; + size = 64; + page_size = 64; + offset = 0x1300; + readsize = 256; ; memory "usersig" @@ -16577,23 +13669,25 @@ part parent ".avr8x" # ATtiny202 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t202"; - desc = "ATtiny202"; - signature = 0x1E 0x91 0x23; +part parent ".avr8x_tiny" + desc = "ATtiny202"; + id = "t202"; + mcuid = 280; + n_interrupts = 26; + signature = 0x1e 0x91 0x23; - memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 64; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x40; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 2048; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16601,23 +13695,25 @@ part parent ".avr8x_tiny" # ATtiny204 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t204"; - desc = "ATtiny204"; - signature = 0x1E 0x91 0x22; +part parent ".avr8x_tiny" + desc = "ATtiny204"; + id = "t204"; + mcuid = 281; + n_interrupts = 26; + signature = 0x1e 0x91 0x22; - memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 64; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x40; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 2048; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16625,23 +13721,25 @@ part parent ".avr8x_tiny" # ATtiny402 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t402"; - desc = "ATtiny402"; - signature = 0x1E 0x92 0x27; +part parent ".avr8x_tiny" + desc = "ATtiny402"; + id = "t402"; + mcuid = 284; + n_interrupts = 26; + signature = 0x1e 0x92 0x27; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16649,23 +13747,25 @@ part parent ".avr8x_tiny" # ATtiny404 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t404"; - desc = "ATtiny404"; - signature = 0x1E 0x92 0x26; +part parent ".avr8x_tiny" + desc = "ATtiny404"; + id = "t404"; + mcuid = 285; + n_interrupts = 26; + signature = 0x1e 0x92 0x26; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16673,23 +13773,25 @@ part parent ".avr8x_tiny" # ATtiny406 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t406"; - desc = "ATtiny406"; - signature = 0x1E 0x92 0x25; +part parent ".avr8x_tiny" + desc = "ATtiny406"; + id = "t406"; + mcuid = 286; + n_interrupts = 26; + signature = 0x1e 0x92 0x25; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16697,23 +13799,25 @@ part parent ".avr8x_tiny" # ATtiny804 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t804"; - desc = "ATtiny804"; - signature = 0x1E 0x93 0x25; +part parent ".avr8x_tiny" + desc = "ATtiny804"; + id = "t804"; + mcuid = 295; + n_interrupts = 31; + signature = 0x1e 0x93 0x25; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16721,23 +13825,25 @@ part parent ".avr8x_tiny" # ATtiny806 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t806"; - desc = "ATtiny806"; - signature = 0x1E 0x93 0x24; +part parent ".avr8x_tiny" + desc = "ATtiny806"; + id = "t806"; + mcuid = 296; + n_interrupts = 31; + signature = 0x1e 0x93 0x24; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16745,23 +13851,25 @@ part parent ".avr8x_tiny" # ATtiny807 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t807"; - desc = "ATtiny807"; - signature = 0x1E 0x93 0x23; +part parent ".avr8x_tiny" + desc = "ATtiny807"; + id = "t807"; + mcuid = 297; + n_interrupts = 31; + signature = 0x1e 0x93 0x23; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16769,23 +13877,25 @@ part parent ".avr8x_tiny" # ATtiny1604 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1604"; - desc = "ATtiny1604"; - signature = 0x1E 0x94 0x25; +part parent ".avr8x_tiny" + desc = "ATtiny1604"; + id = "t1604"; + mcuid = 304; + n_interrupts = 31; + signature = 0x1e 0x94 0x25; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16793,23 +13903,25 @@ part parent ".avr8x_tiny" # ATtiny1606 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1606"; - desc = "ATtiny1606"; - signature = 0x1E 0x94 0x24; +part parent ".avr8x_tiny" + desc = "ATtiny1606"; + id = "t1606"; + mcuid = 305; + n_interrupts = 31; + signature = 0x1e 0x94 0x24; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16817,23 +13929,25 @@ part parent ".avr8x_tiny" # ATtiny1607 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1607"; - desc = "ATtiny1607"; - signature = 0x1E 0x94 0x23; +part parent ".avr8x_tiny" + desc = "ATtiny1607"; + id = "t1607"; + mcuid = 306; + n_interrupts = 31; + signature = 0x1e 0x94 0x23; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16841,23 +13955,25 @@ part parent ".avr8x_tiny" # ATtiny212 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t212"; - desc = "ATtiny212"; - signature = 0x1E 0x91 0x21; +part parent ".avr8x_tiny" + desc = "ATtiny212"; + id = "t212"; + mcuid = 282; + n_interrupts = 26; + signature = 0x1e 0x91 0x21; - memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 64; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x40; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 2048; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16865,23 +13981,25 @@ part parent ".avr8x_tiny" # ATtiny214 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t214"; - desc = "ATtiny214"; - signature = 0x1E 0x91 0x20; +part parent ".avr8x_tiny" + desc = "ATtiny214"; + id = "t214"; + mcuid = 283; + n_interrupts = 26; + signature = 0x1e 0x91 0x20; - memory "flash" - size = 0x800; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 64; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x40; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 2048; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16889,48 +14007,51 @@ part parent ".avr8x_tiny" # ATtiny412 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t412"; - desc = "ATtiny412"; - signature = 0x1E 0x92 0x23; +part parent ".avr8x_tiny" + desc = "ATtiny412"; + id = "t412"; + mcuid = 287; + n_interrupts = 26; + signature = 0x1e 0x92 0x23; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; - #------------------------------------------------------------ # ATtiny414 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t414"; - desc = "ATtiny414"; - signature = 0x1E 0x92 0x22; +part parent ".avr8x_tiny" + desc = "ATtiny414"; + id = "t414"; + mcuid = 288; + n_interrupts = 26; + signature = 0x1e 0x92 0x22; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -16938,98 +14059,103 @@ part parent ".avr8x_tiny" # ATtiny416 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t416"; - desc = "ATtiny416"; - signature = 0x1E 0x92 0x21; +part parent ".avr8x_tiny" + desc = "ATtiny416"; + id = "t416"; + mcuid = 289; + n_interrupts = 26; + signature = 0x1e 0x92 0x21; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; - #------------------------------------------------------------ # ATtiny417 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t417"; - desc = "ATtiny417"; - signature = 0x1E 0x92 0x20; +part parent ".avr8x_tiny" + desc = "ATtiny417"; + id = "t417"; + mcuid = 291; + n_interrupts = 26; + signature = 0x1e 0x92 0x20; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; - #------------------------------------------------------------ # ATtiny814 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t814"; - desc = "ATtiny814"; - signature = 0x1E 0x93 0x22; +part parent ".avr8x_tiny" + desc = "ATtiny814"; + id = "t814"; + mcuid = 298; + n_interrupts = 26; + signature = 0x1e 0x93 0x22; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; - #------------------------------------------------------------ # ATtiny816 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t816"; - desc = "ATtiny816"; - signature = 0x1E 0x93 0x21; +part parent ".avr8x_tiny" + desc = "ATtiny816"; + id = "t816"; + mcuid = 299; + n_interrupts = 26; + signature = 0x1e 0x93 0x21; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17037,23 +14163,25 @@ part parent ".avr8x_tiny" # ATtiny817 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t817"; - desc = "ATtiny817"; - signature = 0x1E 0x93 0x20; +part parent ".avr8x_tiny" + desc = "ATtiny817"; + id = "t817"; + mcuid = 300; + n_interrupts = 26; + signature = 0x1e 0x93 0x20; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17061,23 +14189,25 @@ part parent ".avr8x_tiny" # ATtiny1614 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1614"; - desc = "ATtiny1614"; - signature = 0x1E 0x94 0x22; +part parent ".avr8x_tiny" + desc = "ATtiny1614"; + id = "t1614"; + mcuid = 307; + n_interrupts = 31; + signature = 0x1e 0x94 0x22; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17085,23 +14215,25 @@ part parent ".avr8x_tiny" # ATtiny1616 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1616"; - desc = "ATtiny1616"; - signature = 0x1E 0x94 0x21; +part parent ".avr8x_tiny" + desc = "ATtiny1616"; + id = "t1616"; + mcuid = 308; + n_interrupts = 31; + signature = 0x1e 0x94 0x21; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17109,23 +14241,25 @@ part parent ".avr8x_tiny" # ATtiny1617 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1617"; - desc = "ATtiny1617"; - signature = 0x1E 0x94 0x20; +part parent ".avr8x_tiny" + desc = "ATtiny1617"; + id = "t1617"; + mcuid = 309; + n_interrupts = 31; + signature = 0x1e 0x94 0x20; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17133,23 +14267,34 @@ part parent ".avr8x_tiny" # ATtiny3216 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3216"; - desc = "ATtiny3216"; - signature = 0x1E 0x95 0x21; +part parent ".avr8x_tiny" + desc = "ATtiny3216"; + id = "t3216"; + mcuid = 314; + n_interrupts = 31; + signature = 0x1e 0x95 0x21; + + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; + ; memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; - readsize = 0x100; + size = 0x8000; + page_size = 128; + offset = 0x8000; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "userrow" + size = 64; + page_size = 64; + ; + + memory "usersig" + alias "userrow"; ; ; @@ -17157,47 +14302,36 @@ part parent ".avr8x_tiny" # ATtiny3217 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3217"; - desc = "ATtiny3217"; - signature = 0x1E 0x95 0x22; - - memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; - readsize = 0x100; - ; - - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; - ; +part parent "t3216" + desc = "ATtiny3217"; + id = "t3217"; + mcuid = 315; + signature = 0x1e 0x95 0x22; ; #------------------------------------------------------------ # ATtiny424 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t424"; - desc = "ATtiny424"; - signature = 0x1E 0x92 0x2C; +part parent ".avr8x_tiny" + desc = "ATtiny424"; + id = "t424"; + mcuid = 292; + n_interrupts = 30; + signature = 0x1e 0x92 0x2c; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17205,23 +14339,25 @@ part parent ".avr8x_tiny" # ATtiny426 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t426"; - desc = "ATtiny426"; - signature = 0x1E 0x92 0x2B; +part parent ".avr8x_tiny" + desc = "ATtiny426"; + id = "t426"; + mcuid = 293; + n_interrupts = 30; + signature = 0x1e 0x92 0x2b; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17229,23 +14365,25 @@ part parent ".avr8x_tiny" # ATtiny427 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t427"; - desc = "ATtiny427"; - signature = 0x1E 0x92 0x2A; +part parent ".avr8x_tiny" + desc = "ATtiny427"; + id = "t427"; + mcuid = 294; + n_interrupts = 30; + signature = 0x1e 0x92 0x2a; - memory "flash" - size = 0x1000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 4096; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17253,23 +14391,25 @@ part parent ".avr8x_tiny" # ATtiny824 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t824"; - desc = "ATtiny824"; - signature = 0x1E 0x93 0x29; +part parent ".avr8x_tiny" + desc = "ATtiny824"; + id = "t824"; + mcuid = 301; + n_interrupts = 30; + signature = 0x1e 0x93 0x29; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17277,23 +14417,25 @@ part parent ".avr8x_tiny" # ATtiny826 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t826"; - desc = "ATtiny826"; - signature = 0x1E 0x93 0x28; +part parent ".avr8x_tiny" + desc = "ATtiny826"; + id = "t826"; + mcuid = 302; + n_interrupts = 30; + signature = 0x1e 0x93 0x28; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17301,23 +14443,25 @@ part parent ".avr8x_tiny" # ATtiny827 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t827"; - desc = "ATtiny827"; - signature = 0x1E 0x93 0x27; +part parent ".avr8x_tiny" + desc = "ATtiny827"; + id = "t827"; + mcuid = 303; + n_interrupts = 30; + signature = 0x1e 0x93 0x27; - memory "flash" - size = 0x2000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 128; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x80; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17325,46 +14469,51 @@ part parent ".avr8x_tiny" # ATtiny1624 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1624"; - desc = "ATtiny1624"; - signature = 0x1E 0x94 0x2A; +part parent ".avr8x_tiny" + desc = "ATtiny1624"; + id = "t1624"; + mcuid = 310; + n_interrupts = 30; + signature = 0x1e 0x94 0x2a; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; + #------------------------------------------------------------ # ATtiny1626 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1626"; - desc = "ATtiny1626"; - signature = 0x1E 0x94 0x29; +part parent ".avr8x_tiny" + desc = "ATtiny1626"; + id = "t1626"; + mcuid = 311; + n_interrupts = 30; + signature = 0x1e 0x94 0x29; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17372,23 +14521,25 @@ part parent ".avr8x_tiny" # ATtiny1627 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t1627"; - desc = "ATtiny1627"; - signature = 0x1E 0x94 0x28; +part parent ".avr8x_tiny" + desc = "ATtiny1627"; + id = "t1627"; + mcuid = 312; + n_interrupts = 30; + signature = 0x1e 0x94 0x28; - memory "flash" - size = 0x4000; - offset = 0x8000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x8000; + readsize = 256; ; ; @@ -17396,23 +14547,25 @@ part parent ".avr8x_tiny" # ATtiny3224 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3224"; - desc = "ATtiny3224"; - signature = 0x1E 0x95 0x28; +part parent ".avr8x_tiny" + desc = "ATtiny3224"; + id = "t3224"; + mcuid = 316; + n_interrupts = 30; + signature = 0x1e 0x95 0x28; - memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 128; + offset = 0x8000; + readsize = 256; ; ; @@ -17420,23 +14573,25 @@ part parent ".avr8x_tiny" # ATtiny3226 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3226"; - desc = "ATtiny3226"; - signature = 0x1E 0x95 0x27; +part parent ".avr8x_tiny" + desc = "ATtiny3226"; + id = "t3226"; + mcuid = 317; + n_interrupts = 30; + signature = 0x1e 0x95 0x27; - memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 128; + offset = 0x8000; + readsize = 256; ; ; @@ -17444,23 +14599,25 @@ part parent ".avr8x_tiny" # ATtiny3227 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "t3227"; - desc = "ATtiny3227"; - signature = 0x1E 0x95 0x26; +part parent ".avr8x_tiny" + desc = "ATtiny3227"; + id = "t3227"; + mcuid = 318; + n_interrupts = 30; + signature = 0x1e 0x95 0x26; - memory "flash" - size = 0x8000; - offset = 0x8000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 128; + offset = 0x8000; + readsize = 256; ; ; @@ -17468,23 +14625,25 @@ part parent ".avr8x_tiny" # ATmega808 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m808"; - desc = "ATmega808"; - signature = 0x1E 0x93 0x26; +part parent ".avr8x_tiny" + desc = "ATmega808"; + id = "m808"; + mcuid = 319; + n_interrupts = 36; + signature = 0x1e 0x93 0x26; - memory "flash" - size = 0x2000; - offset = 0x4000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x4000; + readsize = 256; ; ; @@ -17492,23 +14651,25 @@ part parent ".avr8x_tiny" # ATmega809 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m809"; - desc = "ATmega809"; - signature = 0x1E 0x93 0x2A; +part parent ".avr8x_tiny" + desc = "ATmega809"; + id = "m809"; + mcuid = 320; + n_interrupts = 40; + signature = 0x1e 0x93 0x2a; - memory "flash" - size = 0x2000; - offset = 0x4000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x4000; + readsize = 256; ; ; @@ -17516,23 +14677,25 @@ part parent ".avr8x_tiny" # ATmega1608 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m1608"; - desc = "ATmega1608"; - signature = 0x1E 0x94 0x27; +part parent ".avr8x_tiny" + desc = "ATmega1608"; + id = "m1608"; + mcuid = 321; + n_interrupts = 36; + signature = 0x1e 0x94 0x27; - memory "flash" - size = 0x4000; - offset = 0x4000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x4000; + readsize = 256; ; ; @@ -17540,23 +14703,25 @@ part parent ".avr8x_tiny" # ATmega1609 #------------------------------------------------------------ -part parent ".avr8x_tiny" - id = "m1609"; - desc = "ATmega1609"; - signature = 0x1E 0x94 0x26; +part parent ".avr8x_tiny" + desc = "ATmega1609"; + id = "m1609"; + mcuid = 322; + n_interrupts = 40; + signature = 0x1e 0x94 0x26; - memory "flash" - size = 0x4000; - offset = 0x4000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 32; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x20; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x4000; + readsize = 256; ; ; @@ -17564,23 +14729,25 @@ part parent ".avr8x_tiny" # ATmega3208 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m3208"; - desc = "ATmega3208"; - signature = 0x1E 0x95 0x30; +part parent ".avr8x_mega" + desc = "ATmega3208"; + id = "m3208"; + mcuid = 323; + n_interrupts = 36; + signature = 0x1e 0x95 0x30; - memory "flash" - size = 0x8000; - offset = 0x4000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 128; + offset = 0x4000; + readsize = 256; ; ; @@ -17588,23 +14755,25 @@ part parent ".avr8x_mega" # ATmega3209 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m3209"; - desc = "ATmega3209"; - signature = 0x1E 0x95 0x31; +part parent ".avr8x_mega" + desc = "ATmega3209"; + id = "m3209"; + mcuid = 324; + n_interrupts = 40; + signature = 0x1e 0x95 0x31; - memory "flash" - size = 0x8000; - offset = 0x4000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 128; + offset = 0x4000; + readsize = 256; ; ; @@ -17612,23 +14781,25 @@ part parent ".avr8x_mega" # ATmega4808 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m4808"; - desc = "ATmega4808"; - signature = 0x1E 0x96 0x50; +part parent ".avr8x_mega" + desc = "ATmega4808"; + id = "m4808"; + mcuid = 325; + n_interrupts = 36; + signature = 0x1e 0x96 0x50; - memory "flash" - size = 0xC000; - offset = 0x4000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0xc000; + page_size = 128; + offset = 0x4000; + readsize = 256; ; ; @@ -17636,23 +14807,25 @@ part parent ".avr8x_mega" # ATmega4809 #------------------------------------------------------------ -part parent ".avr8x_mega" - id = "m4809"; - desc = "ATmega4809"; - signature = 0x1E 0x96 0x51; +part parent ".avr8x_mega" + desc = "ATmega4809"; + id = "m4809"; + mcuid = 326; + n_interrupts = 40; + signature = 0x1e 0x96 0x51; - memory "flash" - size = 0xC000; - offset = 0x4000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 256; + page_size = 64; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x40; - readsize = 0x100; + memory "flash" + size = 0xc000; + page_size = 128; + offset = 0x4000; + readsize = 256; ; ; @@ -17661,48 +14834,20 @@ part parent ".avr8x_mega" #------------------------------------------------------------ part - id = ".avrdx"; - desc = "AVR-Dx family common values"; - has_updi = yes; - nvm_base = 0x1000; - ocd_base = 0x0F80; - - memory "signature" - size = 3; - offset = 0x1100; - readsize = 0x3; - ; - - memory "prodsig" - size = 0x7D; - offset = 0x1103; - page_size = 0x7D; - readsize = 0x7D; - ; - - memory "tempsense" - size = 2; - offset = 0x1104; - readsize = 1; - ; - - memory "sernum" - size = 16; - offset = 0x1110; - readsize = 1; - ; - - memory "fuses" - size = 9; - offset = 0x1050; - page_size = 0x10; - readsize = 0x10; - ; + desc = "AVR-Dx family common values"; + id = ".avrdx"; + family_id = "AVR "; + prog_modes = PM_SPM | PM_UPDI; + n_boot_sections = 1; + # Dedicated UPDI pin, no HV + hvupdi_variant = 1; + nvm_base = 0x1000; + ocd_base = 0x0f80; memory "fuse0" - size = 1; - offset = 0x1050; - readsize = 1; + size = 1; + offset = 0x1050; + readsize = 1; ; memory "wdtcfg" @@ -17710,9 +14855,9 @@ part ; memory "fuse1" - size = 1; - offset = 0x1051; - readsize = 1; + size = 1; + offset = 0x1051; + readsize = 1; ; memory "bodcfg" @@ -17720,9 +14865,9 @@ part ; memory "fuse2" - size = 1; - offset = 0x1052; - readsize = 1; + size = 1; + offset = 0x1052; + readsize = 1; ; memory "osccfg" @@ -17730,9 +14875,9 @@ part ; memory "fuse4" - size = 1; - offset = 0x1054; - readsize = 1; + size = 1; + offset = 0x1054; + readsize = 1; ; memory "tcd0cfg" @@ -17740,9 +14885,9 @@ part ; memory "fuse5" - size = 1; - offset = 0x1055; - readsize = 1; + size = 1; + offset = 0x1055; + readsize = 1; ; memory "syscfg0" @@ -17750,9 +14895,9 @@ part ; memory "fuse6" - size = 1; - offset = 0x1056; - readsize = 1; + size = 1; + offset = 0x1056; + readsize = 1; ; memory "syscfg1" @@ -17760,9 +14905,9 @@ part ; memory "fuse7" - size = 1; - offset = 0x1057; - readsize = 1; + size = 1; + offset = 0x1057; + readsize = 1; ; memory "codesize" @@ -17774,9 +14919,9 @@ part ; memory "fuse8" - size = 1; - offset = 0x1058; - readsize = 1; + size = 1; + offset = 0x1058; + readsize = 1; ; memory "bootsize" @@ -17787,18 +14932,49 @@ part alias "fuse8"; ; + memory "fuses" + size = 9; + page_size = 16; + offset = 0x1050; + readsize = 16; + ; + memory "lock" - size = 4; - offset = 0x1040; - page_size = 0x1; - readsize = 0x4; + size = 4; + offset = 0x1040; + readsize = 4; + ; + + memory "tempsense" + size = 2; + offset = 0x1104; + readsize = 1; + ; + + memory "signature" + size = 3; + offset = 0x1100; + readsize = 3; + ; + + memory "prodsig" + size = 125; + page_size = 125; + offset = 0x1103; + readsize = 125; + ; + + memory "sernum" + size = 16; + offset = 0x1110; + readsize = 1; ; memory "userrow" - size = 0x20; - offset = 0x1080; - page_size = 0x20; - readsize = 0x20; + size = 32; + page_size = 32; + offset = 0x1080; + readsize = 32; ; memory "usersig" @@ -17807,7 +14983,7 @@ part memory "data" # SRAM, only used to supply the offset - offset = 0x1000000; + offset = 0x1000000; ; ; @@ -17815,23 +14991,25 @@ part # AVR32DA28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32da28"; - desc = "AVR32DA28"; - signature = 0x1E 0x95 0x34; +part parent ".avrdx" + desc = "AVR32DA28"; + id = "avr32da28"; + family_id = " AVR"; + mcuid = 338; + n_interrupts = 41; + signature = 0x1e 0x95 0x34; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17839,23 +15017,25 @@ part parent ".avrdx" # AVR32DA32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32da32"; - desc = "AVR32DA32"; - signature = 0x1E 0x95 0x33; +part parent ".avrdx" + desc = "AVR32DA32"; + id = "avr32da32"; + family_id = " AVR"; + mcuid = 342; + n_interrupts = 44; + signature = 0x1e 0x95 0x33; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17863,23 +15043,25 @@ part parent ".avrdx" # AVR32DA48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32da48"; - desc = "AVR32DA48"; - signature = 0x1E 0x95 0x32; +part parent ".avrdx" + desc = "AVR32DA48"; + id = "avr32da48"; + family_id = " AVR"; + mcuid = 346; + n_interrupts = 58; + signature = 0x1e 0x95 0x32; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17887,23 +15069,25 @@ part parent ".avrdx" # AVR64DA28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64da28"; - desc = "AVR64DA28"; - signature = 0x1E 0x96 0x15; +part parent ".avrdx" + desc = "AVR64DA28"; + id = "avr64da28"; + family_id = " AVR"; + mcuid = 351; + n_interrupts = 41; + signature = 0x1e 0x96 0x15; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17911,23 +15095,25 @@ part parent ".avrdx" # AVR64DA32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64da32"; - desc = "AVR64DA32"; - signature = 0x1E 0x96 0x14; +part parent ".avrdx" + desc = "AVR64DA32"; + id = "avr64da32"; + family_id = " AVR"; + mcuid = 355; + n_interrupts = 44; + signature = 0x1e 0x96 0x14; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17935,23 +15121,25 @@ part parent ".avrdx" # AVR64DA48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64da48"; - desc = "AVR64DA48"; - signature = 0x1E 0x96 0x13; +part parent ".avrdx" + desc = "AVR64DA48"; + id = "avr64da48"; + family_id = " AVR"; + mcuid = 359; + n_interrupts = 58; + signature = 0x1e 0x96 0x13; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17959,23 +15147,25 @@ part parent ".avrdx" # AVR64DA64 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64da64"; - desc = "AVR64DA64"; - signature = 0x1E 0x96 0x12; +part parent ".avrdx" + desc = "AVR64DA64"; + id = "avr64da64"; + family_id = " AVR"; + mcuid = 362; + n_interrupts = 64; + signature = 0x1e 0x96 0x12; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -17983,23 +15173,25 @@ part parent ".avrdx" # AVR128DA28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128da28"; - desc = "AVR128DA28"; - signature = 0x1E 0x97 0x0A; +part parent ".avrdx" + desc = "AVR128DA28"; + id = "avr128da28"; + family_id = " AVR"; + mcuid = 364; + n_interrupts = 41; + signature = 0x1e 0x97 0x0a; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18007,23 +15199,25 @@ part parent ".avrdx" # AVR128DA32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128da32"; - desc = "AVR128DA32"; - signature = 0x1E 0x97 0x09; +part parent ".avrdx" + desc = "AVR128DA32"; + id = "avr128da32"; + family_id = " AVR"; + mcuid = 366; + n_interrupts = 44; + signature = 0x1e 0x97 0x09; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18031,23 +15225,25 @@ part parent ".avrdx" # AVR128DA48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128da48"; - desc = "AVR128DA48"; - signature = 0x1E 0x97 0x08; +part parent ".avrdx" + desc = "AVR128DA48"; + id = "avr128da48"; + family_id = " AVR"; + mcuid = 368; + n_interrupts = 58; + signature = 0x1e 0x97 0x08; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18055,23 +15251,25 @@ part parent ".avrdx" # AVR128DA64 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128da64"; - desc = "AVR128DA64"; - signature = 0x1E 0x97 0x07; +part parent ".avrdx" + desc = "AVR128DA64"; + id = "avr128da64"; + family_id = " AVR"; + mcuid = 370; + n_interrupts = 64; + signature = 0x1e 0x97 0x07; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18079,23 +15277,24 @@ part parent ".avrdx" # AVR32DB28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32db28"; - desc = "AVR32DB28"; - signature = 0x1E 0x95 0x37; +part parent ".avrdx" + desc = "AVR32DB28"; + id = "avr32db28"; + mcuid = 339; + n_interrupts = 42; + signature = 0x1e 0x95 0x37; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18103,23 +15302,24 @@ part parent ".avrdx" # AVR32DB32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32db32"; - desc = "AVR32DB32"; - signature = 0x1E 0x95 0x36; +part parent ".avrdx" + desc = "AVR32DB32"; + id = "avr32db32"; + mcuid = 343; + n_interrupts = 44; + signature = 0x1e 0x95 0x36; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18127,23 +15327,24 @@ part parent ".avrdx" # AVR32DB48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32db48"; - desc = "AVR32DB48"; - signature = 0x1E 0x95 0x35; +part parent ".avrdx" + desc = "AVR32DB48"; + id = "avr32db48"; + mcuid = 347; + n_interrupts = 61; + signature = 0x1e 0x95 0x35; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18151,23 +15352,24 @@ part parent ".avrdx" # AVR64DB28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64db28"; - desc = "AVR64DB28"; - signature = 0x1E 0x96 0x19; +part parent ".avrdx" + desc = "AVR64DB28"; + id = "avr64db28"; + mcuid = 352; + n_interrupts = 42; + signature = 0x1e 0x96 0x19; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18175,23 +15377,24 @@ part parent ".avrdx" # AVR64DB32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64db32"; - desc = "AVR64DB32"; - signature = 0x1E 0x96 0x18; +part parent ".avrdx" + desc = "AVR64DB32"; + id = "avr64db32"; + mcuid = 356; + n_interrupts = 44; + signature = 0x1e 0x96 0x18; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18199,23 +15402,24 @@ part parent ".avrdx" # AVR64DB48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64db48"; - desc = "AVR64DB48"; - signature = 0x1E 0x96 0x17; +part parent ".avrdx" + desc = "AVR64DB48"; + id = "avr64db48"; + mcuid = 360; + n_interrupts = 61; + signature = 0x1e 0x96 0x17; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18223,23 +15427,24 @@ part parent ".avrdx" # AVR64DB64 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64db64"; - desc = "AVR64DB64"; - signature = 0x1E 0x96 0x16; +part parent ".avrdx" + desc = "AVR64DB64"; + id = "avr64db64"; + mcuid = 363; + n_interrupts = 65; + signature = 0x1e 0x96 0x16; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18247,23 +15452,24 @@ part parent ".avrdx" # AVR128DB28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128db28"; - desc = "AVR128DB28"; - signature = 0x1E 0x97 0x0E; +part parent ".avrdx" + desc = "AVR128DB28"; + id = "avr128db28"; + mcuid = 365; + n_interrupts = 42; + signature = 0x1e 0x97 0x0e; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18271,23 +15477,24 @@ part parent ".avrdx" # AVR128DB32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128db32"; - desc = "AVR128DB32"; - signature = 0x1E 0x97 0x0D; +part parent ".avrdx" + desc = "AVR128DB32"; + id = "avr128db32"; + mcuid = 367; + n_interrupts = 44; + signature = 0x1e 0x97 0x0d; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18295,23 +15502,24 @@ part parent ".avrdx" # AVR128DB48 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128db48"; - desc = "AVR128DB48"; - signature = 0x1E 0x97 0x0C; +part parent ".avrdx" + desc = "AVR128DB48"; + id = "avr128db48"; + mcuid = 369; + n_interrupts = 61; + signature = 0x1e 0x97 0x0c; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18319,23 +15527,24 @@ part parent ".avrdx" # AVR128DB64 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr128db64"; - desc = "AVR128DB64"; - signature = 0x1E 0x97 0x0B; +part parent ".avrdx" + desc = "AVR128DB64"; + id = "avr128db64"; + mcuid = 371; + n_interrupts = 65; + signature = 0x1e 0x97 0x0b; - memory "flash" - size = 0x20000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 512; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x20000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18343,23 +15552,25 @@ part parent ".avrdx" # AVR16DD14 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr16dd14"; - desc = "AVR16DD14"; - signature = 0x1E 0x94 0x34; +part parent ".avrdx" + desc = "AVR16DD14"; + id = "avr16dd14"; + mcuid = 329; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x94 0x34; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18367,23 +15578,25 @@ part parent ".avrdx" # AVR16DD20 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr16dd20"; - desc = "AVR16DD20"; - signature = 0x1E 0x94 0x33; +part parent ".avrdx" + desc = "AVR16DD20"; + id = "avr16dd20"; + mcuid = 330; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x94 0x33; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18391,23 +15604,25 @@ part parent ".avrdx" # AVR16DD28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr16dd28"; - desc = "AVR16DD28"; - signature = 0x1E 0x94 0x32; +part parent ".avrdx" + desc = "AVR16DD28"; + id = "avr16dd28"; + mcuid = 331; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x94 0x32; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18415,23 +15630,25 @@ part parent ".avrdx" # AVR16DD32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr16dd32"; - desc = "AVR16DD32"; - signature = 0x1E 0x94 0x31; +part parent ".avrdx" + desc = "AVR16DD32"; + id = "avr16dd32"; + mcuid = 333; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x94 0x31; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18439,23 +15656,25 @@ part parent ".avrdx" # AVR32DD14 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32dd14"; - desc = "AVR32DD14"; - signature = 0x1E 0x95 0x3B; +part parent ".avrdx" + desc = "AVR32DD14"; + id = "avr32dd14"; + mcuid = 336; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x95 0x3b; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18463,23 +15682,25 @@ part parent ".avrdx" # AVR32DD20 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32dd20"; - desc = "AVR32DD20"; - signature = 0x1E 0x95 0x3A; +part parent ".avrdx" + desc = "AVR32DD20"; + id = "avr32dd20"; + mcuid = 337; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x95 0x3a; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18487,23 +15708,25 @@ part parent ".avrdx" # AVR32DD28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32dd28"; - desc = "AVR32DD28"; - signature = 0x1E 0x95 0x39; +part parent ".avrdx" + desc = "AVR32DD28"; + id = "avr32dd28"; + mcuid = 340; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x95 0x39; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18511,23 +15734,25 @@ part parent ".avrdx" # AVR32DD32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr32dd32"; - desc = "AVR32DD32"; - signature = 0x1E 0x95 0x38; +part parent ".avrdx" + desc = "AVR32DD32"; + id = "avr32dd32"; + mcuid = 344; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x95 0x38; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18535,23 +15760,25 @@ part parent ".avrdx" # AVR64DD14 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64dd14"; - desc = "AVR64DD14"; - signature = 0x1E 0x96 0x1D; +part parent ".avrdx" + desc = "AVR64DD14"; + id = "avr64dd14"; + mcuid = 349; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x96 0x1d; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18559,23 +15786,25 @@ part parent ".avrdx" # AVR64DD20 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64dd20"; - desc = "AVR64DD20"; - signature = 0x1E 0x96 0x1C; +part parent ".avrdx" + desc = "AVR64DD20"; + id = "avr64dd20"; + mcuid = 350; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x96 0x1c; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18583,23 +15812,25 @@ part parent ".avrdx" # AVR64DD28 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64dd28"; - desc = "AVR64DD28"; - signature = 0x1E 0x96 0x1B; +part parent ".avrdx" + desc = "AVR64DD28"; + id = "avr64dd28"; + mcuid = 353; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x96 0x1b; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18607,23 +15838,25 @@ part parent ".avrdx" # AVR64DD32 #------------------------------------------------------------ -part parent ".avrdx" - id = "avr64dd32"; - desc = "AVR64DD32"; - signature = 0x1E 0x96 0x1A; +part parent ".avrdx" + desc = "AVR64DD32"; + id = "avr64dd32"; + mcuid = 357; + n_interrupts = 36; + hvupdi_variant = 2; + signature = 0x1e 0x96 0x1a; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x200; - readsize = 0x100; + memory "eeprom" + size = 256; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x100; - offset = 0x1400; - page_size = 0x1; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 512; + offset = 0x800000; + readsize = 256; ; ; @@ -18631,15 +15864,16 @@ part parent ".avrdx" # AVR-Ex family common values #------------------------------------------------------------ -part parent ".avrdx" - id = ".avrex"; - desc = "AVR-Ex family common values"; +part parent ".avrdx" + desc = "AVR-Ex family common values"; + id = ".avrex"; + # Shared UPDI pin, HV on _RESET + hvupdi_variant = 2; memory "userrow" - size = 0x40; - offset = 0x1080; - page_size = 0x40; - readsize = 0x40; + size = 64; + page_size = 64; + readsize = 64; ; memory "usersig" @@ -18651,23 +15885,24 @@ part parent ".avrdx" # AVR8EA28 #------------------------------------------------------------ -part parent ".avrex" - id = "avr8ea28"; - desc = "AVR8EA28"; - signature = 0x1E 0x93 0x2C; +part parent ".avrex" + desc = "AVR8EA28"; + id = "avr8ea28"; + mcuid = 327; + signature = 0x1e 0x93 0x2c; - memory "flash" - size = 0x2000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18675,23 +15910,24 @@ part parent ".avrex" # AVR8EA32 #------------------------------------------------------------ -part parent ".avrex" - id = "avr8ea32"; - desc = "AVR8EA32"; - signature = 0x1E 0x93 0x2B; +part parent ".avrex" + desc = "AVR8EA32"; + id = "avr8ea32"; + mcuid = 328; + signature = 0x1e 0x93 0x2b; - memory "flash" - size = 0x2000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 8192; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18699,23 +15935,24 @@ part parent ".avrex" # AVR16EA28 #------------------------------------------------------------ -part parent ".avrex" - id = "avr16ea28"; - desc = "AVR16EA28"; - signature = 0x1E 0x94 0x37; +part parent ".avrex" + desc = "AVR16EA28"; + id = "avr16ea28"; + mcuid = 332; + signature = 0x1e 0x94 0x37; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18723,23 +15960,24 @@ part parent ".avrex" # AVR16EA32 #------------------------------------------------------------ -part parent ".avrex" - id = "avr16ea32"; - desc = "AVR16EA32"; - signature = 0x1E 0x94 0x36; +part parent ".avrex" + desc = "AVR16EA32"; + id = "avr16ea32"; + mcuid = 334; + signature = 0x1e 0x94 0x36; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18747,23 +15985,24 @@ part parent ".avrex" # AVR16EA48 #------------------------------------------------------------ -part parent ".avrex" - id = "avr16ea48"; - desc = "AVR16EA48"; - signature = 0x1E 0x94 0x35; +part parent ".avrex" + desc = "AVR16EA48"; + id = "avr16ea48"; + mcuid = 335; + signature = 0x1e 0x94 0x35; - memory "flash" - size = 0x4000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x4000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18771,23 +16010,24 @@ part parent ".avrex" # AVR32EA28 #------------------------------------------------------------ -part parent ".avrex" - id = "avr32ea28"; - desc = "AVR32EA28"; - signature = 0x1E 0x95 0x3E; +part parent ".avrex" + desc = "AVR32EA28"; + id = "avr32ea28"; + mcuid = 341; + signature = 0x1e 0x95 0x3e; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18795,23 +16035,24 @@ part parent ".avrex" # AVR32EA32 #------------------------------------------------------------ -part parent ".avrex" - id = "avr32ea32"; - desc = "AVR32EA32"; - signature = 0x1E 0x95 0x3D; +part parent ".avrex" + desc = "AVR32EA32"; + id = "avr32ea32"; + mcuid = 345; + signature = 0x1e 0x95 0x3d; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18819,23 +16060,24 @@ part parent ".avrex" # AVR32EA48 #------------------------------------------------------------ -part parent ".avrex" - id = "avr32ea48"; - desc = "AVR32EA48"; - signature = 0x1E 0x95 0x3C; +part parent ".avrex" + desc = "AVR32EA48"; + id = "avr32ea48"; + mcuid = 348; + signature = 0x1e 0x95 0x3c; - memory "flash" - size = 0x8000; - offset = 0x800000; - page_size = 0x40; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x8000; + page_size = 64; + offset = 0x800000; + readsize = 256; ; ; @@ -18843,23 +16085,25 @@ part parent ".avrex" # AVR64EA28 #------------------------------------------------------------ -part parent ".avrex" - id = "avr64ea28"; - desc = "AVR64EA28"; - signature = 0x1E 0x96 0x20; +part parent ".avrex" + desc = "AVR64EA28"; + id = "avr64ea28"; + mcuid = 354; + n_interrupts = 37; + signature = 0x1e 0x96 0x20; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; ; @@ -18867,23 +16111,25 @@ part parent ".avrex" # AVR64EA32 #------------------------------------------------------------ -part parent ".avrex" - id = "avr64ea32"; - desc = "AVR64EA32"; - signature = 0x1E 0x96 0x1F; +part parent ".avrex" + desc = "AVR64EA32"; + id = "avr64ea32"; + mcuid = 358; + n_interrupts = 37; + signature = 0x1e 0x96 0x1f; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; ; @@ -18891,23 +16137,25 @@ part parent ".avrex" # AVR64EA48 #------------------------------------------------------------ -part parent ".avrex" - id = "avr64ea48"; - desc = "AVR64EA48"; - signature = 0x1E 0x96 0x1E; +part parent ".avrex" + desc = "AVR64EA48"; + id = "avr64ea48"; + mcuid = 361; + n_interrupts = 45; + signature = 0x1e 0x96 0x1e; - memory "flash" - size = 0x10000; - offset = 0x800000; - page_size = 0x80; - readsize = 0x100; + memory "eeprom" + size = 512; + page_size = 8; + offset = 0x1400; + readsize = 256; ; - memory "eeprom" - size = 0x200; - offset = 0x1400; - page_size = 0x8; - readsize = 0x100; + memory "flash" + size = 0x10000; + page_size = 128; + offset = 0x800000; + readsize = 256; ; ; @@ -18916,25 +16164,33 @@ part parent ".avrex" #------------------------------------------------------------ part parent "m88" - id = "lgt8f88p"; - desc = "LGT8F88P"; - signature = 0x1e 0x93 0x0f; + desc = "LGT8F88P"; + id = "lgt8f88p"; + mcuid = 227; + signature = 0x1e 0x93 0x0f; + autobaud_sync = 0x1c; +; - ocdrev = 1; - ; +#------------------------------------------------------------ +# LGT8F168P +#------------------------------------------------------------ part parent "m168" - id = "lgt8f168p"; - desc = "LGT8F168P"; - signature = 0x1e 0x94 0x0b; - - ocdrev = 1; + desc = "LGT8F168P"; + id = "lgt8f168p"; + mcuid = 228; + signature = 0x1e 0x94 0x0b; + autobaud_sync = 0x1c; ; -part parent "m328" - id = "lgt8f328p"; - desc = "LGT8F328P"; - signature = 0x1e 0x95 0x0F; +#------------------------------------------------------------ +# LGT8F328P +#------------------------------------------------------------ - ocdrev = 1; +part parent "m328" + desc = "LGT8F328P"; + id = "lgt8f328p"; + mcuid = 229; + signature = 0x1e 0x95 0x0f; + autobaud_sync = 0x1c; ; diff --git a/megaavr/platform.txt b/megaavr/platform.txt index a42227f..6b6eac4 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -142,31 +142,31 @@ tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} { tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q -tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} -e {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} - -tools.avrdude_nanoevery.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse2="-Ufuse2:w:{bootloader.OSCCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse4="-Ufuse4:w:{bootloader.TCD0CFG}:m" -tools.avrdude_nanoevery.bootloader.fuse5="-Ufuse5:w:{bootloader.SYSCFG0}:m" -tools.avrdude_nanoevery.bootloader.fuse6="-Ufuse6:w:{bootloader.SYSCFG1}:m" -tools.avrdude_nanoevery.bootloader.fuse7="-Ufuse7:w:{bootloader.APPEND}:m" -tools.avrdude_nanoevery.bootloader.fuse8="-Ufuse8:w:{bootloader.BOOTEND}:m" +tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -p{build.mcu} -c{protocol} {program.extra_params} -e {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} + +tools.avrdude_nanoevery.bootloader.fuse0="-Uwdtcfg:w:{bootloader.WDTCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse1="-Ubodcfg:w:{bootloader.BODCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse2="-Uosccfg:w:{bootloader.OSCCFG}:m" +tools.avrdude_nanoevery.bootloader.fuse4="-Utcd0cfg:w:{bootloader.TCD0CFG}:m" +tools.avrdude_nanoevery.bootloader.fuse5="-Usyscfg0:w:{bootloader.SYSCFG0}:m" +tools.avrdude_nanoevery.bootloader.fuse6="-Usyscfg1:w:{bootloader.SYSCFG1}:m" +tools.avrdude_nanoevery.bootloader.fuse7="-Uappend:w:{bootloader.APPEND}:m" +tools.avrdude_nanoevery.bootloader.fuse8="-Ubootend:w:{bootloader.BOOTEND}:m" tools.avrdude_nanoevery.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" -tools.avrdude.bootloader.fuse0="-Ufuse0:w:{bootloader.WDTCFG}:m" -tools.avrdude.bootloader.fuse1="-Ufuse1:w:{bootloader.BODCFG}:m" -tools.avrdude.bootloader.fuse2="-Ufuse2:w:{bootloader.OSCCFG}:m" -tools.avrdude.bootloader.fuse4="-Ufuse4:w:{bootloader.TCD0CFG}:m" -tools.avrdude.bootloader.fuse5="-Ufuse5:w:{bootloader.SYSCFG0}:m" -tools.avrdude.bootloader.fuse6="-Ufuse6:w:{bootloader.SYSCFG1}:m" -tools.avrdude.bootloader.fuse7="-Ufuse7:w:{bootloader.APPEND}:m" -tools.avrdude.bootloader.fuse8="-Ufuse8:w:{bootloader.BOOTEND}:m" +tools.avrdude.bootloader.fuse0="-Uwdtcfg:w:{bootloader.WDTCFG}:m" +tools.avrdude.bootloader.fuse1="-Ubodcfg:w:{bootloader.BODCFG}:m" +tools.avrdude.bootloader.fuse2="-Uosccfg:w:{bootloader.OSCCFG}:m" +tools.avrdude.bootloader.fuse4="-Utcd0cfg:w:{bootloader.TCD0CFG}:m" +tools.avrdude.bootloader.fuse5="-Usyscfg0:w:{bootloader.SYSCFG0}:m" +tools.avrdude.bootloader.fuse6="-Usyscfg1:w:{bootloader.SYSCFG1}:m" +tools.avrdude.bootloader.fuse7="-Uappend:w:{bootloader.APPEND}:m" +tools.avrdude.bootloader.fuse8="-Ubootend:w:{bootloader.BOOTEND}:m" tools.avrdude.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" tools.avrdude.bootloader.params.verbose=-v tools.avrdude.bootloader.params.quiet=-q -q -tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" -v -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" +tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" tools.avrdude_remote.upload.pattern=/usr/bin/run-avrdude /tmp/sketch.hex {upload.verbose} -p{build.mcu} diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index 4b7c8ef..a65ff03 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -1,9 +1,9 @@ -medbg.name=Atmel mEDBG/microUPDI -medbg.communication=usb -medbg.protocol=xplainedmini_updi -medbg.program.protocol=xplainedmini_updi -medbg.program.tool=avrdude -medbg.program.extra_params=-Pusb +xplainedmini.name=microUPDI/Uno Wifi +xplainedmini.communication=usb +xplainedmini.protocol=xplainedmini_updi +xplainedmini.program.protocol=xplainedmini_updi +xplainedmini.program.tool=avrdude +xplainedmini.program.extra_params= serialupdi_57600.name=SerialUPDI (57600 baud) serialupdi_57600.communication=serial @@ -35,37 +35,44 @@ jtag2updi.protocol=jtag2updi jtag2updi.program.tool=avrdude jtag2updi.program.extra_params=-P{serial.port} -nedbg.name=Atmel nEDBG/Curiosity Nano -nedbg.communication=usb -nedbg.protocol=pkobn_updi -nedbg.program.protocol=pkobn_updi -nedbg.program.tool=avrdude -nedbg.program.extra_params=-Pusb +cusiositynano.name=Curiosity Nano +cusiositynano.communication=usb +cusiositynano.protocol=pkobn_updi +cusiositynano.program.protocol=pkobn_updi +cusiositynano.program.tool=avrdude +cusiositynano.program.extra_params= -edbg.name=Atmel EDBG -edbg.communication=usb -edbg.protocol=xplainedpro_updi -edbg.program.protocol=xplainedpro_updi -edbg.program.tool=avrdude -edbg.program.extra_params=-Pusb +xplainedpro.name=Xplained Pro +xplainedpro.communication=usb +xplainedpro.protocol=xplainedpro_updi +xplainedpro.program.protocol=xplainedpro_updi +xplainedpro.program.tool=avrdude +xplainedpro.program.extra_params= -atmelice_updi.name=Atmel-ICE (UPDI) -atmelice_updi.communication=usb -atmelice_updi.protocol=atmelice_updi -atmelice_updi.program.protocol=jtagice3_updi -atmelice_updi.program.tool=avrdude -atmelice_updi.program.extra_params=-Pusb - -pickit4_updi.name=PICkit4 (UPDI) +pickit4_updi.name=PICkit4 UPDI pickit4_updi.communication=usb pickit4_updi.protocol=pickit4_updi pickit4_updi.program.protocol=jtagice3_updi pickit4_updi.program.tool=avrdude -pickit4_updi.program.extra_params=-Pusb +pickit4_updi.program.extra_params= -snap_updi.name=MPLAB SNAP (UPDI) +snap_updi.name=MPLAB SNAP UPDI snap_updi.communication=usb snap_updi.protocol=snap_updi snap_updi.program.protocol=jtagice3_updi snap_updi.program.tool=avrdude -snap_updi.program.extra_params=-Pusb +snap_updi.program.extra_params= + +atmelice_updi.name=Atmel-ICE UPDI +atmelice_updi.communication=usb +atmelice_updi.protocol=atmelice_updi +atmelice_updi.program.protocol=jtagice3_updi +atmelice_updi.program.tool=avrdude +atmelice_updi.program.extra_params= + +jtagice3_updi.name=JTAGICE3 UPDI +jtagice3_updi.communication=usb +jtagice3_updi.protocol=jtag3updi +jtagice3_updi.program.protocol=jtagice3_updi +jtagice3_updi.program.tool=avrdude +atmelice_updi.program.extra_params= \ No newline at end of file From 1093afcb02e2296239e93784181b0488f191d072 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Wed, 11 Jan 2023 19:58:37 +0100 Subject: [PATCH 317/351] Write all fuse bytes in a big bunch rather than induvidually --- megaavr/platform.txt | 26 +++----------------------- 1 file changed, 3 insertions(+), 23 deletions(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 6b6eac4..dc5d862 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -131,38 +131,18 @@ tools.avrdude_nanoevery.upload.params.verbose=-v tools.avrdude_nanoevery.upload.params.quiet=-q -q tools.avrdude_nanoevery.upload.verify= tools.avrdude_nanoevery.upload.params.noverify=-V -tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} -Ufuses:w:{bootloader.WDTCFG},{bootloader.BODCFG},{bootloader.OSCCFG},0xff,{bootloader.TCD0CFG},{bootloader.SYSCFG0},{bootloader.SYSCFG1},{bootloader.APPEND},{bootloader.BOOTEND}:m -Ulock:w:{bootloader.LOCKBIT}:m "-Uflash:w:{build.path}/{build.project_name}.hex:i" tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q # tools.avrdude.program.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value tools.avrdude.program.verify= tools.avrdude.program.params.noverify=-V -tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.with_bootloader.hex:i" {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} +tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} -Ufuses:w:{bootloader.WDTCFG},{bootloader.BODCFG},{bootloader.OSCCFG},0xff,{bootloader.TCD0CFG},{bootloader.SYSCFG0},{bootloader.SYSCFG1},{bootloader.APPEND},{bootloader.BOOTEND}:m -Ulock:w:{bootloader.LOCKBIT}:m "-Uflash:w:{build.path}/{build.project_name}.with_bootloader.hex:i" tools.avrdude.erase.params.verbose=-v tools.avrdude.erase.params.quiet=-q -q -tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -p{build.mcu} -c{protocol} {program.extra_params} -e {bootloader.fuse0} {bootloader.fuse1} {bootloader.fuse2} {bootloader.fuse4} {bootloader.fuse5} {bootloader.fuse6} {bootloader.fuse7} {bootloader.fuse8} {bootloader.lock} - -tools.avrdude_nanoevery.bootloader.fuse0="-Uwdtcfg:w:{bootloader.WDTCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse1="-Ubodcfg:w:{bootloader.BODCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse2="-Uosccfg:w:{bootloader.OSCCFG}:m" -tools.avrdude_nanoevery.bootloader.fuse4="-Utcd0cfg:w:{bootloader.TCD0CFG}:m" -tools.avrdude_nanoevery.bootloader.fuse5="-Usyscfg0:w:{bootloader.SYSCFG0}:m" -tools.avrdude_nanoevery.bootloader.fuse6="-Usyscfg1:w:{bootloader.SYSCFG1}:m" -tools.avrdude_nanoevery.bootloader.fuse7="-Uappend:w:{bootloader.APPEND}:m" -tools.avrdude_nanoevery.bootloader.fuse8="-Ubootend:w:{bootloader.BOOTEND}:m" -tools.avrdude_nanoevery.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" - -tools.avrdude.bootloader.fuse0="-Uwdtcfg:w:{bootloader.WDTCFG}:m" -tools.avrdude.bootloader.fuse1="-Ubodcfg:w:{bootloader.BODCFG}:m" -tools.avrdude.bootloader.fuse2="-Uosccfg:w:{bootloader.OSCCFG}:m" -tools.avrdude.bootloader.fuse4="-Utcd0cfg:w:{bootloader.TCD0CFG}:m" -tools.avrdude.bootloader.fuse5="-Usyscfg0:w:{bootloader.SYSCFG0}:m" -tools.avrdude.bootloader.fuse6="-Usyscfg1:w:{bootloader.SYSCFG1}:m" -tools.avrdude.bootloader.fuse7="-Uappend:w:{bootloader.APPEND}:m" -tools.avrdude.bootloader.fuse8="-Ubootend:w:{bootloader.BOOTEND}:m" -tools.avrdude.bootloader.lock="-Ulock:w:{bootloader.LOCKBIT}:m" +tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" -p{build.mcu} -c{protocol} {program.extra_params} -e -Ufuses:w:{bootloader.WDTCFG},{bootloader.BODCFG},{bootloader.OSCCFG},0xff,{bootloader.TCD0CFG},{bootloader.SYSCFG0},{bootloader.SYSCFG1},{bootloader.APPEND},{bootloader.BOOTEND}:m -Ulock:w:{bootloader.LOCKBIT}:m tools.avrdude.bootloader.params.verbose=-v tools.avrdude.bootloader.params.quiet=-q -q From 47339007f312648fae05df8e8413b6177a7f942b Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 23 Jan 2023 22:09:12 +0100 Subject: [PATCH 318/351] Update PlatformIO.md Add SerialUPDI programmer + update templates --- PlatformIO.md | 236 +++++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 196 insertions(+), 40 deletions(-) diff --git a/PlatformIO.md b/PlatformIO.md index cf6e09a..8e5e2b0 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -35,7 +35,11 @@ The most common functionality is available in this template. As you can see, the More information on what each line means can be found futher down on this page. -## platformio.ini template +## platformio.ini templates +All these templates are very similar, but I've created a few ones for different programmers to make it easier to get started + +
+ATmega4809, microUPDI / Xplained Mini programmer, optional bootloader ```ini ; PlatformIO template configuration file for MegaCoreX @@ -77,12 +81,11 @@ build_flags = ; Monitor port is auto detected. Override here ;monitor_port = -; Serial monitor baud rate monitor_speed = 9600 ; Run the following command to upload with this environment -; pio run -e Upload_UPDI -t upload +; pio run -t upload [env:Upload_UPDI] ; Upload protocol for UPDI upload upload_protocol = xplainedmini_updi @@ -94,8 +97,8 @@ upload_flags = [env:Upload_UART] ; Upload protocol for serial uploads (using Optiboot) upload_protocol = arduino -upload_flags = upload_port = /dev/cu.usbserial* +upload_flags = ; run the following command to set fuses @@ -103,9 +106,94 @@ upload_port = /dev/cu.usbserial* ; run the following command to set fuses + burn bootloader ; pio run -e fuses_bootloader -t bootloader [env:fuses_bootloader] -; Upload protocol for used to set fuses/bootloader -upload_protocol = ${env:Upload_UPDI.upload_protocol} +; Inherit upload settings from the Upload_UPDI environment +extends = env:Upload_UPDI + +; Hardware settings +board_hardware.bod = 2.7v +board_hardware.eesave = yes +board_hardware.uart = no_bootloader +board_hardware.rstpin = reset + +``` + +
+ +
+ATmega4809, SerialUPDI programmer, optional bootloader + +```ini +; PlatformIO template configuration file for MegaCoreX +; https://github.com/MCUdude/MegaCoreX/ +; +; Build options: build flags, source filter +; Hardware options: oscillator type, BOD, UART number, EEPROM retain +; Upload options: custom upload port, speed, and extra flags +; Library options: dependencies, extra library storages +; Advanced options: extra scripting +; +; Please visit documentation for the other options +; https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md +; https://docs.platformio.org/page/projectconf.html +; https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html + +[platformio] +; Default build target +default_envs = Upload_UPDI + +; Parameters used for all environments +[env] +platform = atmelmegaavr +framework = arduino + +; Chip in use +board = ATmega4809 +; Clock frequency in [Hz] +board_build.f_cpu = 16000000L +; Oscillator type (internal or external) +board_hardware.oscillator = internal +; Arduino pinout variant +board_build.variant = 48pin-standard + +; Unflag build flags +build_unflags = +; Extra build flags +build_flags = + +; Monitor port is auto detected. Override here +;monitor_port = ${env:Upload_UPDI.upload_port} +monitor_speed = 9600 +monitor_dtr = 0 + + +; Run the following command to upload with this environment +; pio run -t upload +[env:Upload_UPDI] +; Upload protocol for UPDI upload +upload_protocol = serialupdi +upload_port = /dev/cu.usbserial* +upload_speed = 115200 +upload_flags = + -xrtsdtr=high + + +; Run the following command to upload with this environment +; pio run -e Upload_UART -t upload +[env:Upload_UART] +; Upload protocol for serial uploads (using Optiboot) +upload_protocol = arduino +upload_port = /dev/cu.usbserial* upload_flags = + + +; run the following command to set fuses +; pio run -e fuses_bootloader -t fuses +; run the following command to set fuses + burn bootloader +; pio run -e fuses_bootloader -t bootloader +[env:fuses_bootloader] +; Inherit upload settings from the Upload_UPDI environment +extends = env:Upload_UPDI + ; Hardware settings board_hardware.bod = 2.7v board_hardware.eesave = yes @@ -114,6 +202,91 @@ board_hardware.rstpin = reset ``` +
+ +
+ATmega4809, JTAG2UPDI programmer, optional bootloader + +```ini +; PlatformIO template configuration file for MegaCoreX +; https://github.com/MCUdude/MegaCoreX/ +; +; Build options: build flags, source filter +; Hardware options: oscillator type, BOD, UART number, EEPROM retain +; Upload options: custom upload port, speed, and extra flags +; Library options: dependencies, extra library storages +; Advanced options: extra scripting +; +; Please visit documentation for the other options +; https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md +; https://docs.platformio.org/page/projectconf.html +; https://docs.platformio.org/en/latest/platforms/atmelmegaavr.html + +[platformio] +; Default build target +default_envs = Upload_UPDI + +; Parameters used for all environments +[env] +platform = atmelmegaavr +framework = arduino + +; Chip in use +board = ATmega4809 +; Clock frequency in [Hz] +board_build.f_cpu = 16000000L +; Oscillator type (internal or external) +board_hardware.oscillator = internal +; Arduino pinout variant +board_build.variant = 48pin-standard + +; Unflag build flags +build_unflags = +; Extra build flags +build_flags = + +; Monitor port is auto detected. Override here +;monitor_port = ${env:Upload_UPDI.upload_port} +monitor_speed = 9600 +monitor_dtr = 0 + + +; Run the following command to upload with this environment +; pio run -t upload +[env:Upload_UPDI] +; Upload protocol for UPDI upload +upload_protocol = jtag2updi +upload_port = /dev/cu.usbserial* +upload_speed = 115200 +upload_flags = + + +; Run the following command to upload with this environment +; pio run -e Upload_UART -t upload +[env:Upload_UART] +; Upload protocol for serial uploads (using Optiboot) +upload_protocol = arduino +upload_port = /dev/cu.usbserial* +upload_flags = + + +; run the following command to set fuses +; pio run -e fuses_bootloader -t fuses +; run the following command to set fuses + burn bootloader +; pio run -e fuses_bootloader -t bootloader +[env:fuses_bootloader] +; Inherit upload settings from the Upload_UPDI environment +extends = env:Upload_UPDI + +; Hardware settings +board_hardware.bod = 2.7v +board_hardware.eesave = yes +board_hardware.uart = no_bootloader +board_hardware.rstpin = reset + +``` + +
### `board` PlatformIO requires the `board` parameter to be present. @@ -206,7 +379,7 @@ Specifies what functionality the reset pin should have. Note that the option `re ### `board_build.variant` -Holds the current pinout in use. +Holds the current pinout in use. PlatformIO automatocally selects the *default* one if not specified. See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. | Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | @@ -220,7 +393,11 @@ See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. This parameter is used to unflag flags automatically set by the PlatformIO build environment. **Example:** -`build_unflags =-flto -fpermissive` +``` +build_unflags = + -flto + -fpermissive +``` ### `build_flags` @@ -235,11 +412,15 @@ This parameter is used to set compiler flags. This is useful if you want to for | -DTWI_BUFFER_SIZE=64 | 32 bytes | Sets the TWI (i2c) buffer to 64 bytes | **Example:** -`build_flags = -DSERIAL_RX_BUFFER_SIZE=128 -DSERIAL_TX_BUFFER_SIZE=128` +``` +build_flags = + -DSERIAL_RX_BUFFER_SIZE=128 + -DSERIAL_TX_BUFFER_SIZE=128 +``` ### `upload_port` -Holds the serial port used for uploading. Only needed if you're uploading using a JTAG2UPDI programmer or with a USB to serial adapter using the Optiboot bootloader. PlatformIO automatically detects the serial port. However, if you want to override this you can uncomment `upload_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. +Holds the serial port used for uploading. Only needed if you're uploading using a SerialUPDI or JTAG2UPDI programmer, or with a USB to serial adapter using the Optiboot bootloader. PlatformIO automatically detects the serial port. However, if you want to override this you can uncomment `upload_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. ### `upload_protocol` @@ -247,10 +428,11 @@ Programmer used for uploading. | Supported UPDI programmers in Avrdude | Notes | |---------------------------------------|------------------------------------------------------------------------------------------------------------------| -| `jtag2updi` | Requires upload port | +| [`serialupdi`](https://www.tindie.com/products/mcudude/serialupdi-programmer/) | Requires upload serial port. Change the baud rate in `upload_speed` to increase or decrease upload speed | +| `xplainedmini_updi` | Xplained Mini and [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) programmers | +| `jtag2updi` | Requires serial upload port. Newer JTAG2UPDI firmware versions supports baud rates higher than 115200 baud | | | `arduino` | Used when uploading using the Optiboot bootloader. Requires upload port | -| `xplainedmini_updi` | Xplained Mini (mEDBG) and [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) programmers | -| `pkobn_updi` | On-board Curiosity nano programmer (nEDBG) | +| `pkobn_updi` | On-board Curiosity nano programmer | | `pickit4_updi` | PICkit4 programmer in UPDI mode | | `snap_updi` | MPLAB SNAP programmer in UPDI mode | | `atmelice_updi` | Atmel ICE programmer in UPDI mode | @@ -260,11 +442,10 @@ Programmer used for uploading. ### `upload_flags` Used to pass extra flags to Avrdude when uploading using a programmer. -Typical parameters are `-PUSB` and `-v`. +Typical parameters are `-qq` or `-v`. See the [Avrdude documentation](https://avrdudes.github.io/avrdude/) for more information. **Note that every flag has to be on its own line, and they have to be indented with two spaces:** ```ini upload_flags = - -PUSB -v ``` @@ -275,28 +456,3 @@ PlatformIO detects serial ports automatically. However, if you want to override ### `monitor_speed` Sets the serial monitor baud rate. Defaults to 9600 if not defined. - - -## pyupdi -[pyupdi](https://github.com/mraardvark/pyupdi) is a Python-based tool for programming tinyAVR and megaAVR devices with UPDI interface via a standard serial port. It can be installed directly in the PlatformIO virtual environment using the following command: - -``` -pip install https://github.com/mraardvark/pyupdi/archive/master.zip -``` - -Once pyupdi is installed it can be used as the uploader via a custom upload_command option: - -```ini -[env:pyupdi_upload] -upload_protocol = custom -upload_speed = 115200 -upload_port = /some/serial/port -upload_flags = - -d - $BOARD_MCU - -c - $UPLOAD_PORT - -b - $UPLOAD_SPEED -upload_command = pyupdi $UPLOAD_FLAGS -f $SOURCE -``` From 120fae6aab23cef14d5348f795e3c9eb9f3d116c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sat, 28 Jan 2023 21:51:00 +0100 Subject: [PATCH 319/351] Undo typo fix I have no idea why I pushed 19d91ec4eb0372be3f68e16acb907abdd71dccd2, as it broke the Logic input setup routine. This commit resolves the issue --- megaavr/libraries/Logic/src/Logic.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Logic/src/Logic.cpp b/megaavr/libraries/Logic/src/Logic.cpp index fce2d26..32abadb 100644 --- a/megaavr/libraries/Logic/src/Logic.cpp +++ b/megaavr/libraries/Logic/src/Logic.cpp @@ -109,7 +109,7 @@ void Logic::init() } // Set inputs modes - block.LUTCTRLB = ((input1 & 0xf0) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); + block.LUTCTRLB = ((input1 & 0x0f) << CCL_INSEL1_gp) | ((input0 & 0x0f) << CCL_INSEL0_gp); block.LUTCTRLC = ((input2 & 0x0f) << CCL_INSEL2_gp); // Set truth table From 36219fe6878f54e2e300b6267ab73973d8a1f7b5 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 6 Feb 2023 18:41:00 +0100 Subject: [PATCH 320/351] Fix broken links Closes issue #170 --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 5f7de6c..49e532c 100644 --- a/README.md +++ b/README.md @@ -160,8 +160,8 @@ digitalWrite(0, HIGH); ## Write to own flash As an alternative for UPDI, MegaCoreX uses Optiboot Flash, a bootloader that supports flash writing within the running application, thanks to the work of [@majekw](https://github.com/majekw). This means that content from e.g. a sensor can be stored in the flash memory directly without the need of external memory. Flash memory is much faster than EEPROM, and can handle at least 10 000 write cycles before wear becomes an issue. -For more information on how it works and how you can use this in you own application, check out the [Serial_read_write](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino) for a simple proof-of-concept demo, and -[Flash_put_get](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino) + [Flash_iterate](https://github.com/MCUdude/MegaCoreX/blob/master/avr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino) for useful examples on how you can store strings, structs and variables to flash and retrieve then afterwards. +For more information on how it works and how you can use this in you own application, check out the [Serial_read_write](https://github.com/MCUdude/MegaCoreX/blob/master/megaavr/libraries/Optiboot_flasher/examples/Serial_read_write/Serial_read_write.ino) for a simple proof-of-concept demo, and +[Flash_put_get](https://github.com/MCUdude/MegaCoreX/blob/master/megaavr/libraries/Optiboot_flasher/examples/Flash_put_get/Flash_put_get.ino) + [Flash_iterate](https://github.com/MCUdude/MegaCoreX/blob/master/megaavr/libraries/Optiboot_flasher/examples/Flash_iterate/Flash_iterate.ino) for useful examples on how you can store strings, structs and variables to flash and retrieve then afterwards. ## Memory-mapped flash From 4e97f9eda6ca7beffa266bf8daed3232136d7a3c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Feb 2023 18:52:34 +0100 Subject: [PATCH 321/351] Fix typo in template function --- megaavr/cores/coreX-corefiles/api/Common.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index f7e85f2..2864970 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -114,7 +114,7 @@ inline __attribute__((always_inline)) void check_constant_pin(pin_size_t pin) #ifndef max template - auto max(const T& a, const L& b) -> decltype((b < a) ? b : a) { + auto max(const T& a, const L& b) -> decltype((a < b) ? b : a) { return (a < b) ? b : a; } #endif From 2a06cbf296b68f5fc55c058a9baafe120bb2974b Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Feb 2023 18:54:02 +0100 Subject: [PATCH 322/351] Fix issue where PORTF on Nano Every would be clered by the wire library after running Wire.begin(). Resolves issue #172 --- megaavr/libraries/Wire/src/utility/twi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index 8704cb9..ca34c13 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -73,7 +73,7 @@ void TWI_MasterInit(uint32_t frequency) #if defined(NANO_EVERY_PINOUT) PORTF_PIN2CTRL &= ~PORT_PULLUPEN_bm; // Disable PF2 pullup PORTF_PIN3CTRL &= ~PORT_PULLUPEN_bm; // Disable PF3 pullup - PORTF_DIRCLR |= PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs + PORTF_DIRCLR = PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs #endif pinMode(PIN_WIRE_SDA, INPUT_PULLUP); // Enable PA2 pullup From c7298cdaad039ca31b2a94848809ab7009167476 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Sun, 19 Feb 2023 20:24:58 +0100 Subject: [PATCH 323/351] Fix another incorrect DIRCLR set --- megaavr/libraries/Wire/src/utility/twi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Wire/src/utility/twi.c b/megaavr/libraries/Wire/src/utility/twi.c index ca34c13..b5909d2 100644 --- a/megaavr/libraries/Wire/src/utility/twi.c +++ b/megaavr/libraries/Wire/src/utility/twi.c @@ -119,7 +119,7 @@ void TWI_SlaveInit(uint8_t address, uint8_t receive_broadcast, uint8_t second_ad { PORTF_PIN2CTRL &= ~PORT_PULLUPEN_bm; // Disable PF2 pullup PORTF_PIN3CTRL &= ~PORT_PULLUPEN_bm; // Disable PF3 pullup - PORTF_DIRCLR |= PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs + PORTF_DIRCLR = PIN2_bm | PIN3_bm; // Set PF2 and PF3 as inputs } #endif From 2aec77664842dec8aa082a0382dcdd9990e34130 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 13 Apr 2023 20:07:16 +0200 Subject: [PATCH 324/351] Attempt to fix issue #162 --- megaavr/libraries/Servo/src/megaavr/Servo.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Servo/src/megaavr/Servo.cpp b/megaavr/libraries/Servo/src/megaavr/Servo.cpp index 32c9693..2699c15 100644 --- a/megaavr/libraries/Servo/src/megaavr/Servo.cpp +++ b/megaavr/libraries/Servo/src/megaavr/Servo.cpp @@ -5,7 +5,7 @@ #if (F_CPU > 10000000L) #define usToTicks(_us) ((( (_us) / 2) * clockCyclesPerMicrosecond())) // converts microseconds to tick - #define ticksToUs(_ticks) (((unsigned) _ticks * 2) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds + #define ticksToUs(_ticks) (((unsigned) (_ticks) * 2) / clockCyclesPerMicrosecond()) // converts from ticks back to microseconds #define TRIM_DURATION 37 // compensation ticks to trim adjust for digitalWrite delays #else #define usToTicks(_us) ((( _us ) * clockCyclesPerMicrosecond())) // converts microseconds to tick From a998b6a4bb33fa3cd93792576414a3f650b831c0 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 13 Apr 2023 23:33:51 +0200 Subject: [PATCH 325/351] Bump Servo library version --- megaavr/libraries/Servo/library.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/Servo/library.properties b/megaavr/libraries/Servo/library.properties index f8d54ca..043ab06 100644 --- a/megaavr/libraries/Servo/library.properties +++ b/megaavr/libraries/Servo/library.properties @@ -1,5 +1,5 @@ name=Servo -version=1.2.0 +version=1.2.1 author=Spence Konde and MCUdude based on work by Michael Margolis, Arduino maintainer=MCUdude sentence=Allows megaAVR0 chips to control a variety of servo motors. From 668541ee3709496c6ad98332e9ce23fe94cdb8cd Mon Sep 17 00:00:00 2001 From: MCUdude Date: Mon, 1 May 2023 12:32:50 +0200 Subject: [PATCH 326/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index dc5d862..e635303 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.1.1 +version=1.1.2 # AVR compile variables # --------------------- From d0f0eff16e6d214397e13ca21dd24e53046e42e8 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 24 Jul 2023 10:57:29 +0200 Subject: [PATCH 327/351] Add information about custom fuse values --- PlatformIO.md | 55 +++++++++++++++++++++++++++++++++++---------------- 1 file changed, 38 insertions(+), 17 deletions(-) diff --git a/PlatformIO.md b/PlatformIO.md index 8e5e2b0..17fc9fd 100644 --- a/PlatformIO.md +++ b/PlatformIO.md @@ -1,7 +1,7 @@ # PlatformIO -[PlatformIO](https://platformio.org) is an open source ecosystem for embedded development. -It has a built-in library manager and is Arduino compatible. It supports most operating systems; Windows, MacOS, Linux 32 and 64-bit, ARM and X86. And best of all, MegaCoreX is supported! +[PlatformIO](https://platformio.org) is an open-source ecosystem for embedded development. +It has a built-in library manager and is Arduino-compatible. It supports most operating systems; Windows, MacOS, Linux 32 and 64-bit, ARM, and X86. And best of all, MegaCoreX is supported! * [What is PlatformIO?](http://docs.platformio.org/en/latest/what-is-platformio.html) * [PlatformIO IDE](https://platformio.org/platformio-ide) @@ -11,7 +11,7 @@ It has a built-in library manager and is Arduino compatible. It supports most op ## MegaCoreX + PlatformIO -MegaCoreX and PlatformIO goes great together. You can do serial uploads and upload using a dedicated UPDI programmer, but you can also let PlatformIO calulate the fuses and load the correct bootloader file, just like Arduino IDE does! +MegaCoreX and PlatformIO go great together. You can do serial uploads and upload using a dedicated UPDI programmer, but you can also let PlatformIO calculate the fuses and load the correct bootloader file, just like Arduino IDE does! PlatformIO uses the information provided in platformio.ini to calculate what fuse bits and what bootloader file to load. Simply provide enough information and run the following commands: @@ -21,18 +21,18 @@ Simply provide enough information and run the following commands: pio run -t fuses -e fuses_bootloader ; Set fuses and burn bootloader pio run -t bootloader -e fuses_bootloader -; (where "fuses_bootloader" can be replace with a different environment to match your build configuration) +; (where "fuses_bootloader" can be replaced with a different environment to match your build configuration) ``` -You can find a platformio.ini template you can use when creating a project for a MegaCoreX compatible device below. +You can find a platformio.ini template you can use when creating a project for a MegaCoreX-compatible device below. The most common functionality is available in this template. As you can see, the templated is divided into multiple environments. -* The default build environment are defined under *[platformio]*. +* The default build environment is defined under *[platformio]*. * All parameters that are common for all environments are defined under *[env]*. * Use the *[env:Upload_UPDI]* or *[env:Upload_UART]* to upload to your target. * Use *[env:fuses_bootloader]* to set the fuses or burn the bootloader. -More information on what each line means can be found futher down on this page. +More information on what each line means can be found further down on this page. ## platformio.ini templates @@ -48,7 +48,7 @@ All these templates are very similar, but I've created a few ones for different ; Build options: build flags, source filter ; Hardware options: oscillator type, BOD, UART number, EEPROM retain ; Upload options: custom upload port, speed, and extra flags -; Library options: dependencies, extra library storages +; Library options: dependencies, extra library storage ; Advanced options: extra scripting ; ; Please visit documentation for the other options @@ -129,7 +129,7 @@ board_hardware.rstpin = reset ; Build options: build flags, source filter ; Hardware options: oscillator type, BOD, UART number, EEPROM retain ; Upload options: custom upload port, speed, and extra flags -; Library options: dependencies, extra library storages +; Library options: dependencies, extra library storage ; Advanced options: extra scripting ; ; Please visit documentation for the other options @@ -160,7 +160,7 @@ build_unflags = ; Extra build flags build_flags = -; Monitor port is auto detected. Override here +; Monitor port is auto-detected. Override here ;monitor_port = ${env:Upload_UPDI.upload_port} monitor_speed = 9600 monitor_dtr = 0 @@ -214,7 +214,7 @@ board_hardware.rstpin = reset ; Build options: build flags, source filter ; Hardware options: oscillator type, BOD, UART number, EEPROM retain ; Upload options: custom upload port, speed, and extra flags -; Library options: dependencies, extra library storages +; Library options: dependencies, extra library storage ; Advanced options: extra scripting ; ; Please visit documentation for the other options @@ -245,7 +245,7 @@ build_unflags = ; Extra build flags build_flags = -; Monitor port is auto detected. Override here +; Monitor port is auto-detected. Override here ;monitor_port = ${env:Upload_UPDI.upload_port} monitor_speed = 9600 monitor_dtr = 0 @@ -326,7 +326,7 @@ Below is a table with supported clocks for MegaCoreX. Defaults to 16 MHz interna ### `board_hardware.oscillator` -Spefices to use the internal or an external oscillator. +Specifies to use the internal or an external oscillator. | Oscillator option | |----------------------| @@ -379,7 +379,7 @@ Specifies what functionality the reset pin should have. Note that the option `re ### `board_build.variant` -Holds the current pinout in use. PlatformIO automatocally selects the *default* one if not specified. +Holds the current pinout in use. PlatformIO automatically selects the *default* one if not specified. See [pinout pics](https://github.com/MCUdude/MegaCoreX#pinout) for more info. | Pinouts 48 pin parts | Pinouts 40 pin parts | Pinouts 32 pin parts | Pinouts 28 pin parts | @@ -420,7 +420,7 @@ build_flags = ### `upload_port` -Holds the serial port used for uploading. Only needed if you're uploading using a SerialUPDI or JTAG2UPDI programmer, or with a USB to serial adapter using the Optiboot bootloader. PlatformIO automatically detects the serial port. However, if you want to override this you can uncomment `upload_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. +Holds the serial port used for uploading. Only needed if you're uploading using a SerialUPDI or JTAG2UPDI programmer or with a USB-to-serial adapter using the Optiboot bootloader. PlatformIO automatically detects the serial port. However, if you want to override this you can uncomment `upload_port`. Use `/dev/[port]` on Unix-compatible systems, and use `COMx` on Windows. ### `upload_protocol` @@ -430,7 +430,7 @@ Programmer used for uploading. |---------------------------------------|------------------------------------------------------------------------------------------------------------------| | [`serialupdi`](https://www.tindie.com/products/mcudude/serialupdi-programmer/) | Requires upload serial port. Change the baud rate in `upload_speed` to increase or decrease upload speed | | `xplainedmini_updi` | Xplained Mini and [microUPDI](https://www.tindie.com/products/MCUdude/microupdi-programmer/) programmers | -| `jtag2updi` | Requires serial upload port. Newer JTAG2UPDI firmware versions supports baud rates higher than 115200 baud | | +| `jtag2updi` | Requires serial upload port. Newer JTAG2UPDI firmware versions support baud rates higher than 115200 baud | | `arduino` | Used when uploading using the Optiboot bootloader. Requires upload port | | `pkobn_updi` | On-board Curiosity nano programmer | | `pickit4_updi` | PICkit4 programmer in UPDI mode | @@ -451,8 +451,29 @@ upload_flags = ### `monitor_port` -PlatformIO detects serial ports automatically. However, if you want to override this you can uncomment `monitor_port`. Use `/dev/[port]` on Unix compatible systems, and use `COMx` on Windows. +PlatformIO detects serial ports automatically. However, if you want to override this you can uncomment `monitor_port`. Use `/dev/[port]` on Unix-compatible systems, and use `COMx` on Windows. ### `monitor_speed` Sets the serial monitor baud rate. Defaults to 9600 if not defined. + + +## User-defined fuses +Even though PlatformIO can calculate fuse values depending on the user-specified data in platformio.ini, there may be applications where the fuses have to be set to known values. This can be done like so: +```ini +; run the following command to set fuses +; pio run -e custom_fuses -t fuses +[env:custom_fuses] +; Inherit upload settings from the Upload_UPDI environment +extends = env:Upload_UPDI + +; Fuse settings +board_fuses.wdtcfg = 0x00 +board_fuses.bodcfg = 0x00 +board_fuses.osccfg = 0x01 +board_fuses.tcd0cfg = 0x00 +board_fuses.syscfg0 = 0xC9 +board_fuses.syscfg1 = 0x06 +board_fuses.append = 0x00 +board_fuses.bootend = 0x00 +``` From 78545afd8c41c08653d855cf777ab0330cc89669 Mon Sep 17 00:00:00 2001 From: Joshua Scoggins Date: Mon, 25 Mar 2024 19:23:17 -0700 Subject: [PATCH 328/351] Provide libmodbus compatibility with as few changes as possible --- megaavr/cores/coreX-corefiles/api/Client.h | 5 ++++- megaavr/cores/coreX-corefiles/api/IPAddress.h | 3 +++ megaavr/cores/coreX-corefiles/api/Udp.h | 5 ++++- 3 files changed, 11 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/api/Client.h b/megaavr/cores/coreX-corefiles/api/Client.h index 25cbd95..e42a66a 100644 --- a/megaavr/cores/coreX-corefiles/api/Client.h +++ b/megaavr/cores/coreX-corefiles/api/Client.h @@ -21,7 +21,7 @@ #include "IPAddress.h" #include "Stream.h" - +namespace arduino { class Client : public Stream { public: @@ -41,3 +41,6 @@ class Client : public Stream protected: uint8_t *rawIPAddress(IPAddress &addr) { return addr.raw_address(); }; }; +} +using arduino::Client; + diff --git a/megaavr/cores/coreX-corefiles/api/IPAddress.h b/megaavr/cores/coreX-corefiles/api/IPAddress.h index e95c8fb..59cf9d7 100644 --- a/megaavr/cores/coreX-corefiles/api/IPAddress.h +++ b/megaavr/cores/coreX-corefiles/api/IPAddress.h @@ -24,6 +24,7 @@ #include "Printable.h" #include "String.h" +namespace arduino { // A class to make it easier to handle and pass around IP addresses class IPAddress : public Printable @@ -75,3 +76,5 @@ class IPAddress : public Printable }; extern const IPAddress INADDR_NONE; +} +using arduino::IPAddress; diff --git a/megaavr/cores/coreX-corefiles/api/Udp.h b/megaavr/cores/coreX-corefiles/api/Udp.h index 9c13995..252f7a4 100644 --- a/megaavr/cores/coreX-corefiles/api/Udp.h +++ b/megaavr/cores/coreX-corefiles/api/Udp.h @@ -36,7 +36,7 @@ #include "Stream.h" #include "IPAddress.h" - +namespace arduino { class UDP : public Stream { public: @@ -84,3 +84,6 @@ class UDP : public Stream protected: uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); }; }; +} + +using arduino::UDP; From 7e5cbf3d9cafccd741d63d7d881b9f5854262242 Mon Sep 17 00:00:00 2001 From: Joshua Scoggins Date: Mon, 25 Mar 2024 19:28:05 -0700 Subject: [PATCH 329/351] Define the serial connections for the standard pinouts --- .../variants/28pin-standard/pins_arduino.h | 19 ++++++++++++++++++ .../variants/32pin-standard/pins_arduino.h | 19 ++++++++++++++++++ .../variants/40pin-standard/pins_arduino.h | 20 +++++++++++++++++++ .../variants/48pin-standard/pins_arduino.h | 20 +++++++++++++++++++ 4 files changed, 78 insertions(+) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index e66f077..c036e77 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -302,6 +302,25 @@ const uint8_t digital_pin_to_timer[] = { #endif +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_HARDWARE_OPEN Serial2 + void initVariant() __attribute__((weak)); void initVariant() { } diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index 77b71cd..b0ca2ff 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -340,6 +340,25 @@ const uint8_t digital_pin_to_timer[] = { #endif +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_HARDWARE_OPEN Serial2 + void initVariant() __attribute__((weak)); void initVariant() { } diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index 5d7a334..65b8e03 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -378,6 +378,26 @@ const uint8_t digital_pin_to_timer[] = { #endif +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_HARDWARE_OPEN Serial2 + + void initVariant() __attribute__((weak)); void initVariant() { diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index 1edb899..ec7e9de 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -446,6 +446,26 @@ const uint8_t digital_pin_to_timer[] = { #endif +// These serial port names are intended to allow libraries and architecture-neutral +// sketches to automatically default to the correct port name for a particular type +// of use. For example, a GPS module would normally connect to SERIAL_PORT_HARDWARE_OPEN, +// the first hardware serial port whose RX/TX pins are not dedicated to another use. +// +// SERIAL_PORT_MONITOR Port which normally prints to the Arduino Serial Monitor +// +// SERIAL_PORT_USBVIRTUAL Port which is USB virtual serial +// +// SERIAL_PORT_LINUXBRIDGE Port which connects to a Linux system via Bridge library +// +// SERIAL_PORT_HARDWARE Hardware serial port, physical RX & TX pins. +// +// SERIAL_PORT_HARDWARE_OPEN Hardware serial ports which are open for use. Their RX & TX +// pins are NOT connected to anything by default. +#define SERIAL_PORT_MONITOR Serial +#define SERIAL_PORT_HARDWARE Serial1 +#define SERIAL_PORT_HARDWARE_OPEN Serial2 +#define SERIAL_PORT_HARDWARE_OPEN2 Serial3 + void initVariant() __attribute__((weak)); void initVariant() { } From 75a6452b162317226034a0cfafc5750fc2749439 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 10 Oct 2024 19:58:01 +0200 Subject: [PATCH 330/351] Add PICkit5 UPDI programmer option --- megaavr/programmers.txt | 28 ++++++++++++++++++---------- 1 file changed, 18 insertions(+), 10 deletions(-) diff --git a/megaavr/programmers.txt b/megaavr/programmers.txt index a65ff03..cbc933e 100644 --- a/megaavr/programmers.txt +++ b/megaavr/programmers.txt @@ -1,9 +1,3 @@ -xplainedmini.name=microUPDI/Uno Wifi -xplainedmini.communication=usb -xplainedmini.protocol=xplainedmini_updi -xplainedmini.program.protocol=xplainedmini_updi -xplainedmini.program.tool=avrdude -xplainedmini.program.extra_params= serialupdi_57600.name=SerialUPDI (57600 baud) serialupdi_57600.communication=serial @@ -29,6 +23,13 @@ serialupdi_460800.protocol=serialupdi serialupdi_460800.program.tool=avrdude serialupdi_460800.program.extra_params=-P{serial.port} -b460800 -xrtsdtr=high +xplainedmini.name=microUPDI/Uno Wifi +xplainedmini.communication=usb +xplainedmini.protocol=xplainedmini_updi +xplainedmini.program.protocol=xplainedmini_updi +xplainedmini.program.tool=avrdude +xplainedmini.program.extra_params= + jtag2updi.name=JTAG2UPDI jtag2updi.communication=serial jtag2updi.protocol=jtag2updi @@ -49,30 +50,37 @@ xplainedpro.program.protocol=xplainedpro_updi xplainedpro.program.tool=avrdude xplainedpro.program.extra_params= +pickit5_updi.name=PICkit5 UPDI +pickit5_updi.communication=usb +pickit5_updi.protocol=pickit5_updi +pickit5_updi.program.protocol=pickit5_updi +pickit5_updi.program.tool=avrdude +pickit5_updi.program.extra_params= + pickit4_updi.name=PICkit4 UPDI pickit4_updi.communication=usb pickit4_updi.protocol=pickit4_updi -pickit4_updi.program.protocol=jtagice3_updi +pickit4_updi.program.protocol=pickit4_updi pickit4_updi.program.tool=avrdude pickit4_updi.program.extra_params= snap_updi.name=MPLAB SNAP UPDI snap_updi.communication=usb snap_updi.protocol=snap_updi -snap_updi.program.protocol=jtagice3_updi +snap_updi.program.protocol=snap_updi snap_updi.program.tool=avrdude snap_updi.program.extra_params= atmelice_updi.name=Atmel-ICE UPDI atmelice_updi.communication=usb atmelice_updi.protocol=atmelice_updi -atmelice_updi.program.protocol=jtagice3_updi +atmelice_updi.program.protocol=atmelice_updi atmelice_updi.program.tool=avrdude atmelice_updi.program.extra_params= jtagice3_updi.name=JTAGICE3 UPDI jtagice3_updi.communication=usb jtagice3_updi.protocol=jtag3updi -jtagice3_updi.program.protocol=jtagice3_updi +jtagice3_updi.program.protocol=jtag3updi jtagice3_updi.program.tool=avrdude atmelice_updi.program.extra_params= \ No newline at end of file From 2e2f9e0532f2a1ae65d8ba040da9a5623db71b79 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 10 Oct 2024 20:03:13 +0200 Subject: [PATCH 331/351] SPI pinswap 2 is available Closes #199 --- megaavr/variants/48pin-standard/pins_arduino.h | 1 - 1 file changed, 1 deletion(-) diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index ec7e9de..c826f11 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -116,7 +116,6 @@ // SPI 0 // No pinswap enabled by default -// Pinswap 2 not available #define SPI_INTERFACES_COUNT 1 #define SPI_MUX PORTMUX_SPI0_DEFAULT_gc #define SPI_MUX_PINSWAP_1 PORTMUX_SPI0_ALT1_gc From 17c75ea26d252931ba104e5c04731ea5165eca29 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 10 Oct 2024 21:01:35 +0200 Subject: [PATCH 332/351] Remove local avrdude.conf file We'll use the one that Avrdude ships with instead --- megaavr/avrdude.conf | 16196 ----------------------------------------- 1 file changed, 16196 deletions(-) delete mode 100644 megaavr/avrdude.conf diff --git a/megaavr/avrdude.conf b/megaavr/avrdude.conf deleted file mode 100644 index ade0ddb..0000000 --- a/megaavr/avrdude.conf +++ /dev/null @@ -1,16196 +0,0 @@ -# $Id$ -*- text -*- -# -# AVRDUDE Configuration File -# -# This file contains configuration data used by AVRDUDE which describes -# the programming hardware pinouts and also provides part definitions. -# AVRDUDE's "-C" command line option specifies the location of the -# configuration file. The "-c" option names the programmer configuration -# which must match one of the entry's "id" parameter. The "-p" option -# identifies which part AVRDUDE is going to be programming and must match -# one of the parts' "id" parameter. -# -# DO NOT MODIFY THIS FILE. Modifications will be overwritten the next -# time a "make install" is run. For user-specific additions, use the -# "-C +filename" command line option. -# -# Possible entry formats are: -# -# programmer -# parent # optional parent -# id = [, ... ] ; # are quoted strings -# desc = ; # quoted string -# type = ; # programmer type, quoted string -# # supported types can be listed by "-c ?type" -# prog_modes = PM_ {| PM_} # interfaces, eg, PM_SPM|PM_PDI (1) -# connection_type = parallel | serial | usb | spi -# baudrate = ; # baudrate for avr910-programmer -# vcc = [, ... ] ; # pin number(s) -# buff = [, ... ] ; # pin number(s) -# reset = ; # pin number -# sck = ; # pin number -# sdo = ; # pin number -# sdi = ; # pin number -# errled = ; # pin number -# rdyled = ; # pin number -# pgmled = ; # pin number -# vfyled = ; # pin number -# usbvid = ; # USB VID (Vendor ID) -# usbpid = [, ...] ; # USB PID (Product ID) (2) -# usbdev = ; # USB interface or other device info -# usbvendor = ; # USB Vendor Name -# usbproduct = ; # USB Product Name -# usbsn = ; # USB Serial Number -# hvupdi_support = [, , ... ] ; # UPDI HV Variants Support -# ; -# -# # To invert a pin use = ~ -# # To invert a pin list (all pins get inverted) use ~ ( [, ... ] ) -# # -# # (1) The following program modes are known: -# # - PM_SPM: Bootloaders, self-programming with SPM opcodes or NVM Controllers -# # - PM_TPI: Tiny Programming Interface (t4, t5, t9, t10, t20, t40, t102, t104) -# # - PM_ISP: SPI programming for In-System Programming (almost all classic parts) -# # - PM_PDI: Program and Debug Interface (xmega parts) -# # - PM_UPDI: Unified Program and Debug Interface -# # - PM_HVSP: High Voltage Serial Programming (some classic parts) -# # - PM_HVPP: High Voltage Parallel Programming (most non-HVSP classic parts) -# # - PM_debugWIRE: Simpler alternative to JTAG (a subset of HVPP/HVSP parts) -# # - PM_JTAG: Joint Test Action Group standard (some classic parts) -# # - PM_JTAGmkI: Subset of PM_JTAG, older parts, Atmel ICE mkI -# # - PM_XMEGAJTAG: JTAG, some XMEGA parts -# # - PM_AVR32JTAG: JTAG for 32-bit AVRs -# # - PM_aWire: AVR32 parts -# # -# # (2) Not all programmer types can process a list of PIDs -# -# part -# desc = ; # quoted string -# id = ; # quoted string -# family_id = ; # quoted string, eg, "megaAVR" or "tinyAVR" -# prog_modes = PM_ {| PM_} # interfaces, eg, PM_SPM|PM_ISP|PM_HVPP|PM_debugWIRE -# mcuid = ; # unique id in 0..2039 for 8-bit AVRs -# n_interrupts = ; # number of interrupts, used for vector bootloaders -# n_page_erase = ; # if set, number of pages erased during SPM erase -# n_boot_sections = ; # Number of boot sections -# boot_section_size = ; # Size of (smallest) boot section, if any -# hvupdi_variant = ; # numeric -1 (n/a) or 0..2 -# devicecode = ; # deprecated, use stk500_devcode -# stk500_devcode = ; # numeric -# avr910_devcode = ; # numeric -# has_jtag = ; # part has JTAG i/f (deprecated, use prog_modes) -# has_debugwire = ; # part has debugWire i/f (deprecated, use prog_modes) -# has_pdi = ; # part has PDI i/f (deprecated, use prog_modes) -# has_updi = ; # part has UPDI i/f (deprecated, use prog_modes) -# has_tpi = ; # part has TPI i/f (deprecated, use prog_modes) -# is_avr32 = ; # AVR32 part (deprecated, use prog_modes) -# is_at90s1200 = ; # AT90S1200 part -# signature = ; # signature bytes -# usbpid = ; # DFU USB PID -# chip_erase_delay = ; # micro-seconds -# reset = dedicated | io ; -# retry_pulse = reset | sck ; -# chip_erase_delay = ; # chip erase delay (us) -# # STK500 parameters (parallel programming IO lines) -# pagel = ; # pin name in hex, i.e., 0xD7 -# bs2 = ; # pin name in hex, i.e., 0xA0 -# serial = ; # can use serial downloading -# parallel = ; # can use par. programming -# # STK500v2 parameters, to be taken from Atmel's ATDF files -# timeout = ; -# stabdelay = ; -# cmdexedelay = ; -# synchloops = ; -# bytedelay = ; -# pollvalue = ; -# pollindex = ; -# predelay = ; -# postdelay = ; -# pollmethod = ; -# hvspcmdexedelay = ; -# # STK500v2 HV programming parameters, from ATDFs -# pp_controlstack = , , ... ; # PP only -# hvsp_controlstack = , , ... ; # HVSP only -# flash_instr = , , ; -# eeprom_instr = , , ... ; -# hventerstabdelay = ; -# progmodedelay = ; # PP only -# latchcycles = ; -# togglevtg = ; -# poweroffdelay = ; -# resetdelayms = ; -# resetdelayus = ; -# hvleavestabdelay = ; -# resetdelay = ; -# synchcycles = ; # HVSP only -# chiperasepulsewidth = ; # PP only -# chiperasepolltimeout = ; -# chiperasetime = ; # HVSP only -# programfusepulsewidth = ; # PP only -# programfusepolltimeout = ; -# programlockpulsewidth = ; # PP only -# programlockpolltimeout = ; -# # debugWIRE and/or JTAG ICE mkII parameters, also from ATDF files -# allowfullpagebitstream = ; -# enablepageprogramming = ; -# idr = ; # IO addr of IDR (OCD) reg -# rampz = ; # IO addr of RAMPZ reg -# spmcr = ; # mem addr of SPMC[S]R reg -# eecr = ; # mem addr of EECR reg only when != 0x3f -# eind = ; # mem addr of EIND reg -# mcu_base = ; -# nvm_base = ; -# ocd_base = ; -# ocdrev = ; -# pgm_enable = ; -# chip_erase = ; -# # parameters for bootloaders -# autobaud_sync = ; # autobaud detection byte, default 0x30 -# -# memory -# paged = ; # yes/no (flash only, do not use for EEPROM) -# offset = ; # memory offset -# size = ; # bytes -# page_size = ; # bytes -# num_pages = ; # numeric -# n_word_writes = ; # TPI only: if set, number of words to write -# min_write_delay = ; # micro-seconds -# max_write_delay = ; # micro-seconds -# readback = ; # pair of byte values -# readback_p1 = ; # byte value (first component) -# readback_p2 = ; # byte value (second component) -# pwroff_after_write = ; # yes/no -# mode = ; # STK500 v2 file parameter from ATDF files -# delay = ; # " -# blocksize = ; # " -# readsize = ; # " -# read = ; -# write = ; -# read_lo = ; -# read_hi = ; -# write_lo = ; -# write_hi = ; -# loadpage_lo = ; -# loadpage_hi = ; -# writepage = ; -# ; -# ; -# -# If any of the above parameters are not specified, the default value -# of 0 is used for numerics (except for mcuid, hvupdi_variant and -# ocdrev, where the default value is -1, and for autobaud_sync which -# defaults to 0x30), or the empty string "" for string values. If a -# required parameter is left empty, AVRDUDE will complain. Almost all -# occurrences of numbers (with the exception of pin numbers and where -# they are separated by space, eg, in signature and readback) can also -# be given as simple expressions involving arithemtic and bitwise -# operators. -# -# Parts can also inherit parameters from previously defined parts -# using the following syntax. In this case specified integer and -# string values override parameter values from the parent part. New -# memory definitions are added to the definitions inherited from the -# parent. If, however, a new memory definition refers to an existing -# one of the same name for that part then, from v7.1, the existing -# memory definition is extended, and components overwritten with new -# values. Assigning NULL removes an inherited SPI instruction format, -# memory definition, control stack, eeprom or flash instruction, eg, -# as in memory "efuse" = NULL; -# -# part parent # quoted string -# id = ; # quoted string -# -# ; -# -# NOTES: -# * 'devicecode' is the device code used by the STK500 (see codes -# listed below) -# * Not all memory types will implement all instructions -# * AVR Fuse bits and Lock bits are implemented as a type of memory -# * Example memory types are: -# "flash", "eeprom", "fuse", "lfuse" (low fuse), "hfuse" (high -# fuse), "signature", "calibration", "lock" -# * The memory type specified on the avrdude command line must match -# one of the memory types defined for the specified chip -# * The pwroff_after_write flag causes avrdude to attempt to -# power the device off and back on after an unsuccessful write to -# the affected memory area if VCC programmer pins are defined. If -# VCC pins are not defined for the programmer, a message -# indicating that the device needs a power-cycle is printed out. -# This flag was added to work around a problem with the -# at90s4433/2333's; see the at90s4433 errata at: -# -# http://www.atmel.com/dyn/resources/prod_documents/doc1280.pdf -# -# INSTRUCTION FORMATS -# -# Instruction formats are specified as a comma separated list of -# string values containing information (bit specifiers) about each -# of the 32 bits of the instruction. Bit specifiers may be one of -# the following formats: -# -# '1' = the bit is always set on input as well as output -# -# '0' = the bit is always clear on input as well as output -# -# 'x' = the bit is ignored on input and output and set as 0 -# -# 'a' = the bit is an address bit; from v 7.1 the bit-number -# is set to match the right bit position for the -# instruction to "just work" -# -# 'aN' = the bit is the Nth address bit, bit-number = N, i.e., a12 -# is address bit 12 on input, a0 is address bit 0. -# -# 'i' = the bit is an input data bit -# -# 'o' = the bit is an output data bit -# -# Each instruction must be composed of 32 bit specifiers. The -# instruction specification closely follows the instruction data -# provided in Atmel's data sheets for their parts. Note that flash -# addresses always refer to *word* addresses whilst all other -# memory types specify *byte* addresses. -# -# Example for signature read on the ATmega328P: -# read = "0 0 1 1 0 0 0 0", "0 0 0 x x x x x", -# "x x x x x x a1 a0", "o o o o o o o o"; -# -# As the address bit numbers in the SPI opcodes are highly -# systematic, they don't really need to be specified. A compact -# version of the format specification neither uses bit-numbers for -# address lines nor spaces. If such a string is longer than 7 -# characters, then the characters 0, 1, x, a, i and o will be -# recognised as the corresponding bit, whilst any of the characters -# ., -, _ or / can act as arbitrary visual separators, which are -# ignored. Examples: -# -# loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; -# -# loadpage_lo = "0100.0000", "000x.xxxx", "xxaa.aaaa", "iiii.iiii"; -# -# -# The following are STK500 part device codes to use for the -# "devicecode" field of the part. These came from Atmel's software -# section avr061.zip which accompanies the application note -# AVR061 available from: -# -# https://ww1.microchip.com/downloads/en/Appnotes/doc2525.pdf -# - -#define ATTINY10 0x10 /* the _old_ one that never existed! */ -#define ATTINY11 0x11 -#define ATTINY12 0x12 -#define ATTINY15 0x13 -#define ATTINY13 0x14 - -#define ATTINY22 0x20 -#define ATTINY26 0x21 -#define ATTINY28 0x22 -#define ATTINY2313 0x23 - -#define AT90S1200 0x33 - -#define AT90S2313 0x40 -#define AT90S2323 0x41 -#define AT90S2333 0x42 -#define AT90S2343 0x43 - -#define AT90S4414 0x50 -#define AT90S4433 0x51 -#define AT90S4434 0x52 -#define ATMEGA48 0x59 - -#define AT90S8515 0x60 -#define AT90S8535 0x61 -#define AT90C8534 0x62 -#define ATMEGA8515 0x63 -#define ATMEGA8535 0x64 - -#define ATMEGA8 0x70 -#define ATMEGA88 0x73 -#define ATMEGA168 0x86 - -#define ATMEGA161 0x80 -#define ATMEGA163 0x81 -#define ATMEGA16 0x82 -#define ATMEGA162 0x83 -#define ATMEGA169 0x84 - -#define ATMEGA323 0x90 -#define ATMEGA32 0x91 - -#define ATMEGA64 0xA0 - -#define ATMEGA103 0xB1 -#define ATMEGA128 0xB2 -#define AT90CAN128 0xB3 -#define AT90CAN64 0xB3 -#define AT90CAN32 0xB3 - -#define AT86RF401 0xD0 - -#define AT89START 0xE0 -#define AT89S51 0xE0 -#define AT89S52 0xE1 - -# The following table lists the devices in the original AVR910 -# appnote: -# |Device |Signature | Code | -# +-------+----------+------+ -# |tiny12 | 1E 90 05 | 0x55 | -# |tiny15 | 1E 90 06 | 0x56 | -# | | | | -# | S1200 | 1E 90 01 | 0x13 | -# | | | | -# | S2313 | 1E 91 01 | 0x20 | -# | S2323 | 1E 91 02 | 0x48 | -# | S2333 | 1E 91 05 | 0x34 | -# | S2343 | 1E 91 03 | 0x4C | -# | | | | -# | S4414 | 1E 92 01 | 0x28 | -# | S4433 | 1E 92 03 | 0x30 | -# | S4434 | 1E 92 02 | 0x6C | -# | | | | -# | S8515 | 1E 93 01 | 0x38 | -# | S8535 | 1E 93 03 | 0x68 | -# | | | | -# |mega32 | 1E 95 01 | 0x72 | -# |mega83 | 1E 93 05 | 0x65 | -# |mega103| 1E 97 01 | 0x41 | -# |mega161| 1E 94 01 | 0x60 | -# |mega163| 1E 94 02 | 0x64 | - -# Appnote AVR109 also has a table of AVR910 device codes, which -# lists: -# dev avr910 signature -# ATmega8 0x77 0x1E 0x93 0x07 -# ATmega8515 0x3B 0x1E 0x93 0x06 -# ATmega8535 0x6A 0x1E 0x93 0x08 -# ATmega16 0x75 0x1E 0x94 0x03 -# ATmega162 0x63 0x1E 0x94 0x04 -# ATmega163 0x66 0x1E 0x94 0x02 -# ATmega169 0x79 0x1E 0x94 0x05 -# ATmega32 0x7F 0x1E 0x95 0x02 -# ATmega323 0x73 0x1E 0x95 0x01 -# ATmega64 0x46 0x1E 0x96 0x02 -# ATmega128 0x44 0x1E 0x97 0x02 -# -# These codes refer to "BOOT" device codes which are apparently -# different than standard device codes, for whatever reasons -# (often one above the standard code). - -# There are several extended versions of AVR910 implementations around -# in the Internet. These add the following codes (only devices that -# actually exist are listed): - -# ATmega8515 0x3A -# ATmega128 0x43 -# ATmega64 0x45 -# ATtiny26 0x5E -# ATmega8535 0x69 -# ATmega32 0x72 -# ATmega16 0x74 -# ATmega8 0x76 -# ATmega169 0x78 - -# -# Overall avrdude defaults; suitable for ~/.config/avrdude/avrdude.rc -# -default_parallel = "/dev/parport0"; -default_serial = "/dev/ttyS0"; -default_spi = ""; -# default_bitclock = 2.5; - - - - - - - -# -# PROGRAMMER DEFINITIONS -# - -#------------------------------------------------------------ -# wiring -#------------------------------------------------------------ - -# http://wiring.org.co/ -# Basically STK500v2 protocol, with some glue to trigger the bootloader - -programmer - id = "wiring"; - desc = "Wiring for bootloader using STK500 v2 protocol"; - type = "wiring"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# arduino -#------------------------------------------------------------ - -programmer - id = "arduino"; - desc = "Arduino for bootloader using STK500 v1 protocol"; - type = "arduino"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# urclock -#------------------------------------------------------------ - -# See https://github.com/stefanrueger/urboot -programmer - id = "urclock"; - desc = "Urclock programmer for urboot bootloaders using urprotocol"; - type = "urclock"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# xbee -#------------------------------------------------------------ - -programmer - id = "xbee"; - desc = "XBee for Series 2 Over-The-Air (XBeeBoot) bootloader using STK500 v1 protocol"; - type = "xbee"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# ft2232h -#------------------------------------------------------------ - -# this will interface with the chips on these programmers: -# -# http://real.kiev.ua/old/avreal/en/adapters -# http://www.amontec.com/jtagkey.shtml, jtagkey-tiny.shtml -# http://www.olimex.com/dev/arm-usb-ocd.html, arm-usb-tiny.html -# http://www.ethernut.de/en/hardware/turtelizer/index.html -# http://elk.informatik.fh-augsburg.de/hhweb/doc/openocd/usbjtag/usbjtag.html -# http://dangerousprototypes.com/docs/FT2232_breakout_board -# http://www.ftdichip.com/Products/Modules/DLPModules.htm,DLP-2232*,DLP-USB1232H -# http://flashrom.org/FT2232SPI_Programmer -# -# The drivers will look for a specific device and use the first one found. -# If you have mulitple devices, then look for unique information (like SN) -# And fill that in here. -# -# Note that the pin numbers for the main ISP signals (reset, sck, -# sdo, sdi) are fixed and cannot be changed, since they must match -# the way the Multi-Protocol Synchronous Serial Engine (MPSSE) of -# these FTDI ICs has been designed. - -programmer - id = "ft2232h"; - desc = "FT2232H based generic programmer"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x6010; - usbdev = "A"; -# ISP-signals - lower ADBUS-Nibble (default) - reset = 3; # AD3 (TMS) - sck = 0; # AD0 (TCK) - sdo = 1; # AD1 (TDI) - sdi = 2; # AD2 (TDO) -; - -#------------------------------------------------------------ -# avrftdi -#------------------------------------------------------------ - -programmer parent "ft2232h" - id = "avrftdi"; - desc = "FT2232D based generic programmer"; -; - -#------------------------------------------------------------ -# 2232HIO -#------------------------------------------------------------ - -# This is an implementation of the above with a buffer IC (74AC244) and -# 4 LEDs directly attached, all active low. - -programmer parent "ft2232h" - id = "2232hio"; - desc = "2232hio based on FT2232H with buffer and LEDs"; - buff = ~4; -# LED SIGNALs - errled = ~11; - rdyled = ~14; - pgmled = ~13; - vfyled = ~12; -; - -#------------------------------------------------------------ -# tigard -#------------------------------------------------------------ - -# Tigard - FT2232H based multi-protocol tool for hardware hacking -# https://github.com/tigard-tools/tigard - -programmer parent "ft2232h" - id = "tigard"; - desc = "Tigard interface board"; - usbdev = "B"; -# Reset is different to the FT2232H; sck, sdo, sdi remain at 0, 1, 2 - reset = 5; # BD5 (GPIOL1) -; - -#------------------------------------------------------------ -# ft4232h -#------------------------------------------------------------ - -#The FT4232H can be treated as FT2232H, but it has a different USB -#device ID of 0x6011. - -programmer parent "ft2232h" - id = "ft4232h"; - desc = "FT4232H based generic programmer"; - usbpid = 0x6011; -; - -#------------------------------------------------------------ -# 4232h -#------------------------------------------------------------ - -programmer parent "ft4232h" - id = "4232h"; -; - -#------------------------------------------------------------ -# jtagkey -#------------------------------------------------------------ - -programmer - id = "jtagkey"; - desc = "Amontec JTAGKey, JTAGKey-Tiny and JTAGKey2"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; -# Note: This PID is used in all JTAGKey variants - usbpid = 0xcff8; - usbdev = "A"; - buff = ~4; -# ISP-signals => 20 - Pin connector on JTAGKey - reset = 3; # TMS 7 violet - sck = 0; # TCK 9 white - sdo = 1; # TDI 5 green - sdi = 2; # TDO 13 orange -# VTG VREF 1 brown with red tip -# GND GND 20 black -# The colors are on the 20 pin breakout cable from Amontec -; - -#------------------------------------------------------------ -# ft232h -#------------------------------------------------------------ - -programmer - id = "ft232h"; - desc = "FT232H based generic programmer"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x6014; - usbdev = "A"; -# ISP-signals - reset = 3; # AD3 (TMS) - sck = 0; # AD0 (TCK) - sdo = 1; # AD1 (TDI) - sdi = 2; # AD2 (TDO) -; - -#------------------------------------------------------------ -# um232h -#------------------------------------------------------------ - -# Pin J2-7 (AD0) is SCK -# Pin J2-8 (AD1) is SDO -# Pin J2-9 (AD2) is SDI -# Pin J2-10 (AD3) is RESET -# Pin J2-6 is GND -# Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get -# a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. - -programmer parent "ft232h" - id = "um232h"; - desc = "UM232H module from FTDI"; -; - -#------------------------------------------------------------ -# c232hm -#------------------------------------------------------------ - -# Orange (Pin 2) is SCK -# Yellow (Pin 3) is SDO -# Green (Pin 4) is SDI -# Brown (Pin 5) is RESET -# Black (Pin 10) is GND -# Use the -b flag to set the SPI clock rate eg -b 3750000 is the fastest I could get -# a 16MHz Atmega1280 to program reliably. The 232H is conveniently 5V tolerant. - -programmer parent "ft232h" - id = "c232hm"; - desc = "C232HM cable from FTDI"; -; - -#------------------------------------------------------------ -# o-link -#------------------------------------------------------------ - -# On the adapter you can read "O-Link". On the PCB is printed "OpenJTAG v3.1" -# You can find it as "OpenJTAG ARM JTAG USB" in the internet. -# (But there are also several projects called Open JTAG, eg. -# http://www.openjtag.org, which are completely different.) -# http://www.100ask.net/shop/english.html (website seems to be outdated) -# http://item.taobao.com/item.htm?id=1559277013 -# http://www.micro4you.com/store/openjtag-arm-jtag-usb.html (schematics!) -# some other sources which call it O-Link -# http://www.andahammer.com/olink/ -# http://www.developmentboard.net/31-o-link-debugger.html -# http://armwerks.com/catalog/o-link-debugger-copy/ -# or just have a look at ebay ... -# It is basically the same entry as jtagkey with different usb ids. - -programmer parent "jtagkey" - id = "o-link"; - desc = "O-Link, OpenJTAG from www.100ask.net"; - usbvid = 0x1457; - usbpid = 0x5118; - usbvendor = "www.100ask.net"; - usbproduct = "USB<=>JTAG&RS232"; -; - -#------------------------------------------------------------ -# openmoko -#------------------------------------------------------------ - -# http://wiki.openmoko.org/wiki/Debug_Board_v3 - -programmer - id = "openmoko"; - desc = "Openmoko debug board (v3)"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - usbvid = 0x1457; - usbpid = 0x5118; - usbdev = "A"; - reset = 3; # TMS 7 - sck = 0; # TCK 9 - sdo = 1; # TDI 5 - sdi = 2; # TDO 13 -; - -#------------------------------------------------------------ -# lm3s811 -#------------------------------------------------------------ - -# Only Rev. A boards. -# Schematic and user manual: http://www.cs.put.poznan.pl/wswitala/download/pdf/811EVBK.pdf - -programmer - id = "lm3s811"; - desc = "Luminary Micro LM3S811 Eval Board (Rev. A)"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0xbcd9; - usbdev = "A"; - usbvendor = "LMI"; - usbproduct = "LM3S811 Evaluation Board"; -# Enable correct buffers - buff = 7; -# ISP-signals - lower ACBUS-Nibble (default) - reset = 3; - sck = 0; - sdo = 1; - sdi = 2; -; - -#------------------------------------------------------------ -# tumpa -#------------------------------------------------------------ - -# submitted as bug #46020 - -programmer - id = "tumpa"; - desc = "TIAO USB Multi-Protocol Adapter"; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x8a98; - usbdev = "A"; - usbvendor = "TIAO"; - reset = 3; # TMS 7 - sck = 0; # TCK 9 - sdo = 1; # TDI 5 - sdi = 2; # TDO 13 -; - -#------------------------------------------------------------ -# ktlink -#------------------------------------------------------------ - -# Kristech KT-LINK FT2232H interface with IO switching and voltage buffers. -# Created on 20220410 by CeDeROM Tomasz CEDRO (www.cederom.io). -# Interface DataSheet: https://kristech.pl/files/KT-LINK-UM-ENG.pdf -# AVRDUDE FT2232H PIN NUMBER DECODE: -# | 0 | 1 | .. | 7 | 8 | 9 | .. | 15 | -# | ADBUS0 | ADBUS1 | .. | ADBUS7 | ACBUS0 | ACBUS1 | .. | ACBUS7 | -# KT-LINK JTAG CONN: -# 1=Vsense(->EXT13), 19=5V(EXT1->EXT3), 20=GND, 3=TPIRST, 9=TPICLK, 7=TPIDATA. -# INTERNALS CONFIGURATION ("~" MEANS ACTIVE LOW): -# ~TRST_EN=10(ACBUS2), ~CLK_EN=14(ACBUS6), ~SDO_EN=13(ACBUS5), -# TMS_SEL=5(ADBUS5), ~TMS_EN=12(ACBUS4), LED=~15(ACBUS7). -# CONNECTION NOTES: -# * Connect EXT connector pin 1 with 3 to get 5V on JTAG connector pin 19. -# * Connect JTAG connector pin 1 to 5V (i.e. EXT pin 13 or JTAG pin 19). -# * For TPI connection use resistors: TDO --[470R]-- TPIDATA --[470R]-- TDI. -# * Powering target from JTAG pin 19 allows KT-LINK current measurement. - -programmer - id = "ktlink"; - desc = "KT-LINK FT2232H interface with IO switching and voltage buffers."; - type = "avrftdi"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0xbbe2; - usbdev = "A"; - buff = 5, ~10, ~13, ~14; - reset = 8; - sck = 0; - sdo = 1; - sdi = 2; - rdyled = ~15; -; - -#------------------------------------------------------------ -# digilent-hs2 -#------------------------------------------------------------ - -# Digilent JTAG HS2 programmer. FT232H-based dongle with buffers. -# https://digilent.com/reference/_media/reference/programmers/jtag-hs2/jtag-hs2_rm.pdf - -programmer - id = "digilent-hs2"; - desc = "Digilient JTAG HS2 (MPSSE)"; - type = "avrftdi"; - connection_type = usb; - usbvid = 0x0403; - usbpid = 0x6014; - usbdev = "A"; - buff = 5, 6, 7; - reset = 3; - sck = 0; - sdo = 1; - sdi = 2; -; - -#------------------------------------------------------------ -# serialupdi -#------------------------------------------------------------ - -programmer - id = "serialupdi"; - desc = "SerialUPDI"; - type = "serialupdi"; - prog_modes = PM_UPDI; - connection_type = serial; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# avrisp -#------------------------------------------------------------ - -programmer - id = "avrisp"; - desc = "Atmel AVR ISP"; - type = "stk500"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# avrispv2 -#------------------------------------------------------------ - -programmer - id = "avrispv2"; - desc = "Atmel AVR ISP v2"; - type = "stk500v2"; - prog_modes = PM_TPI | PM_ISP | PM_PDI; - connection_type = serial; -; - -#------------------------------------------------------------ -# avrispmkII -#------------------------------------------------------------ - -programmer - id = "avrispmkII"; - desc = "Atmel AVR ISP mkII"; - type = "stk500v2"; - prog_modes = PM_TPI | PM_ISP | PM_PDI; - connection_type = usb; -; - -#------------------------------------------------------------ -# avrisp2 -#------------------------------------------------------------ - -programmer parent "avrispmkII" - id = "avrisp2"; -; - -#------------------------------------------------------------ -# buspirate -#------------------------------------------------------------ - -programmer - id = "buspirate"; - desc = "The Bus Pirate"; - type = "buspirate"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# buspirate_bb -#------------------------------------------------------------ - -programmer - id = "buspirate_bb"; - desc = "The Bus Pirate (bitbang interface, supports TPI)"; - type = "buspirate_bb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; - # pins are bits in bitbang byte (numbers are 87654321) - # 1|POWER|PULLUP|AUX|SDO|CLK|SDI|CS - reset = 1; - sck = 3; - sdo = 4; - sdi = 2; - # vcc = 7; # Internally set independent of this setting -; - -#------------------------------------------------------------ -# stk500 -#------------------------------------------------------------ - -# This is supposed to be the "default" STK500 entry. -# Attempts to select the correct firmware version -# by probing for it. Better use one of the entries -# below instead. - -programmer - id = "stk500"; - desc = "Atmel STK500"; - type = "stk500generic"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# stk500v1 -#------------------------------------------------------------ - -programmer - id = "stk500v1"; - desc = "Atmel STK500 version 1.x firmware"; - type = "stk500"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# mib510 -#------------------------------------------------------------ - -programmer - id = "mib510"; - desc = "Crossbow MIB510 programming board"; - type = "stk500"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# stk500v2 -#------------------------------------------------------------ - -programmer - id = "stk500v2"; - desc = "Atmel STK500 version 2.x firmware"; - type = "stk500v2"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# stk500pp -#------------------------------------------------------------ - -programmer - id = "stk500pp"; - desc = "Atmel STK500 v2 in parallel programming mode"; - type = "stk500pp"; - prog_modes = PM_HVPP; - connection_type = serial; -; - -#------------------------------------------------------------ -# stk500hvsp -#------------------------------------------------------------ - -programmer - id = "stk500hvsp"; - desc = "Atmel STK500 v2 in high-voltage serial programming mode"; - type = "stk500hvsp"; - prog_modes = PM_HVSP; - connection_type = serial; -; - -#------------------------------------------------------------ -# stk600 -#------------------------------------------------------------ - -programmer - id = "stk600"; - desc = "Atmel STK600"; - type = "stk600"; - prog_modes = PM_TPI | PM_ISP | PM_PDI; - connection_type = usb; -; - -#------------------------------------------------------------ -# stk600pp -#------------------------------------------------------------ - -programmer - id = "stk600pp"; - desc = "Atmel STK600 in parallel programming mode"; - type = "stk600pp"; - prog_modes = PM_HVPP; - connection_type = usb; -; - -#------------------------------------------------------------ -# stk600hvsp -#------------------------------------------------------------ - -programmer - id = "stk600hvsp"; - desc = "Atmel STK600 in high-voltage serial programming mode"; - type = "stk600hvsp"; - prog_modes = PM_HVSP; - connection_type = usb; -; - -#------------------------------------------------------------ -# avr910 -#------------------------------------------------------------ - -programmer - id = "avr910"; - desc = "Atmel Low Cost Serial Programmer"; - type = "avr910"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# ft245r -#------------------------------------------------------------ - -programmer - id = "ft245r"; - desc = "FT245R based generic programmer"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 4; # D4 - sck = 0; # D0 - sdo = 2; # D2 - sdi = 1; # D1 -; - -#------------------------------------------------------------ -# ft232r -#------------------------------------------------------------ - -programmer - id = "ft232r"; - desc = "FT232R based generic programmer"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 4; # DTR - sck = 0; # TxD - sdo = 2; # RTS - sdi = 1; # RxD -; - -#------------------------------------------------------------ -# bwmega -#------------------------------------------------------------ - -# see http://www.bitwizard.nl/wiki/index.php/FTDI_ATmega - -programmer - id = "bwmega"; - desc = "BitWizard ftdi_atmega builtin programmer"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 7; # RI - sck = 6; # DCD - sdo = 3; # CTS - sdi = 5; # DSR -; - -#------------------------------------------------------------ -# arduino-ft232r -#------------------------------------------------------------ - -# see http://www.geocities.jp/arduino_diecimila/bootloader/index_en.html -# Note: pins are numbered from 1! - -programmer - id = "arduino-ft232r"; - desc = "Arduino: FT232R connected to ISP"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 7; # RI X3(4) - sck = 5; # DSR X3(2) - sdo = 6; # DCD X3(3) - sdi = 3; # CTS X3(1) -; - -#------------------------------------------------------------ -# tc2030 -#------------------------------------------------------------ - -programmer - id = "tc2030"; - desc = "Tag-Connect TC2030"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - # FOR TPI devices: - reset = 3; # CTS = D3 (wire to ~RESET) - sck = 2; # RTS = D2 (wire to SCK) - sdo = 0; # TxD = D0 (wire to TPIDATA via 1k resistor) - sdi = 1; # RxD = D1 (wire to TPIDATA directly) -; - -#------------------------------------------------------------ -# diecimila -#------------------------------------------------------------ - -# website mentioned above uses this id - -programmer parent "arduino-ft232r" - id = "diecimila"; - desc = "alias for arduino-ft232r"; -; - -#------------------------------------------------------------ -# uncompatino -#------------------------------------------------------------ - -# There is a ATmega328P kit PCB called "uncompatino". -# This board allows ISP via its on-board FT232R. -# This is designed like Arduino Duemilanove but has no standard ICPS header. -# Its 4 pairs of pins are shorted to enable ftdi_syncbb. -# http://akizukidenshi.com/catalog/g/gP-07487/ -# http://akizukidenshi.com/download/ds/akizuki/k6096_manual_20130816.pdf - -programmer - id = "uncompatino"; - desc = "uncompatino with all pairs of pins shorted"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 7; # ri - sck = 5; # dsr - sdo = 6; # dcd - sdi = 3; # cts -; - -#------------------------------------------------------------ -# ttl232r -#------------------------------------------------------------ - -# FTDI USB to serial cable TTL-232R-5V with a custom adapter for ICSP -# http://www.ftdichip.com/Products/Cables/USBTTLSerial.htm -# http://www.ftdichip.com/Support/Documents/DataSheets/Cables/DS_TTL-232R_CABLES.pdf -# For ICSP pinout see for example http://www.atmel.com/images/doc2562.pdf -# (Figure 1. ISP6PIN header pinout and Table 1. Connections required for ISP ...) -# TTL-232R GND 1 Black -> ICPS GND (pin 6) -# TTL-232R CTS 2 Brown -> ICPS SDO (pin 4) -# TTL-232R VCC 3 Red -> ICPS VCC (pin 2) -# TTL-232R TXD 4 Orange -> ICPS RESET (pin 5) -# TTL-232R RXD 5 Yellow -> ICPS SCK (pin 3) -# TTL-232R RTS 6 Green -> ICPS SDI (pin 1) -# Except for VCC and GND, you can connect arbitual pairs as long as -# the following table is adjusted. - -programmer - id = "ttl232r"; - desc = "FTDI TTL232R-5V with ICSP adapter"; - type = "ftdi_syncbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - reset = 0; # txd - sck = 1; # rxd - sdo = 3; # cts - sdi = 2; # rts -; - -#------------------------------------------------------------ -# usbasp -#------------------------------------------------------------ - -programmer - id = "usbasp"; - desc = "USBasp, http://www.fischl.de/usbasp/"; - type = "usbasp"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x16c0; # VOTI - usbpid = 0x05dc; # Obdev's free shared PID - usbvendor = "www.fischl.de"; - usbproduct = "USBasp"; - # following variants are autodetected for id "usbasp" - - # original usbasp from fischl.de - # see above "usbasp" - - # old usbasp from fischl.de - # usbvid = 0x03EB; # ATMEL - # usbpid = 0xC7B4; # (unoffical) USBasp - # usbvendor = "www.fischl.de"; - # usbproduct = "USBasp"; - - # NIBObee (only if -P nibobee is given on command line) - # see below "nibobee" -; - -#------------------------------------------------------------ -# nibobee -#------------------------------------------------------------ - -programmer - id = "nibobee"; - desc = "NIBObee"; - type = "usbasp"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x16c0; # VOTI - usbpid = 0x092f; # NIBObee PID - usbvendor = "www.nicai-systems.com"; - usbproduct = "NIBObee"; -; - -#------------------------------------------------------------ -# usbasp-clone -#------------------------------------------------------------ - -programmer - id = "usbasp-clone"; - desc = "Any usbasp clone with correct VID/PID"; - type = "usbasp"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x16c0; # VOTI - usbpid = 0x05dc; # Obdev's free shared PID -; - -#------------------------------------------------------------ -# usbtiny -#------------------------------------------------------------ - -# USBtiny can also be used for TPI programming. -# In that case, a resistor of 1 kOhm is needed between SDI and SDO -# pins of the connector, and SDI (pin 1 of the 6-pin connector) -# connects to TPIDATA. - -programmer - id = "usbtiny"; - desc = "USBtiny simple USB programmer, https://learn.adafruit.com/usbtinyisp"; - type = "usbtiny"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x1781; - usbpid = 0x0c9f; -; - -#------------------------------------------------------------ -# arduino_gemma -#------------------------------------------------------------ - -# https://github.com/arduino/ArduinoCore-avr/tree/master/bootloaders/gemma - -programmer - id = "arduino_gemma"; - desc = "Arduino Gemma bootloader disguised as USBtiny"; - type = "usbtiny"; - prog_modes = PM_SPM; - connection_type = usb; - usbvid = 0x2341; - usbpid = 0x0c9f; -; - -#------------------------------------------------------------ -# adafruit_gemma -#------------------------------------------------------------ - -# https://github.com/adafruit/Adafruit-Trinket-Gemma-Bootloader - -programmer - id = "adafruit_gemma"; - desc = "Adafruit Trinket Gemma bootloader disguised as USBtiny"; - type = "usbtiny"; - prog_modes = PM_SPM; - connection_type = usb; - usbvid = 0x1781; - usbpid = 0x0c9f; -; - -#------------------------------------------------------------ -# arduinoisp -#------------------------------------------------------------ - -programmer - id = "arduinoisp"; - desc = "Arduino ISP Programmer"; - type = "usbtiny"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x2341; - usbpid = 0x0049; -; - -#------------------------------------------------------------ -# arduinoisporg -#------------------------------------------------------------ - -programmer - id = "arduinoisporg"; - desc = "Arduino ISP Programmer"; - type = "usbtiny"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x2a03; - usbpid = 0x0049; -; - -#------------------------------------------------------------ -# ehajo-isp -#------------------------------------------------------------ - -# commercial version of USBtiny, using a separate VID/PID - -programmer - id = "ehajo-isp"; - desc = "avr-isp-programmer from eHaJo, http://www.eHaJo.de"; - type = "usbtiny"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x16d0; - usbpid = 0x0ba5; -; - -#------------------------------------------------------------ -# iseavrprog -#------------------------------------------------------------ - -# commercial version of USBtiny, using a separate VID/PID -# https://github.com/IowaScaledEngineering/ckt-avrprogrammer - -programmer - id = "iseavrprog"; - desc = "USBtiny-based programmer, https://iascaled.com"; - type = "usbtiny"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - usbvid = 0x1209; - usbpid = 0x6570; -; - -#------------------------------------------------------------ -# micronucleus -#------------------------------------------------------------ - -programmer - id = "micronucleus"; - desc = "Micronucleus for bootloader"; - type = "micronucleus"; - prog_modes = PM_SPM; - connection_type = usb; - usbvid = 0x16d0; - usbpid = 0x0753; -; - -#------------------------------------------------------------ -# teensy -#------------------------------------------------------------ - -programmer - id = "teensy"; - desc = "Teensy for bootloader"; - type = "teensy"; - prog_modes = PM_SPM; - connection_type = usb; - usbvid = 0x16c0; - usbpid = 0x0478; -; - -#------------------------------------------------------------ -# butterfly -#------------------------------------------------------------ - -programmer - id = "butterfly"; - desc = "Atmel for bootloader (Butterfly Development Board)"; - type = "butterfly"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# avr109 -#------------------------------------------------------------ - -programmer - id = "avr109"; - desc = "Atmel for bootloader using AppNote AVR109"; - type = "butterfly"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# avr911 -#------------------------------------------------------------ - -programmer - id = "avr911"; - desc = "Atmel for bootloader using AppNote AVR911 AVROSP"; - type = "butterfly"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# mkbutterfly -#------------------------------------------------------------ - -# suggested in http://forum.mikrokopter.de/topic-post48317.html - -programmer - id = "mkbutterfly"; - desc = "Mikrokopter.de Butterfly for bootloader"; - type = "butterfly_mk"; - prog_modes = PM_SPM; - connection_type = serial; -; - -#------------------------------------------------------------ -# butterfly_mk -#------------------------------------------------------------ - -programmer parent "mkbutterfly" - id = "butterfly_mk"; -; - -#------------------------------------------------------------ -# jtagmkI -#------------------------------------------------------------ - -programmer - id = "jtagmkI"; - desc = "Atmel JTAG ICE (mkI)"; - type = "jtagmki"; - prog_modes = PM_JTAGmkI; - connection_type = serial; - baudrate = 115200; # default is 115200 -; - -#------------------------------------------------------------ -# jtag1 -#------------------------------------------------------------ - -# easier to type - -programmer parent "jtagmkI" - id = "jtag1"; -; - -#------------------------------------------------------------ -# jtag1slow -#------------------------------------------------------------ - -# easier to type - -programmer parent "jtag1" - id = "jtag1slow"; - baudrate = 19200; -; - -#------------------------------------------------------------ -# jtagmkII -#------------------------------------------------------------ - -# The JTAG ICE mkII has both, serial and USB connectivity. As it is -# mostly used through USB these days (AVR Studio 5 only supporting it -# that way), we make connection_type = usb the default. Users are -# still free to use a serial port with the -P option. - -programmer - id = "jtagmkII"; - desc = "Atmel JTAG ICE mkII"; - type = "jtagmkii"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - baudrate = 19200; # default is 19200 -; - -#------------------------------------------------------------ -# jtag2slow -#------------------------------------------------------------ - -# easier to type - -programmer parent "jtagmkII" - id = "jtag2slow"; -; - -#------------------------------------------------------------ -# jtag2fast -#------------------------------------------------------------ - -# JTAG ICE mkII @ 115200 Bd - -programmer parent "jtag2slow" - id = "jtag2fast"; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtag2 -#------------------------------------------------------------ - -# make the fast one the default, people will love that - -programmer parent "jtag2fast" - id = "jtag2"; -; - -#------------------------------------------------------------ -# jtag2isp -#------------------------------------------------------------ - -# JTAG ICE mkII in ISP mode - -programmer - id = "jtag2isp"; - desc = "Atmel JTAG ICE mkII in ISP mode"; - type = "jtagmkii_isp"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtag2dw -#------------------------------------------------------------ - -# JTAG ICE mkII in debugWire mode - -programmer - id = "jtag2dw"; - desc = "Atmel JTAG ICE mkII in debugWire mode"; - type = "jtagmkii_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtagmkII_avr32 -#------------------------------------------------------------ - -# JTAG ICE mkII in AVR32 mode - -programmer - id = "jtagmkII_avr32"; - desc = "Atmel JTAG ICE mkII in AVR32 mode"; - type = "jtagmkii_avr32"; - prog_modes = PM_aWire; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtag2avr32 -#------------------------------------------------------------ - -# JTAG ICE mkII in AVR32 mode - -programmer - id = "jtag2avr32"; - desc = "Atmel JTAG ICE mkII in AVR32 mode"; - type = "jtagmkii_avr32"; - prog_modes = PM_aWire; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtag2pdi -#------------------------------------------------------------ - -# JTAG ICE mkII in PDI mode - -programmer - id = "jtag2pdi"; - desc = "Atmel JTAG ICE mkII in PDI mode"; - type = "jtagmkii_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_jtag -#------------------------------------------------------------ - -# AVR Dragon in JTAG mode - -programmer - id = "dragon_jtag"; - desc = "Atmel AVR Dragon in JTAG mode"; - type = "dragon_jtag"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_isp -#------------------------------------------------------------ - -# AVR Dragon in ISP mode - -programmer - id = "dragon_isp"; - desc = "Atmel AVR Dragon in ISP mode"; - type = "dragon_isp"; - prog_modes = PM_TPI | PM_ISP; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_pp -#------------------------------------------------------------ - -# AVR Dragon in PP mode - -programmer - id = "dragon_pp"; - desc = "Atmel AVR Dragon in PP mode"; - type = "dragon_pp"; - prog_modes = PM_HVPP; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_hvsp -#------------------------------------------------------------ - -# AVR Dragon in HVSP mode - -programmer - id = "dragon_hvsp"; - desc = "Atmel AVR Dragon in HVSP mode"; - type = "dragon_hvsp"; - prog_modes = PM_HVSP; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_dw -#------------------------------------------------------------ - -# AVR Dragon in debugWire mode - -programmer - id = "dragon_dw"; - desc = "Atmel AVR Dragon in debugWire mode"; - type = "dragon_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# dragon_pdi -#------------------------------------------------------------ - -# AVR Dragon in PDI mode - -programmer - id = "dragon_pdi"; - desc = "Atmel AVR Dragon in PDI mode"; - type = "dragon_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - baudrate = 115200; -; - -#------------------------------------------------------------ -# jtag3 -#------------------------------------------------------------ - -programmer - id = "jtag3"; - desc = "Atmel AVR JTAGICE3 in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - usbpid = 0x2110, 0x2140; -; - -#------------------------------------------------------------ -# jtag3pdi -#------------------------------------------------------------ - -programmer - id = "jtag3pdi"; - desc = "Atmel AVR JTAGICE3 in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2110, 0x2140; -; - -#------------------------------------------------------------ -# jtag3updi -#------------------------------------------------------------ - -programmer - id = "jtag3updi"; - desc = "Atmel AVR JTAGICE3 in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2110, 0x2140; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# jtag3dw -#------------------------------------------------------------ - -programmer - id = "jtag3dw"; - desc = "Atmel AVR JTAGICE3 in debugWIRE mode"; - type = "jtagice3_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - usbpid = 0x2110, 0x2140; -; - -#------------------------------------------------------------ -# jtag3isp -#------------------------------------------------------------ - -programmer - id = "jtag3isp"; - desc = "Atmel AVR JTAGICE3 in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2110, 0x2140; -; - -#------------------------------------------------------------ -# xplainedpro -#------------------------------------------------------------ - -programmer - id = "xplainedpro"; - desc = "Atmel AVR XplainedPro in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - usbpid = 0x2111; -; - -#------------------------------------------------------------ -# xplainedpro_pdi -#------------------------------------------------------------ - -programmer - id = "xplainedpro_pdi"; - desc = "Atmel AVR XplainedPro in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2111; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# xplainedpro_updi -#------------------------------------------------------------ - -programmer - id = "xplainedpro_updi"; - desc = "Atmel AVR XplainedPro in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2111; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# xplainedmini -#------------------------------------------------------------ - -programmer - id = "xplainedmini"; - desc = "Atmel AVR XplainedMini in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2145; -; - -#------------------------------------------------------------ -# xplainedmini_dw -#------------------------------------------------------------ - -programmer - id = "xplainedmini_dw"; - desc = "Atmel AVR XplainedMini in debugWIRE mode"; - type = "jtagice3_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - usbpid = 0x2145; -; - -#------------------------------------------------------------ -# xplainedmini_updi -#------------------------------------------------------------ - -programmer - id = "xplainedmini_updi"; - desc = "Atmel AVR XplainedMini in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2145; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# xplainedmini_tpi -#------------------------------------------------------------ - -programmer - id = "xplainedmini_tpi"; - desc = "Atmel AVR XplainedMini in TPI mode"; - type = "jtagice3_tpi"; - prog_modes = PM_TPI; - connection_type = usb; - usbpid = 0x2145; -; - -#------------------------------------------------------------ -# atmelice -#------------------------------------------------------------ - -programmer - id = "atmelice"; - desc = "Atmel-ICE (ARM/AVR) in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - usbpid = 0x2141; -; - -#------------------------------------------------------------ -# atmelice_pdi -#------------------------------------------------------------ - -programmer - id = "atmelice_pdi"; - desc = "Atmel-ICE (ARM/AVR) in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2141; -; - -#------------------------------------------------------------ -# atmelice_updi -#------------------------------------------------------------ - -programmer - id = "atmelice_updi"; - desc = "Atmel-ICE (ARM/AVR) in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2141; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# atmelice_dw -#------------------------------------------------------------ - -programmer - id = "atmelice_dw"; - desc = "Atmel-ICE (ARM/AVR) in debugWIRE mode"; - type = "jtagice3_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - usbpid = 0x2141; -; - -#------------------------------------------------------------ -# atmelice_isp -#------------------------------------------------------------ - -programmer - id = "atmelice_isp"; - desc = "Atmel-ICE (ARM/AVR) in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2141; -; - -#------------------------------------------------------------ -# atmelice_tpi -#------------------------------------------------------------ - -programmer - id = "atmelice_tpi"; - desc = "Atmel-ICE (ARM/AVR) in TPI mode"; - type = "jtagice3_tpi"; - prog_modes = PM_TPI; - connection_type = usb; - usbpid = 0x2141; -; - -#------------------------------------------------------------ -# powerdebugger -#------------------------------------------------------------ - -programmer - id = "powerdebugger"; - desc = "Atmel PowerDebugger (ARM/AVR) in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG | PM_AVR32JTAG; - connection_type = usb; - usbpid = 0x2144; -; - -#------------------------------------------------------------ -# powerdebugger_pdi -#------------------------------------------------------------ - -programmer - id = "powerdebugger_pdi"; - desc = "Atmel PowerDebugger (ARM/AVR) in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2144; -; - -#------------------------------------------------------------ -# powerdebugger_updi -#------------------------------------------------------------ - -programmer - id = "powerdebugger_updi"; - desc = "Atmel PowerDebugger (ARM/AVR) in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2144; - hvupdi_support = 0, 1; -; - -#------------------------------------------------------------ -# powerdebugger_dw -#------------------------------------------------------------ - -programmer - id = "powerdebugger_dw"; - desc = "Atmel PowerDebugger (ARM/AVR) in debugWire mode"; - type = "jtagice3_dw"; - prog_modes = PM_debugWIRE; - connection_type = usb; - usbpid = 0x2144; -; - -#------------------------------------------------------------ -# powerdebugger_isp -#------------------------------------------------------------ - -programmer - id = "powerdebugger_isp"; - desc = "Atmel PowerDebugger (ARM/AVR) in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2144; -; - -#------------------------------------------------------------ -# powerdebugger_tpi -#------------------------------------------------------------ - -programmer - id = "powerdebugger_tpi"; - desc = "Atmel PowerDebugger (ARM/AVR) in TPI mode"; - type = "jtagice3_tpi"; - prog_modes = PM_TPI; - connection_type = usb; - usbpid = 0x2144; -; - -#------------------------------------------------------------ -# pickit4 -#------------------------------------------------------------ - -programmer - id = "pickit4"; - desc = "MPLAB(R) PICkit 4 in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; -; - -#------------------------------------------------------------ -# pickit4_updi -#------------------------------------------------------------ - -programmer - id = "pickit4_updi"; - desc = "MPLAB(R) PICkit 4 in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; - hvupdi_support = 0, 1, 2; -; - -#------------------------------------------------------------ -# pickit4_pdi -#------------------------------------------------------------ - -programmer - id = "pickit4_pdi"; - desc = "MPLAB(R) PICkit 4 in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; -; - -#------------------------------------------------------------ -# pickit4_isp -#------------------------------------------------------------ - -programmer - id = "pickit4_isp"; - desc = "MPLAB(R) PICkit 4 in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; -; - -#------------------------------------------------------------ -# pickit4_tpi -#------------------------------------------------------------ - -programmer - id = "pickit4_tpi"; - desc = "MPLAB(R) PICkit 4 in TPI mode"; - type = "jtagice3_tpi"; - prog_modes = PM_TPI; - connection_type = usb; - usbpid = 0x2177, 0x2178, 0x2179; -; - -#------------------------------------------------------------ -# snap -#------------------------------------------------------------ - -programmer - id = "snap"; - desc = "MPLAB(R) Snap in JTAG mode"; - type = "jtagice3"; - prog_modes = PM_JTAG | PM_XMEGAJTAG; - connection_type = usb; - usbpid = 0x2180, 0x217f, 0x2181; -; - -#------------------------------------------------------------ -# snap_updi -#------------------------------------------------------------ - -programmer - id = "snap_updi"; - desc = "MPLAB(R) SNAP in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2180, 0x217f, 0x2181; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# snap_pdi -#------------------------------------------------------------ - -programmer - id = "snap_pdi"; - desc = "MPLAB(R) SNAP in PDI mode"; - type = "jtagice3_pdi"; - prog_modes = PM_PDI; - connection_type = usb; - usbpid = 0x2180, 0x217f, 0x2181; -; - -#------------------------------------------------------------ -# snap_isp -#------------------------------------------------------------ - -programmer - id = "snap_isp"; - desc = "MPLAB(R) SNAP in ISP mode"; - type = "jtagice3_isp"; - prog_modes = PM_ISP; - connection_type = usb; - usbpid = 0x2180, 0x217f, 0x2181; -; - -#------------------------------------------------------------ -# snap_tpi -#------------------------------------------------------------ - -programmer - id = "snap_tpi"; - desc = "MPLAB(R) SNAP in TPI mode"; - type = "jtagice3_tpi"; - prog_modes = PM_TPI; - connection_type = usb; - usbpid = 0x2180, 0x217f, 0x2181; -; - -#------------------------------------------------------------ -# pkobn_updi -#------------------------------------------------------------ - -programmer - id = "pkobn_updi"; - desc = "Curiosity nano (nEDBG) in UPDI mode"; - type = "jtagice3_updi"; - prog_modes = PM_UPDI; - connection_type = usb; - usbpid = 0x2175; - hvupdi_support = 1; -; - -#------------------------------------------------------------ -# pavr -#------------------------------------------------------------ - -programmer - id = "pavr"; - desc = "Jason Kyle's pAVR Serial Programmer"; - type = "avr910"; - prog_modes = PM_ISP; - connection_type = serial; -; - -#------------------------------------------------------------ -# pickit2 -#------------------------------------------------------------ - -programmer - id = "pickit2"; - desc = "MicroChip's PICkit2 Programmer"; - type = "pickit2"; - prog_modes = PM_ISP; - connection_type = usb; -; - -#------------------------------------------------------------ -# flip1 -#------------------------------------------------------------ - -programmer - id = "flip1"; - desc = "FLIP for bootloader using USB DFU protocol version 1 (doc7618)"; - type = "flip1"; - prog_modes = PM_SPM; - connection_type = usb; -; - -#------------------------------------------------------------ -# flip2 -#------------------------------------------------------------ - -programmer - id = "flip2"; - desc = "FLIP for bootloader using USB DFU protocol version 2 (AVR4023)"; - type = "flip2"; - prog_modes = PM_SPM; - connection_type = usb; -; - -#------------------------------------------------------------ -# ponyser -#------------------------------------------------------------ - -# some ultra cheap programmers use bitbanging on the serialport -# -# PC - DB9 - Pins for RS232: -# -# GND 5 -- |O -# | O| <- 9 RI -# DTR 4 <- |O | -# | O| <- 8 CTS -# TXD 3 <- |O | -# | O| -> 7 RTS -# RXD 2 -> |O | -# | O| <- 6 DSR -# DCD 1 -> |O -# -# Using RXD is currently not supported. -# Using RI is not supported under Win32 but is supported under Posix. - -# serial ponyprog design (dasa2 in uisp) -# reset=!txd sck=rts sdo=dtr sdi=cts - -programmer - id = "ponyser"; - desc = "design ponyprog serial, reset=!txd sck=rts sdo=dtr sdi=cts"; - type = "serbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; - reset = ~3; - sck = 7; - sdo = 4; - sdi = 8; -; - -#------------------------------------------------------------ -# siprog -#------------------------------------------------------------ - -# Same as above, different name -# reset=!txd sck=rts sdo=dtr sdi=cts - -programmer parent "ponyser" - id = "siprog"; - desc = "Lancos SI-Prog "; -; - -#------------------------------------------------------------ -# dasa -#------------------------------------------------------------ - -# unknown (dasa in uisp) -# reset=rts sck=dtr sdo=txd sdi=cts - -programmer - id = "dasa"; - desc = "serial port banging, reset=rts sck=dtr sdo=txd sdi=cts"; - type = "serbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; - reset = 7; - sck = 4; - sdo = 3; - sdi = 8; -; - -#------------------------------------------------------------ -# dasa3 -#------------------------------------------------------------ - -# unknown (dasa3 in uisp) -# reset=!dtr sck=rts sdo=txd sdi=cts - -programmer - id = "dasa3"; - desc = "serial port banging, reset=!dtr sck=rts sdo=txd sdi=cts"; - type = "serbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; - reset = ~4; - sck = 7; - sdo = 3; - sdi = 8; -; - -#------------------------------------------------------------ -# C2N232i -#------------------------------------------------------------ - -# C2N232i (jumper configuration "auto") -# reset=dtr sck=!rts sdo=!txd sdi=!cts - -programmer - id = "c2n232i"; - desc = "serial port banging, reset=dtr sck=!rts sdo=!txd sdi=!cts"; - type = "serbb"; - prog_modes = PM_TPI | PM_ISP; - connection_type = serial; - reset = 4; - sck = ~7; - sdo = ~3; - sdi = ~8; -; - -#------------------------------------------------------------ -# jtag2updi -#------------------------------------------------------------ - -# JTAG2UPDI -# https://github.com/ElTangas/jtag2updi - -programmer - id = "jtag2updi"; - desc = "JTAGv2 to UPDI bridge"; - type = "jtagmkii_updi"; - prog_modes = PM_UPDI; - connection_type = serial; - baudrate = 115200; - hvupdi_support = 1; -; - -# -# PART DEFINITIONS -# - -#------------------------------------------------------------ -# ATtiny11 -#------------------------------------------------------------ - -# This is an HVSP-only device. - -part - desc = "ATtiny11"; - id = "t11"; - prog_modes = PM_HVSP; - mcuid = 8; - n_interrupts = 5; - stk500_devcode = 0x11; - chip_erase_delay = 20000; - signature = 0x1e 0x90 0x04; - serial = no; - timeout = 200; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, - 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - - memory "eeprom" - size = 64; - delay = 5; - blocksize = 64; - readsize = 256; - ; - - memory "flash" - size = 1024; - delay = 3; - blocksize = 128; - readsize = 256; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - ; - - memory "signature" - size = 3; - ; - - memory "calibration" - size = 1; - ; -; - -#------------------------------------------------------------ -# ATtiny12 -#------------------------------------------------------------ - -part - desc = "ATtiny12"; - id = "t12"; - prog_modes = PM_ISP | PM_HVSP; - mcuid = 9; - n_interrupts = 6; - stk500_devcode = 0x12; - avr910_devcode = 0x55; - chip_erase_delay = 20000; - signature = 0x1e 0x90 0x05; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, - 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 8; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 1024; - min_write_delay = 4500; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 5; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--101x.xxxx--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny13 -#------------------------------------------------------------ - -part - desc = "ATtiny13"; - id = "t13"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 10; - n_interrupts = 10; - stk500_devcode = 0x14; - chip_erase_delay = 4000; - signature = 0x1e 0x90 0x07; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - flash_instr = 0xb4, 0x0e, 0x1e; - eeprom_instr = - 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x0e, 0xb4, 0x0e, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 90; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 0; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4000; - readback = 0xff 0xff; - mode = 65; - delay = 5; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--xxaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xxaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 1024; - page_size = 32; - num_pages = 32; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.000a--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.000a--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.000a--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 2; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny13A -#------------------------------------------------------------ - -part parent "t13" - desc = "ATtiny13A"; - id = "t13a"; - mcuid = 11; -; - -#------------------------------------------------------------ -# ATtiny15 -#------------------------------------------------------------ - -part - desc = "ATtiny15"; - id = "t15"; - prog_modes = PM_ISP | PM_HVSP; - mcuid = 12; - n_interrupts = 9; - stk500_devcode = 0x13; - avr910_devcode = 0x56; - chip_erase_delay = 8200; - signature = 0x1e 0x90 0x06; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, - 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - latchcycles = 16; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - hvspcmdexedelay = 5; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - min_write_delay = 8200; - max_write_delay = 8200; - readback = 0xff 0xff; - mode = 4; - delay = 10; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 1024; - min_write_delay = 4100; - max_write_delay = 4100; - readback = 0xff 0xff; - mode = 4; - delay = 5; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--oooo.xxoo"; - write = "1010.1100--101x.xxxx--xxxx.xxxx--iiii.11ii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s1200 -#------------------------------------------------------------ - -part - desc = "AT90S1200"; - id = "1200"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 183; - n_interrupts = 4; - stk500_devcode = 0x33; - avr910_devcode = 0x13; - chip_erase_delay = 20000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x90 0x01; - is_at90s1200 = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 1; - pollvalue = 0xff; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x00 0xff; - mode = 4; - delay = 20; - blocksize = 32; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xxaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 1024; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 2; - delay = 15; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s4414 -#------------------------------------------------------------ - -part - desc = "AT90S4414"; - id = "4414"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 190; - n_interrupts = 13; - stk500_devcode = 0x50; - avr910_devcode = 0x28; - chip_erase_delay = 20000; - signature = 0x1e 0x92 0x01; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x80 0x7f; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x7f 0x7f; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s2313 -#------------------------------------------------------------ - -part - desc = "AT90S2313"; - id = "2313"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 186; - n_interrupts = 11; - stk500_devcode = 0x40; - avr910_devcode = 0x20; - chip_erase_delay = 20000; - signature = 0x1e 0x91 0x01; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x80 0x7f; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 2048; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x7f 0x7f; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - write = "1010.1100--111x.xiix--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s2333 -#------------------------------------------------------------ - -part -##### WARNING: No XML file for device 'AT90S2333'! ##### - desc = "AT90S2333"; - id = "2333"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 188; - n_interrupts = 14; - stk500_devcode = 0x42; - avr910_devcode = 0x34; - chip_erase_delay = 20000; - signature = 0x1e 0x91 0x05; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x00 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 2048; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - pwroff_after_write = yes; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; - write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s2343 (also AT90s2323 and ATtiny22) -#------------------------------------------------------------ - -part - desc = "AT90S2343"; - id = "2343"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP; - mcuid = 189; - n_interrupts = 3; - stk500_devcode = 0x43; - avr910_devcode = 0x4c; - chip_erase_delay = 18000; - signature = 0x1e 0x91 0x03; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x00, - 0x68, 0x78, 0x68, 0x68, 0x00, 0x00, 0x68, 0x78, - 0x78, 0x00, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - hventerstabdelay = 100; - latchcycles = 1; - poweroffdelay = 25; - resetdelayus = 50; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x00 0xff; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read = "1010.0000--0000.0000--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.0000--xaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 2048; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 128; - read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooox.xxxo"; - write = "1010.1100--1011.111i--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooox.xxxo"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s4433 -#------------------------------------------------------------ - -part - desc = "AT90S4433"; - id = "4433"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 191; - n_interrupts = 14; - stk500_devcode = 0x51; - avr910_devcode = 0x30; - chip_erase_delay = 20000; - signature = 0x1e 0x92 0x03; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x00 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - pwroff_after_write = yes; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; - write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s4434 -#------------------------------------------------------------ - -part -##### WARNING: No XML file for device 'AT90S4434'! ##### - desc = "AT90S4434"; - id = "4434"; - prog_modes = PM_SPM | PM_ISP; - mcuid = 192; - n_interrupts = 17; - stk500_devcode = 0x52; - avr910_devcode = 0x6c; - chip_erase_delay = 20000; - signature = 0x1e 0x92 0x02; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x00 0xff; - read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 4096; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxoo.oooo"; - write = "1010.1100--101i.iiii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 20000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s8515 -#------------------------------------------------------------ - -part - desc = "AT90S8515"; - id = "8515"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 193; - n_interrupts = 13; - stk500_devcode = 0x60; - avr910_devcode = 0x38; - chip_erase_delay = 20000; - signature = 0x1e 0x93 0x01; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x80 0x7f; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 8192; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x7f 0x7f; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90s8535 -#------------------------------------------------------------ - -part - desc = "AT90S8535"; - id = "8535"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 195; - n_interrupts = 17; - stk500_devcode = 0x61; - avr910_devcode = 0x68; - chip_erase_delay = 20000; - signature = 0x1e 0x93 0x03; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0x00 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - size = 8192; - min_write_delay = 9000; - max_write_delay = 20000; - readback = 0xff 0xff; - mode = 4; - delay = 12; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write_lo = "0100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - write_hi = "0100.1000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxxo"; - write = "1010.1100--1011.111i--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--ooxx.xxxx"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega103 -#------------------------------------------------------------ - -part - desc = "ATmega103"; - id = "m103"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 84; - n_interrupts = 24; - stk500_devcode = 0xb1; - avr910_devcode = 0x41; - chip_erase_delay = 112000; - signature = 0x1e 0x97 0x01; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x8e, 0x9e, 0x2e, 0x3e, 0xae, 0xbe, - 0x4e, 0x5e, 0xce, 0xde, 0x6e, 0x7e, 0xee, 0xde, - 0x66, 0x76, 0xe6, 0xf6, 0x6a, 0x7a, 0xea, 0x7a, - 0x7f, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepulsewidth = 15; - programfusepulsewidth = 2; - programlockpolltimeout = 10; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - min_write_delay = 4000; - max_write_delay = 9000; - readback = 0x80 0x7f; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 22000; - max_write_delay = 56000; - readback = 0xff 0xff; - mode = 17; - delay = 70; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "fuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xxox.o1oo"; - write = "1010.1100--1011.i1ii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xoox"; - write = "1010.1100--1111.1ii1--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega64 -#------------------------------------------------------------ - -part - desc = "ATmega64"; - id = "m64"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 72; - n_interrupts = 35; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xa0; - avr910_devcode = 0x45; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x96 0x02; - reset = io; - allowfullpagebitstream = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x22; - spmcr = 0x68; - ocdrev = 2; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 20; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega64A -#------------------------------------------------------------ - -part parent "m64" - desc = "ATmega64A"; - id = "m64a"; - mcuid = 73; -; - -#------------------------------------------------------------ -# ATmega128 -#------------------------------------------------------------ - -part - desc = "ATmega128"; - id = "m128"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 85; - n_interrupts = 35; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xb2; - avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x97 0x02; - reset = io; - allowfullpagebitstream = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x22; - rampz = 0x3b; - spmcr = 0x68; - ocdrev = 1; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 12; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega128A -#------------------------------------------------------------ - -part parent "m128" - desc = "ATmega128A"; - id = "m128a"; - mcuid = 86; -; - -#------------------------------------------------------------ -# AT90CAN128 -#------------------------------------------------------------ - -part - desc = "AT90CAN128"; - id = "c128"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 176; - n_interrupts = 37; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xb3; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; -# avr910_devcode = 0x43; - signature = 0x1e 0x97 0x81; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 8; - readsize = 256; - read = "1010.0000--000x.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90CAN64 -#------------------------------------------------------------ - -part - desc = "AT90CAN64"; - id = "c64"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 172; - n_interrupts = 37; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xb3; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; -# avr910_devcode = 0x43; - signature = 0x1e 0x96 0x81; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 8; - readsize = 256; - read = "1010.0000--000x.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90CAN32 -#------------------------------------------------------------ - -part - desc = "AT90CAN32"; - id = "c32"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 171; - n_interrupts = 37; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xb3; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; -# avr910_devcode = 0x43; - signature = 0x1e 0x95 0x81; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 8; - readsize = 256; - read = "1010.0000--000x.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 256; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega16 -#------------------------------------------------------------ - -part - desc = "ATmega16"; - id = "m16"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 49; - n_interrupts = 21; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x82; - avr910_devcode = 0x74; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x03; - reset = io; - allowfullpagebitstream = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - progmodedelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 2; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 10; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--000x.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega16A -#------------------------------------------------------------ - -part parent "m16" - desc = "ATmega16A"; - id = "m16a"; - mcuid = 50; -; - -#------------------------------------------------------------ -# ATmega324P -#------------------------------------------------------------ - -part - desc = "ATmega324P"; - id = "m324p"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 111; - n_interrupts = 31; - n_boot_sections = 4; - boot_section_size = 512; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - chip_erase_delay = 55000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x95 0x08; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--0aaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega164P -#------------------------------------------------------------ - -part parent "m324p" - desc = "ATmega164P"; - id = "m164p"; - mcuid = 93; - boot_section_size = 256; - signature = 0x1e 0x94 0x0a; - - memory "eeprom" - size = 512; - ; - - memory "flash" - size = 0x4000; - num_pages = 128; - ; -; - -#------------------------------------------------------------ -# ATmega164PA -#------------------------------------------------------------ - -part parent "m164p" - desc = "ATmega164PA"; - id = "m164pa"; - mcuid = 94; -; - -#------------------------------------------------------------ -# ATmega164A -#------------------------------------------------------------ - -part parent "m164p" - desc = "ATmega164A"; - id = "m164a"; - mcuid = 92; - signature = 0x1e 0x94 0x0f; -; - -#------------------------------------------------------------ -# ATmega324PB -#------------------------------------------------------------ - -part parent "m324p" - desc = "ATmega324PB"; - id = "m324pb"; - mcuid = 113; - n_interrupts = 51; - signature = 0x1e 0x95 0x17; -; - -#------------------------------------------------------------ -# ATmega324PA -#------------------------------------------------------------ - -part parent "m324p" - desc = "ATmega324PA"; - id = "m324pa"; - mcuid = 112; - signature = 0x1e 0x95 0x11; -; - -#------------------------------------------------------------ -# ATmega324A -#------------------------------------------------------------ - -part parent "m324p" - desc = "ATmega324A"; - id = "m324a"; - mcuid = 110; - signature = 0x1e 0x95 0x15; -; - -#------------------------------------------------------------ -# ATmega644 -#------------------------------------------------------------ - -part - desc = "ATmega644"; - id = "m644"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 127; - n_interrupts = 28; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - chip_erase_delay = 55000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x96 0x09; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega644A -#------------------------------------------------------------ - -part parent "m644" - desc = "ATmega644A"; - id = "m644a"; - mcuid = 128; - n_interrupts = 31; -; - -#------------------------------------------------------------ -# ATmega644P -#------------------------------------------------------------ - -part parent "m644" - desc = "ATmega644P"; - id = "m644p"; - mcuid = 129; - n_interrupts = 31; - signature = 0x1e 0x96 0x0a; -; - -#------------------------------------------------------------ -# ATmega644PA -#------------------------------------------------------------ - -part parent "m644" - desc = "ATmega644PA"; - id = "m644pa"; - mcuid = 130; - n_interrupts = 31; - signature = 0x1e 0x96 0x0a; -; - -#------------------------------------------------------------ -# ATmega1284 -#------------------------------------------------------------ - -part - desc = "ATmega1284"; - id = "m1284"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 140; - n_interrupts = 35; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0x82; # no STK500v1 support, use the ATmega16 one - avr910_devcode = 0x74; - chip_erase_delay = 55000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x97 0x06; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - latchcycles = 6; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega1284P -#------------------------------------------------------------ - -part parent "m1284" - desc = "ATmega1284P"; - id = "m1284p"; - mcuid = 141; - signature = 0x1e 0x97 0x05; -; - -#------------------------------------------------------------ -# ATmega162 -#------------------------------------------------------------ - -part - desc = "ATmega162"; - id = "m162"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 90; - n_interrupts = 28; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x83; - avr910_devcode = 0x63; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x04; - reset = io; - allowfullpagebitstream = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x04; - spmcr = 0x57; - ocdrev = 2; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 16000; - max_write_delay = 16000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--00xx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--00xx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega163 -#------------------------------------------------------------ - -part - desc = "ATmega163"; - id = "m163"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 91; - n_interrupts = 18; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x81; - avr910_devcode = 0x64; - chip_erase_delay = 32000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x02; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepolltimeout = 30; - programfusepolltimeout = 2; - programlockpolltimeout = 2; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 4000; - max_write_delay = 4000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 16000; - max_write_delay = 16000; - readback = 0xff 0xff; - mode = 17; - delay = 20; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.0000--xxxx.xxxx--ooxx.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--ii11.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.1000--xxxx.xxxx--xxxx.1ooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.0xxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega169 -#------------------------------------------------------------ - -part - desc = "ATmega169"; - id = "m169"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 104; - n_interrupts = 23; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x85; - avr910_devcode = 0x78; - chip_erase_delay = 9000; - signature = 0x1e 0x94 0x05; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 2; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega169A -#------------------------------------------------------------ - -part parent "m169" - desc = "ATmega169A"; - id = "m169a"; - mcuid = 105; - signature = 0x1e 0x94 0x11; - reset = io; -; - -#------------------------------------------------------------ -# ATmega169P -#------------------------------------------------------------ - -part parent "m169" - desc = "ATmega169P"; - id = "m169p"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 106; - reset = io; -; - -#------------------------------------------------------------ -# ATmega169PA -#------------------------------------------------------------ - -part parent "m169" - desc = "ATmega169PA"; - id = "m169pa"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 107; - reset = io; -; - -#------------------------------------------------------------ -# ATmega329 -#------------------------------------------------------------ - -part - desc = "ATmega329"; - id = "m329"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 121; - n_interrupts = 23; - n_boot_sections = 4; - boot_section_size = 512; -# stk500_devcode = 0x85; # no STK500 support, only STK500v2 -# avr910_devcode = 0x?; # try the ATmega169 one: - avr910_devcode = 0x75; - chip_erase_delay = 9000; - signature = 0x1e 0x95 0x03; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega329A -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega329A"; - id = "m329a"; - mcuid = 122; -; - -#------------------------------------------------------------ -# ATmega329P -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega329P"; - id = "m329p"; - mcuid = 123; - signature = 0x1e 0x95 0x0b; -; - -#------------------------------------------------------------ -# ATmega329PA -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega329PA"; - id = "m329pa"; - mcuid = 124; - signature = 0x1e 0x95 0x0b; -; - -#------------------------------------------------------------ -# ATmega3290 -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega3290"; - id = "m3290"; - mcuid = 150; - n_interrupts = 25; - signature = 0x1e 0x95 0x04; -; - -#------------------------------------------------------------ -# ATmega3290A -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega3290A"; - id = "m3290a"; - mcuid = 151; - n_interrupts = 25; - signature = 0x1e 0x95 0x04; -; - -#------------------------------------------------------------ -# ATmega3290P -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega3290P"; - id = "m3290p"; - mcuid = 152; - n_interrupts = 25; - signature = 0x1e 0x95 0x0c; -; - -#------------------------------------------------------------ -# ATmega3290PA -#------------------------------------------------------------ - -part parent "m329" - desc = "ATmega3290PA"; - id = "m3290pa"; - mcuid = 153; - n_interrupts = 25; - signature = 0x1e 0x95 0x0c; -; - -#------------------------------------------------------------ -# ATmega649 -#------------------------------------------------------------ - -part - desc = "ATmega649"; - id = "m649"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 135; - n_interrupts = 23; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0x85; # no STK500 support, only STK500v2 -# avr910_devcode = 0x?; # try the ATmega169 one: - avr910_devcode = 0x75; - chip_erase_delay = 9000; - signature = 0x1e 0x96 0x03; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega649A -#------------------------------------------------------------ - -part parent "m649" - desc = "ATmega649A"; - id = "m649a"; - mcuid = 136; -; - -#------------------------------------------------------------ -# ATmega649P -#------------------------------------------------------------ - -part parent "m649" - desc = "ATmega649P"; - id = "m649p"; - mcuid = 137; - signature = 0x1e 0x96 0x0b; -; - -#------------------------------------------------------------ -# ATmega6490 -#------------------------------------------------------------ - -part parent "m649" - desc = "ATmega6490"; - id = "m6490"; - mcuid = 157; - n_interrupts = 25; - signature = 0x1e 0x96 0x04; -; - -#------------------------------------------------------------ -# ATmega6490A -#------------------------------------------------------------ - -part parent "m649" - desc = "ATmega6490A"; - id = "m6490a"; - mcuid = 158; - n_interrupts = 25; - signature = 0x1e 0x96 0x04; -; - -#------------------------------------------------------------ -# ATmega6490P -#------------------------------------------------------------ - -part parent "m649" - desc = "ATmega6490P"; - id = "m6490p"; - mcuid = 159; - n_interrupts = 25; - signature = 0x1e 0x96 0x0c; -; - -#------------------------------------------------------------ -# ATmega32 -#------------------------------------------------------------ - -part - desc = "ATmega32"; - id = "m32"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG | PM_JTAGmkI; - mcuid = 58; - n_interrupts = 21; - n_boot_sections = 4; - boot_section_size = 512; - stk500_devcode = 0x91; - avr910_devcode = 0x72; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x95 0x02; - reset = io; - allowfullpagebitstream = yes; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 2; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 10; - blocksize = 64; - readsize = 256; - read = "1010.0000--00xx.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega161 -#------------------------------------------------------------ - -part - desc = "ATmega161"; - id = "m161"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 89; - n_interrupts = 21; - n_boot_sections = 1; - boot_section_size = 1024; - stk500_devcode = 0x80; - avr910_devcode = 0x60; - chip_erase_delay = 28000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x01; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - chiperasepolltimeout = 30; - programfusepolltimeout = 2; - programlockpolltimeout = 2; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 3400; - max_write_delay = 3400; - readback = 0xff 0xff; - mode = 4; - delay = 5; - blocksize = 128; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 14000; - max_write_delay = 14000; - readback = 0xff 0xff; - mode = 33; - delay = 16; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "fuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--xxxx.xxxx--xxxx.xxxx--xoxo.oooo"; - write = "1010.1100--101x.xxxx--xxxx.xxxx--1i1i.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega32A -#------------------------------------------------------------ - -part parent "m32" - desc = "ATmega32A"; - id = "m32a"; - mcuid = 59; -; - -#------------------------------------------------------------ -# ATmega8 -#------------------------------------------------------------ - -part - desc = "ATmega8"; - id = "m8"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 45; - n_interrupts = 19; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x70; - avr910_devcode = 0x76; - chip_erase_delay = 10000; - pagel = 0xd7; - bs2 = 0xc2; - signature = 0x1e 0x93 0x07; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 20; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0x00; - mode = 33; - delay = 10; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega8A -#------------------------------------------------------------ - -part parent "m8" - desc = "ATmega8A"; - id = "m8a"; - mcuid = 46; -; - -#------------------------------------------------------------ -# ATmega8515 -#------------------------------------------------------------ - -part - desc = "ATmega8515"; - id = "m8515"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 160; - n_interrupts = 17; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x63; - avr910_devcode = 0x3a; - chip_erase_delay = 9000; - signature = 0x1e 0x93 0x06; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 20; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega8535 -#------------------------------------------------------------ - -part - desc = "ATmega8535"; - id = "m8535"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP; - mcuid = 161; - n_interrupts = 21; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x64; - avr910_devcode = 0x69; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x93 0x08; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 20; - blocksize = 128; - readsize = 256; - read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 2000; - max_write_delay = 2000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--00xx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny26 -#------------------------------------------------------------ - -part - desc = "ATtiny26"; - id = "t26"; - prog_modes = PM_ISP | PM_HVPP; - mcuid = 17; - n_interrupts = 12; - stk500_devcode = 0x21; - avr910_devcode = 0x5e; - chip_erase_delay = 9000; - pagel = 0xb3; - bs2 = 0xb2; - signature = 0x1e 0x91 0x09; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, - 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, - 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, - 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 4; - delay = 10; - blocksize = 64; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - ; - - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 33; - delay = 6; - blocksize = 16; - readsize = 256; - read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxx.xxaa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--xxxi.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; - write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 4; - read = "0011.1000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny261 -#------------------------------------------------------------ - -part - desc = "ATtiny261"; - id = "t261"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 30; - n_interrupts = 19; - chip_erase_delay = 4000; - pagel = 0xb3; - bs2 = 0xb2; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x91 0x0c; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, - 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, - 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, - 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb4, 0x00, 0x10; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - page_size = 4; - num_pages = 32; - min_write_delay = 4000; - max_write_delay = 4000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xxaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxx.xxaa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; - write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny261A -#------------------------------------------------------------ - -part parent "t261" - desc = "ATtiny261A"; - id = "t261a"; - mcuid = 31; -; - -#------------------------------------------------------------ -# ATtiny461 -#------------------------------------------------------------ - -part - desc = "ATtiny461"; - id = "t461"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 33; - n_interrupts = 19; - chip_erase_delay = 4000; - pagel = 0xb3; - bs2 = 0xb2; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x92 0x08; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, - 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, - 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, - 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb4, 0x00, 0x10; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - num_pages = 64; - min_write_delay = 4000; - max_write_delay = 4000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxx--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxx.xaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; - write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny461A -#------------------------------------------------------------ - -part parent "t461" - desc = "ATtiny461A"; - id = "t461a"; - mcuid = 34; -; - -#------------------------------------------------------------ -# ATtiny861 -#------------------------------------------------------------ - -part - desc = "ATtiny861"; - id = "t861"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 38; - n_interrupts = 19; - chip_erase_delay = 4000; - pagel = 0xb3; - bs2 = 0xb2; -# stk500_devcode = 0x21; -# avr910_devcode = 0x5e; - signature = 0x1e 0x93 0x0d; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0xc4, 0xe4, 0xc4, 0xe4, 0xcc, 0xec, 0xcc, 0xec, - 0xd4, 0xf4, 0xd4, 0xf4, 0xdc, 0xfc, 0xdc, 0xfc, - 0xc8, 0xe8, 0xd8, 0xf8, 0x4c, 0x6c, 0x5c, 0x7c, - 0xec, 0xbc, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb4, 0x00, 0x10; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x00, 0xb4, 0x00, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 2; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 4000; - max_write_delay = 4000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxx.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--xxxx.xxxx--xxxx.xxxx--xxxx.xxoo"; - write = "1010.1100--1111.11ii--xxxx.xxxx--xxxx.xxxx"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny861A -#------------------------------------------------------------ - -part parent "t861" - desc = "ATtiny861A"; - id = "t861a"; - mcuid = 39; -; - -#------------------------------------------------------------ -# ATtiny28 -#------------------------------------------------------------ - -# This is an HVPP-only device. - -part - desc = "ATtiny28"; - id = "t28"; - prog_modes = PM_HVPP; - mcuid = 18; - n_interrupts = 6; - stk500_devcode = 0x22; - avr910_devcode = 0x5c; - signature = 0x1e 0x91 0x07; - serial = no; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - - memory "flash" - size = 2048; - page_size = 2; - delay = 5; - readsize = 256; - ; - - memory "fuse" - size = 1; - ; - - memory "lock" - size = 1; - ; - - memory "signature" - size = 3; - ; - - memory "calibration" - size = 1; - ; -; - -#------------------------------------------------------------ -# ATmega48 -#------------------------------------------------------------ - -part - desc = "ATmega48"; - id = "m48"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 67; - n_interrupts = 26; - stk500_devcode = 0x59; - chip_erase_delay = 45000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x92 0x05; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega48A -#------------------------------------------------------------ - -part parent "m48" - desc = "ATmega48A"; - id = "m48a"; - mcuid = 68; -; - -#------------------------------------------------------------ -# ATmega48P -#------------------------------------------------------------ - -part parent "m48" - desc = "ATmega48P"; - id = "m48p"; - mcuid = 69; - signature = 0x1e 0x92 0x0a; -; - -#------------------------------------------------------------ -# ATmega48PA -#------------------------------------------------------------ - -part parent "m48" - desc = "ATmega48PA"; - id = "m48pa"; - mcuid = 70; - signature = 0x1e 0x92 0x0a; -; - -#------------------------------------------------------------ -# ATmega48PB -#------------------------------------------------------------ - -part parent "m48" - desc = "ATmega48PB"; - id = "m48pb"; - mcuid = 71; - n_interrupts = 27; - chip_erase_delay = 10500; - signature = 0x1e 0x92 0x10; -; - -#------------------------------------------------------------ -# ATmega88 -#------------------------------------------------------------ - -part - desc = "ATmega88"; - id = "m88"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 79; - n_interrupts = 26; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x73; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x93 0x0a; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega88A -#------------------------------------------------------------ - -part parent "m88" - desc = "ATmega88A"; - id = "m88a"; - mcuid = 80; -; - -#------------------------------------------------------------ -# ATmega88P -#------------------------------------------------------------ - -part parent "m88" - desc = "ATmega88P"; - id = "m88p"; - mcuid = 81; - signature = 0x1e 0x93 0x0f; -; - -#------------------------------------------------------------ -# ATmega88PA -#------------------------------------------------------------ - -part parent "m88" - desc = "ATmega88PA"; - id = "m88pa"; - mcuid = 82; - signature = 0x1e 0x93 0x0f; -; - -#------------------------------------------------------------ -# ATmega88PB -#------------------------------------------------------------ - -part parent "m88" - desc = "ATmega88PB"; - id = "m88pb"; - mcuid = 83; - n_interrupts = 27; - chip_erase_delay = 10500; - signature = 0x1e 0x93 0x16; -; - -#------------------------------------------------------------ -# ATmega168 -#------------------------------------------------------------ - -part - desc = "ATmega168"; - id = "m168"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 99; - n_interrupts = 26; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x86; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x94 0x06; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--000a.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega168A -#------------------------------------------------------------ - -part parent "m168" - desc = "ATmega168A"; - id = "m168a"; - mcuid = 100; -; - -#------------------------------------------------------------ -# ATmega168P -#------------------------------------------------------------ - -part parent "m168" - desc = "ATmega168P"; - id = "m168p"; - mcuid = 101; - signature = 0x1e 0x94 0x0b; -; - -#------------------------------------------------------------ -# ATmega168PA -#------------------------------------------------------------ - -part parent "m168" - desc = "ATmega168PA"; - id = "m168pa"; - mcuid = 102; - signature = 0x1e 0x94 0x0b; -; - -#------------------------------------------------------------ -# ATmega168PB -#------------------------------------------------------------ - -part parent "m168" - desc = "ATmega168PB"; - id = "m168pb"; - mcuid = 103; - n_interrupts = 27; - chip_erase_delay = 10500; - signature = 0x1e 0x94 0x15; -; - -#------------------------------------------------------------ -# ATtiny828 -#------------------------------------------------------------ - -part - desc = "ATtiny828"; - id = "t828"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 35; - n_interrupts = 26; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x86; - chip_erase_delay = 15000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x93 0x14; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 5; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--111i.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny828R -#------------------------------------------------------------ - -part parent "t828" - desc = "ATtiny828R"; - id = "t828r"; - mcuid = 36; -; - -#------------------------------------------------------------ -# ATtiny87 -#------------------------------------------------------------ - -part - desc = "ATtiny87"; - id = "t87"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 27; - n_interrupts = 20; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 15000; - signature = 0x1e 0x93 0x87; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, - 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; - ; -# ATtiny87 has Signature Bytes: 0x1E 0x93 0x87. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny167 -#------------------------------------------------------------ - -part - desc = "ATtiny167"; - id = "t167"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 29; - n_interrupts = 20; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = 0x??; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 15000; - signature = 0x1e 0x94 0x87; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, - 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--00xx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--00xx.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--000a.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--000a.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; - ; -# ATtiny167 has Signature Bytes: 0x1E 0x94 0x87. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny48 -#------------------------------------------------------------ - -part - desc = "ATtiny48"; - id = "t48"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 23; - n_interrupts = 20; - stk500_devcode = 0x73; - chip_erase_delay = 15000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x92 0x09; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 64; - read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.111i"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny88 -#------------------------------------------------------------ - -part - desc = "ATtiny88"; - id = "t88"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 28; - n_interrupts = 20; - stk500_devcode = 0x73; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x93 0x11; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 64; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 64; - read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega328 -#------------------------------------------------------------ - -part - desc = "ATmega328"; - id = "m328"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 118; - n_interrupts = 26; - n_boot_sections = 4; - boot_section_size = 512; - stk500_devcode = 0x86; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc2; -# avr910_devcode = 0x??; - signature = 0x1e 0x95 0x14; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega328P -#------------------------------------------------------------ - -part parent "m328" - desc = "ATmega328P"; - id = "m328p"; - mcuid = 119; - signature = 0x1e 0x95 0x0f; -; - -#------------------------------------------------------------ -# ATmega328PB -#------------------------------------------------------------ - -part parent "m328" - desc = "ATmega328PB"; - id = "m328pb"; - mcuid = 120; - n_interrupts = 45; - chip_erase_delay = 10500; - signature = 0x1e 0x95 0x16; - - memory "efuse" - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; -; - -#------------------------------------------------------------ -# ATmega32m1 -#------------------------------------------------------------ - -part parent "m328" - desc = "ATmega32M1"; - id = "m32m1"; - mcuid = 63; - n_interrupts = 31; - bs2 = 0xe2; -# stk500_devcode = 0x??; -# avr910_devcode = 0x??; - signature = 0x1e 0x95 0x84; - - memory "efuse" - write = "1010.1100--1010.0100--xxxx.xxxx--xxii.iiii"; - ; -; - -#------------------------------------------------------------ -# ATmega64m1 -#------------------------------------------------------------ - -part parent "m328" - desc = "ATmega64M1"; - id = "m64m1"; - mcuid = 76; - n_interrupts = 31; - boot_section_size = 1024; - bs2 = 0xe2; -# stk500_devcode = 0x??; -# avr910_devcode = 0x??; - signature = 0x1e 0x96 0x84; - - memory "eeprom" - size = 2048; - page_size = 8; - read = "1010.0000--000x.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - size = 0x10000; - page_size = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "efuse" - write = "1010.1100--1010.0100--xxxx.xxxx--xxii.iiii"; - ; -; - -#------------------------------------------------------------ -# ATtiny2313 -#------------------------------------------------------------ - -part - desc = "ATtiny2313"; - id = "t2313"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 42; - n_interrupts = 19; - stk500_devcode = 0x23; -# Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - chip_erase_delay = 9000; - pagel = 0xd4; - bs2 = 0xd6; - signature = 0x1e 0x91 0x0a; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, - 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb2, 0x0f, 0x1f; - eeprom_instr = - 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xba, 0x0f, 0xb2, 0x0f, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 0; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; -# The information in the data sheet of April/2004 is wrong, this works: - loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; -# The information in the data sheet of April/2004 is wrong, this works: - loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; -# The information in the data sheet of April/2004 is wrong, this works: - writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# ATtiny2313 has Signature Bytes: 0x1E 0x91 0x0A. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; -# The Tiny2313 has calibration data for both 4 MHz and 8 MHz. -# The information in the data sheet of April/2004 is wrong, this works: - - memory "calibration" - size = 2; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny2313A -#------------------------------------------------------------ - -part parent "t2313" - desc = "ATtiny2313A"; - id = "t2313a"; - mcuid = 43; - n_interrupts = 21; -; - -#------------------------------------------------------------ -# ATtiny4313 -#------------------------------------------------------------ - -part - desc = "ATtiny4313"; - id = "t4313"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 44; - n_interrupts = 21; - stk500_devcode = 0x23; -# Use the ATtiny26 devcode: - avr910_devcode = 0x5e; - chip_erase_delay = 9000; - pagel = 0xd4; - bs2 = 0xd6; - signature = 0x1e 0x92 0x0d; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, - 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb2, 0x0f, 0x1f; - eeprom_instr = - 0xbb, 0xfe, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xba, 0x0f, 0xb2, 0x0f, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 0; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# ATtiny4313 has Signature Bytes: 0x1E 0x92 0x0D. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 2; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90PWM2 -#------------------------------------------------------------ - -part - desc = "AT90PWM2"; - id = "pwm2"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 167; - n_interrupts = 32; - n_boot_sections = 4; - boot_section_size = 256; - stk500_devcode = 0x65; - chip_erase_delay = 9000; - pagel = 0xd8; - bs2 = 0xe2; -# avr910_devcode = ?; - signature = 0x1e 0x93 0x81; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# AT90PWM2 has Signature Bytes: 0x1E 0x93 0x81. - memory "signature" - size = 3; - read = "0011.0000--00xx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90PWM3 -#------------------------------------------------------------ - -# Completely identical to AT90PWM2 (including the signature!) - -part parent "pwm2" - desc = "AT90PWM3"; - id = "pwm3"; - mcuid = 169; -; - -#------------------------------------------------------------ -# AT90PWM2B -#------------------------------------------------------------ -# Same as AT90PWM2 but different signature. - -part parent "pwm2" - desc = "AT90PWM2B"; - id = "pwm2b"; - mcuid = 168; - signature = 0x1e 0x93 0x83; - ocdrev = 1; -; - -#------------------------------------------------------------ -# AT90PWM3B -#------------------------------------------------------------ - -# Completely identical to AT90PWM2B (including the signature!) - -part parent "pwm2b" - desc = "AT90PWM3B"; - id = "pwm3b"; - mcuid = 170; -; - -#------------------------------------------------------------ -# AT90PWM316 -#------------------------------------------------------------ - -# Similar to AT90PWM3B, but with 16 kiB flash, 512 B EEPROM, and 1024 B SRAM. - -part parent "pwm3b" - desc = "AT90PWM316"; - id = "pwm316"; - mcuid = 180; - boot_section_size = 512; - signature = 0x1e 0x94 0x83; - - memory "flash" - size = 0x4000; - page_size = 128; - mode = 33; - blocksize = 128; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--00xx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; -; - -#------------------------------------------------------------ -# AT90PWM216 -#------------------------------------------------------------ -# Completely identical to AT90PWM316 (including the signature!) - -part parent "pwm316" - desc = "AT90PWM216"; - id = "pwm216"; - mcuid = 179; -; - -#------------------------------------------------------------ -# ATtiny25 -#------------------------------------------------------------ - -part - desc = "ATtiny25"; - id = "t25"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 16; - n_interrupts = 15; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x91 0x08; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - flash_instr = 0xb4, 0x02, 0x12; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# ATtiny25 has Signature Bytes: 0x1E 0x91 0x08. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny45 -#------------------------------------------------------------ - -part - desc = "ATtiny45"; - id = "t45"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 22; - n_interrupts = 15; - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x92 0x06; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - flash_instr = 0xb4, 0x02, 0x12; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# ATtiny45 has Signature Bytes: 0x1E 0x92 0x08. (Data sheet 2586C-AVR-06/05 (doc2586.pdf) indicates otherwise!) - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny85 -#------------------------------------------------------------ - -part - desc = "ATtiny85"; - id = "t85"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 26; - n_interrupts = 15; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x93 0x0b; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x00; - flash_instr = 0xb4, 0x02, 0x12; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x02, 0xb4, 0x02, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayms = 1; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; -# ATtiny85 has Signature Bytes: 0x1E 0x93 0x08. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega640 -#------------------------------------------------------------ -# Almost same as ATmega1280, except for different memory sizes - -part - desc = "ATmega640"; - id = "m640"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 126; - n_interrupts = 57; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x96 0x08; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 10; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega1280 -#------------------------------------------------------------ - -part - desc = "ATmega1280"; - id = "m1280"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 138; - n_interrupts = 57; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x97 0x03; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 10; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega1281 -#------------------------------------------------------------ -# Identical to ATmega1280 - -part parent "m1280" - desc = "ATmega1281"; - id = "m1281"; - mcuid = 139; - signature = 0x1e 0x97 0x04; -; - -#------------------------------------------------------------ -# ATmega2560 -#------------------------------------------------------------ - -part - desc = "ATmega2560"; - id = "m2560"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 143; - n_interrupts = 57; - n_boot_sections = 4; - boot_section_size = 1024; - stk500_devcode = 0xb2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x98 0x01; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 4; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x40000; - page_size = 256; - num_pages = 1024; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 10; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - load_ext_addr = "0100.1101--0000.0000--0000.000a--0000.0000"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega2561 -#------------------------------------------------------------ - -part parent "m2560" - desc = "ATmega2561"; - id = "m2561"; - mcuid = 144; - signature = 0x1e 0x98 0x02; -; - -#------------------------------------------------------------ -# ATmega128RFA1 -#------------------------------------------------------------ -# Identical to ATmega2561 but half the ROM - -part parent "m2561" - desc = "ATmega128RFA1"; - id = "m128rfa1"; - mcuid = 87; - n_interrupts = 72; - chip_erase_delay = 55000; - bs2 = 0xe2; - signature = 0x1e 0xa7 0x01; - ocdrev = 3; - - memory "flash" - size = 0x20000; - num_pages = 512; - min_write_delay = 50000; - max_write_delay = 50000; - delay = 20; - load_ext_addr = NULL; - ; -; - -#------------------------------------------------------------ -# ATmega256RFR2 -#------------------------------------------------------------ - -part parent "m2561" - desc = "ATmega256RFR2"; - id = "m256rfr2"; - mcuid = 108; - n_interrupts = 77; - chip_erase_delay = 18500; - bs2 = 0xe2; - signature = 0x1e 0xa8 0x02; - - memory "eeprom" - size = 8192; - min_write_delay = 13000; - max_write_delay = 13000; - read = "1010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxa.aaaa--aaaa.aaaa--iiii.iiii"; - writepage = "1100.0010--00xa.aaaa--aaaa.a000--xxxx.xxxx"; - ; -; - -#------------------------------------------------------------ -# ATmega128RFR2 -#------------------------------------------------------------ - -part parent "m128rfa1" - desc = "ATmega128RFR2"; - id = "m128rfr2"; - mcuid = 88; - n_interrupts = 77; - signature = 0x1e 0xa7 0x02; -; - -#------------------------------------------------------------ -# ATmega64RFR2 -#------------------------------------------------------------ - -part parent "m128rfa1" - desc = "ATmega64RFR2"; - id = "m64rfr2"; - mcuid = 78; - n_interrupts = 77; - signature = 0x1e 0xa6 0x02; - - memory "eeprom" - size = 2048; - min_write_delay = 13000; - max_write_delay = 13000; - read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - size = 0x10000; - num_pages = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; -; - -#------------------------------------------------------------ -# ATmega2564RFR2 -#------------------------------------------------------------ - -part parent "m256rfr2" - desc = "ATmega2564RFR2"; - id = "m2564rfr2"; - mcuid = 145; - signature = 0x1e 0xa8 0x03; -; - -#------------------------------------------------------------ -# ATmega1284RFR2 -#------------------------------------------------------------ - -part parent "m128rfr2" - desc = "ATmega1284RFR2"; - id = "m1284rfr2"; - mcuid = 142; - signature = 0x1e 0xa7 0x03; -; - -#------------------------------------------------------------ -# ATmega644RFR2 -#------------------------------------------------------------ - -part parent "m64rfr2" - desc = "ATmega644RFR2"; - id = "m644rfr2"; - mcuid = 131; - signature = 0x1e 0xa6 0x03; -; - -#------------------------------------------------------------ -# ATtiny24 -#------------------------------------------------------------ - -part - desc = "ATtiny24"; - id = "t24"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 14; - n_interrupts = 17; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x91 0x0b; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; - flash_instr = 0xb4, 0x07, 0x17; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 128; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--xaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--xaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 2048; - page_size = 32; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.00aa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.00aa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; - ; -# ATtiny24 has Signature Bytes: 0x1E 0x91 0x0B. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny24A -#------------------------------------------------------------ - -part parent "t24" - desc = "ATtiny24A"; - id = "t24a"; - mcuid = 15; -; - -#------------------------------------------------------------ -# ATtiny44 -#------------------------------------------------------------ - -part - desc = "ATtiny44"; - id = "t44"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 20; - n_interrupts = 17; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x92 0x07; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; - flash_instr = 0xb4, 0x07, 0x17; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; - ; -# ATtiny44 has Signature Bytes: 0x1E 0x92 0x07. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny44A -#------------------------------------------------------------ - -part parent "t44" - desc = "ATtiny44A"; - id = "t44a"; - mcuid = 21; -; - -#------------------------------------------------------------ -# ATtiny84 -#------------------------------------------------------------ - -part - desc = "ATtiny84"; - id = "t84"; - prog_modes = PM_SPM | PM_ISP | PM_HVSP | PM_debugWIRE; - mcuid = 24; - n_interrupts = 17; -# no STK500 devcode in XML file, use the ATtiny45 one - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 4500; - signature = 0x1e 0x93 0x0c; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - hvsp_controlstack = - 0x4c, 0x0c, 0x1c, 0x2c, 0x3c, 0x64, 0x74, 0x66, - 0x68, 0x78, 0x68, 0x68, 0x7a, 0x6a, 0x68, 0x78, - 0x78, 0x7d, 0x6d, 0x0c, 0x80, 0x40, 0x20, 0x10, - 0x11, 0x08, 0x04, 0x02, 0x03, 0x08, 0x04, 0x0f; - flash_instr = 0xb4, 0x07, 0x17; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 1; - togglevtg = 1; - poweroffdelay = 25; - resetdelayus = 70; - hvleavestabdelay = 100; - resetdelay = 25; - chiperasepolltimeout = 40; - programfusepolltimeout = 25; - programlockpolltimeout = 25; - synchcycles = 6; - spmcr = 0x57; - eecr = 0x3c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 64; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 32; - readsize = 256; - read_lo = "0010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--xxxx.xxii"; - ; -# ATtiny84 has Signature Bytes: 0x1E 0x93 0x0C. - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny84A -#------------------------------------------------------------ - -part parent "t84" - desc = "ATtiny84A"; - id = "t84a"; - mcuid = 25; -; - -#------------------------------------------------------------ -# ATtiny441 -#------------------------------------------------------------ - -part parent "t44" - desc = "ATtiny441"; - id = "t441"; - mcuid = 32; - n_interrupts = 30; - n_page_erase = 4; - signature = 0x1e 0x92 0x15; - - memory "flash" - page_size = 16; - num_pages = 256; - blocksize = 16; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.xaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.xaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaaa.axxx--xxxx.xxxx"; - ; - - memory "efuse" - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; -; - -#------------------------------------------------------------ -# ATtiny841 -#------------------------------------------------------------ - -part parent "t84" - desc = "ATtiny841"; - id = "t841"; - mcuid = 37; - n_interrupts = 30; - n_page_erase = 4; - signature = 0x1e 0x93 0x15; - - memory "flash" - page_size = 16; - num_pages = 512; - blocksize = 16; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.xaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.xaaa--iiii.iiii"; - writepage = "0100.1100--0000.aaaa--aaaa.axxx--xxxx.xxxx"; - ; - - memory "efuse" - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; -; - -#------------------------------------------------------------ -# ATtiny43U -#------------------------------------------------------------ - -part - desc = "ATtiny43U"; - id = "t43u"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 19; - n_interrupts = 16; - stk500_devcode = 0x14; -# avr910_devcode = ?; -# Try the AT90S2313 devcode: - avr910_devcode = 0x20; - chip_erase_delay = 1000; - signature = 0x1e 0x92 0x0c; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x06, 0x16, 0x46, 0x56, 0x0a, 0x1a, 0x4a, 0x5a, - 0x1e, 0x7c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb4, 0x07, 0x17; - eeprom_instr = - 0xbb, 0xff, 0xbb, 0xee, 0xbb, 0xcc, 0xb2, 0x0d, - 0xbc, 0x07, 0xb4, 0x07, 0xba, 0x0d, 0xbb, 0xbc, - 0x99, 0xe1, 0xbb, 0xac; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 20; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - paged = yes; - size = 64; - page_size = 4; - num_pages = 16; - min_write_delay = 4000; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 5; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxx--00aa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxx--00aa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxx--00aa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 4096; - page_size = 64; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 64; - readsize = 256; - read_lo = "0010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxa.aaaa--iiii.iiii"; - writepage = "0100.1100--0000.0aaa--aaax.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.xxxi"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.000a--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega16u4 -#------------------------------------------------------------ - -part - desc = "ATmega16U4"; - id = "m16u4"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 57; - n_interrupts = 43; - n_boot_sections = 4; - boot_section_size = 512; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x88; - usbpid = 0x2ff4; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--00oo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega32u4 -#------------------------------------------------------------ - -part - desc = "ATmega32U4"; - id = "m32u4"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 65; - n_interrupts = 43; - n_boot_sections = 4; - boot_section_size = 512; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x95 0x87; - usbpid = 0x2ff4; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--1111.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90USB646 -#------------------------------------------------------------ - -part - desc = "AT90USB646"; - id = "usb646"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 181; - n_interrupts = 38; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x96 0x82; - usbpid = 0x2ff9; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.xaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.xaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.xaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--0aaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90USB647 -#------------------------------------------------------------ -# identical to AT90USB646 - -part parent "usb646" - desc = "AT90USB647"; - id = "usb647"; - mcuid = 182; -; - -#------------------------------------------------------------ -# AT90USB1286 -#------------------------------------------------------------ - -part - desc = "AT90USB1286"; - id = "usb1286"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 184; - n_interrupts = 38; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0xB2; -# avr910_devcode = 0x43; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x97 0x82; - usbpid = 0x2ffb; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - rampz = 0x3b; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 4096; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--xxxx.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--xxxx.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--00xx.aaaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x20000; - page_size = 256; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 256; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--axxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--xxxx.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--xxxx.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90USB1287 -#------------------------------------------------------------ -# identical to AT90USB1286 - -part parent "usb1286" - desc = "AT90USB1287"; - id = "usb1287"; - mcuid = 185; -; - -#------------------------------------------------------------ -# AT90USB162 -#------------------------------------------------------------ - -part - desc = "AT90USB162"; - id = "usb162"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 178; - n_interrupts = 29; - n_boot_sections = 4; - boot_section_size = 512; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc6; - signature = 0x1e 0x94 0x82; - usbpid = 0x2ffa; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - eind = 0x5c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# AT90USB82 -#------------------------------------------------------------ - -part - desc = "AT90USB82"; - id = "usb82"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 174; - n_interrupts = 29; - n_boot_sections = 4; - boot_section_size = 512; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc6; - signature = 0x1e 0x93 0x82; - usbpid = 0x2ff7; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - eind = 0x5c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega32U2 -#------------------------------------------------------------ - -part - desc = "ATmega32U2"; - id = "m32u2"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 64; - n_interrupts = 29; - n_boot_sections = 4; - boot_section_size = 512; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc6; - signature = 0x1e 0x95 0x8a; - usbpid = 0x2ff0; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - eind = 0x5c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 1024; - page_size = 4; - num_pages = 256; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega16U2 -#------------------------------------------------------------ - -part - desc = "ATmega16U2"; - id = "m16u2"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 56; - n_interrupts = 29; - n_boot_sections = 4; - boot_section_size = 512; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc6; - signature = 0x1e 0x94 0x89; - usbpid = 0x2fef; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - eind = 0x5c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega8U2 -#------------------------------------------------------------ - -part - desc = "ATmega8U2"; - id = "m8u2"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 48; - n_interrupts = 29; - n_boot_sections = 4; - boot_section_size = 512; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xc6; - signature = 0x1e 0x93 0x89; - usbpid = 0x2fee; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3f; - eind = 0x5c; - ocdrev = 1; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 9000; - max_write_delay = 9000; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.aaaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.aaaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.aaaa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 8192; - page_size = 128; - num_pages = 64; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--xxxx.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--iiii.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega165 -#------------------------------------------------------------ - -part - desc = "ATmega165"; - id = "m165"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 95; - n_interrupts = 22; - n_boot_sections = 4; - boot_section_size = 256; -# stk500_devcode = 0x??; -# avr910_devcode = 0x??; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x94 0x10; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 6; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - eecr = 0x3f; - ocdrev = 3; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - min_write_delay = 3600; - max_write_delay = 3600; - mode = 65; - delay = 20; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.00xa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.00xa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.00xa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 128; - num_pages = 128; - min_write_delay = 4500; - max_write_delay = 4500; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--xxxa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.xxxx--xxaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.xxxx--xxaa.aaaa--iiii.iiii"; - writepage = "0100.1100--xxxa.aaaa--aaxx.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxx.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--0000.0000--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega165A -#------------------------------------------------------------ - -part parent "m165" - desc = "ATmega165A"; - id = "m165a"; - mcuid = 96; -; - -#------------------------------------------------------------ -# ATmega165P -#------------------------------------------------------------ - -part parent "m165" - desc = "ATmega165P"; - id = "m165p"; - mcuid = 97; - signature = 0x1e 0x94 0x07; -; - -#------------------------------------------------------------ -# ATmega165PA -#------------------------------------------------------------ - -part parent "m165" - desc = "ATmega165PA"; - id = "m165pa"; - mcuid = 98; - signature = 0x1e 0x94 0x07; -; - -#------------------------------------------------------------ -# ATmega325 -#------------------------------------------------------------ - -part - desc = "ATmega325"; - id = "m325"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 114; - n_interrupts = 22; - n_boot_sections = 4; - boot_section_size = 512; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x95 0x05; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--0000.0000--0000.0000"; - pgm_enable = "1010.1100--0101.0011--0000.0000--0000.0000"; - - memory "eeprom" - size = 1024; - page_size = 4; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 4; - readsize = 256; - read = "1010.0000--0000.00aa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.00aa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--0000.00aa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x8000; - page_size = 128; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--0aaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.0000--aaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.0000--aaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--0aaa.aaaa--aaaa.aaaa--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.0000--0000.0000--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.1000--0000.0000--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.0100--0000.0000--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1110.0000--0000.0000--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--0000.0000--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--0000.0000--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega325A -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega325A"; - id = "m325a"; - mcuid = 115; -; - -#------------------------------------------------------------ -# ATmega325P -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega325P"; - id = "m325p"; - mcuid = 116; - signature = 0x1e 0x95 0x0d; -; - -#------------------------------------------------------------ -# ATmega325PA -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega325PA"; - id = "m325pa"; - mcuid = 117; - signature = 0x1e 0x95 0x0d; -; - -#------------------------------------------------------------ -# ATmega645 -#------------------------------------------------------------ - -part - desc = "ATmega645"; - id = "m645"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_JTAG; - mcuid = 132; - n_interrupts = 22; - n_boot_sections = 4; - boot_section_size = 1024; -# stk500_devcode = 0x??; # No STK500v1 support? -# avr910_devcode = 0x??; # Try the ATmega16 one - avr910_devcode = 0x74; - chip_erase_delay = 9000; - pagel = 0xd7; - bs2 = 0xa0; - signature = 0x1e 0x96 0x05; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - hventerstabdelay = 100; - latchcycles = 5; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - idr = 0x31; - spmcr = 0x57; - ocdrev = 3; - chip_erase = "1010.1100--1000.0000--0000.0000--0000.0000"; - pgm_enable = "1010.1100--0101.0011--0000.0000--0000.0000"; - - memory "eeprom" - size = 2048; - page_size = 8; - min_write_delay = 9000; - max_write_delay = 9000; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 8; - readsize = 256; - read = "1010.0000--0000.0aaa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--0000.0aaa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.0aaa--iiii.iiii"; - writepage = "1100.0010--0000.0aaa--aaaa.a000--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x10000; - page_size = 256; - num_pages = 256; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 10; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--aaaa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--0000.0000--aaaa.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--0000.0000--aaaa.aaaa--iiii.iiii"; - writepage = "0100.1100--aaaa.aaaa--aaaa.aaaa--0000.0000"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.0000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.0000--0000.0000--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.1000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.1000--0000.0000--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.0000--0000.1000--0000.0000--oooo.oooo"; - write = "1010.1100--1010.0100--0000.0000--1111.1iii"; - ; - - memory "lock" - size = 1; - min_write_delay = 9000; - max_write_delay = 9000; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1110.0000--0000.0000--11ii.iiii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--0000.0000--0000.00aa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--0000.0000--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATmega645A -#------------------------------------------------------------ - -part parent "m645" - desc = "ATmega645A"; - id = "m645a"; - mcuid = 133; -; - -#------------------------------------------------------------ -# ATmega645P -#------------------------------------------------------------ - -part parent "m645" - desc = "ATmega645P"; - id = "m645p"; - mcuid = 134; - signature = 0x1e 0x96 0x0d; -; - -#------------------------------------------------------------ -# ATmega3250 -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega3250"; - id = "m3250"; - mcuid = 146; - n_interrupts = 25; - signature = 0x1e 0x95 0x06; -; - -#------------------------------------------------------------ -# ATmega3250A -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega3250A"; - id = "m3250a"; - mcuid = 147; - n_interrupts = 25; - signature = 0x1e 0x95 0x06; -; - -#------------------------------------------------------------ -# ATmega3250P -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega3250P"; - id = "m3250p"; - mcuid = 148; - n_interrupts = 25; - signature = 0x1e 0x95 0x0e; -; - -#------------------------------------------------------------ -# ATmega3250PA -#------------------------------------------------------------ - -part parent "m325" - desc = "ATmega3250PA"; - id = "m3250pa"; - mcuid = 149; - n_interrupts = 25; - signature = 0x1e 0x95 0x0e; -; - -#------------------------------------------------------------ -# ATmega6450 -#------------------------------------------------------------ - -part parent "m645" - desc = "ATmega6450"; - id = "m6450"; - mcuid = 154; - n_interrupts = 25; - signature = 0x1e 0x96 0x06; -; - -#------------------------------------------------------------ -# ATmega6450A -#------------------------------------------------------------ - -part parent "m645" - desc = "ATmega6450A"; - id = "m6450a"; - mcuid = 155; - n_interrupts = 25; - signature = 0x1e 0x96 0x06; -; - -#------------------------------------------------------------ -# ATmega6450P -#------------------------------------------------------------ - -part parent "m645" - desc = "ATmega6450P"; - id = "m6450p"; - mcuid = 156; - n_interrupts = 25; - signature = 0x1e 0x96 0x0e; -; - -#------------------------------------------------------------ -# AVR XMEGA family common values -#------------------------------------------------------------ - -part - desc = "AVR XMEGA family common values"; - id = ".xmega"; - prog_modes = PM_SPM | PM_PDI; - n_boot_sections = 1; - mcu_base = 0x0090; - nvm_base = 0x01c0; - autobaud_sync = 0x20; - - memory "fuse1" - size = 1; - offset = 0x8f0021; - ; - - memory "fuse2" - size = 1; - offset = 0x8f0022; - ; - - memory "fuse4" - size = 1; - offset = 0x8f0024; - ; - - memory "fuse5" - size = 1; - offset = 0x8f0025; - ; - - memory "lock" - size = 1; - offset = 0x8f0027; - ; - - memory "signature" - size = 3; - offset = 0x1000090; - ; - - memory "prodsig" - size = 50; - page_size = 50; - offset = 0x8e0200; - readsize = 50; - ; - - memory "data" - # SRAM, only used to supply the offset - offset = 0x1000000; - ; -; - -#------------------------------------------------------------ -# ATxmega16A4U -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega16A4U"; - id = "x16a4u"; - mcuid = 232; - n_interrupts = 127; - boot_section_size = 4096; - signature = 0x1e 0x94 0x41; - usbpid = 0x2fe3; - - memory "eeprom" - size = 1024; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x5000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x4000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 256; - offset = 0x803000; - readsize = 256; - ; - - memory "boot" - size = 4096; - page_size = 256; - offset = 0x804000; - readsize = 256; - ; - - memory "usersig" - size = 256; - page_size = 256; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega16C4 -#------------------------------------------------------------ - -part parent "x16a4u" - desc = "ATxmega16C4"; - id = "x16c4"; - mcuid = 233; - signature = 0x1e 0x94 0x43; -; - -#------------------------------------------------------------ -# ATxmega16D4 -#------------------------------------------------------------ - -part parent "x16a4u" - desc = "ATxmega16D4"; - id = "x16d4"; - mcuid = 234; - n_interrupts = 91; - signature = 0x1e 0x94 0x42; -; - -#------------------------------------------------------------ -# ATxmega16A4 -#------------------------------------------------------------ - -part parent "x16a4u" - desc = "ATxmega16A4"; - id = "x16a4"; - mcuid = 231; - n_interrupts = 94; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega32A4U -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega32A4U"; - id = "x32a4u"; - mcuid = 239; - n_interrupts = 127; - boot_section_size = 4096; - signature = 0x1e 0x95 0x41; - usbpid = 0x2fe4; - - memory "eeprom" - size = 1024; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x9000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x8000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 256; - offset = 0x807000; - readsize = 256; - ; - - memory "boot" - size = 4096; - page_size = 256; - offset = 0x808000; - readsize = 256; - ; - - memory "usersig" - size = 256; - page_size = 256; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega32C4 -#------------------------------------------------------------ - -part parent "x32a4u" - desc = "ATxmega32C4"; - id = "x32c4"; - mcuid = 240; - signature = 0x1e 0x95 0x44; -; - -#------------------------------------------------------------ -# ATxmega32D4 -#------------------------------------------------------------ - -part parent "x32a4u" - desc = "ATxmega32D4"; - id = "x32d4"; - mcuid = 241; - n_interrupts = 91; - signature = 0x1e 0x95 0x42; -; - -#------------------------------------------------------------ -# ATxmega32A4 -#------------------------------------------------------------ - -part parent "x32a4u" - desc = "ATxmega32A4"; - id = "x32a4"; - mcuid = 238; - n_interrupts = 94; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega64A4U -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega64A4U"; - id = "x64a4u"; - mcuid = 252; - n_interrupts = 127; - boot_section_size = 4096; - signature = 0x1e 0x96 0x46; - usbpid = 0x2fe5; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x11000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x10000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 256; - offset = 0x80f000; - readsize = 256; - ; - - memory "boot" - size = 4096; - page_size = 256; - offset = 0x810000; - readsize = 256; - ; - - memory "usersig" - size = 256; - page_size = 256; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega64C3 -#------------------------------------------------------------ - -part parent "x64a4u" - desc = "ATxmega64C3"; - id = "x64c3"; - mcuid = 249; - signature = 0x1e 0x96 0x49; - usbpid = 0x2fd6; -; - -#------------------------------------------------------------ -# ATxmega64D3 -#------------------------------------------------------------ - -part parent "x64a4u" - desc = "ATxmega64D3"; - id = "x64d3"; - mcuid = 250; - n_interrupts = 114; - signature = 0x1e 0x96 0x4a; -; - -#------------------------------------------------------------ -# ATxmega64D4 -#------------------------------------------------------------ - -part parent "x64a4u" - desc = "ATxmega64D4"; - id = "x64d4"; - mcuid = 253; - n_interrupts = 91; - signature = 0x1e 0x96 0x47; -; - -#------------------------------------------------------------ -# ATxmega64A1 -#------------------------------------------------------------ - -part parent "x64a4u" - desc = "ATxmega64A1"; - id = "x64a1"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 243; - n_interrupts = 125; - signature = 0x1e 0x96 0x4e; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega64A1U -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64A1U"; - id = "x64a1u"; - mcuid = 244; - n_interrupts = 127; - usbpid = 0x2fe8; -; - -#------------------------------------------------------------ -# ATxmega64A3 -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64A3"; - id = "x64a3"; - mcuid = 246; - n_interrupts = 122; - signature = 0x1e 0x96 0x42; -; - -#------------------------------------------------------------ -# ATxmega64A3U -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64A3U"; - id = "x64a3u"; - mcuid = 247; - n_interrupts = 127; - signature = 0x1e 0x96 0x42; -; - -#------------------------------------------------------------ -# ATxmega64A4 -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64A4"; - id = "x64a4"; - mcuid = 251; - signature = 0x1e 0x96 0x46; -; - -#------------------------------------------------------------ -# ATxmega64B1 -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64B1"; - id = "x64b1"; - mcuid = 245; - n_interrupts = 81; - signature = 0x1e 0x96 0x52; - usbpid = 0x2fe1; -; - -#------------------------------------------------------------ -# ATxmega64B3 -#------------------------------------------------------------ - -part parent "x64a1" - desc = "ATxmega64B3"; - id = "x64b3"; - mcuid = 248; - n_interrupts = 54; - signature = 0x1e 0x96 0x51; - usbpid = 0x2fdf; -; - -#------------------------------------------------------------ -# ATxmega128C3 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega128C3"; - id = "x128c3"; - mcuid = 261; - n_interrupts = 127; - boot_section_size = 8192; - signature = 0x1e 0x97 0x52; - usbpid = 0x2fd7; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x22000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 8192; - page_size = 512; - offset = 0x81e000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 512; - offset = 0x820000; - readsize = 256; - ; - - memory "usersig" - size = 512; - page_size = 512; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega128D3 -#------------------------------------------------------------ - -part parent "x128c3" - desc = "ATxmega128D3"; - id = "x128d3"; - mcuid = 262; - n_interrupts = 114; - signature = 0x1e 0x97 0x48; -; - -#------------------------------------------------------------ -# ATxmega128D4 -#------------------------------------------------------------ - -part parent "x128c3" - desc = "ATxmega128D4"; - id = "x128d4"; - mcuid = 265; - n_interrupts = 91; - signature = 0x1e 0x97 0x47; - - memory "flash" - page_size = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega128A1 -#------------------------------------------------------------ - -part parent "x128c3" - desc = "ATxmega128A1"; - id = "x128a1"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 254; - n_interrupts = 125; - signature = 0x1e 0x97 0x4c; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega128A1 revision D -#------------------------------------------------------------ - -part parent "x128a1" - desc = "ATxmega128A1revD"; - id = "x128a1d"; - mcuid = 255; - signature = 0x1e 0x97 0x41; -; - -#------------------------------------------------------------ -# ATxmega128A1U -#------------------------------------------------------------ - -part parent "x128a1" - desc = "ATxmega128A1U"; - id = "x128a1u"; - mcuid = 256; - n_interrupts = 127; - usbpid = 0x2fed; -; - -#------------------------------------------------------------ -# ATxmega128A3 -#------------------------------------------------------------ - -part parent "x128a1" - desc = "ATxmega128A3"; - id = "x128a3"; - mcuid = 258; - n_interrupts = 122; - signature = 0x1e 0x97 0x42; -; - -#------------------------------------------------------------ -# ATxmega128A3U -#------------------------------------------------------------ - -part parent "x128a1" - desc = "ATxmega128A3U"; - id = "x128a3u"; - mcuid = 259; - n_interrupts = 127; - signature = 0x1e 0x97 0x42; - usbpid = 0x2fe6; -; - -#------------------------------------------------------------ -# ATxmega128A4 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega128A4"; - id = "x128a4"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 263; - signature = 0x1e 0x97 0x46; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x22000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 512; - offset = 0x81f000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 512; - offset = 0x820000; - readsize = 256; - ; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; - - memory "usersig" - size = 512; - page_size = 512; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega128A4U -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega128A4U"; - id = "x128a4u"; - mcuid = 264; - n_interrupts = 127; - boot_section_size = 8192; - signature = 0x1e 0x97 0x46; - usbpid = 0x2fde; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x22000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x20000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 256; - offset = 0x81f000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 256; - offset = 0x820000; - readsize = 256; - ; - - memory "usersig" - size = 256; - page_size = 256; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega128B1 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega128B1"; - id = "x128b1"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 257; - n_interrupts = 81; - boot_section_size = 8192; - signature = 0x1e 0x97 0x4d; - usbpid = 0x2fea; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x22000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x20000; - page_size = 256; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 8192; - page_size = 256; - offset = 0x81e000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 256; - offset = 0x820000; - readsize = 256; - ; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; - - memory "usersig" - size = 256; - page_size = 256; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega128B3 -#------------------------------------------------------------ - -part parent "x128b1" - desc = "ATxmega128B3"; - id = "x128b3"; - mcuid = 260; - n_interrupts = 54; - signature = 0x1e 0x97 0x4b; - usbpid = 0x2fe0; -; - -#------------------------------------------------------------ -# ATxmega192C3 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega192C3"; - id = "x192c3"; - mcuid = 269; - n_interrupts = 127; - boot_section_size = 8192; - signature = 0x1e 0x97 0x51; -# usbpid = 0x2f??; - - memory "eeprom" - size = 2048; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x32000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x30000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 8192; - page_size = 512; - offset = 0x82e000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 512; - offset = 0x830000; - readsize = 256; - ; - - memory "usersig" - size = 512; - page_size = 512; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega192D3 -#------------------------------------------------------------ - -part parent "x192c3" - desc = "ATxmega192D3"; - id = "x192d3"; - mcuid = 270; - n_interrupts = 114; - signature = 0x1e 0x97 0x49; -; - -#------------------------------------------------------------ -# ATxmega192A1 -#------------------------------------------------------------ - -part parent "x192c3" - desc = "ATxmega192A1"; - id = "x192a1"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 266; - signature = 0x1e 0x97 0x4e; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega192A3 -#------------------------------------------------------------ - -part parent "x192a1" - desc = "ATxmega192A3"; - id = "x192a3"; - mcuid = 267; - n_interrupts = 122; - signature = 0x1e 0x97 0x44; -; - -#------------------------------------------------------------ -# ATxmega192A3U -#------------------------------------------------------------ - -part parent "x192a1" - desc = "ATxmega192A3U"; - id = "x192a3u"; - mcuid = 268; - signature = 0x1e 0x97 0x44; - usbpid = 0x2fe7; -; - -#------------------------------------------------------------ -# ATxmega256C3 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega256C3"; - id = "x256c3"; - mcuid = 276; - n_interrupts = 127; - boot_section_size = 8192; - signature = 0x1e 0x98 0x46; - usbpid = 0x2fda; - - memory "eeprom" - size = 4096; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x42000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x40000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 8192; - page_size = 512; - offset = 0x83e000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 512; - offset = 0x840000; - readsize = 256; - ; - - memory "usersig" - size = 512; - page_size = 512; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega256D3 -#------------------------------------------------------------ - -part parent "x256c3" - desc = "ATxmega256D3"; - id = "x256d3"; - mcuid = 277; - n_interrupts = 114; - signature = 0x1e 0x98 0x44; -; - -#------------------------------------------------------------ -# ATxmega256A1 -#------------------------------------------------------------ - -part parent "x256c3" - desc = "ATxmega256A1"; - id = "x256a1"; - prog_modes = PM_SPM | PM_PDI | PM_XMEGAJTAG; - mcuid = 271; - - memory "fuse0" - size = 1; - offset = 0x8f0020; - ; -; - -#------------------------------------------------------------ -# ATxmega256A3 -#------------------------------------------------------------ - -part parent "x256a1" - desc = "ATxmega256A3"; - id = "x256a3"; - mcuid = 272; - n_interrupts = 122; - signature = 0x1e 0x98 0x42; -; - -#------------------------------------------------------------ -# ATxmega256A3U -#------------------------------------------------------------ - -part parent "x256a1" - desc = "ATxmega256A3U"; - id = "x256a3u"; - mcuid = 275; - signature = 0x1e 0x98 0x42; - usbpid = 0x2fec; -; - -#------------------------------------------------------------ -# ATxmega256A3B -#------------------------------------------------------------ - -part parent "x256a1" - desc = "ATxmega256A3B"; - id = "x256a3b"; - mcuid = 273; - n_interrupts = 122; - signature = 0x1e 0x98 0x43; -; - -#------------------------------------------------------------ -# ATxmega256A3BU -#------------------------------------------------------------ - -part parent "x256a1" - desc = "ATxmega256A3BU"; - id = "x256a3bu"; - mcuid = 274; - signature = 0x1e 0x98 0x43; - usbpid = 0x2fe2; -; - -#------------------------------------------------------------ -# ATxmega384C3 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega384C3"; - id = "x384c3"; - mcuid = 278; - n_interrupts = 127; - boot_section_size = 8192; - signature = 0x1e 0x98 0x45; - usbpid = 0x2fdb; - - memory "eeprom" - size = 4096; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x62000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x60000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 8192; - page_size = 512; - offset = 0x85e000; - readsize = 256; - ; - - memory "boot" - size = 8192; - page_size = 512; - offset = 0x860000; - readsize = 256; - ; - - memory "usersig" - size = 512; - page_size = 512; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega384D3 -#------------------------------------------------------------ - -part parent "x384c3" - desc = "ATxmega384D3"; - id = "x384d3"; - mcuid = 279; - n_interrupts = 114; - signature = 0x1e 0x98 0x47; -; - -#------------------------------------------------------------ -# ATxmega8E5 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega8E5"; - id = "x8e5"; - mcuid = 230; - n_interrupts = 43; - boot_section_size = 2048; - signature = 0x1e 0x93 0x41; - - memory "eeprom" - size = 512; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x2800; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 8192; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 2048; - page_size = 128; - offset = 0x801800; - readsize = 256; - ; - - memory "boot" - size = 2048; - page_size = 128; - offset = 0x802000; - readsize = 256; - ; - - memory "usersig" - size = 128; - page_size = 128; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega16E5 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega16E5"; - id = "x16e5"; - mcuid = 235; - n_interrupts = 43; - boot_section_size = 4096; - signature = 0x1e 0x94 0x45; - - memory "eeprom" - size = 512; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x5000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x4000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 128; - offset = 0x803000; - readsize = 256; - ; - - memory "boot" - size = 4096; - page_size = 128; - offset = 0x804000; - readsize = 256; - ; - - memory "usersig" - size = 128; - page_size = 128; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATxmega32E5 -#------------------------------------------------------------ - -part parent ".xmega" - desc = "ATxmega32E5"; - id = "x32e5"; - mcuid = 242; - n_interrupts = 43; - boot_section_size = 4096; - signature = 0x1e 0x95 0x4c; - - memory "eeprom" - size = 1024; - page_size = 32; - offset = 0x8c0000; - readsize = 256; - ; - - memory "flash" - size = 0x9000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "application" - size = 0x8000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; - - memory "apptable" - size = 4096; - page_size = 128; - offset = 0x807000; - readsize = 256; - ; - - memory "boot" - size = 4096; - page_size = 128; - offset = 0x808000; - readsize = 256; - ; - - memory "usersig" - size = 128; - page_size = 128; - offset = 0x8e0400; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32UC3A0512 -#------------------------------------------------------------ - -part - desc = "AT32UC3A0512"; - id = "uc3a0512"; - prog_modes = PM_AVR32JTAG | PM_aWire; - signature = 0xed 0xc0 0x3f; - - memory "flash" - paged = yes; - size = 0x80000; # could be set dynamicly - page_size = 512; # bytes - num_pages = 1024; # could be set dynamicly - offset = 0x80000000; - readsize = 512; # bytes - ; -; - -#------------------------------------------------------------ -# deprecated, use 'uc3a0512' -#------------------------------------------------------------ - -part parent "uc3a0512" - desc = "deprecated, use 'uc3a0512'"; - id = "ucr2"; -; - -#------------------------------------------------------------ -# ATtiny1634 -#------------------------------------------------------------ - -part - desc = "ATtiny1634"; - id = "t1634"; - prog_modes = PM_SPM | PM_ISP | PM_HVPP | PM_debugWIRE; - mcuid = 40; - n_interrupts = 28; - n_page_erase = 4; - stk500_devcode = 0x86; - chip_erase_delay = 9000; - pagel = 0xb3; - bs2 = 0xb1; -# avr910_devcode = 0x??; - signature = 0x1e 0x94 0x12; - reset = io; - timeout = 200; - stabdelay = 100; - cmdexedelay = 25; - synchloops = 32; - pollindex = 3; - pollvalue = 0x53; - predelay = 1; - postdelay = 1; - pollmethod = 1; - pp_controlstack = - 0x0e, 0x1e, 0x0e, 0x1e, 0x2e, 0x3e, 0x2e, 0x3e, - 0x4e, 0x5e, 0x4e, 0x5e, 0x6e, 0x7e, 0x6e, 0x7e, - 0x26, 0x36, 0x66, 0x76, 0x2a, 0x3a, 0x6a, 0x7a, - 0x2e, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - flash_instr = 0xb6, 0x01, 0x11; - eeprom_instr = - 0xbd, 0xf2, 0xbd, 0xe1, 0xbb, 0xcf, 0xb4, 0x00, - 0xbe, 0x01, 0xb6, 0x01, 0xbc, 0x00, 0xbb, 0xbf, - 0x99, 0xf9, 0xbb, 0xaf; - hventerstabdelay = 100; - togglevtg = 1; - poweroffdelay = 15; - resetdelayms = 1; - hvleavestabdelay = 15; - resetdelay = 15; - chiperasepolltimeout = 10; - programfusepolltimeout = 5; - programlockpolltimeout = 5; - spmcr = 0x57; - eecr = 0x3c; - chip_erase = "1010.1100--100x.xxxx--xxxx.xxxx--xxxx.xxxx"; - pgm_enable = "1010.1100--0101.0011--xxxx.xxxx--xxxx.xxxx"; - - memory "eeprom" - size = 256; - page_size = 4; - min_write_delay = 3600; - max_write_delay = 3600; - readback = 0xff 0xff; - mode = 65; - delay = 5; - blocksize = 4; - readsize = 256; - read = "1010.0000--000x.xxxa--aaaa.aaaa--oooo.oooo"; - write = "1100.0000--000x.xxxa--aaaa.aaaa--iiii.iiii"; - loadpage_lo = "1100.0001--0000.0000--0000.00aa--iiii.iiii"; - writepage = "1100.0010--00xx.xxxa--aaaa.aa00--xxxx.xxxx"; - ; - - memory "flash" - paged = yes; - size = 0x4000; - page_size = 32; - num_pages = 512; - min_write_delay = 4500; - max_write_delay = 4500; - readback = 0xff 0xff; - mode = 65; - delay = 6; - blocksize = 128; - readsize = 256; - read_lo = "0010.0000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - read_hi = "0010.1000--00aa.aaaa--aaaa.aaaa--oooo.oooo"; - loadpage_lo = "0100.0000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - loadpage_hi = "0100.1000--000x.xxxx--xxxx.aaaa--iiii.iiii"; - writepage = "0100.1100--00aa.aaaa--aaaa.xxxx--xxxx.xxxx"; - ; - - memory "lfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0000--xxxx.xxxx--iiii.iiii"; - ; - - memory "hfuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.1000--xxxx.xxxx--iiii.iiii"; - ; - - memory "efuse" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.0000--0000.1000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--1010.0100--xxxx.xxxx--xxxi.iiii"; - ; - - memory "lock" - size = 1; - min_write_delay = 4500; - max_write_delay = 4500; - read = "0101.1000--0000.0000--xxxx.xxxx--oooo.oooo"; - write = "1010.1100--111x.xxxx--xxxx.xxxx--1111.11ii"; - ; - - memory "signature" - size = 3; - read = "0011.0000--000x.xxxx--xxxx.xxaa--oooo.oooo"; - ; - - memory "calibration" - size = 1; - read = "0011.1000--000x.xxxx--0000.0000--oooo.oooo"; - ; -; - -#------------------------------------------------------------ -# ATtiny1634R -#------------------------------------------------------------ - -part parent "t1634" - desc = "ATtiny1634R"; - id = "t1634r"; - mcuid = 41; -; - -#------------------------------------------------------------ -# Common values for reduced core tinys (4/5/9/10/20/40) -#------------------------------------------------------------ - -part - desc = "Common values for reduced core tinys"; - id = ".reduced_core_tiny"; - prog_modes = PM_TPI; - - memory "fuse" - size = 1; - page_size = 16; - offset = 0x3f40; - blocksize = 4; - ; - - memory "lockbits" - size = 1; - page_size = 16; - offset = 0x3f00; - ; - - memory "signature" - size = 3; - page_size = 16; - offset = 0x3fc0; - ; - - memory "calibration" - size = 1; - page_size = 16; - offset = 0x3f80; - ; -; - -#------------------------------------------------------------ -# ATtiny4 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny4"; - id = "t4"; - mcuid = 0; - n_interrupts = 10; - signature = 0x1e 0x8f 0x0a; - - memory "flash" - size = 512; - page_size = 16; - offset = 0x4000; - blocksize = 128; - ; -; - -#------------------------------------------------------------ -# ATtiny5 -#------------------------------------------------------------ - -part parent "t4" - desc = "ATtiny5"; - id = "t5"; - mcuid = 1; - n_interrupts = 11; - signature = 0x1e 0x8f 0x09; -; - -#------------------------------------------------------------ -# ATtiny9 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny9"; - id = "t9"; - mcuid = 2; - n_interrupts = 10; - signature = 0x1e 0x90 0x08; - - memory "flash" - size = 1024; - page_size = 16; - offset = 0x4000; - blocksize = 128; - ; -; - -#------------------------------------------------------------ -# ATtiny10 -#------------------------------------------------------------ - -part parent "t9" - desc = "ATtiny10"; - id = "t10"; - mcuid = 3; - n_interrupts = 11; - signature = 0x1e 0x90 0x03; -; - -#------------------------------------------------------------ -# ATtiny20 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny20"; - id = "t20"; - mcuid = 4; - n_interrupts = 17; - signature = 0x1e 0x91 0x0f; - - memory "flash" - size = 2048; - page_size = 16; - n_word_writes = 2; - offset = 0x4000; - blocksize = 128; - ; - - memory "fuse" - n_word_writes = 2; - ; -; - -#------------------------------------------------------------ -# ATtiny40 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny40"; - id = "t40"; - mcuid = 5; - n_interrupts = 18; - signature = 0x1e 0x92 0x0e; - - memory "flash" - size = 4096; - page_size = 64; - n_word_writes = 4; - offset = 0x4000; - blocksize = 128; - ; - - memory "fuse" - n_word_writes = 4; - ; -; - -#------------------------------------------------------------ -# ATtiny102 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny102"; - id = "t102"; - mcuid = 6; - n_interrupts = 16; - signature = 0x1e 0x90 0x0c; - - memory "flash" - size = 1024; - page_size = 16; - offset = 0x4000; - blocksize = 128; - ; - - memory "sigrow" - size = 16; - page_size = 16; - offset = 0x3fc6; - ; -; - -#------------------------------------------------------------ -# ATtiny104 -#------------------------------------------------------------ - -part parent ".reduced_core_tiny" - desc = "ATtiny104"; - id = "t104"; - mcuid = 7; - n_interrupts = 16; - signature = 0x1e 0x90 0x0b; - - memory "flash" - size = 1024; - page_size = 16; - offset = 0x4000; - blocksize = 128; - ; - - memory "sigrow" - size = 16; - page_size = 16; - offset = 0x3fc6; - ; -; - -#------------------------------------------------------------ -# ATmega406 -#------------------------------------------------------------ - -part - desc = "ATmega406"; - id = "m406"; - prog_modes = PM_SPM | PM_HVPP | PM_JTAG; - mcuid = 125; - n_interrupts = 23; - n_boot_sections = 4; - boot_section_size = 512; - # STK500 parameters (parallel programming IO lines) - pagel = 0xa7; - bs2 = 0xa0; - signature = 0x1e 0x95 0x07; - reset = io; - serial = no; - # STK500v2 HV programming parameters, from XML - pp_controlstack = - 0x0e, 0x1e, 0x0f, 0x1f, 0x2e, 0x3e, 0x2f, 0x3f, - 0x4e, 0x5e, 0x4f, 0x5f, 0x6e, 0x7e, 0x6f, 0x7f, - 0x66, 0x76, 0x67, 0x77, 0x6a, 0x7a, 0x6b, 0x7b, - 0xbe, 0xfd, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; - idr = 0x51; - spmcr = 0x57; - eecr = 0x3f; - - memory "eeprom" - size = 512; - page_size = 4; - num_pages = 128; - blocksize = 4; - readsize = 4; - ; - - memory "flash" - paged = yes; - size = 0xa000; - page_size = 128; - num_pages = 320; - blocksize = 128; - readsize = 128; - ; - - memory "lfuse" - size = 1; - ; - - memory "hfuse" - size = 1; - ; - - memory "lockbits" - size = 1; - ; - - memory "signature" - size = 3; - ; -; - -#------------------------------------------------------------ -# AVR8X family common values -#------------------------------------------------------------ - -part - desc = "AVR8X family common values"; - id = ".avr8x"; - prog_modes = PM_SPM | PM_UPDI; - n_boot_sections = 1; - nvm_base = 0x1000; - ocd_base = 0x0f80; - - memory "fuse0" - size = 1; - offset = 0x1280; - readsize = 1; - ; - - memory "wdtcfg" - alias "fuse0"; - ; - - memory "fuse1" - size = 1; - offset = 0x1281; - readsize = 1; - ; - - memory "bodcfg" - alias "fuse1"; - ; - - memory "fuse2" - size = 1; - offset = 0x1282; - readsize = 1; - ; - - memory "osccfg" - alias "fuse2"; - ; - - memory "fuse4" - size = 1; - offset = 0x1284; - readsize = 1; - ; - - memory "tcd0cfg" - alias "fuse4"; - ; - - memory "fuse5" - size = 1; - offset = 0x1285; - readsize = 1; - ; - - memory "syscfg0" - alias "fuse5"; - ; - - memory "fuse6" - size = 1; - offset = 0x1286; - readsize = 1; - ; - - memory "syscfg1" - alias "fuse6"; - ; - - memory "fuse7" - size = 1; - offset = 0x1287; - readsize = 1; - ; - - memory "append" - alias "fuse7"; - ; - - memory "codesize" - alias "fuse7"; - ; - - memory "fuse8" - size = 1; - offset = 0x1288; - readsize = 1; - ; - - memory "bootend" - alias "fuse8"; - ; - - memory "bootsize" - alias "fuse8"; - ; - - memory "fuses" - size = 9; - page_size = 10; - offset = 0x1280; - readsize = 10; - ; - - memory "lock" - size = 1; - offset = 0x128a; - readsize = 1; - ; - - memory "tempsense" - size = 2; - offset = 0x1120; - readsize = 1; - ; - - memory "signature" - size = 3; - offset = 0x1100; - readsize = 3; - ; - - memory "prodsig" - size = 61; - page_size = 61; - offset = 0x1103; - readsize = 61; - ; - - memory "sernum" - size = 10; - offset = 0x1104; - readsize = 1; - ; - - memory "osccal16" - size = 2; - offset = 0x1118; - readsize = 1; - ; - - memory "osccal20" - size = 2; - offset = 0x111a; - readsize = 1; - ; - - memory "osc16err" - size = 2; - offset = 0x1122; - readsize = 1; - ; - - memory "osc20err" - size = 2; - offset = 0x1124; - readsize = 1; - ; - - memory "data" - # SRAM, only used to supply the offset - offset = 0x1000000; - ; -; - -#------------------------------------------------------------ -# AVR8X tiny family common values -#------------------------------------------------------------ - -part parent ".avr8x" - desc = "AVR8X tiny family common values"; - id = ".avr8x_tiny"; - family_id = "tinyAVR"; - # Shared UPDI pin, HV on UPDI pin - hvupdi_variant = 0; - - memory "userrow" - size = 32; - page_size = 32; - offset = 0x1300; - readsize = 256; - ; - - memory "usersig" - alias "userrow"; - ; -; - -#------------------------------------------------------------ -# AVR8X mega family common values -#------------------------------------------------------------ - -part parent ".avr8x" - desc = "AVR8X mega family common values"; - id = ".avr8x_mega"; - family_id = "megaAVR"; - # Dedicated UPDI pin, no HV - hvupdi_variant = 1; - - memory "userrow" - size = 64; - page_size = 64; - offset = 0x1300; - readsize = 256; - ; - - memory "usersig" - alias "userrow"; - ; -; - -#------------------------------------------------------------ -# ATtiny202 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny202"; - id = "t202"; - mcuid = 280; - n_interrupts = 26; - signature = 0x1e 0x91 0x23; - - memory "eeprom" - size = 64; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 2048; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny204 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny204"; - id = "t204"; - mcuid = 281; - n_interrupts = 26; - signature = 0x1e 0x91 0x22; - - memory "eeprom" - size = 64; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 2048; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny402 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny402"; - id = "t402"; - mcuid = 284; - n_interrupts = 26; - signature = 0x1e 0x92 0x27; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny404 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny404"; - id = "t404"; - mcuid = 285; - n_interrupts = 26; - signature = 0x1e 0x92 0x26; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny406 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny406"; - id = "t406"; - mcuid = 286; - n_interrupts = 26; - signature = 0x1e 0x92 0x25; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny804 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny804"; - id = "t804"; - mcuid = 295; - n_interrupts = 31; - signature = 0x1e 0x93 0x25; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny806 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny806"; - id = "t806"; - mcuid = 296; - n_interrupts = 31; - signature = 0x1e 0x93 0x24; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny807 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny807"; - id = "t807"; - mcuid = 297; - n_interrupts = 31; - signature = 0x1e 0x93 0x23; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1604 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1604"; - id = "t1604"; - mcuid = 304; - n_interrupts = 31; - signature = 0x1e 0x94 0x25; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1606 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1606"; - id = "t1606"; - mcuid = 305; - n_interrupts = 31; - signature = 0x1e 0x94 0x24; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1607 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1607"; - id = "t1607"; - mcuid = 306; - n_interrupts = 31; - signature = 0x1e 0x94 0x23; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny212 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny212"; - id = "t212"; - mcuid = 282; - n_interrupts = 26; - signature = 0x1e 0x91 0x21; - - memory "eeprom" - size = 64; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 2048; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny214 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny214"; - id = "t214"; - mcuid = 283; - n_interrupts = 26; - signature = 0x1e 0x91 0x20; - - memory "eeprom" - size = 64; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 2048; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny412 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny412"; - id = "t412"; - mcuid = 287; - n_interrupts = 26; - signature = 0x1e 0x92 0x23; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny414 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny414"; - id = "t414"; - mcuid = 288; - n_interrupts = 26; - signature = 0x1e 0x92 0x22; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny416 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny416"; - id = "t416"; - mcuid = 289; - n_interrupts = 26; - signature = 0x1e 0x92 0x21; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny417 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny417"; - id = "t417"; - mcuid = 291; - n_interrupts = 26; - signature = 0x1e 0x92 0x20; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny814 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny814"; - id = "t814"; - mcuid = 298; - n_interrupts = 26; - signature = 0x1e 0x93 0x22; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny816 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny816"; - id = "t816"; - mcuid = 299; - n_interrupts = 26; - signature = 0x1e 0x93 0x21; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny817 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny817"; - id = "t817"; - mcuid = 300; - n_interrupts = 26; - signature = 0x1e 0x93 0x20; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1614 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1614"; - id = "t1614"; - mcuid = 307; - n_interrupts = 31; - signature = 0x1e 0x94 0x22; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1616 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1616"; - id = "t1616"; - mcuid = 308; - n_interrupts = 31; - signature = 0x1e 0x94 0x21; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1617 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1617"; - id = "t1617"; - mcuid = 309; - n_interrupts = 31; - signature = 0x1e 0x94 0x20; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny3216 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny3216"; - id = "t3216"; - mcuid = 314; - n_interrupts = 31; - signature = 0x1e 0x95 0x21; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x8000; - readsize = 256; - ; - - memory "userrow" - size = 64; - page_size = 64; - ; - - memory "usersig" - alias "userrow"; - ; -; - -#------------------------------------------------------------ -# ATtiny3217 -#------------------------------------------------------------ - -part parent "t3216" - desc = "ATtiny3217"; - id = "t3217"; - mcuid = 315; - signature = 0x1e 0x95 0x22; -; - -#------------------------------------------------------------ -# ATtiny424 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny424"; - id = "t424"; - mcuid = 292; - n_interrupts = 30; - signature = 0x1e 0x92 0x2c; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny426 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny426"; - id = "t426"; - mcuid = 293; - n_interrupts = 30; - signature = 0x1e 0x92 0x2b; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny427 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny427"; - id = "t427"; - mcuid = 294; - n_interrupts = 30; - signature = 0x1e 0x92 0x2a; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 4096; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny824 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny824"; - id = "t824"; - mcuid = 301; - n_interrupts = 30; - signature = 0x1e 0x93 0x29; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny826 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny826"; - id = "t826"; - mcuid = 302; - n_interrupts = 30; - signature = 0x1e 0x93 0x28; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny827 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny827"; - id = "t827"; - mcuid = 303; - n_interrupts = 30; - signature = 0x1e 0x93 0x27; - - memory "eeprom" - size = 128; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1624 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1624"; - id = "t1624"; - mcuid = 310; - n_interrupts = 30; - signature = 0x1e 0x94 0x2a; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1626 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1626"; - id = "t1626"; - mcuid = 311; - n_interrupts = 30; - signature = 0x1e 0x94 0x29; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny1627 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny1627"; - id = "t1627"; - mcuid = 312; - n_interrupts = 30; - signature = 0x1e 0x94 0x28; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny3224 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny3224"; - id = "t3224"; - mcuid = 316; - n_interrupts = 30; - signature = 0x1e 0x95 0x28; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny3226 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny3226"; - id = "t3226"; - mcuid = 317; - n_interrupts = 30; - signature = 0x1e 0x95 0x27; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATtiny3227 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATtiny3227"; - id = "t3227"; - mcuid = 318; - n_interrupts = 30; - signature = 0x1e 0x95 0x26; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x8000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega808 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATmega808"; - id = "m808"; - mcuid = 319; - n_interrupts = 36; - signature = 0x1e 0x93 0x26; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega809 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATmega809"; - id = "m809"; - mcuid = 320; - n_interrupts = 40; - signature = 0x1e 0x93 0x2a; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega1608 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATmega1608"; - id = "m1608"; - mcuid = 321; - n_interrupts = 36; - signature = 0x1e 0x94 0x27; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega1609 -#------------------------------------------------------------ - -part parent ".avr8x_tiny" - desc = "ATmega1609"; - id = "m1609"; - mcuid = 322; - n_interrupts = 40; - signature = 0x1e 0x94 0x26; - - memory "eeprom" - size = 256; - page_size = 32; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega3208 -#------------------------------------------------------------ - -part parent ".avr8x_mega" - desc = "ATmega3208"; - id = "m3208"; - mcuid = 323; - n_interrupts = 36; - signature = 0x1e 0x95 0x30; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega3209 -#------------------------------------------------------------ - -part parent ".avr8x_mega" - desc = "ATmega3209"; - id = "m3209"; - mcuid = 324; - n_interrupts = 40; - signature = 0x1e 0x95 0x31; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 128; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega4808 -#------------------------------------------------------------ - -part parent ".avr8x_mega" - desc = "ATmega4808"; - id = "m4808"; - mcuid = 325; - n_interrupts = 36; - signature = 0x1e 0x96 0x50; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0xc000; - page_size = 128; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# ATmega4809 -#------------------------------------------------------------ - -part parent ".avr8x_mega" - desc = "ATmega4809"; - id = "m4809"; - mcuid = 326; - n_interrupts = 40; - signature = 0x1e 0x96 0x51; - - memory "eeprom" - size = 256; - page_size = 64; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0xc000; - page_size = 128; - offset = 0x4000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR-Dx family common values -#------------------------------------------------------------ - -part - desc = "AVR-Dx family common values"; - id = ".avrdx"; - family_id = "AVR "; - prog_modes = PM_SPM | PM_UPDI; - n_boot_sections = 1; - # Dedicated UPDI pin, no HV - hvupdi_variant = 1; - nvm_base = 0x1000; - ocd_base = 0x0f80; - - memory "fuse0" - size = 1; - offset = 0x1050; - readsize = 1; - ; - - memory "wdtcfg" - alias "fuse0"; - ; - - memory "fuse1" - size = 1; - offset = 0x1051; - readsize = 1; - ; - - memory "bodcfg" - alias "fuse1"; - ; - - memory "fuse2" - size = 1; - offset = 0x1052; - readsize = 1; - ; - - memory "osccfg" - alias "fuse2"; - ; - - memory "fuse4" - size = 1; - offset = 0x1054; - readsize = 1; - ; - - memory "tcd0cfg" - alias "fuse4"; - ; - - memory "fuse5" - size = 1; - offset = 0x1055; - readsize = 1; - ; - - memory "syscfg0" - alias "fuse5"; - ; - - memory "fuse6" - size = 1; - offset = 0x1056; - readsize = 1; - ; - - memory "syscfg1" - alias "fuse6"; - ; - - memory "fuse7" - size = 1; - offset = 0x1057; - readsize = 1; - ; - - memory "codesize" - alias "fuse7"; - ; - - memory "append" - alias "fuse7"; - ; - - memory "fuse8" - size = 1; - offset = 0x1058; - readsize = 1; - ; - - memory "bootsize" - alias "fuse8"; - ; - - memory "bootend" - alias "fuse8"; - ; - - memory "fuses" - size = 9; - page_size = 16; - offset = 0x1050; - readsize = 16; - ; - - memory "lock" - size = 4; - offset = 0x1040; - readsize = 4; - ; - - memory "tempsense" - size = 2; - offset = 0x1104; - readsize = 1; - ; - - memory "signature" - size = 3; - offset = 0x1100; - readsize = 3; - ; - - memory "prodsig" - size = 125; - page_size = 125; - offset = 0x1103; - readsize = 125; - ; - - memory "sernum" - size = 16; - offset = 0x1110; - readsize = 1; - ; - - memory "userrow" - size = 32; - page_size = 32; - offset = 0x1080; - readsize = 32; - ; - - memory "usersig" - alias "userrow"; - ; - - memory "data" - # SRAM, only used to supply the offset - offset = 0x1000000; - ; -; - -#------------------------------------------------------------ -# AVR32DA28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DA28"; - id = "avr32da28"; - family_id = " AVR"; - mcuid = 338; - n_interrupts = 41; - signature = 0x1e 0x95 0x34; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DA32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DA32"; - id = "avr32da32"; - family_id = " AVR"; - mcuid = 342; - n_interrupts = 44; - signature = 0x1e 0x95 0x33; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DA48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DA48"; - id = "avr32da48"; - family_id = " AVR"; - mcuid = 346; - n_interrupts = 58; - signature = 0x1e 0x95 0x32; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DA28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DA28"; - id = "avr64da28"; - family_id = " AVR"; - mcuid = 351; - n_interrupts = 41; - signature = 0x1e 0x96 0x15; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DA32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DA32"; - id = "avr64da32"; - family_id = " AVR"; - mcuid = 355; - n_interrupts = 44; - signature = 0x1e 0x96 0x14; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DA48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DA48"; - id = "avr64da48"; - family_id = " AVR"; - mcuid = 359; - n_interrupts = 58; - signature = 0x1e 0x96 0x13; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DA64 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DA64"; - id = "avr64da64"; - family_id = " AVR"; - mcuid = 362; - n_interrupts = 64; - signature = 0x1e 0x96 0x12; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DA28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DA28"; - id = "avr128da28"; - family_id = " AVR"; - mcuid = 364; - n_interrupts = 41; - signature = 0x1e 0x97 0x0a; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DA32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DA32"; - id = "avr128da32"; - family_id = " AVR"; - mcuid = 366; - n_interrupts = 44; - signature = 0x1e 0x97 0x09; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DA48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DA48"; - id = "avr128da48"; - family_id = " AVR"; - mcuid = 368; - n_interrupts = 58; - signature = 0x1e 0x97 0x08; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DA64 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DA64"; - id = "avr128da64"; - family_id = " AVR"; - mcuid = 370; - n_interrupts = 64; - signature = 0x1e 0x97 0x07; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DB28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DB28"; - id = "avr32db28"; - mcuid = 339; - n_interrupts = 42; - signature = 0x1e 0x95 0x37; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DB32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DB32"; - id = "avr32db32"; - mcuid = 343; - n_interrupts = 44; - signature = 0x1e 0x95 0x36; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DB48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DB48"; - id = "avr32db48"; - mcuid = 347; - n_interrupts = 61; - signature = 0x1e 0x95 0x35; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DB28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DB28"; - id = "avr64db28"; - mcuid = 352; - n_interrupts = 42; - signature = 0x1e 0x96 0x19; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DB32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DB32"; - id = "avr64db32"; - mcuid = 356; - n_interrupts = 44; - signature = 0x1e 0x96 0x18; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DB48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DB48"; - id = "avr64db48"; - mcuid = 360; - n_interrupts = 61; - signature = 0x1e 0x96 0x17; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DB64 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DB64"; - id = "avr64db64"; - mcuid = 363; - n_interrupts = 65; - signature = 0x1e 0x96 0x16; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DB28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DB28"; - id = "avr128db28"; - mcuid = 365; - n_interrupts = 42; - signature = 0x1e 0x97 0x0e; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DB32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DB32"; - id = "avr128db32"; - mcuid = 367; - n_interrupts = 44; - signature = 0x1e 0x97 0x0d; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DB48 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DB48"; - id = "avr128db48"; - mcuid = 369; - n_interrupts = 61; - signature = 0x1e 0x97 0x0c; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR128DB64 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR128DB64"; - id = "avr128db64"; - mcuid = 371; - n_interrupts = 65; - signature = 0x1e 0x97 0x0b; - - memory "eeprom" - size = 512; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x20000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16DD14 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR16DD14"; - id = "avr16dd14"; - mcuid = 329; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x94 0x34; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16DD20 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR16DD20"; - id = "avr16dd20"; - mcuid = 330; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x94 0x33; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16DD28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR16DD28"; - id = "avr16dd28"; - mcuid = 331; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x94 0x32; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16DD32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR16DD32"; - id = "avr16dd32"; - mcuid = 333; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x94 0x31; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DD14 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DD14"; - id = "avr32dd14"; - mcuid = 336; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x95 0x3b; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DD20 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DD20"; - id = "avr32dd20"; - mcuid = 337; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x95 0x3a; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DD28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DD28"; - id = "avr32dd28"; - mcuid = 340; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x95 0x39; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32DD32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR32DD32"; - id = "avr32dd32"; - mcuid = 344; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x95 0x38; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DD14 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DD14"; - id = "avr64dd14"; - mcuid = 349; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x96 0x1d; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DD20 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DD20"; - id = "avr64dd20"; - mcuid = 350; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x96 0x1c; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DD28 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DD28"; - id = "avr64dd28"; - mcuid = 353; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x96 0x1b; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64DD32 -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR64DD32"; - id = "avr64dd32"; - mcuid = 357; - n_interrupts = 36; - hvupdi_variant = 2; - signature = 0x1e 0x96 0x1a; - - memory "eeprom" - size = 256; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 512; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR-Ex family common values -#------------------------------------------------------------ - -part parent ".avrdx" - desc = "AVR-Ex family common values"; - id = ".avrex"; - # Shared UPDI pin, HV on _RESET - hvupdi_variant = 2; - - memory "userrow" - size = 64; - page_size = 64; - readsize = 64; - ; - - memory "usersig" - alias "userrow"; - ; -; - -#------------------------------------------------------------ -# AVR8EA28 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR8EA28"; - id = "avr8ea28"; - mcuid = 327; - signature = 0x1e 0x93 0x2c; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR8EA32 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR8EA32"; - id = "avr8ea32"; - mcuid = 328; - signature = 0x1e 0x93 0x2b; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 8192; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16EA28 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR16EA28"; - id = "avr16ea28"; - mcuid = 332; - signature = 0x1e 0x94 0x37; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16EA32 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR16EA32"; - id = "avr16ea32"; - mcuid = 334; - signature = 0x1e 0x94 0x36; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR16EA48 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR16EA48"; - id = "avr16ea48"; - mcuid = 335; - signature = 0x1e 0x94 0x35; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x4000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32EA28 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR32EA28"; - id = "avr32ea28"; - mcuid = 341; - signature = 0x1e 0x95 0x3e; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32EA32 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR32EA32"; - id = "avr32ea32"; - mcuid = 345; - signature = 0x1e 0x95 0x3d; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR32EA48 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR32EA48"; - id = "avr32ea48"; - mcuid = 348; - signature = 0x1e 0x95 0x3c; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x8000; - page_size = 64; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64EA28 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR64EA28"; - id = "avr64ea28"; - mcuid = 354; - n_interrupts = 37; - signature = 0x1e 0x96 0x20; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64EA32 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR64EA32"; - id = "avr64ea32"; - mcuid = 358; - n_interrupts = 37; - signature = 0x1e 0x96 0x1f; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# AVR64EA48 -#------------------------------------------------------------ - -part parent ".avrex" - desc = "AVR64EA48"; - id = "avr64ea48"; - mcuid = 361; - n_interrupts = 45; - signature = 0x1e 0x96 0x1e; - - memory "eeprom" - size = 512; - page_size = 8; - offset = 0x1400; - readsize = 256; - ; - - memory "flash" - size = 0x10000; - page_size = 128; - offset = 0x800000; - readsize = 256; - ; -; - -#------------------------------------------------------------ -# Logic Green parts -#------------------------------------------------------------ - -part parent "m88" - desc = "LGT8F88P"; - id = "lgt8f88p"; - mcuid = 227; - signature = 0x1e 0x93 0x0f; - autobaud_sync = 0x1c; -; - -#------------------------------------------------------------ -# LGT8F168P -#------------------------------------------------------------ - -part parent "m168" - desc = "LGT8F168P"; - id = "lgt8f168p"; - mcuid = 228; - signature = 0x1e 0x94 0x0b; - autobaud_sync = 0x1c; -; - -#------------------------------------------------------------ -# LGT8F328P -#------------------------------------------------------------ - -part parent "m328" - desc = "LGT8F328P"; - id = "lgt8f328p"; - mcuid = 229; - signature = 0x1e 0x95 0x0f; - autobaud_sync = 0x1c; -; From 957689a792469665e59343b1b327dda0510fd95e Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 10 Oct 2024 21:05:52 +0200 Subject: [PATCH 333/351] Bump version + fix avrdude.conf path --- megaavr/platform.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index e635303..0cfe6bb 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.1.2 +version=1.1.3 # AVR compile variables # --------------------- @@ -115,7 +115,7 @@ recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} { tools.avrdude.path={runtime.tools.avrdude.path} tools.avrdude.cmd.path={runtime.tools.avrdude.path}/bin/avrdude -tools.avrdude.config.path={runtime.platform.path}/avrdude.conf +tools.avrdude.config.path={runtime.tools.avrdude.path}/bin/avrdude.conf tools.avrdude.network_cmd={runtime.tools.arduinoOTA.path}/bin/arduinoOTA @@ -131,7 +131,7 @@ tools.avrdude_nanoevery.upload.params.verbose=-v tools.avrdude_nanoevery.upload.params.quiet=-q -q tools.avrdude_nanoevery.upload.verify= tools.avrdude_nanoevery.upload.params.noverify=-V -tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.platform.path}/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} -Ufuses:w:{bootloader.WDTCFG},{bootloader.BODCFG},{bootloader.OSCCFG},0xff,{bootloader.TCD0CFG},{bootloader.SYSCFG0},{bootloader.SYSCFG1},{bootloader.APPEND},{bootloader.BOOTEND}:m -Ulock:w:{bootloader.LOCKBIT}:m "-Uflash:w:{build.path}/{build.project_name}.hex:i" +tools.avrdude_nanoevery.upload.pattern="{runtime.tools.avrdude.path}/bin/avrdude" "-C{runtime.tools.avrdude.path}/etc/avrdude.conf" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} {program.extra_params} -Ufuses:w:{bootloader.WDTCFG},{bootloader.BODCFG},{bootloader.OSCCFG},0xff,{bootloader.TCD0CFG},{bootloader.SYSCFG0},{bootloader.SYSCFG1},{bootloader.APPEND},{bootloader.BOOTEND}:m -Ulock:w:{bootloader.LOCKBIT}:m "-Uflash:w:{build.path}/{build.project_name}.hex:i" tools.avrdude.program.params.verbose=-v tools.avrdude.program.params.quiet=-q -q From 6c4912625c0db08203120d8643835812679180f0 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 10 Oct 2024 21:38:34 +0200 Subject: [PATCH 334/351] Fix avrdude.conf path --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index 0cfe6bb..a46a036 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -115,7 +115,7 @@ recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} { tools.avrdude.path={runtime.tools.avrdude.path} tools.avrdude.cmd.path={runtime.tools.avrdude.path}/bin/avrdude -tools.avrdude.config.path={runtime.tools.avrdude.path}/bin/avrdude.conf +tools.avrdude.config.path={runtime.tools.avrdude.path}/etc/avrdude.conf tools.avrdude.network_cmd={runtime.tools.arduinoOTA.path}/bin/arduinoOTA From 160391c68aa88c76d9d554f28ae5c52e6a1b7fc5 Mon Sep 17 00:00:00 2001 From: Joshua Scoggins Date: Sun, 17 Nov 2024 15:55:41 -0800 Subject: [PATCH 335/351] Fix IPAddress further so that the Ethernet library will work again --- megaavr/cores/coreX-corefiles/api/IPAddress.h | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/api/IPAddress.h b/megaavr/cores/coreX-corefiles/api/IPAddress.h index 59cf9d7..7c7b739 100644 --- a/megaavr/cores/coreX-corefiles/api/IPAddress.h +++ b/megaavr/cores/coreX-corefiles/api/IPAddress.h @@ -24,6 +24,10 @@ #include "Printable.h" #include "String.h" +class EthernetClass; +class DhcpClass; +class DNSClient; + namespace arduino { // A class to make it easier to handle and pass around IP addresses @@ -67,12 +71,13 @@ class IPAddress : public Printable virtual size_t printTo(Print& p) const; - friend class EthernetClass; friend class UDP; friend class Client; friend class Server; - friend class DhcpClass; - friend class DNSClient; + + friend ::EthernetClass; + friend ::DhcpClass; + friend ::DNSClient; }; extern const IPAddress INADDR_NONE; From e3e9af26fdd33f0a04b3a97d264530e689b30185 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 28 Jan 2025 09:35:16 +0100 Subject: [PATCH 336/351] Fix digitalPinHasPWM issue Closes #205 --- megaavr/variants/28pin-standard/pins_arduino.h | 6 +++--- megaavr/variants/32pin-standard/pins_arduino.h | 6 +++--- megaavr/variants/nano-4808/pins_arduino.h | 6 +++--- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index c036e77..d17cfa8 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -71,13 +71,13 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) #else // default to MILLIS_USE_TIMERB2 - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index b0ca2ff..dedf95b 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -74,13 +74,13 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) #else // default to MILLIS_USE_TIMERB2 - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index 43ae94a..a37c133 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -90,13 +90,13 @@ // PWM pins #if defined(MILLIS_USE_TIMERB0) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA3) || ((p) == PIN_PC0)) #elif defined(MILLIS_USE_TIMERB1) - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PC0)) #else // default to MILLIS_USE_TIMERB2 - #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD1) || ((p) == PIN_PD3) || \ + #define digitalPinHasPWM(p) (((p) == PIN_PD0) || ((p) == PIN_PD1) || ((p) == PIN_PD2) || ((p) == PIN_PD3) || \ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif From 2a0de3722e4c6fa9c9e433095b295e01cd6802c3 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 13 May 2025 17:07:06 +0200 Subject: [PATCH 337/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index a46a036..bb16769 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.1.3 +version=1.1.4 # AVR compile variables # --------------------- From 7881778691bd574cb02322db35fb1bb6092c6a9c Mon Sep 17 00:00:00 2001 From: Hans Date: Tue, 13 May 2025 17:15:18 +0200 Subject: [PATCH 338/351] Update README.md Remove Travis badge --- README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/README.md b/README.md index 49e532c..3814aaf 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,4 @@ # MegaCoreX -[![Build Status](https://travis-ci.com/MCUdude/MegaCoreX.svg?branch=master)](https://travis-ci.com/MCUdude/MegaCoreX) An Arduino core for ATmega4809, ATmega4808, ATmega3209, ATmega3208, ATmega1609, ATmega1608, ATmega809 and ATmega808. This megaAVR-0 chip family offers lots of features and peripherals at an incredible price point. The largest one, the ATmega4809 can be found in products like the Arduino Uno WiFi Rev2 and the Arduino Nano Every. Some of their key features include multiple serial ports, SPI and i2c interfaces, built-in programmable logic, up to 16 analog input pins, and an analog comparator with a built-in programmable voltage reference and hysteresis and much more! From 901bdf06ebf5d07e45fdf71b4b124e171d714c82 Mon Sep 17 00:00:00 2001 From: Joshua Scoggins Date: Wed, 14 May 2025 16:45:40 -0700 Subject: [PATCH 339/351] Move INADDR_NONE out of the arduino namespace to not break the Ethernet library When I grafted the newer arduino namespace in for Modbus library compatibility, I introduced a very subtle problem where constant objects defined in the arduino namespace had to be fully qualified. I suspect that the changes that arduino made to their API in the versions since 1.0.0 somehow allowed for unqualified name resolution. --- megaavr/cores/coreX-corefiles/api/IPAddress.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/IPAddress.h b/megaavr/cores/coreX-corefiles/api/IPAddress.h index 7c7b739..cb3bf27 100644 --- a/megaavr/cores/coreX-corefiles/api/IPAddress.h +++ b/megaavr/cores/coreX-corefiles/api/IPAddress.h @@ -80,6 +80,7 @@ class IPAddress : public Printable friend ::DNSClient; }; -extern const IPAddress INADDR_NONE; } using arduino::IPAddress; + +extern const IPAddress INADDR_NONE; From 450c39e4c18c518284a21566a24db33b2cf21c5c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 15 May 2025 22:50:23 +0200 Subject: [PATCH 340/351] Bump version --- megaavr/platform.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/platform.txt b/megaavr/platform.txt index bb16769..a727d82 100644 --- a/megaavr/platform.txt +++ b/megaavr/platform.txt @@ -6,7 +6,7 @@ # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5-3rd-party-Hardware-specification name=MegaCoreX -version=1.1.4 +version=1.1.5 # AVR compile variables # --------------------- From 1e8fea02fd0e39ad7e5f1600f2c4061e2d770521 Mon Sep 17 00:00:00 2001 From: Hans Date: Mon, 2 Feb 2026 21:08:20 +0100 Subject: [PATCH 341/351] Fix SPI prescaler bug Bug inherited from the official Arduino SPI library for megaAVR devices. Closes #213 --- megaavr/libraries/SPI/src/SPI.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/megaavr/libraries/SPI/src/SPI.cpp b/megaavr/libraries/SPI/src/SPI.cpp index 4355ae4..811135b 100644 --- a/megaavr/libraries/SPI/src/SPI.cpp +++ b/megaavr/libraries/SPI/src/SPI.cpp @@ -289,7 +289,7 @@ void SPIClass::setDataMode(uint8_t mode) void SPIClass::setClockDivider(uint8_t div) { SPI0.CTRLA = ((SPI0.CTRLA & - ((~SPI_PRESC_gm) | (~SPI_CLK2X_bm) )) // mask out values + (~(SPI_PRESC_gm | SPI_CLK2X_bm))) // mask out values | div); // write value } From 258ab5378a307d4bcce080dc996fd3521420cb22 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 3 Feb 2026 00:13:53 +0100 Subject: [PATCH 342/351] Initial support for new API function pwmWrite This will let the user set a PWM pin based on the actual timer number and not some pre-defined pin mapping for PWM like analogWrite has. However, for this to be predictable, it should be used alongsinge a function that utilizes PORTMUX, so the user actually knows which pin the PWM signal is routed out to --- megaavr/cores/coreX-corefiles/api/Common.h | 6 ++ megaavr/cores/coreX-corefiles/wiring_analog.c | 95 +++++++++++++++++++ .../variants/28pin-standard/pins_arduino.h | 16 ++++ .../variants/32pin-standard/pins_arduino.h | 16 ++++ .../variants/40pin-standard/pins_arduino.h | 19 ++++ .../variants/48pin-standard/pins_arduino.h | 19 ++++ megaavr/variants/nano-4808/pins_arduino.h | 17 +++- megaavr/variants/nano-every/pins_arduino.h | 19 ++++ megaavr/variants/uno-wifi/pins_arduino.h | 19 ++++ 9 files changed, 225 insertions(+), 1 deletion(-) diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 2864970..9962a4c 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -33,6 +33,12 @@ void yield(void); typedef void (*voidFuncPtr)(void); +#ifdef __cplusplus +enum pwm_timers_t : uint8_t; +#else +typedef uint8_t pwm_timers_t; +#endif + // interrupts() / noInterrupts() must be defined by the core #define lowByte(w) ((uint8_t) ((w) & 0xff)) diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 5305d72..977aef3 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -228,3 +228,98 @@ void analogWriteFrequency(uint8_t kHz) // note that this setting also influences Tone.cpp } + +void pwmWrite(pwm_timers_t pwmTimer, int val) { + // Find corresponding IO pin based on pwmTimer + uint8_t route = 0; + uint8_t pin_bp = 0; + VPORT_t *vport; + if(pwmTimer <= TCA0_5) { + route = PORTMUX.TCAROUTEA; + pin_bp = pwmTimer; + vport = &VPORTA + route; + } else if(pwmTimer == TCB_0) { + route = PORTMUX.TCBROUTEA & 0x01; + pin_bp = route? PIN4_bp: PIN2_bp; + vport = route? &VPORTF: &VPORTA; + } else if(pwmTimer == TCB_1) { + route = PORTMUX.TCBROUTEA & 0x02; + pin_bp = route? PIN5_bp: PIN3_bp; + vport = route? &VPORTF: &VPORTA; + } else if(pwmTimer == TCB_2) { + route = PORTMUX.TCBROUTEA & 0x04; + pin_bp = route? PIN4_bp: PIN0_bp; + vport = route? &VPORTB: &VPORTC; + } else if(pwmTimer == TCB_3) { + route = PORTMUX.TCBROUTEA & 0x08; + pin_bp = route? PIN1_bp: PIN5_bp; + vport = route? &VPORTC: &VPORTB; + } else { + return; + } + + // Set IO pin as output + vport->DIR |= (1<= 255) { + // Turn off PWM + uint8_t bitpos = pin_bp; + switch (pwmTimer) { + case TCA0_0...TCA0_5: + if (bitpos >= 3) ++bitpos; // Upper 3 bits are shifted by 1 + TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bitpos)); + break; + + case TCB_0: + case TCB_1: + case TCB_2: + case TCB_3: + timer_B = &TCB0 + (pwmTimer-TCB_0); + timer_B->CTRLB &= ~(TCB_CCMPEN_bm); + break; + + default: + break; + } + // Set pin high or low + if(val <= 0) + vport->OUT &= ~(1<OUT |= (1<= 3) { + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.HCMP0)) + 2*(pin_bp-3); + ++pin_bp; + } else { + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.LCMP0)) + 2*pin_bp; + } + cli(); + *timer_cmp_out = val; + SREG = savedSREG; + TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + pin_bp)); + break; + + case TCB_0: + case TCB_1: + case TCB_2: + case TCB_3: + timer_B = &TCB0 + (pwmTimer-TCB_0); + savedSREG = SREG; + cli(); + timer_B->CCMPL = timer_B->CCMPL; + timer_B->CCMPH = val; + SREG = savedSREG; + timer_B->CTRLB |= (TCB_CCMPEN_bm); + break; + } + } +} diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index d17cfa8..0e9a1ec 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -81,6 +81,22 @@ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, +} pwm_timers_t; + // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] #define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index dedf95b..f0f3528 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -84,6 +84,22 @@ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, +} pwm_timers_t; + // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] #define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index 65b8e03..b58b910 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -96,6 +96,25 @@ ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #endif +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_1 = 1, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_4 = 4, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, + TCB_3 = 9, +} pwm_timers_t; + // Timer pin swaps #define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] #define TCB0_PINS PORTMUX_TCB0_bm // TCB0 output on PF4 instead of PA2 diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index c826f11..c00b0e8 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -107,6 +107,25 @@ ((p) == PIN_PC4) || ((p) == PIN_PC5) || ((p) == PIN_PF4) || ((p) == PIN_PF5)) #endif +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_1 = 1, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_4 = 4, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, + TCB_3 = 9, +} pwm_timers_t; + // Timer pin swaps #define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] #define TCB0_PINS PORTMUX_TCB0_bm // TCB0 output on PF4 instead of PA2 diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index a37c133..3471f7b 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -82,7 +82,6 @@ ((p) >= 22 && (p) <= 25) ? ((p) - 18) : \ ((p) >= 18 && (p) <= 21) ? ((p) - 6) : NOT_A_PIN) - // Timer to use for millis/micros #if !defined(MILLIS_USE_TIMERB0) || !defined(MILLIS_USE_TIMERB1) || !defined(MILLIS_USE_TIMERB2) #define MILLIS_USE_TIMERB2 // Use TCB2 if nothing else if defined @@ -100,6 +99,22 @@ ((p) == PIN_PD4) || ((p) == PIN_PD5) || ((p) == PIN_PA2) || ((p) == PIN_PA3)) #endif +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, +} pwm_timers_t; + // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] #define TCB0_PINS 0x00 // TCB0 output on PA2 instead of PF4 diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index d44b278..af2b0fb 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -97,6 +97,25 @@ // PWM pins #define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_1 = 1, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_4 = 4, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, + TCB_3 = 9, +} pwm_timers_t; + // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTB_gc #define TCB0_PINS PORTMUX_TCB0_bm diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index e32ffbc..c92b1a0 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -98,6 +98,25 @@ // PWM pins #define digitalPinHasPWM(p) ((p) == 3 || (p) == 5 || (p) == 6 || (p) == 9 || (p) == 10 || (p) == 27) +// Timer enums +#ifdef __cplusplus +enum pwm_timers_t : uint8_t +#else +enum pwm_timers_t +#endif +{ + TCA0_0 = 0, + TCA0_1 = 1, + TCA0_2 = 2, + TCA0_3 = 3, + TCA0_4 = 4, + TCA0_5 = 5, + TCB_0 = 6, + TCB_1 = 7, + TCB_2 = 8, + TCB_3 = 9, +} pwm_timers_t; + // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTB_gc #define TCB0_PINS PORTMUX_TCB0_bm From c04ae9556faf49909653b8370ae7e9bb547e4d09 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 3 Feb 2026 09:53:09 +0100 Subject: [PATCH 343/351] Move pwmWrite to a dedicated cpp file outside the API folder and add support for pinrouting using the built-in PORTMUX --- megaavr/cores/coreX-corefiles/Arduino.h | 4 + megaavr/cores/coreX-corefiles/api/Common.h | 6 - megaavr/cores/coreX-corefiles/pwm_write.cpp | 113 ++++++++++++++++++ megaavr/cores/coreX-corefiles/wiring_analog.c | 95 --------------- .../variants/48pin-standard/pins_arduino.h | 27 ++++- 5 files changed, 138 insertions(+), 107 deletions(-) create mode 100644 megaavr/cores/coreX-corefiles/pwm_write.cpp diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 4baa483..66fb819 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -26,6 +26,7 @@ #include #include + #ifdef __cplusplus extern "C"{ #endif @@ -135,6 +136,9 @@ void setup_timers(); #error "Targets with both UART0 and CDC serial not supported" #endif + +void pwmWrite(pwm_timers_t pwmTimer, uint16_t value, timers_route_t timerRoute = ROUTE_UNTOUCHED); + // These are used as the second to N argument to pinConfigure(pin, ...) // Directives are handled in the order they show up on this list, by pin function: // PIN_DIR Direction diff --git a/megaavr/cores/coreX-corefiles/api/Common.h b/megaavr/cores/coreX-corefiles/api/Common.h index 9962a4c..2864970 100644 --- a/megaavr/cores/coreX-corefiles/api/Common.h +++ b/megaavr/cores/coreX-corefiles/api/Common.h @@ -33,12 +33,6 @@ void yield(void); typedef void (*voidFuncPtr)(void); -#ifdef __cplusplus -enum pwm_timers_t : uint8_t; -#else -typedef uint8_t pwm_timers_t; -#endif - // interrupts() / noInterrupts() must be defined by the core #define lowByte(w) ((uint8_t) ((w) & 0xff)) diff --git a/megaavr/cores/coreX-corefiles/pwm_write.cpp b/megaavr/cores/coreX-corefiles/pwm_write.cpp new file mode 100644 index 0000000..0584a2d --- /dev/null +++ b/megaavr/cores/coreX-corefiles/pwm_write.cpp @@ -0,0 +1,113 @@ +#include "Arduino.h" +#include "pins_arduino.h" +#include "wiring_private.h" + +void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { + // Set PORTMUX to route PWM to the correct pin + if (timerRoute != ROUTE_UNTOUCHED) { + if(timerRoute & 0x40) + PORTMUX.TCAROUTEA = timerRoute & 0x07; + else { + uint8_t tcb_index = (timerRoute >> 4) & 0x03; + uint8_t route_bit = timerRoute & 0x01; + uint8_t mask = (1 << tcb_index); + if(route_bit) + PORTMUX.TCBROUTEA |= mask; + else + PORTMUX.TCBROUTEA &= ~mask; + } + } + + // Find corresponding IO pin based on pwmTimer + uint8_t route = 0; + uint8_t pin_bp = 0; + VPORT_t *vport; + if(pwmTimer <= TCA0_5) { + route = PORTMUX.TCAROUTEA; + pin_bp = pwmTimer; + vport = &VPORTA + route; + } else if(pwmTimer == TCB_0) { + route = PORTMUX.TCBROUTEA & 0x01; + pin_bp = route? PIN4_bp: PIN2_bp; + vport = route? &VPORTF: &VPORTA; + } else if(pwmTimer == TCB_1) { + route = PORTMUX.TCBROUTEA & 0x02; + pin_bp = route? PIN5_bp: PIN3_bp; + vport = route? &VPORTF: &VPORTA; + } else if(pwmTimer == TCB_2) { + route = PORTMUX.TCBROUTEA & 0x04; + pin_bp = route? PIN4_bp: PIN0_bp; + vport = route? &VPORTB: &VPORTC; + } else if(pwmTimer == TCB_3) { + route = PORTMUX.TCBROUTEA & 0x08; + pin_bp = route? PIN1_bp: PIN5_bp; + vport = route? &VPORTC: &VPORTB; + } else { + return; + } + + // Set IO pin as output + vport->DIR |= (1<= 255) { + // Turn off PWM + uint8_t bitpos = pin_bp; + switch (pwmTimer) { + case TCA0_0...TCA0_5: + if (bitpos >= 3) ++bitpos; // Upper 3 bits are shifted by 1 + TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bitpos)); + break; + + case TCB_0: + case TCB_1: + case TCB_2: + case TCB_3: + timer_B = &TCB0 + (pwmTimer-TCB_0); + timer_B->CTRLB &= ~(TCB_CCMPEN_bm); + break; + + default: + break; + } + // Set pin high or low + if(val <= 0) + vport->OUT &= ~(1<OUT |= (1<= 3) { + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.HCMP0)) + 2*(pin_bp-3); + ++pin_bp; + } else { + timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.LCMP0)) + 2*pin_bp; + } + cli(); + *timer_cmp_out = val; + SREG = savedSREG; + TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + pin_bp)); + break; + + case TCB_0: + case TCB_1: + case TCB_2: + case TCB_3: + timer_B = &TCB0 + (pwmTimer-TCB_0); + savedSREG = SREG; + cli(); + timer_B->CCMPL = timer_B->CCMPL; + timer_B->CCMPH = val; + SREG = savedSREG; + timer_B->CTRLB |= (TCB_CCMPEN_bm); + break; + } + } +} diff --git a/megaavr/cores/coreX-corefiles/wiring_analog.c b/megaavr/cores/coreX-corefiles/wiring_analog.c index 977aef3..5305d72 100644 --- a/megaavr/cores/coreX-corefiles/wiring_analog.c +++ b/megaavr/cores/coreX-corefiles/wiring_analog.c @@ -228,98 +228,3 @@ void analogWriteFrequency(uint8_t kHz) // note that this setting also influences Tone.cpp } - -void pwmWrite(pwm_timers_t pwmTimer, int val) { - // Find corresponding IO pin based on pwmTimer - uint8_t route = 0; - uint8_t pin_bp = 0; - VPORT_t *vport; - if(pwmTimer <= TCA0_5) { - route = PORTMUX.TCAROUTEA; - pin_bp = pwmTimer; - vport = &VPORTA + route; - } else if(pwmTimer == TCB_0) { - route = PORTMUX.TCBROUTEA & 0x01; - pin_bp = route? PIN4_bp: PIN2_bp; - vport = route? &VPORTF: &VPORTA; - } else if(pwmTimer == TCB_1) { - route = PORTMUX.TCBROUTEA & 0x02; - pin_bp = route? PIN5_bp: PIN3_bp; - vport = route? &VPORTF: &VPORTA; - } else if(pwmTimer == TCB_2) { - route = PORTMUX.TCBROUTEA & 0x04; - pin_bp = route? PIN4_bp: PIN0_bp; - vport = route? &VPORTB: &VPORTC; - } else if(pwmTimer == TCB_3) { - route = PORTMUX.TCBROUTEA & 0x08; - pin_bp = route? PIN1_bp: PIN5_bp; - vport = route? &VPORTC: &VPORTB; - } else { - return; - } - - // Set IO pin as output - vport->DIR |= (1<= 255) { - // Turn off PWM - uint8_t bitpos = pin_bp; - switch (pwmTimer) { - case TCA0_0...TCA0_5: - if (bitpos >= 3) ++bitpos; // Upper 3 bits are shifted by 1 - TCA0.SPLIT.CTRLB &= ~(1 << (TCA_SPLIT_LCMP0EN_bp + bitpos)); - break; - - case TCB_0: - case TCB_1: - case TCB_2: - case TCB_3: - timer_B = &TCB0 + (pwmTimer-TCB_0); - timer_B->CTRLB &= ~(TCB_CCMPEN_bm); - break; - - default: - break; - } - // Set pin high or low - if(val <= 0) - vport->OUT &= ~(1<OUT |= (1<= 3) { - timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.HCMP0)) + 2*(pin_bp-3); - ++pin_bp; - } else { - timer_cmp_out = ((uint8_t *)(&TCA0.SPLIT.LCMP0)) + 2*pin_bp; - } - cli(); - *timer_cmp_out = val; - SREG = savedSREG; - TCA0.SPLIT.CTRLB |= (1 << (TCA_SPLIT_LCMP0EN_bp + pin_bp)); - break; - - case TCB_0: - case TCB_1: - case TCB_2: - case TCB_3: - timer_B = &TCB0 + (pwmTimer-TCB_0); - savedSREG = SREG; - cli(); - timer_B->CCMPL = timer_B->CCMPL; - timer_B->CCMPH = val; - SREG = savedSREG; - timer_B->CTRLB |= (TCB_CCMPEN_bm); - break; - } - } -} diff --git a/megaavr/variants/48pin-standard/pins_arduino.h b/megaavr/variants/48pin-standard/pins_arduino.h index c00b0e8..4c1e864 100644 --- a/megaavr/variants/48pin-standard/pins_arduino.h +++ b/megaavr/variants/48pin-standard/pins_arduino.h @@ -109,11 +109,7 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, TCA0_1 = 1, TCA0_2 = 2, @@ -124,7 +120,26 @@ enum pwm_timers_t TCB_1 = 7, TCB_2 = 8, TCB_3 = 9, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTB = 0x41, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTE = 0x44, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_TCB2_PB4 = 0x21, + ROUTE_TCB3_PB5 = 0x30, + ROUTE_TCB3_PC1 = 0x31, + ROUTE_UNTOUCHED = 0x80, +}; +#endif // Timer pin swaps #define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] From 9b25ede34f23b0acd1da60a11456222dd417e588 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Tue, 3 Feb 2026 22:03:52 +0100 Subject: [PATCH 344/351] Add pwmPrescaler to set the prescaler for a PWM output --- megaavr/cores/coreX-corefiles/Arduino.h | 14 ++++++++++ megaavr/cores/coreX-corefiles/pwm_write.cpp | 13 +++++++++ .../variants/28pin-standard/pins_arduino.h | 25 ++++++++++++----- .../variants/32pin-standard/pins_arduino.h | 24 ++++++++++++----- .../variants/40pin-standard/pins_arduino.h | 25 ++++++++++++----- megaavr/variants/nano-4808/pins_arduino.h | 24 ++++++++++++----- megaavr/variants/nano-every/pins_arduino.h | 27 ++++++++++++++----- megaavr/variants/uno-wifi/pins_arduino.h | 9 +++---- 8 files changed, 125 insertions(+), 36 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 66fb819..26e16db 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -136,8 +136,22 @@ void setup_timers(); #error "Targets with both UART0 and CDC serial not supported" #endif +enum timers_prescaler_t : uint8_t { + TCA_DIV1 = 0x00, + TCA_DIV2 = 0x02, + TCA_DIV4 = 0x04, + TCA_DIV8 = 0x06, + TCA_DIV16 = 0x08, + TCA_DIV64 = 0x0A, + TCA_DIV256 = 0x0C, + TCA_DIV1024 = 0x0E, + TCB_DIV1 = 0x00, + TCB_DIV2 = 0x20, + TCB_CLKTCA = 0x40, +}; void pwmWrite(pwm_timers_t pwmTimer, uint16_t value, timers_route_t timerRoute = ROUTE_UNTOUCHED); +void pwmPrescaler(pwm_timers_t pwmTimer, timers_prescaler_t prescaler); // These are used as the second to N argument to pinConfigure(pin, ...) // Directives are handled in the order they show up on this list, by pin function: diff --git a/megaavr/cores/coreX-corefiles/pwm_write.cpp b/megaavr/cores/coreX-corefiles/pwm_write.cpp index 0584a2d..08b486f 100644 --- a/megaavr/cores/coreX-corefiles/pwm_write.cpp +++ b/megaavr/cores/coreX-corefiles/pwm_write.cpp @@ -2,6 +2,9 @@ #include "pins_arduino.h" #include "wiring_private.h" + + + void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { // Set PORTMUX to route PWM to the correct pin if (timerRoute != ROUTE_UNTOUCHED) { @@ -111,3 +114,13 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { } } } + +void pwmPrescaler(pwm_timers_t pwmTimer, timers_prescaler_t prescaler) { + if(pwmTimer <= TCA0_5) + TCA0.SPLIT.CTRLA = prescaler | TCA_SPLIT_ENABLE_bm; + else { + TCB_t *timer_B = &TCB0 + (pwmTimer-TCB_0); + uint8_t p = (prescaler >> 4) & TCB_CLKSEL_gm; + timer_B->CTRLA = ((timer_B->CTRLA & ~TCB_CLKSEL_gm) | p); + } +} diff --git a/megaavr/variants/28pin-standard/pins_arduino.h b/megaavr/variants/28pin-standard/pins_arduino.h index 0e9a1ec..7e53a4c 100644 --- a/megaavr/variants/28pin-standard/pins_arduino.h +++ b/megaavr/variants/28pin-standard/pins_arduino.h @@ -83,19 +83,32 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, + TCA0_1 = 1, TCA0_2 = 2, TCA0_3 = 3, + TCA0_4 = 4, TCA0_5 = 5, TCB_0 = 6, TCB_1 = 7, TCB_2 = 8, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_UNTOUCHED = 0x80, +}; + +#endif // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] diff --git a/megaavr/variants/32pin-standard/pins_arduino.h b/megaavr/variants/32pin-standard/pins_arduino.h index f0f3528..8291fe6 100644 --- a/megaavr/variants/32pin-standard/pins_arduino.h +++ b/megaavr/variants/32pin-standard/pins_arduino.h @@ -86,19 +86,31 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, + TCA0_1 = 1, TCA0_2 = 2, TCA0_3 = 3, + TCA0_4 = 4, TCA0_5 = 5, TCB_0 = 6, TCB_1 = 7, TCB_2 = 8, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_UNTOUCHED = 0x80, +}; +#endif // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] diff --git a/megaavr/variants/40pin-standard/pins_arduino.h b/megaavr/variants/40pin-standard/pins_arduino.h index b58b910..f3a2058 100644 --- a/megaavr/variants/40pin-standard/pins_arduino.h +++ b/megaavr/variants/40pin-standard/pins_arduino.h @@ -98,11 +98,7 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, TCA0_1 = 1, TCA0_2 = 2, @@ -113,7 +109,24 @@ enum pwm_timers_t TCB_1 = 7, TCB_2 = 8, TCB_3 = 9, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTE = 0x44, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_TCB3_PC1 = 0x31, + ROUTE_UNTOUCHED = 0x80, +}; + +#endif // Timer pin swaps #define TCA0_PINS PORTMUX_TCA0_PORTC_gc // TCA0 output on PC[0:5] diff --git a/megaavr/variants/nano-4808/pins_arduino.h b/megaavr/variants/nano-4808/pins_arduino.h index 3471f7b..5c6ce86 100644 --- a/megaavr/variants/nano-4808/pins_arduino.h +++ b/megaavr/variants/nano-4808/pins_arduino.h @@ -101,19 +101,31 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, + TCA0_1 = 1, TCA0_2 = 2, TCA0_3 = 3, + TCA0_4 = 4, TCA0_5 = 5, TCB_0 = 6, TCB_1 = 7, TCB_2 = 8, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_UNTOUCHED = 0x80, +}; +#endif // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTD_gc // TCA0 output on PD[0:5] diff --git a/megaavr/variants/nano-every/pins_arduino.h b/megaavr/variants/nano-every/pins_arduino.h index af2b0fb..15fab7a 100644 --- a/megaavr/variants/nano-every/pins_arduino.h +++ b/megaavr/variants/nano-every/pins_arduino.h @@ -99,11 +99,7 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, TCA0_1 = 1, TCA0_2 = 2, @@ -114,7 +110,26 @@ enum pwm_timers_t TCB_1 = 7, TCB_2 = 8, TCB_3 = 9, -} pwm_timers_t; +}; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTB = 0x41, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTE = 0x44, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_TCB2_PB4 = 0x21, + ROUTE_TCB3_PB5 = 0x30, + ROUTE_TCB3_PC1 = 0x31, + ROUTE_UNTOUCHED = 0x80, +}; +#endif // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTB_gc diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index c92b1a0..5d30633 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -100,11 +100,7 @@ // Timer enums #ifdef __cplusplus -enum pwm_timers_t : uint8_t -#else -enum pwm_timers_t -#endif -{ +enum pwm_timers_t : uint8_t { TCA0_0 = 0, TCA0_1 = 1, TCA0_2 = 2, @@ -115,7 +111,8 @@ enum pwm_timers_t TCB_1 = 7, TCB_2 = 8, TCB_3 = 9, -} pwm_timers_t; +}; +#endif // Timer pin mapping #define TCA0_PINS PORTMUX_TCA0_PORTB_gc From 3d56226d3b03cc16f57bcda97016f5f125eda3e6 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 5 Feb 2026 21:13:01 +0100 Subject: [PATCH 345/351] Add pwmSetResolution --- megaavr/cores/coreX-corefiles/Arduino.h | 1 + megaavr/cores/coreX-corefiles/pwm_write.cpp | 34 ++++++++++++++++++--- 2 files changed, 30 insertions(+), 5 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/Arduino.h b/megaavr/cores/coreX-corefiles/Arduino.h index 26e16db..8bdf1b3 100644 --- a/megaavr/cores/coreX-corefiles/Arduino.h +++ b/megaavr/cores/coreX-corefiles/Arduino.h @@ -152,6 +152,7 @@ enum timers_prescaler_t : uint8_t { void pwmWrite(pwm_timers_t pwmTimer, uint16_t value, timers_route_t timerRoute = ROUTE_UNTOUCHED); void pwmPrescaler(pwm_timers_t pwmTimer, timers_prescaler_t prescaler); +void pwmSetResolution(pwm_timers_t pwmTimer, uint8_t maxValue); // These are used as the second to N argument to pinConfigure(pin, ...) // Directives are handled in the order they show up on this list, by pin function: diff --git a/megaavr/cores/coreX-corefiles/pwm_write.cpp b/megaavr/cores/coreX-corefiles/pwm_write.cpp index 08b486f..8a0e615 100644 --- a/megaavr/cores/coreX-corefiles/pwm_write.cpp +++ b/megaavr/cores/coreX-corefiles/pwm_write.cpp @@ -2,9 +2,6 @@ #include "pins_arduino.h" #include "wiring_private.h" - - - void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { // Set PORTMUX to route PWM to the correct pin if (timerRoute != ROUTE_UNTOUCHED) { @@ -24,27 +21,33 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { // Find corresponding IO pin based on pwmTimer uint8_t route = 0; uint8_t pin_bp = 0; + uint8_t d_max = 0; VPORT_t *vport; if(pwmTimer <= TCA0_5) { route = PORTMUX.TCAROUTEA; pin_bp = pwmTimer; - vport = &VPORTA + route; + vport = &VPORTA + route; + d_max = TCA0.SPLIT.LPER; } else if(pwmTimer == TCB_0) { route = PORTMUX.TCBROUTEA & 0x01; pin_bp = route? PIN4_bp: PIN2_bp; vport = route? &VPORTF: &VPORTA; + d_max = TCB0.CCMPL; } else if(pwmTimer == TCB_1) { route = PORTMUX.TCBROUTEA & 0x02; pin_bp = route? PIN5_bp: PIN3_bp; vport = route? &VPORTF: &VPORTA; + d_max = TCB1.CCMPL; } else if(pwmTimer == TCB_2) { route = PORTMUX.TCBROUTEA & 0x04; pin_bp = route? PIN4_bp: PIN0_bp; vport = route? &VPORTB: &VPORTC; + d_max = TCB2.CCMPL; } else if(pwmTimer == TCB_3) { route = PORTMUX.TCBROUTEA & 0x08; pin_bp = route? PIN1_bp: PIN5_bp; vport = route? &VPORTC: &VPORTB; + d_max = TCB3.CCMPL; } else { return; } @@ -53,7 +56,7 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { vport->DIR |= (1<= 255) { + if(val <= 0 || val > d_max) { // Turn off PWM uint8_t bitpos = pin_bp; switch (pwmTimer) { @@ -124,3 +127,24 @@ void pwmPrescaler(pwm_timers_t pwmTimer, timers_prescaler_t prescaler) { timer_B->CTRLA = ((timer_B->CTRLA & ~TCB_CLKSEL_gm) | p); } } + +void pwmSetResolution(pwm_timers_t pwmTimer, uint8_t maxValue) { + // The max value will disable PWM and set pin high + uint8_t top = maxValue? maxValue-1: 1; + + if(pwmTimer <= TCA0_5) { + TCA0.SPLIT.LPER = + TCA0.SPLIT.HPER = top; + TCA0.SPLIT.LCMP0 = + TCA0.SPLIT.LCMP1 = + TCA0.SPLIT.LCMP2 = + TCA0.SPLIT.HCMP0 = + TCA0.SPLIT.HCMP1 = + TCA0.SPLIT.HCMP2 = top >> 1; + } else { + TCB_t *timer_B = &TCB0 + (pwmTimer-TCB_0); + timer_B->CCMPL = top; + timer_B->CCMPH = top >> 1; + } + +} \ No newline at end of file From a2af4494de669cf4e0123e3bdf2b3f8117cf2731 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Fri, 6 Feb 2026 22:50:33 +0100 Subject: [PATCH 346/351] Update extended API documentation --- Extended-API.md | 111 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 111 insertions(+) diff --git a/Extended-API.md b/Extended-API.md index 6e509ac..c512672 100644 --- a/Extended-API.md +++ b/Extended-API.md @@ -11,6 +11,9 @@ My goal isn't to "Arduino wrap" all hardware functionality the megaAVR-0 series * [Peripheral pin swapping](#peripheral-pin-swapping) * [pinConfigure](#pinConfigure---extended-pin-configuration) * [Printf support](#printf-support) +* [pwmWrite](#pwmwrite---flexible-pwm-routing) +* [pwmPrescaler](#pwmprescaler---pwm-frequency-setting) +* [pwmSetResolution](#pwmsetresolution) ## Analog read resolution @@ -140,3 +143,111 @@ Unlike the official Arduino core, MegaCoreX has printf support out of the box. I Note that the default printf implementation will NOT print floats or doubles by default. This is a limitation of the avr-libc printf implementation on AVR microcontrollers, but can be enabled by setting a build flag. This can easily be done if you're using [PlatformIO](https://github.com/MCUdude/MegaCoreX/blob/master/PlatformIO.md). If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other common libraries that inherit the Print class (and thus supports printf) are SoftwareSerial, the LiquidCrystal LCD library and the u8g2 graphical LCD library. + + +# pwmWrite - flexible PWM routing +The Arduino pinout definition and the `analogWrite` function have the PWM output pins pre-defined, and can't be moved or routed to different pins using the default Arduino API, even though the chip itself supports this. The `pwmWrite` function lets to use every supported PWM output pin, and you can route the PWM signals as you like. Note that the chip limits which timer output can be routed to which pins, and you also need to make sure you don't route the PWM signal to a pins that's used for something else, like UART or SPI. Also keep in mind that the timer used for millis/micros is occupied and can not be used for PWM generation. For the Nano Every 4809 and Uno Wifi Rev2 this means timer TCB2, and for all the other pinouts TCB2. Also note that low-pinout parts does not have timer TCB3 and all the routing pin options due to the lack of physical IO. + +### Declaration +```c++ +void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute); +``` + +### Example +```c++ +// Route timer TCB0 PWM output to pin PF4 and set the duty cycle to 50% (128/255) +pwmWrite(TCB_0, 128, ROUTE_TCB0_PF4); +// Set the timer TCB0 duty cycle to 30% but leave the routing as is +pwmWrite(TCB_0, 76); +// Route all TCA0 timer to PORTA, enable the 2nd TCA0 PWM output (PA2 in this case), and set dyty cycle to 50% +pwmWrite(TCA0_2, 128, ROUTE_TCA0_PORTA); +``` + +### Table of valid options + +| Timer enums | Description | +|-------------|----------------------------------| +| `TCA0_0` | Identifier for TCA0 PWM output 0 | +| `TCA0_1` | Identifier for TCA0 PWM output 1 | +| `TCA0_2` | Identifier for TCA0 PWM output 2 | +| `TCA0_3` | Identifier for TCA0 PWM output 3 | +| `TCA0_4` | Identifier for TCA0 PWM output 4 | +| `TCA0_5` | Identifier for TCA0 PWM output 5 | +| `TCB_0` | Identifier for TCB0 PWM output | +| `TCB_1` | Identifier for TCB1 PWM output | +| `TCB_2` | Identifier for TCB2 PWM output | +| `TCB_3` | Identifier for TCB3 PWM output | + +| PWM routing enums | Description | +|--------------------|---------------------------------------------------------------------------------| +| `ROUTE_TCA0_PORTA` | Route all six TCA0 PWM channels to PA0..PA5 | +| `ROUTE_TCA0_PORTB` | Route all six TCA0 PWM channels to PB0..PB5 (not present on low pincount parts) | +| `ROUTE_TCA0_PORTC` | Route all six TCA0 PWM channels to PC0..PC5 | +| `ROUTE_TCA0_PORTD` | Route all six TCA0 PWM channels to PD0..PD5 | +| `ROUTE_TCA0_PORTE` | Route all six TCA0 PWM channels to PE0..PE5 (not present on low pincount parts) | +| `ROUTE_TCA0_PORTF` | Route all six TCA0 PWM channels to PF0..PF5 | +| `ROUTE_TCB0_PA2` | Route the TCB0 PWM output to pin PA2 | +| `ROUTE_TCB0_PF4` | Route the TCB0 PWM output to pin PF4 | +| `ROUTE_TCB1_PA3` | Route the TCB1 PWM output to pin PA3 | +| `ROUTE_TCB1_PF5` | Route the TCB1 PWM output to pin PF5 | +| `ROUTE_TCB2_PC0` | Route the TCB2 PWM output to pin PC0 | +| `ROUTE_TCB2_PB4` | Route the TCB2 PWM output to pin PB4 (not present on low pincount parts) | +| `ROUTE_TCB3_PB5` | Route the TCB3 PWM output to pin PB5 (not present on low pincount parts) | +| `ROUTE_TCB3_PC1` | Route the TCB3 PWM output to pin PC1 (not present on low pincount parts) | + + +# pwmPrescaler - PWM frequency setting +`pwmPrescaler` sets the clock source that drives timer. Timer TCA0 has the most options, while the TCB timers have fewer. +The prescaler direcly affects the PWM frequency, and this is the formula that determines the frequency: +`F_CPU / resolution / prescaler`. For instance, the default TCB PWM prescaler with a system clock of 16 MHz is 1/64, which results in a PWM frequency of just under 1 kHz. + +### Declaration +```c++ +void pwmPrescaler(pwm_timers_t pwmTimer, timers_prescaler_t prescaler); +``` + +### Example +```c++ +// Set the TCA0 timer prescaler to 1/64 of the system clock frequency +pwmPrescaler(TCA0_0, TCA_DIV64); +// Set timer TCB0 to run off the TCA0 clock +pwmPrescaler(TCB_0, TCB_CLKTCA); +// Set timer TCB1 prescaler to 1/2 of the system clock frequency +pwmPrescaler(TCB_1, TCB_DIV2); +``` + +### Table of valid options + +| Prescaler | Timer | Description | Notes | +|---------------|---------|----------------------------------------------------|-------------------------------------------------| +| `TCB_DIV1` | TCB0..3 | Runs TCB at full system clock speed | | +| `TCB_DIV2` | TCB0..3 | Runs TCB at 1/2 of the system clock | | +| `TCB_CLKTCA` | TCB0..3 | Runs TCB at the same clock as TCA0 is running off | Default option for all TCB timers | +| `TCA_DIV1` | TCA0 | Runs TCA0 full system clock speed | | +| `TCA_DIV2` | TCA0 | Runs TCA0 at 1/2 of the system clock | | +| `TCA_DIV4` | TCA0 | Runs TCA0 at 1/4 of the system clock | | +| `TCA_DIV8` | TCA0 | Runs TCA0 at 1/8 of the system clock | | +| `TCA_DIV16` | TCA0 | Runs TCA0 at 1/16 of the system clock | | +| `TCA_DIV64` | TCA0 | Runs TCA0 at 1/64 of the system clock | Default option when using a 16 MHz system clock | +| `TCA_DIV256` | TCA0 | Runs TCA0 at 1/256 of the system clock | | +| `TCA_DIV1024` | TCA0 | Runs TCA0 at 1/1024 the system clock | | + + +# pwmSetResolution +This function lets you change the PWM resolution in favour of increased PWM frequency. The default PWM range is 0-255, but the upper limit can be set to anything between 1 and 254. The resolution also affects the PWM frequency. The frequency can be calculated using this formula: +`F_CPU / resolution / prescaler` + +### Declaration +```c++ +void pwmSetResolution(pwm_timers_t pwmTimer, uint8_t maxValue); +``` + +### Example +```c++ +// Set TCA0 timer max value to 127 +pwmSetResolution(TCA0_0, 127); +// Set TCB0 timer max value to 31 +pwmSetResolution(TCB_0, 31); +// Set TCB1 timer max value to 99 +pwmSetResolution(TCB_1, 99); +``` \ No newline at end of file From 958a4c68fcf21f5dfa9b94ca7f0f02cabe6deb79 Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 22 Feb 2026 22:52:53 +0100 Subject: [PATCH 347/351] Fix typos --- Extended-API.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Extended-API.md b/Extended-API.md index c512672..b5ea4a7 100644 --- a/Extended-API.md +++ b/Extended-API.md @@ -2,7 +2,7 @@ MegaCoreX is Arduino compatible out of the box, but also includes extra functionality that's not available on the official Arduino "megaavr" core. This is functionality that I personally have been missing in the official Arduino API, and have added to MegaCoreX instead. -My goal isn't to "Arduino wrap" all hardware functionality the megaAVR-0 series brings to the table, but to expose functionality advanced users may benefit from and actually use. If you have a very niche application that utilizes one of the more obscure features the chip has, you're probably better off writing the low-level code yourself. Very spesific needs for ADC readings? Obscure timer needs? Read the approperiate Microchip application note w! +My goal isn't to "Arduino wrap" all hardware functionality the megaAVR-0 series brings to the table, but to expose functionality advanced users may benefit from and actually use. If you have a very niche application that utilizes one of the more obscure features the chip has, you're probably better off writing the low-level code yourself. Very spesific needs for ADC readings? Obscure timer needs? Read the approperiate Microchip application note! ## Table of contents @@ -145,7 +145,7 @@ Note that the default printf implementation will NOT print floats or doubles by If you're using a serial port, simply use `Serial.printf("Milliseconds since start: %ld\n", millis());`. Other common libraries that inherit the Print class (and thus supports printf) are SoftwareSerial, the LiquidCrystal LCD library and the u8g2 graphical LCD library. -# pwmWrite - flexible PWM routing +## pwmWrite - flexible PWM routing The Arduino pinout definition and the `analogWrite` function have the PWM output pins pre-defined, and can't be moved or routed to different pins using the default Arduino API, even though the chip itself supports this. The `pwmWrite` function lets to use every supported PWM output pin, and you can route the PWM signals as you like. Note that the chip limits which timer output can be routed to which pins, and you also need to make sure you don't route the PWM signal to a pins that's used for something else, like UART or SPI. Also keep in mind that the timer used for millis/micros is occupied and can not be used for PWM generation. For the Nano Every 4809 and Uno Wifi Rev2 this means timer TCB2, and for all the other pinouts TCB2. Also note that low-pinout parts does not have timer TCB3 and all the routing pin options due to the lack of physical IO. ### Declaration @@ -196,7 +196,7 @@ pwmWrite(TCA0_2, 128, ROUTE_TCA0_PORTA); | `ROUTE_TCB3_PC1` | Route the TCB3 PWM output to pin PC1 (not present on low pincount parts) | -# pwmPrescaler - PWM frequency setting +## pwmPrescaler - PWM frequency setting `pwmPrescaler` sets the clock source that drives timer. Timer TCA0 has the most options, while the TCB timers have fewer. The prescaler direcly affects the PWM frequency, and this is the formula that determines the frequency: `F_CPU / resolution / prescaler`. For instance, the default TCB PWM prescaler with a system clock of 16 MHz is 1/64, which results in a PWM frequency of just under 1 kHz. @@ -233,7 +233,7 @@ pwmPrescaler(TCB_1, TCB_DIV2); | `TCA_DIV1024` | TCA0 | Runs TCA0 at 1/1024 the system clock | | -# pwmSetResolution +## pwmSetResolution This function lets you change the PWM resolution in favour of increased PWM frequency. The default PWM range is 0-255, but the upper limit can be set to anything between 1 and 254. The resolution also affects the PWM frequency. The frequency can be calculated using this formula: `F_CPU / resolution / prescaler` @@ -250,4 +250,4 @@ pwmSetResolution(TCA0_0, 127); pwmSetResolution(TCB_0, 31); // Set TCB1 timer max value to 99 pwmSetResolution(TCB_1, 99); -``` \ No newline at end of file +``` From 35d72d2afc6fd4273f79234c11de5c38db118fc1 Mon Sep 17 00:00:00 2001 From: Hans Date: Sun, 22 Feb 2026 23:03:56 +0100 Subject: [PATCH 348/351] Update README.md Add information about the new PWM routing functionality --- README.md | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/README.md b/README.md index 3814aaf..830341e 100644 --- a/README.md +++ b/README.md @@ -27,6 +27,7 @@ They're small programmers with excellent software support, and can be used with * [Reset pin](#reset-pin) * [Printf support](#printf-support) * [Fast IO](#fast-io) +* [Flexible PWM setup and routing](#flexible-pwm-setup-and-routing) * [Pin macros](#pin-macros) * [Write to own flash](#write-to-own-flash) * [Memory-mapped flash](#memory-mapped-flash) @@ -143,6 +144,21 @@ For timing critical applications the standard `digitalRead()` and `digitalWrite( [**See the extended API documentation for more information!**](https://github.com/MCUdude/MegaCoreX/tree/master/Extended-API.md#fast-io) +## Flexible PWM setup and routing + +The various pinout this core provides are optimized to expose as many features on the available IO pins as possible. This is great where you want to have as many options as possible. For instance, I've tried my best to route various peripherals around so they don't share the same pins as other, frequencly used peripherals. +By default, PWM pins can't be moved around using the Arduino framework. And the megaAVR-0 family of chips only allows you to route a PWM output to a few pin options. To overcome this limitation and provide greater flexibility, I've added a few functions that makes PWM setup and routing much easier! Here's an example of how you would re-route the PWM output from timer TCB0 to a different pin: + +```c +// Route timer TCB0 PWM output to pin PF4 and set the duty cycle to 50% (128/255) +pwmWrite(TCB_0, 128, ROUTE_TCB0_PF4); +// Set the timer TCB0 duty cycle to 30% but leave the routing as is +pwmWrite(TCB_0, 76); +``` + +[**See the PWM section in the extended API documentation for more information!**](https://github.com/MCUdude/MegaCoreX/tree/master/Extended-API.md#pwmwrite---flexible-pwm-routing) + + ## Pin macros Note that you don't have to use the digital pin numbers to refer to the pins. You can also use some predefined macros that map "Arduino pins" to the port and port number. Note that all my Arduino cores have these macros if you prefer to use these rather than the default Arduino pin number. From a6148505449e174efb71df4a5ae8db2a396e0dc8 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 5 Mar 2026 19:42:21 +0100 Subject: [PATCH 349/351] Add missing enum Closes #217 --- megaavr/variants/uno-wifi/pins_arduino.h | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/megaavr/variants/uno-wifi/pins_arduino.h b/megaavr/variants/uno-wifi/pins_arduino.h index 5d30633..ed0c177 100644 --- a/megaavr/variants/uno-wifi/pins_arduino.h +++ b/megaavr/variants/uno-wifi/pins_arduino.h @@ -112,6 +112,24 @@ enum pwm_timers_t : uint8_t { TCB_2 = 8, TCB_3 = 9, }; + +enum timers_route_t : uint8_t { + ROUTE_TCA0_PORTA = 0x40, + ROUTE_TCA0_PORTB = 0x41, + ROUTE_TCA0_PORTC = 0x42, + ROUTE_TCA0_PORTD = 0x43, + ROUTE_TCA0_PORTE = 0x44, + ROUTE_TCA0_PORTF = 0x45, + ROUTE_TCB0_PA2 = 0x00, + ROUTE_TCB0_PF4 = 0x01, + ROUTE_TCB1_PA3 = 0x10, + ROUTE_TCB1_PF5 = 0x11, + ROUTE_TCB2_PC0 = 0x20, + ROUTE_TCB2_PB4 = 0x21, + ROUTE_TCB3_PB5 = 0x30, + ROUTE_TCB3_PC1 = 0x31, + ROUTE_UNTOUCHED = 0x80, +}; #endif // Timer pin mapping From b4f1a4ef9ff857f344d8cb6fe3265282d3880d8c Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 5 Mar 2026 19:43:49 +0100 Subject: [PATCH 350/351] Remove badCall This messes up compilation without LTO Closes #218 --- megaavr/libraries/Event/src/Event.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/megaavr/libraries/Event/src/Event.cpp b/megaavr/libraries/Event/src/Event.cpp index bd25ebd..577c4ba 100644 --- a/megaavr/libraries/Event/src/Event.cpp +++ b/megaavr/libraries/Event/src/Event.cpp @@ -858,7 +858,7 @@ void Event::long_soft_event(uint8_t length) { event::gen::generator_t Event::gen_from_peripheral(AC_t& comp) { #if defined(TINY_1_SERIES) && PROGMEM_SIZE > 8192 - badCall("gen_from_peripheral() does not support channel-specific generators. The AC's larger 1-series are."); + // badCall("gen_from_peripheral() does not support channel-specific generators. The AC's larger 1-series are."); #else #if defined(AC0) if(&comp == &AC0) { @@ -1018,7 +1018,7 @@ event::user::user_t Event::user_from_peripheral(TCA_t& timer, uint8_t user_type) event::gen::generator_t Event::gen_from_peripheral(TCB_t& timer, uint8_t event_type) { int8_t gentype = -1; #if defined(TINY_0_OR_1_SERIES) - badCall("gen_from_peripheral() does not support channel-specific generators. The TCBs on 0/1-series are."); + // badCall("gen_from_peripheral() does not support channel-specific generators. The TCBs on 0/1-series are."); #else #if defined(MEGACOREX) // Dx-series and 2-series have ovf event, others don't. if(event_type != 1) { From d9b3447d8e2ea71b7d0c2521c73ad4bf8ebfa3a7 Mon Sep 17 00:00:00 2001 From: MCUdude Date: Thu, 5 Mar 2026 21:51:53 +0100 Subject: [PATCH 351/351] Fix issue where parts that doesn't have TCB3 wouldn't compile Closes #220 --- megaavr/cores/coreX-corefiles/pwm_write.cpp | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/megaavr/cores/coreX-corefiles/pwm_write.cpp b/megaavr/cores/coreX-corefiles/pwm_write.cpp index 8a0e615..d89739f 100644 --- a/megaavr/cores/coreX-corefiles/pwm_write.cpp +++ b/megaavr/cores/coreX-corefiles/pwm_write.cpp @@ -43,12 +43,16 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { pin_bp = route? PIN4_bp: PIN0_bp; vport = route? &VPORTB: &VPORTC; d_max = TCB2.CCMPL; - } else if(pwmTimer == TCB_3) { + } + #if defined(TCB3) + else if(pwmTimer == TCB_3) { route = PORTMUX.TCBROUTEA & 0x08; pin_bp = route? PIN1_bp: PIN5_bp; vport = route? &VPORTC: &VPORTB; d_max = TCB3.CCMPL; - } else { + } + #endif + else { return; } @@ -68,7 +72,9 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { case TCB_0: case TCB_1: case TCB_2: + #if defined(TCB3) case TCB_3: + #endif timer_B = &TCB0 + (pwmTimer-TCB_0); timer_B->CTRLB &= ~(TCB_CCMPEN_bm); break; @@ -105,7 +111,9 @@ void pwmWrite(pwm_timers_t pwmTimer, uint16_t val, timers_route_t timerRoute) { case TCB_0: case TCB_1: case TCB_2: + #if defined(TCB3) case TCB_3: + #endif timer_B = &TCB0 + (pwmTimer-TCB_0); savedSREG = SREG; cli();