Uploading Arduino Sketches with Arduino as ISP programmer to MEGA2560

Hello everyone.

I have an Arduino MEGA 2560 R3 that got semi bricked, God knows why. The thing was still working with the last programmed sketch, but won't receive any new code via the USB programming feature. Though the USB still connects (makes that windows USB in sound and all), and Windows see it as a COM port, trying to establish a serial connection (i.e. Serial monitor) fails. I suppose that somewhere in the board, the Serial over USB stopped working... the built in pin13 LED no longer lights up, neither do the TX and RX LEDs.

So I figured, if the MEGA2560 processor still working, why not just program it directly via the ICSP header, using a programmer? Well while I lack the programmer itself, the "semi" death of this arduino prompted me to get a few extra Arduino MEGA, so I found out about the MEGA ISP found on the arduino examples and built the wiring to connect one of my good arduinos, uploaded the sketch to it and started attempting to program.

Using the Arduino IDE, avrdude seems to run without problems. It writes and verify the sketch bytes, no error messages are reported. The issue is that though the upload happens, the sketch doesn't seem to be running. Obviously I choose using the Blink example to upload via programmer because nothing could be simpler, and even though the built in LED on the bad board isn't working, sticking a LED between GND and PIN13 should do the job.

Frustrated with the non-working of the sketches, I decided to burn the bootloader to the bad board, and I was surprise to see the LED on pin 13 blink in a quick fashion. I suppose that's what the bootloader does when it's just hanging in there with nothing else.

I grabbed another good Arduino and tried programming sketches on it. The result is always the same... uploads ok, nothing happens after that. I also found out that uploading sketches via the IDE eliminates the bootloader completely, so the good board is no longer programmable via USB, until you burn back the bootloader to it. For a few minutes I thought I bricked another one, those were sad minutes. :frowning:

After lots of reading here and there, and talking to some friends who are into MCUs I was persuaded to install Atmel Studio 7 and try writing a program there to see how it would behave. So I figured I'd write the blink example, of course.

#ifdef F_CPU
#undef F_CPU
#endif

#define F_CPU 16000000 // Set MEGA 2560 R3 Clock

#include <avr/io.h>
#include <util/delay.h>

int main(void)
{
    //setup
    DDRB = 0x80; // pinMode(13, OUTPUT)

    //loop
    while (1) 
    {
        PORTB = 0x80; // digitalWrite(13, HIGH)
        _delay_ms(1000);
        PORTB = 0x00; // digitalWrite(13, LOW)	   	   	 		   
        _delay_ms(1000);
    }
}

Then I setup a custom upload tool, which is basically a copy of the same line the arduino uses to upload the sketch, changing just the name of the HEX file output by Atmel Studio and WHOA! It works. :o

That prompted me with numerous head scratches trying to understand why in the world an HEX generated by the Arduino IDE won't work, and this one by the Atmel Studio 7 will.

I also tried manually running command lines for the HEX files generated by the "Export Compiled Binary" menu functions, both the Blink.ino.mega.hex, and Blink.ino.with_bootloader.mega.hex, still the same non working result.

TL;DR;
So then, I seek your guidance with the question that summarize the entire story above:

How can I get sketches made in the Arduino IDE, uploaded to an Arduino MEGA2560 R3 using another Arduino MEGA as the programmer, to run on the target Arduino as it would if it had been uploaded via USB?

Thank you in advance. :smiley:

Your hfuse is probably still set to 0xD8 (for use with a bootloader), use avrdude to set it to 0xD9.

