Printf Oddity : Programming Challange

Here is a challange for the FIRST programming community. I promise a super-tremendous prize, like a candy bar, at nationals to whoever figures it out.

The Challange:
Recently, aka for nobody knows how long but recently found, we have had a problem with our autonomous program where we have vital print statements. If we remove certain printf statments, now named vital, our program stops printing anything out and tries to run backwards through the closest wall. We don’t really know how long it has been in the code, because we normally left the ‘vital’ print statements in anyway just because they were useful. However, we were running out of code space and trying to cut down on memory usage and we took one out and discovered this problem.
We did some experimentation and discovered that it didn’t matter what the vital print statements printed, but they had to print something. Integer, just “Nothing,” it didn’t matter. The spots where the vital print statements had to be were seemingly random places in our code, at the very beginning, when we move through our 3D data structure. We managed to eliminate the need for one print statement by correcting a small error in our data structure, but the other one remained. We tried almost everything, moving statements around, adding them at odd places, nothing eliminated the need for the statement.
At first we suspected a syntax error somewhere that the print statement was, somehow, correcting. No luck. Then we thought of stdio. It didn’t matter whether we included it or not or where. Again no luck. Ok, at this point we’d pretty much accepted our odd print statement as a permenate part of our code that we’re just going to have to deal with. It was something we worked on in our free time. Not that we had that much time, but it bugged us enough to occupy all we had.
Eventually I randomly removed the initialization printf statement in User Initialization in User Routines (that is included in the default code) and suddenly our code worked. No other print statements were required anymore to stop it from trying to kill us.
I don’t understand. Does anyone understand? This doesn’t make logical sense that the initialization printf statement would require a second statement to stop it from destroying our program. Keep in mind that we have not edited that statement at all since we got the default code. We have had various programmers proofread our code. No one has found any odd syntax error or statement re-declaration.

Summary:

  1. Without some vital printf("…"); statements our program does not work
  2. With some vital printf("…"); we start at nearly the right place in our data structure, but one step too far
  3. When we remove all but the vital printf statements our program works perfectly
  4. When we remove ALL the print statements in our seperate autonomous file, and also remove the default initialization statement our program works perfectly.
  5. We use 3 Interrupts. I’m not sure this is significant, but I always suspect interrupts.

Here is the question that must be answered: Why?

Feel request other information.

I have a few questions.

  1. Are any of the printf’s in an interrupt handler?
  2. Do u try to access any sensor variables during initialization?
  3. Does the program work immediatly after download?
  4. Does the contoroller have to be reset for the error to appear?
  5. Does the Program State indicator flash red?
  6. Do you get any warnings when you compile that do not halt the build?

-Scitobor

What file(s) do you have the autonomous in/spread across, and what exactly did you change?

If it comes to it that you can’t figure out what it’s doing, I reccomend downloading a new default code file, then re-working your autonomous into it… I know, it’s a lot of work to do, but maybe(?) it could be a problem with one of your files…

PS: Also, it could possibly be the compiler? Hate to ask a stupid question, but are you sure you’re using the MCC18 compiler v2.4? I don’t know if that could cause a problem anyway, but what you have there is strange, so it’d be best to try different things and see what works…

EDIT: I read through it again, I didn’t see that you got it working in my first read through. I don’t know… I suggest using a program (I think textpad does it - www.textpad.com) to compare each of your files… your custom code to a newly downloaded default… and see what doesn’t line up… That’d be my best advice to you as of now. Otherwise, I’m just as confused as you are.

  1. No
  2. We store an arm pot offset during init. Is that a sensor variable?
  3. Do you mean does the auto code run? No we have to use a dongle.
  4. No
  5. No
  6. Only stupid “function calls w/o prototype” but those are in default code any way.

We make a separate .c .h file for autonomous. Many attempts were made to clean this file (not personally by me).

We are using the MCC18 compiler v2.4 but I don’t trust it more than its predecessor. I once completely removed an abs function from the code and the old complier decided to apply it to random PWM outputs instead of deleting it.

Realize this is no longer a problem with our code, its a challenge. We simply remove the initialization printf and all others and we are ok (we still include stdio). DarkAlex just want some kind of explanation for this asinine problem that caused him way more frustration than its worth.
**Warning: Don’t think about this problem for too long, your head will explode! ** :ahh:

Yeah, that sums it up pretty well. In user routines fast we have some initialization, interrupts handler calls, and our autonomous function call. This is still a very odd error.

These are the classic symptoms of a memory overwrite.

Usually the problem isn’t caused by the statements you are fiddling with. Changing the “vital” statements simply causes things to be relocated/reorganized in the link map. I bet the overwrite is still happening, but it’s probably overwriting unimportant locations now like unassigned space or variables that get initialized later anyway.

One way to track it down is to cause the error, look in the link map for the data memory location where you know the results are bad, then backtrack to see what is located before that corrupted memory location.

The cause, for instance, might be writing more values to an array than it is sized for. The extra values will clobber the next n memory bytes, one of which happens to be “vital”, a static variable for example.

Ok, overwriting anything seems like bad news. I checked our structure when you mentioned writing too many values in an array. It doesn’t seem to be the one causing an error. If the initialization statement, which might be stored as a static array of characters, was, for some reason, larger than the allowed buffer on the printf statement (about 42?) would that possibly cause the error? I don’t think it was, but just in case. We’ll probably be pit neighbors at Drexel. I’ll bring a candy bar.

Printf can be a source of this kind of problem. I know with the old IFI implementation the string array was copied into a data buffer of fixed size with no limit check. If the format string was > 80 characters an overwrite occurred. This is usually easy to spot because the clobbered variables have typical ASCII values like 8224 (2 blank spaces).

Bring Skittles;)