I am transitioning some working code from Kiel to SDCC and having some
The SDCC compiler seems to be adding some rogue code to my program. It's
added like __mcs51_genRAMCLEAR and __mcs51_genXRAMCLEAR, but unlike them
isn't identified by name. It comes right after the global variable
initialization, and writes into internal RAM and the SFRs. It begins its
writing at 0x23, the beginning of the stack area, and continues to 0x7F,
then it seamlessly continues in the SFRs. All of the instructions are MOV
What it's writing appears to be the addresses of the SFRs in ascending
order. It starts with 0x80 and continues upward, skipping all the unused
addresses. After it reaches 0x80 it's writing SFR addresses into the SFRs
themselves. When it reaches SP it writes 0xEE, overwriting 0x22. It ends
that mode at address 0x91, where it writes 0xFF.
Then it starts setting bits in the bit-addressable SFRs. For some reason it
starts at 0x90.2, making 0x90 assume the values 0x04, 0x0C, 0x1C, etc., in
order, before moving on to 0x98, 0xA0, etc. When it reaches 0xA8 (IE)
its last step enables interrupts and it immediately *is* interrupted, going
to my Timer 0 ISR. I haven't traced flow beyond that point, but it finds
its way back to the start of the rogue code, continually looping.
> When it reaches 0xA8 (IE) its last step enables interrupts and it immediately *is* interrupted,
If this is the case then you do not use an 8051 :^)
Instead you seem to be using a derivative which maps
its SFR into idata memory?
Use option --iram-size to limit SDCC to the lower 128 bytes then.
Thanks for your prompt response.
I should have given more detail about my project. I'm using a SiLabs C8051F320. It's an enhanced 8051 (actually an 8052, in Intel's part numbering) with a lot of on-chip peripherals. The instruction MOV direct,#data will write to the first 128 bytes of internal memory or to the SFRs, depending on the direct address - to internal memory for direct addresses 0x00 to 0x7F, and to SFRs for direct addresses 0x80 to 0xFF.
That is, the 8051 is faithfully executing the code. I am questioning where the code came from, what it's for, and how to get rid of it.
I don't understand why the interrupt behavior makes it seem that my processor is not an 8051.
> I don't understand why the interrupt behavior makes it seem that my processor is not an 8051.
Sorry, I was probably falsely assuming that the idata clearing loop was the cause
(as you mentioned __mcs51_genRAMCLEAR and I did not read carefully enough).
> where the code came from,
At which address is it located? Can you post a
disassembled section with the tool d52?
(and then compare the addresses with the *.mem file)
Another option is (if the offending code is within
the startup code) to copy the files
into your source directory, assemble them there
(using the same options -plosgff as in
sdcc/device/lib/mcs51/Makefile.in) and then link
the generated *.rel files explicitely with your binary.
This should give you *.rst files with the absolute
addresses for the startup code as well.
Compare these with a D52 disassembly of the binary
of the file that you upload to your target.
Then just to be sure compare it with the binary
that you downloaded from your target again.
That should narrow things down.
Unfortunately there's no binaries in a current (version 3.4.0) D52 package :-(
> Unfortunately there's no binaries in a current (version 3.4.0) D52 package :-(
getting them should be straigtforward. I used:
~> unzip -l /tmp/d52v340.zip
~> cd d52v340
~> sudo make install
Binaries should be included according to author's description at web page.
Output of 'make' on my WXP machine (never used any before, I'm surprised that it is available - obviously part of C++Builder :-) ):
MAKE Version 5.2 Copyright (c) 1987, 2000 Borland
gcc -Wall -O2 -c ./obj/d52.o -o ./obj/d52.o
gcc: ./obj/d52.o: No such file or directory
gcc: no input files
Some mail with these binaries via SF? I promise that I will install gcc or other compiler and learn to use 'make'... someday... I promise! :-)
there might still be two ways out (my first proposal presumed you
were using Unix)
a) most likely the Makefile is not compatible with Borland's make.
(if gcc is fed told to compile an object file from an object
file -c ./obj/d52.o -o ./obj/d52.o there is something wrong)
You could get a GNU make f.e. from mingw or cygwin and then
it should at least fail somewhere different:^)
b) on an alternate download location
there seems to be a windows binary?
b) Same d52v340.zip as on author's page - also no binaries. Only dis52 binaries (GUI front end, but needs D52).
a) I just found some cygwin installation on my machine - remnant of my older play with eCos :-) It worked - 'exe' created :-) Some error happened, gcc probably tried to link 'd52' file instead of accepting name for output file.
$ cd "d52v340"
gcc -Wall -O2 -c d52.c -o obj/d52.o
gcc -Wall -O2 -c common.c -o obj/common.o
gcc -Wall -O2 -c d52pass1.c -o obj/d52pass1.o
gcc -Wall -O2 -c d52pass2.c -o obj/d52pass2.o
gcc -Wall -O2 -c d52table.c -o obj/d52table.o
gcc -Wall -O2 -c analyze52.c -o obj/analyze52.o
gcc -Wall -O2 ./obj/d52.o ./obj/common.o ./obj/d52pass1.o ./obj/d52pass2.o ./obj
/d52table.o ./obj/analyze52.o -o d52
strip: d52: No such file or directory
make: *** [d52] Error 1
I have contacted the author and binaries are now available at http://home.pacbell.net/theposts/ and 8052.com.
You're most probably using the wrong header file. If you use a header file for the Keil compiler it tries to declare SFRs with C statements that SDCC considers initializations.
sfr P0 = 0x80; //the Keil way
sfr at 0x80 P0; //the SDCC way
Bingo. Wrong header file was the problem. I was sure I had changed from Keil to SDCC long ago, but I had only done so on my desktop computer, not on the laptop I use for tests.
Thanks, everyone, for helpful suggestions.