Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Erasing Return Address of Call

Status
Not open for further replies.

jpanhalt

Well-Known Member
Most Helpful Member
Processor: 16F1829
Language: MPASM

I am revising a major part of the code that formed the basis for my last question about "reading RA2," specifically the portion that receives 2 bytes of data with the EUSART RX . I could use GOTO/BRA's, but that complicates calibration and zeroing that use part, but not all of the section that is used for receipt of useful data. A call with various returns can also work; however, since three of the returns would be on errors, I would need to set flags and handle such returns appropriately from the calling spot.

A third option I have been playing with is to simply cancel the return address in the stack upon an error and use a GOTO/BRA instruction.
Here is what I trying to describe from my test sandbox:
Code:
Called Address
OnError
     Banksel   TOSL        ;|B31                         
     clrf      TOSL        ;|B31
     clrf      TOSH        ;|B31
     GOTO      SomewhereElse

Is that acceptable coding practice?
What if I just don't mess with TOSL/H and simply watch my calls and returns so I don't overflow the stack? (NB: No interrupts in the program)

John
 
That'll work too, but so will setting a flag on error. So often it seems there are several alternative ways, and each takes the same amount of time.

I expect the errors to be rare, testing something on return would have to be done every time. Clearing the last entry to the stack would happen only on error.

John
 
Could be problematic. You'd be leaving one level on the stack...

Cheerful regards, Mike
 
Last edited:
Removing both high and low address of calling location. What else is put on to the stack with a Call?

John
 
To remove an address from the stack you would increment the stack pointer, assuming the stack grows down.

Personally, I'd find an alternative way to do this.

Mike.
 
Well, you're just clearing the return address value, you're not really removing it. You would have to "pop" the stack (adjust the stack pointer) to remove the return address. Unfortunately, I don't believe there's any way to do that on the 'enhanced' 16F devices. Instead, why not replace the return address contained in TOSL and TOSH with the address of your error handler and 'return' to that? The error handler should set page and bank registers as required.

Doing it this way can get messy. I'd look for an alternative method...

Regards, Mike

Code:
Example Subroutine
        ~~~
        ~~~
NoError
        return                  ;                      |??
OnError
        banksel TOSL            ; bank 31              |B31
        movlw   low(handler)    ;                      |B31
        movwf   TOSL            ;                      |B31
        movlw   high(handler)   ;                      |B31
        movwf   TOSH            ;                      |B31
        return                  ;                      |B31

<added>

I stand corrected. Just spotted the STKPTR register in the datasheet (see section 3.4) so it looks like you could pop the stack and use a 'goto'...

Code:
OnError
        banksel TOSL            ; bank 31              |B31
        decf    STKPTR,F        ; pop return address   |B31
        goto    handler         ; goto error handler   |B31
 
Last edited:
Thank you both.

Mike (K8LH), I haven't tried your first method, but the second seems to work in simulation and doesn't overflow. The code in my original post did overflow, of course, when run long enough.

As for alternatives I considered, one is to use GOTO/BRA's and another is to break up the larger section of code into smaller callable units for each purpose. Thus, getting actionable data would have additional calls compared to getting the zero or initialization data. I will definitely try using STKPTR first just for a new experience, if nothing else.

Regards, John
 
No, it's incredibly bad practice - don't even consider it.

Self-modifying code is faster (in a simple non-pipeline processor) but so is sliding on a banana peel top a greased slide to hell.
 
Last edited:
Well, I have heard from authorities that it is just as difficult for a camel to pass through the eye of a needle as for a rich man to go to heaven. Based on all the "flat broke" politicians littering the American political landscape, going to hell might not be so bad.

What about all of the MCU's with boot loaders? Even Microchip has come around and allowed code to modify program space. And, I thought pushing and popping to/from the stack was a time-honored tradition for some processors.

Anyway, I did it without K8LH's code, but I saved his code for the future. It is not hard to see a use for it. My program is working, but I still don't like the lag/latency of updates. I am working on that and will show (with live video) or just the code when I get it done.

John
 
Well, I have heard from authorities that it is just as difficult for a camel to pass through the eye of a needle as for a rich man to go to heaven. Based on all the "flat broke" politicians littering the American political landscape, going to hell might not be so bad.

What about all of the MCU's with boot loaders? Even Microchip has come around and allowed code to modify program space. And, I thought pushing and popping to/from the stack was a time-honored tradition for some processors.

