Bug 766299

Summary: g++ sometimes miscompiles code for the avr target
Product: [Fedora] Fedora Reporter: David Howells <dhowells>
Component: avr-gccAssignee: Thibault North <thibault.north>
Status: CLOSED ERRATA QA Contact: Fedora Extras Quality Assurance <extras-qa>
Severity: high Docs Contact:
Priority: unspecified    
Version: 16CC: rhbugs, thibault.north, trond.danielsen
Target Milestone: ---   
Target Release: ---   
Hardware: Unspecified   
OS: Unspecified   
Whiteboard:
Fixed In Version: avr-gcc-4.6.2-1.fc16 Doc Type: Bug Fix
Doc Text:
Story Points: ---
Clone Of: Environment:
Last Closed: 2011-12-21 17:03:17 UTC Type: ---
Regression: --- Mount Type: ---
Documentation: --- CRM:
Verified Versions: Category: ---
oVirt Team: --- RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: --- Target Upstream Version:
Embargoed:
Attachments:
Description Flags
Test case showing the problem none

Description David Howells 2011-12-11 14:18:54 UTC
Created attachment 545277 [details]
Test case showing the problem

Description of problem:

I'm trying to build stuff for my Arduino board, but the compiler occasionally
clobbers the return value of a function it just called.  This is notable in the
Arduino Ethernet library where the interactions with the W5100 chipset go
interestingly wrong.

I opened a bug on this in the gcc bugzilla:

    http://gcc.gnu.org/bugzilla/show_bug.cgi?id=51445

but the problem appears fixed in gcc-4.6.2 (I found that by building that for myself and trying it).

Version-Release number of selected component (if applicable):

avr-gcc-4.6.1-3 and -4.

How reproducible:

100%.

Steps to Reproduce:
1. Build the attached test case using:

avr-gcc -g -Os -w -mmcu=atmega328p -ffunction-sections -fdata-sections -o tmp.o -c tmp.cpp

2. Use avr-objdump -d to disassemble the resulting tmp.o and look for the send_data_processing method.

3. Find the first CALL instruction.  The result of this function call is returned in the R24 register.
  
Actual results:

With the #if set to 1 in the test case, it can be seen that the return value from the function call is clobbered immediately after the return:

  26:   0e 94 00 00     call    0       ; 0x0
<W5100Class::send_data_processing(unsigned char, unsigned char*, unsigned int)>
  2a:   81 2f           mov     r24, r17

(data moves right to left in the MOV instruction).

Expected results:

R24 should be saved as it's needed later.  Flipping the #if to 0 in the test case shows this instead:

  24:   0e 94 00 00     call    0       ; 0x0 <W5100Class::send_data_processing(unsigned char, unsigned char*, unsigned int)>
  28:   e8 2e           mov     r14, r24
  2a:   81 2f           mov     r24, r17

Additional info:

This seems to be fixed in 4.6.2:

  24:   0e 94 00 00     call    0       ; 0x0 <W5100Class::send_data_processing(unsigned char, unsigned char*, unsigned int)>
  28:   a8 2e           mov     r10, r24
  2a:   81 2f           mov     r24, r17

I tested this by substituting the 4.6.2 gcc in the spec file and dropping the progmem patch.

Comment 1 Thibault North 2011-12-11 15:37:12 UTC
Hello,
Thanks for your report. Indeed I have to update to 4.6.2. Will do ASAP.

Comment 2 Fedora Update System 2011-12-11 17:05:50 UTC
avr-gcc-4.6.2-1.fc16 has been submitted as an update for Fedora 16.
https://admin.fedoraproject.org/updates/avr-gcc-4.6.2-1.fc16

Comment 3 Fedora Update System 2011-12-11 21:52:43 UTC
Package avr-gcc-4.6.2-1.fc16:
* should fix your issue,
* was pushed to the Fedora 16 testing repository,
* should be available at your local mirror within two days.
Update it with:
# su -c 'yum update --enablerepo=updates-testing avr-gcc-4.6.2-1.fc16'
as soon as you are able to.
Please go to the following url:
https://admin.fedoraproject.org/updates/FEDORA-2011-16971/avr-gcc-4.6.2-1.fc16
then log in and leave karma (feedback).

Comment 4 David Howells 2011-12-11 23:38:48 UTC
Works for me.

Comment 5 Fedora Update System 2011-12-21 17:03:17 UTC
avr-gcc-4.6.2-1.fc16 has been pushed to the Fedora 16 stable repository.  If problems still persist, please make note of it in this bug report.