Is IDE Compiler broken? -- Address operation to stack arrays

Am I the only one having issues with the compiler when doing operations to stack arrays?

------ CODE EDITED -----

void PlayMix(unsigned short n) {
  char buf[64], *p = buf;

  for (; n != 0; n /= 10)
    *p++ = '0' + n % 10;

  *p = '\0';
  strcpy(p, ".mp3");
  Serial.println(buf);
}

The monitor displays rubbish. The stack seems to get corrupted at times, resulting in unhinged behaviour. There is no evidence of stack overflow or underflow - and this has been thoroughly checked. Neither has the stack been popped, as the anomaly is inside Function(). A sprintf(buf, ...) can make that happen. The problem also happens when arrays are addressed: buf[n++] = 'a'.

Although the anomaly is eminently reproducible, it does not happen for all code that operate on a stack buffer - about 1 out of 10 such code instances exhibit the anomaly.

Declaring buffer as static makes the problem go away.

If nobody else has reported this issue, I will post code that will make it happen.

The code includes SdFat and SFEMP3SHIELD libraries. Processor is a Mega. I have converted all my arrays to static.

Please post a complete sketch that illustrates the problem rather than just a snippet of code

If the libraries are necessary to reproduce the problem, I would worry about the libraries more than the compiler.

That tends to point to your array being used after it has gone out of scope

1 Like

Well, you haven't even provided a complete code that compiles let alone one that actually reproduces the objectionable behavior.

Nor have you provided an actionable description of what that behavior is --- "unhinged behaviour (sic)" is a useless description.

Given the above, it's unclear what you're looking for from the forum's members. However, if I were a betting man, my money would be on Pilot Error.

Bear in mind that the compiler the IDE invokes isn't an Arduino specific piece of software, it's the widely used gcc. That being the case, there's almost no chance that the issue is a compiler bug. As @gfvalvo said - Pilot Error.

1 Like

I have updated my original post.

I am pretty sure the % operator has precedence over the + operator. I'll check that.

"unhinged means", crashes, runaways, infinite loops, rubbish in the buffer, etc. When the stack gets corrupted, anything can happen. That is called "unhinged". What would you call it?

Behaviour is not (sic) -- that is how the British write it.

As explained -- You will not be able to reproduce it, as it rarely happens. But once it happens, it is reproducible. I can't post the whole 1000 lines of code, and the libraries.

Thanks

How can we spot the memory problem and have a look at the memory usage if we can't see the sketch ?
Some of us are used to look at thousands lines of code to spot that one single problem.

I simply asked if anybody else has such a problem, and if not, then I will post reproducible code.

The sketch is 1000 lines plus another 2000 lines of libraries. About 20 files. Is that what you need?

Seems like you should be able to provoke the behaviour of one straight ahead function with a simple test program.

That’s what we want, mostly because you will probably solve your problem trying to,prove you don’t have one, or something like that.

Don’t do that. It can make nonsense of the comments that follow.

a7

1 Like

Please do.

The thing I look for first in a program with wacky behaviour is dynamic memory allocation - it's risky business on an Arduino with little RAM. Don't forget that String objects use malloc behind the scenes.

1 Like

Thanks wildbill and alto777.

I am afraid the anomaly depends on the wider context, as it is very unusual. I will try to reduce the issue without the libraries and post code. But I am afraid the issue is context sensitive and will go away. The problem may be with the two libraries, but as you can see I have not called a library function. And the issue cannot depend on the Serial object or sprintf.

Not having a debugger, I have been looking at the address values with Serial.print((long) p), and I see rubbish. Is this a proper way to check the address?

Haha, humans will find things like

  strcpy(buf, ".mp3");   // Oops.

trying to prove your function is fine.

a7

Don't know proper. Whilst hacking I hacked this:

  unsigned long kk = (unsigned long) p;
  Serial.print(kk, HEX);
  Serial.print("<  ");

I put that in the loop where you place the chars in buf.

a7

1 Like

Thanks a7.

Yes, I have already fixed that. The strcpy line is not in the original code.

I am trying to reduce the code without the libraries and still make the anomaly happen. Still trying.

Twenty Thousand Leagues Under the Seas is a lot and 20000 code lines is a lot, but 3000 is not.

Will do - trying to get into a manageable form.

What band rate are you using for the Serial printing?

I was able to get some (bad) changes to the functioning of PlayMix by using different speeds.

a7

I am not a code or compiler guru but looking from a mile away it would seem the issue has to do with something on your computer not being cleared, deleted or some such issue. In my limited experience I've found closing then reopening the Arduino IDE or at worst rebooting the OS cured similar problems.
And I can assure none of my sketches are as complex as yours.

So if you have it happen again, try closing and reopening the IDE and see if it is still reproducible.

Problem solved! It was a scope issue due to variable redeclaration that the compiler did not catch -- which I believe it should have caught.

Winner of the 'contest': johnwasser
Hat tip: alto777, wildbill, and all.

I have an array declared statically and global. The result of my 'itoa' like function is put in this array and the address is returned back to the caller. (I just wanted to eliminate passing down another parameter for a results array.)

Well, in an upgrade to this itoa, I had declared a local array of the SAME NAME, which conflicted with the static array. The compiler then silently put the return string in this local array on the stack and its stack address was returned to the calling function, out of scope! Thus the string got obliterated resulting in unruly behaviour downstream.

I could be wrong, but I think the compiler should declare an error condition when a local variable redeclares a static variable outside the function, of the same name. The scope of the local variable silently overrides that of the static variable. Surely a warning is issued, but who looks at warnings? :laughing:

Thanks to all, that made me look deeper into this matter.

It's possible that a warning was issued. You can set your warning level in the IDE menus. But the compiler can never "understand" code. It can only recognize patterns.