Anyway, I did it without K8LH's code, but I saved his code for the future. It is not hard to see a use for it. My program is working, but I still don't like the lag/latency of updates. I am working on that and will show (with live video) or just the code when I get it done.

John

We have all sinned. (in programming) It's like using goto in C. In an embedded driver in the correct context it's better and cleaner, in an applications program it's a blasphemy to the gods of structured programming. Most subtle bugs happen in the pursuit of speed and small size especially when interrupts are involved.

Glad to see you are making progress on the project. Enjoy.
 
That's how structured exception handing works in C++ and alike. At some point in the program you remember STKPTR - this is your return point. Once you figured out something went wrong, you restore STKPTR to the saved value and then GOTO to the return point. As a result, all the function calls that you may have done in between are gone - you've returned from all of them at once and got a clean start.
 
John, may I ask what you're working on, Sir? I apologize if you mentioned it in another thread that I may have missed.
 
That's how structured exception handing works in C++ and alike. At some point in the program you remember STKPTR - this is your return point. Once you figured out something went wrong, you restore STKPTR to the saved value and then GOTO to the return point. As a result, all the function calls that you may have done in between are gone - you've returned from all of them at once and got a clean start.

That's why it's a bomb that should be handled with care.
https://blogs.msdn.com/b/larryosterman/archive/2004/09/10/228068.aspx

The security exploits due the SEH are legendary.
Rule #1 Never use exceptions for normal program flow.

I will let Google say it in a thoughtful way.
**broken link removed**
 
Last edited:
John, may I ask what you're working on, Sir? I apologize if you mentioned it in another thread that I may have missed.

No apologies needed. Simply put, I get a thrill out of trying to write code to make a dumb device do what I want it to do. The project I am working on, which was started several years ago, is just a means to that end. I wanted to make a remote level that will allow me to level pallet forks attached to my tractor's loader when I cannot see them. First attempt used a thermal accelerometer (Memsic). You may recall those early attempts and the help you gave me for controlling a GLCD display. The display and sensor were wirelessly connected with XBee. It all works well, and I am still amazed by the sensitivity of that technology to tilt. Unfortunately, the bounce/vibration of the tractor gave way too much variation in the readings, even when sitting still. Ian Rogers used a different accelerometer with cranes, so maybe my experience had more to do with choice of device rather than the approach. Also, the GLCD was quite hard to see under various light conditions outside.

Nevertheless, I decided that since the lift mechanism is basically a parallelogram, I could measure a couple of angles and get to the same end result. Looked at a few angle encoder technologies (e.g., optical, capacitative, magnetic) and settled on using a magnetic encoder. Tried an Avago chip, but found the AMS AS5048 easier to use. Amazingly, it offers 14-bit resolution and is quite inexpensive (**broken link removed** ). I am using the SPI interface with the sensor to a 16F1519, which will be my sending unit. Will probably use a different chip in the end, as I won't need all the pins and capabilities of that chip. Here is a link to the prototype sensor that will attach to each of two pivots on the tractor.

The display part of the project is what I am currently working on. I anticipate serial communication via a EUSART or similar between the display and sensor. That part is done. As for the display, I wanted something like a gauge with a needle. Air-core gauges, stepper gauges, model servos have been considered. A model servo, say a digital one with 2uS dead band, is my plan B. I am quite familiar with using such servos. Right now, though, I am working on using a stepper motor that actually is used in instrument clusters of many GM cars. Post #37 here has a demo program I got working. The current program that prompted this thread simply takes the serial data from the 16F1519/AS5048, clips it to 10 or 11 bits, and drives that gauge proportionately.

Best regards, John
 
Last edited:
Ian Rogers used a different accelerometer with cranes

It's probably the same technology, but the device I use has built in intelegence.. It has an SPI interface and it spits out an analogue (linear) voltage that represents the angle... They are VERY accurate... When using the SPI interface, they can also temperature compensate!! The -30~+30 types would be better for fork truck leveling, whereas I need the -80~+80 type...

They are £38 for a one off... A bit steep, but they work!
 
As I recall, the accelerometer you linked to in another thread uses a suspended mass, as do many others. The Memsic is based on convection of a heated gas.

John
 
As I recall, the accelerometer you linked to in another thread uses a suspended mass, as do many others. The Memsic is based on convection of a heated gas.

John
Okay!! I've never used a memsic one then!!! Sorry, I thought they were all basically the same!
 
Status
Not open for further replies.

New Articles From Microcontroller Tips

Back
Top