(It is a long story. You use a pre 6.1 avrdude, right? (maybe 6.0.1?)? Because of a limitation in the combination ArduinoISP/avrdude pre-6.1, your sketch ends up in the middle of memory @128K. With hfuse set to 0xD8, the mcu starts executing just before 256K, where the bootloader normally resides. The mcu will wrap around to 0K where nothing is found (all 0xff's). It will in the end reach your skech @128K, but it cannot run from there. Setting the hfuse to 0xD9 will make the mcu start @0x00000 and has the side effect that your sketch correctly ends up @0x00000 too, even with the old avrdude.)

I've found that using Arduino AVR Boards 1.6.12 or 1.6.14, which use AVRDUDE 6.3.0 the issue no longer occurs with the stock hfuse setting. So that could be another solution, to just update your Arduino IDE and/or Arduino AVR Boards version.

PeterVH:
Your hfuse is probably still set to 0xD8 (for use with a bootloader), use avrdude to set it to 0xD9.

(It is a long story. You use a pre 6.1 avrdude, right? (maybe 6.0.1?)? Because of a limitation in the combination ArduinoISP/avrdude pre-6.1, your sketch ends up in the middle of memory @128K. With hfuse set to 0xD8, the mcu starts executing just before 256K, where the bootloader normally resides. The mcu will wrap around to 0K where nothing is found (all 0xff's). It will in the end reach your skech @128K, but it cannot run from there. Setting the hfuse to 0xD9 will make the mcu start @0x00000 and has the side effect that your sketch correctly ends up @0x00000 too, even with the old avrdude.)

Is there a thread where the long story is described in detail?

dmjlambert:
Is there a thread where the long story is described in detail?

Maybe PeterVH will chime in with more info but the question was also asked in the issue report and PeterVH responded:

I explained it here: ArduinoISP reliability and portability improvements. | PeterVH scroll to the chapter "avrdude 6.1".

and

Hmm, that explanation is not that great. The "clever fixes in avrdude 6.1" consist of sending "universal" commands to the stk500v1 programmer (Arduino as ISP) to make it send the "Load Extended Address Byte" command to the target.

OK, I did read all that stuff and I would like to know more.

What I don't get #1:

Older avrdude and old Arduino as ISP sketch have worked for years to burn the bootloader on ATmega2560 where it belongs end of its 256 KB flash. So how is it that work done to the Arduino as ISP sketch and deployment of a newer avrdude fix problems with burning the bootloader on the ATmega2560? Who was having problems with that? Perhaps it is because I don't often use Windows that I didn't have problems?

What I don't get #2:

For upload using programmer, I also don't understand how setting hfuse to 0xD9 would have any impact on changing the location in flash that the sketch gets written. So if hfuse is set to 0xD8, the sketch gets written starting at middle of memory at 128K, but setting hfuse to 0xD9 somehow affects where avrdude writes the sketch so it gets written in lower memory at 0x00000? How could the value of fuses impact what part of memory the upload occupies? Writing a sketch using programmer does not work when hfuse is set to 0xD8, and that I do understand, because the BOOTRST fuse is telling the MCU to run a program at the bootloader place in memory and there is no bootloader there. You would think simply changing that one fuse value to 0xD9 would fix it so the sketch previously uploaded could run. But that is not the case and you do indeed need to re-upload the sketch in order for it to run. So it seems to confirm what PeterVH is saying. I just don't understand where the malfunction is that could cause that. Just a bug in old avrdude? How would avrdude or the Arduino as ISP sketch even know what the BOOTRST fuse value is set to when it starts uploading a sketch using programmer?

pert:
I've found that using Arduino AVR Boards 1.6.12 or 1.6.14, which use AVRDUDE 6.3.0 the issue no longer occurs with the stock hfuse setting. So that could be another solution, to just update your Arduino IDE and/or Arduino AVR Boards version.

You are so right about that! I was using 1.6.11 IDE, updated it to 1.6.12 and it uploads and works like a charm.

I also tested uploading from VisualMicro, and no problems either.

I didn't get to test setting HFuse to D9, but that'd probably have solved it with 1.6.11. Thanks pert and PeterVH for your prompt responses.

All the best! :slight_smile:

Glad it works.

@dmjlambert: You can find answers to both questions here:

The writeup is about older versions of usbasp, but the combo "Arduino as ISP" + "avrdude pre 6.1" suffer the same problem.

#1: you're right, and the link above explains why that always worked.

#2:

How could the value of fuses impact what part of memory the upload occupies?

The atmega2560 seems to behave that way. I have no official doc to confirm this, but you can easily verify this observation: set the hfuse to 0xD8, burn a sketch to a mega with the latest ArduinoISP sketch + avrdude 6.0.1. Read it back in with the same ArduinoISP sketch, but use avrdude 6.1 (or higher). (You can trust the latter combo). You will see in the .hex file that the sketch is at 128KB.

I just don't understand where the malfunction is that could cause that.

The 'malfunction' or rather limitation consists of not sending "Load Extended Address Byte" command.

Thanks for the clarification. I've been wondering about this for a while.

OK ! You guys are WAAAAAY over my head. For the last few days, I have read article after article trying to find a solution that will let me load and run sketches on my Mega 2560. After all the reading that I have done, I don't feel that I am that smart of a person.
So, am I to understand that if I get IDE1.6.12 , my problem will be solved? Someone please help bring my torment to an END.

Techno-quest:
So, am I to understand that if I get IDE1.6.12 , my problem will be solved?

Why not give it a try?

Just like TulioAdriano said in one of the posts above, "You are so right about that! I was using 1.6.11 IDE, updated it to 1.6.12 and it uploads and works like a charm."

With that said, I'm still using 1.6.6 and I kind of like the torment. I like to dish it out and to receive it. It keeps my brain going....

Thanks Pert
Thanks dmjlambert

It worked. Not only did it let me upload my sketch! It allowed my wave shield to work on the Mega 2560( with pin mods) Yessssss, I can keep my JOB!!

dmjlambert:
I'm still using 1.6.6 and I kind of like the torment.

1.6.6 is for the true masochists!