I'm quite new to context switch and embedded software development. I'm developing a standalone application (no OS) with aduc7026 and keil uVision3. My problem is that at the end of an uart messagge, which I must receive by interrupt, depending on the content of the messagge I've to return return in main in the state saved before entering in the ISR or I've have to return in a specified point where a funcion call is executed.
Hoping that I've been clear. Does anyone have suggestions?
Thank ìs in advance,
Matteo
I've have to return in a specified point where a funcion call is executed.
And no, you almost certainly ... should [not] be be trying to at this point on your learning curve.
I would say this has nothing to do with the "point on your learning curve". I know of no technique that can do this safely, at least in C. I can visualize some "monkey code" in assembler that might make it 'work' in a non-mainatinable way.
Erik
So I should implement a context switch to a specified point in assembly and add it to the c code? In the assembly code I should save the state in the specific point where I want to retur if specific messagge is received. Then if the messagge arrives I should Pop the stack with the saved information for the state where the interrupt wants to come back and load the state saved and set the program counter to the address of the saved state? Does This work and recover main from hangs? Don't care about the manteinment and portability of the code.
So I should implement a context switch to a specified point in assembly and add it to the c code?
No, you shouldn't. And I find it really hard to see how you arrived at that conclusion from the advice you've been given here. It's a Bad Idea(no TM).
You appear to be going at this from entirely the wrong angle. The cure you're trying so very hard to administer is almost certainly worse than the possible problem you're worried about. It's quite possible that this crazy technique not only won't help if main is unstable, but it's actually going to make it unstable.
I understood all of your suggesttions and i'm gratefull to all. However my supervisor insist to force me to the inyours opinions bad solution... So i'll have meeting with it tomorrow where I can spek with it about other possible solutions... Thanks to all Matteo
10 tips.
1 state machine. 2 state machine 3 state machine 4 state machine 5 state machine 6 state machine 7 state machine 8 state machine 9 state machine 10 stat machine
The loop running the state machine steps will not hang unless you introduce bugs or the hardware suffers problems.
Long tasks can be splitted into multiple steps, making them breakable before they are fully done.
Task switches are for running multiple jobs concurrently - most environments cant survive that you kill/restart at arbitrary place becauce of atomicity reasons.
If you still manage to.hang your main loop, then you have no real option but a (watchdog) reset. The reason is that you have then managed to put the processor in a state where it can't be trusted.
The choice is yours. Solving a problem the established way, or assume your problem is unique and implement a spaghetti failure you will spend the next couple of years trying to get reliable.
Perhaps your supervisor could come and join this discussion...?
Either you have badly misunderstood/misinterpreted what (s)he's telling you, or (s)he is giving you bad advice!
Your supervisor is either a skilled developer, or (s)he isn't.
If skilled, then I'm convinced you have misunderstood something. If not, then it's time you suggest he/she switches from supervisor to developer and implements the failure.
The closest you can expect to get directing further evaluation from an interrupt is with a RTOS. An interrupt can tell the scheduler that it should perform a rescheduling. Such a rescheduling will mean that the program doesn't return to the same place it was before the interrupt. But it does not jump to a fixed address. Instead it jump to the current location of that other thread.
So if you do get a rescheduling to a thread that was already busy with a long command, that command will have to be computed to the end (unless you have state machines within the threads). The scheduler will only switch to that thread if it had the highest priority. But if it had, then you wouldn't even need any rescheduling because then the thread was already busy with the previous command when the interrupt came.
In the end, you either have commands that are fully processed before the processor reschedules. Or you have one or more state machines, where you can force a restart of a state machine.
Note that restarting a state machine from an ISR can't be done by just assigning a new value to the state variable. The reason is that the ISR may be activated while the state machine is busy handling state x, and the state machine may after the ISR process a source line that assigns a new state, overwriting the expected new state from the ISR. So having a ISR forcing a new state should be done by setting a separate variable "force_state", and the state machine should check this variable to see if it should switch state at the top or bottom of the state machine loop. In some situations, you may even need cleanup states.
Any attempts to have an ISR force a fixed return address will end with a black eye and a bloody nose. A C compiler expects that a single thread is always executed sequentially without anything interfering. And ISR or OS scheduler must be written to be invincible. They may "pause time" for a task, but execution must return at the exact same place with all registers and relevant variables in their known states. If not, then your program will not fulfill the requirements of the C standard, and all bets are off what will really happen. You would then have introduced a number of random dices giving you percentages on an infinite number of potential failures in your code.
In reality, you will get the same if the main program is written in assembler. The reason is that no normal human developer can write code while assembler instruction by assembler instruction all the time think about the concept of the execution breaking at an arbitrary position just to jump to another position.
State machines have the advantage that they only switch action between two states. So the states can be documented. And it's possible to keep track of what happens when breaking between two states since the behaviour of the program will follow the C rules.