2007-12-14 Shaun Jackman * include/avr/boot.h (__boot_page_fill_normal, __boot_page_erase_normal, __boot_page_write_normal, __boot_rww_enable): Use an out instruction rather than an sts instruction when possible. Index: include/avr/boot.h =================================================================== RCS file: /sources/avr-libc/avr-libc/include/avr/boot.h,v retrieving revision 1.26 diff -u -p -r1.26 boot.h --- include/avr/boot.h 23 Jan 2007 15:32:48 -0000 1.26 +++ include/avr/boot.h 14 Dec 2007 23:46:15 -0000 @@ -187,23 +187,35 @@ #define __BOOT_RWW_ENABLE (_BV(SPMEN) | _BV(__COMMON_ASRE)) #define __BOOT_LOCK_BITS_SET (_BV(SPMEN) | _BV(BLBSET)) -#define __boot_page_fill_normal(address, data) \ -({ \ - __asm__ __volatile__ \ - ( \ - "movw r0, %3\n\t" \ - "movw r30, %2\n\t" \ - "sts %0, %1\n\t" \ - "spm\n\t" \ - "clr r1\n\t" \ - : \ - : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ - "r" ((uint8_t)__BOOT_PAGE_FILL), \ - "r" ((uint16_t)address), \ - "r" ((uint16_t)data) \ - : "r0", "r30", "r31" \ - ); \ -}) +static inline void __spm1(uint8_t __command) +{ + __SPM_REG = __command; + __asm__ __volatile__ ("spm"); +} + +static inline void __spm2(uint8_t __command, uint16_t __address) +{ + register uint16_t __a asm("r30") = __address; + __SPM_REG = __command; + __asm__ __volatile__ ("spm" :: "z" (__a)); +} + +static inline void __spm3(uint8_t __command, + uint16_t __address, uint16_t __data) +{ + register uint16_t __a asm("r30") = __address; + register uint16_t __d asm("r0") = __data; + __SPM_REG = __command; + __asm__ __volatile__ + ( + "spm\n\t" + "clr __zero_reg__" + :: "z" (__a), "r" (__d) + ); +} + +#define __boot_page_fill_normal(address, data) \ + __spm3(__BOOT_PAGE_FILL, address, data) #define __boot_page_fill_alternate(address, data)\ ({ \ @@ -245,20 +257,8 @@ ); \ }) -#define __boot_page_erase_normal(address) \ -({ \ - __asm__ __volatile__ \ - ( \ - "movw r30, %2\n\t" \ - "sts %0, %1\n\t" \ - "spm\n\t" \ - : \ - : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ - "r" ((uint8_t)__BOOT_PAGE_ERASE), \ - "r" ((uint16_t)address) \ - : "r30", "r31" \ - ); \ -}) +#define __boot_page_erase_normal(address) \ + __spm2(__BOOT_PAGE_ERASE, address) #define __boot_page_erase_alternate(address) \ ({ \ @@ -294,20 +294,8 @@ ); \ }) -#define __boot_page_write_normal(address) \ -({ \ - __asm__ __volatile__ \ - ( \ - "movw r30, %2\n\t" \ - "sts %0, %1\n\t" \ - "spm\n\t" \ - : \ - : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ - "r" ((uint8_t)__BOOT_PAGE_WRITE), \ - "r" ((uint16_t)address) \ - : "r30", "r31" \ - ); \ -}) +#define __boot_page_write_normal(address) \ + __spm2(__BOOT_PAGE_WRITE, address) #define __boot_page_write_alternate(address) \ ({ \ @@ -343,17 +331,8 @@ ); \ }) -#define __boot_rww_enable() \ -({ \ - __asm__ __volatile__ \ - ( \ - "sts %0, %1\n\t" \ - "spm\n\t" \ - : \ - : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ - "r" ((uint8_t)__BOOT_RWW_ENABLE) \ - ); \ -}) +#define __boot_rww_enable() \ + __spm1(__BOOT_RWW_ENABLE) #define __boot_rww_enable_alternate() \ ({ \