diff options
author | Anatoly Sokolov <aesok@post.ru> | 2008-02-22 23:16:50 +0300 |
---|---|---|
committer | Anatoly Sokolov <aesok@gcc.gnu.org> | 2008-02-22 23:16:50 +0300 |
commit | 34d02d17ac7041fa9e89b456a5b5759c856312e3 (patch) | |
tree | 8958b7ea45ece356e6722e805a43728669134084 | |
parent | a4899c012381f6e44797e48a254b2d649747717e (diff) | |
download | gcc-34d02d17ac7041fa9e89b456a5b5759c856312e3.zip gcc-34d02d17ac7041fa9e89b456a5b5759c856312e3.tar.gz gcc-34d02d17ac7041fa9e89b456a5b5759c856312e3.tar.bz2 |
libgcc.S (__RAMPZ__): Define.
* config/avr/libgcc.S (__RAMPZ__): Define.
(__do_copy_data): Add for devices with 128KB code memory.
From-SVN: r132555
-rw-r--r-- | gcc/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/config/avr/libgcc.S | 50 |
2 files changed, 48 insertions, 7 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index fd4ca31..52921c3 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,8 @@ +2008-02-22 Anatoly Sokolov <aesok@post.ru> + + * config/avr/libgcc.S (__RAMPZ__): Define. + (__do_copy_data): Add for devices with 128KB code memory. + 2008-02-22 Nathan Froyd <froydnj@codesourcery.com> * config/rs6000/linuxspe.h (SUBSUBTARGET_OVERRIDE_OPTIONS): diff --git a/gcc/config/avr/libgcc.S b/gcc/config/avr/libgcc.S index 397778b..8fdba55 100644 --- a/gcc/config/avr/libgcc.S +++ b/gcc/config/avr/libgcc.S @@ -32,6 +32,7 @@ Boston, MA 02110-1301, USA. */ #define __SREG__ 0x3f #define __SP_H__ 0x3e #define __SP_L__ 0x3d +#define __RAMPZ__ 0x3B /* Most of the functions here are called directly from avr.md patterns, instead of using the standard libcall mechanisms. @@ -686,20 +687,54 @@ __tablejump__: .endfunc #endif /* defined (L_tablejump) */ -/* __do_copy_data is only necessary if there is anything in .data section. - Does not use RAMPZ - crt*.o provides a replacement for >64K devices. */ - #ifdef L_copy_data .section .init4,"ax",@progbits .global __do_copy_data __do_copy_data: +#if defined(__AVR_HAVE_ELPMX__) + ldi r17, hi8(__data_end) + ldi r26, lo8(__data_start) + ldi r27, hi8(__data_start) + ldi r30, lo8(__data_load_start) + ldi r31, hi8(__data_load_start) + ldi r16, hh8(__data_load_start) + out __RAMPZ__, r16 + rjmp .L__do_copy_data_start +.L__do_copy_data_loop: + elpm r0, Z+ + st X+, r0 +.L__do_copy_data_start: + cpi r26, lo8(__data_end) + cpc r27, r17 + brne .L__do_copy_data_loop +#elif !defined(__AVR_HAVE_ELPMX__) && defined(__AVR_HAVE_ELPM__) + ldi r17, hi8(__data_end) + ldi r26, lo8(__data_start) + ldi r27, hi8(__data_start) + ldi r30, lo8(__data_load_start) + ldi r31, hi8(__data_load_start) + ldi r16, hh8(__data_load_start - 0x10000) +.L__do_copy_data_carry: + inc r16 + out __RAMPZ__, r16 + rjmp .L__do_copy_data_start +.L__do_copy_data_loop: + elpm + st X+, r0 + adiw r30, 1 + brcs .L__do_copy_data_carry +.L__do_copy_data_start: + cpi r26, lo8(__data_end) + cpc r27, r17 + brne .L__do_copy_data_loop +#elif !defined(__AVR_HAVE_ELPMX__) && !defined(__AVR_HAVE_ELPM__) ldi r17, hi8(__data_end) ldi r26, lo8(__data_start) ldi r27, hi8(__data_start) ldi r30, lo8(__data_load_start) ldi r31, hi8(__data_load_start) - rjmp .do_copy_data_start -.do_copy_data_loop: + rjmp .L__do_copy_data_start +.L__do_copy_data_loop: #if defined (__AVR_HAVE_LPMX__) lpm r0, Z+ #else @@ -707,10 +742,11 @@ __do_copy_data: adiw r30, 1 #endif st X+, r0 -.do_copy_data_start: +.L__do_copy_data_start: cpi r26, lo8(__data_end) cpc r27, r17 - brne .do_copy_data_loop + brne .L__do_copy_data_loop +#endif /* !defined(__AVR_HAVE_ELPMX__) && !defined(__AVR_HAVE_ELPM__) */ #endif /* L_copy_data */ /* __do_clear_bss is only necessary if there is anything in .bss section. */ |