call statements - use them or lose them?

I've been toying around with PIC processors for awhile and I've always written CALL statements. It's nice to have repeatable functions and it makes the code easier to read.

Recently my CPU crashed and after hours of research, checking over hardware, etc., I discovered that it actually ran out of stack space. I suspect that I had too many levels of call statements (more than 10 deep at times). I took out a few and fixed it.

The other day I came across a message that said to "never use CALL statements" in assembly. The reason is, you're relying on memory reads/writes and memory on PICs can and will fail leading to hours of troubleshooting and/or strange operation (kind of like my experience).

Should this be a major concern? Should I remove the CALL statements and just use sloppy GOTOs instead? Or was the author overboard?

Reply to
Pokey
Loading thread data ...

Thats true if...

you have practically no memory limitations...

but you should use it to avoid duplication of code.

Using gotos would result in much more code, which may not fit into your EEPROM/FLASH. So use subroutines when code is duplicated, but not for nested structuring of your code. It may still be feasable to use one level for structuring.

Regards, Kurt

--
Kurt Harders
PiN -Präsenz im Netz GITmbH
 Click to see the full signature
Reply to
Kurt Harders

I haven't messed with PICs for a while, but...

OK

IIRC, most of the PIC16 family only have 8 levels of stack, including interrupts. Structuring your code with call/ret isn't a really good option.

If a function is called from only one location, it probably makes sense to goto rather than call it (and goto rather than ret at the end of the function).

Or simply write it in-line. This will save even the goto instructions, though it may make the code harder to read. The C compiler I used (CCS) would do this automatically -- even though the C code indicated a function was being called, the code was plunked in-line at the machine code level..

But calling utility functions, functions that are called from more than one location, is a serious win. It not only saves memory, it simplifies maintenance by eliminating duplicated code.

Overboard.

The "reason" given is nonsense. Memory can fail in any device, and if you can't trust your memory to hold an address long enough to return to the right place, you can't trust it to do simple arithmetic either. Following his advice would mean abandoning the interrupt mechanism as well, or avoiding jump tables (which are the only means of implementing tables of constants in the PIC).

Regards, -=Dave

--
Change is inevitable, progress is not.
Reply to
Dave Hansen

When you are using a PIC with limited stack space, you have to check for yourself that you are not calling too many levels deep. You cannot program as if you were writing for a PC when you do embedded systems programming. It is worth noting that if you use C, the CCS compiler (and probably most others too) will analyze the calling tree and report the depth of stack used. Also, a C compiler will often optimize away a call by replacing it with a goto or by placing the called function inline.

-Robert Scott Ypsilanti, Michigan

Reply to
Robert Scott

Yow!

YES!

If memory reads/writes on PICs are not reliable, then you bloody well better be concerned.

If memory reads/writes aren't reliable it really doesn't matter what sort of code you write. Might well just fill the code space with NOOPs and call it done.

--
Grant Edwards                   grante             Yow!  It's so OBVIOUS!!
                                  at               
 Click to see the full signature
Reply to
Grant Edwards

Yes indeed. What are you (the OP) talking about? If your micro can't read and write it's own memory, you're pretty well screwed no matter what kind of code you write...

Bob

Reply to
Bob Stephens

Many a PIC can't read or write its own code memory, being Hahvahd and all.

Best regards, Spehro Pefhany

--
"it's the network..."                          "The Journey is the reward"
speff@interlog.com             Info for manufacturers: http://www.trexon.com
 Click to see the full signature
Reply to
Spehro Pefhany

;-) Well, it's not in the data memory space.

Best regards, Spehro Pefhany

--
"it's the network..."                          "The Journey is the reward"
speff@interlog.com             Info for manufacturers: http://www.trexon.com
 Click to see the full signature
Reply to
Spehro Pefhany

The nice thing about this feature is that it does not matter from where you call a subroutine, when you return you always return to the same address :-)

Regards Anton Erasmus

Reply to
Anton Erasmus

"For the ultimate in deterministic behavior..."

--
Grant Edwards                   grante             Yow!  Eisenhower!! Your
                                  at               mimeograph machine upsets
 Click to see the full signature
Reply to
Grant Edwards

If you are just toying around, why are you using CPUs with a lot of limitations? Waste of time... A CPU with a stack and 512-1024 byte of SRAM will be virtually unlimited for assembly CALLs.

--
Best Regards,
Ulf Samuelsson
 Click to see the full signature
Reply to
Ulf Samuelsson

If you prohibit recursion then some stuff like that might actually be possible.

Best regards, Spehro Pefhany

--
"it's the network..."                          "The Journey is the reward"
speff@interlog.com             Info for manufacturers: http://www.trexon.com
 Click to see the full signature
Reply to
Spehro Pefhany

___ Here's a snippet from the datasheet for the 16F688 PIC:

From page 19 of 16F688 datasheet:

"2.3.2 STACK The PIC16F688 family has an 8-level x 13-bit wide hardware stack (see Figure 2-1). The stack space is not part of either program or data space and the stack pointer is not readable or writable. The PC is PUSHed onto the stack when a CALL instruction is executed or an interrupt causes a branch. The stack is POPed in the event of a RETURN, RETLW or a RETFIE instruction execution. PCLATH is not affected by a PUSH or POP operation. The stack operates as a circular buffer. This means that after the stack has been PUSHed eight times, the ninth push overwrites the value that was stored from the first push. The tenth push overwrites the second push (and so on).

Note 1: There are no Status bits to indicate stack overflow or stack underflow conditions.

2: There are no instructions/mnemonics called PUSH or POP. These are actions that occur from the execution of the CALL, RETURN, RETLW and RETFIE instructions or the vectoring to an interrupt address."

Looks like it's located in Netherland and can't be seen or touched. Jest watch your CALLS and INTS, Matey. ARGGGH!

Reply to
Charles Jean

All this is true for Atmel ATMega too. And the C development is much cheaper and has a vera nice IDE: eclipse.

Regards, Kurt

--
Kurt Harders
PiN -Präsenz im Netz GITmbH
 Click to see the full signature
Reply to
Kurt Harders

Eclipse baffles me. There are thousands of downloadable items, but there is no obvious distinction between complete standalone programs vs plugins or what-have-you. You have to know the secret code name identifying whatever project you're interested in, and guess from the written-by-cognoscenti documentation what else is required.

I was told it's a great IDE for working on embedded C projects, but after downloading a couple of hundred megabytes of files, I've yet to get it to do anything at all. Typical of Java software, really.

Reply to
larwe

ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here. All logos and trade names are the property of their respective owners.