Forum Menu




 


Log in Problems?
New User? Sign Up!
AVR Freaks Forum Index

Post new topic   Reply to topic
View previous topic Printable version Log in to check your private messages View next topic
Author Message
The_Dutchman
PostPosted: Feb 24, 2012 - 03:37 PM
Newbie


Joined: Nov 15, 2011
Posts: 19


Hello,

I'm writing a quite complex program based on a FSM from
http://www.gedan.net/2009/03/18/finite-state-machine-matrix-style-c-implementation-function-pointers-addon/

I use it for touchscreen navigation between menus.
It uses a function pointer to call void function(void) functions to do an action.

When the action is executed and finished, I don't return to the main loop, but get a reset. It seems that the AVR is forgetting where to return to. So the stack pointer has the wrong value I suppose? Is there any way I can fix this?

main calls stateEval calls action using function pointer calls some subfunctions of action. So it is 4 levels of calling.
 
 View user's profile Send private message  
Reply with quote Back to top
clawson
PostPosted: Feb 24, 2012 - 03:53 PM
10k+ Postman


Joined: Jul 18, 2005
Posts: 62348
Location: (using avr-gcc in) Finchingfield, Essex, England

As I peer into my crystal ball I see a mega64 or mega128 operating in mega103 mode.

Am I right? Do I win the £5?

(if I'm wrong it could still be code built for the wrong target).

BTW from the article you linked:
Code:
void main() {
     void (*fp)();
    fp functionPointer = function_a;
    (*fp)();  //prints "a"
    fp functionPointer = function_b;
    (*fp)();  //prints "b"
}

It seems to me the first line of main() is missing the word typedef? They also use the fn_ptr in a cumbersome way, I'd go with:
Code:
typedef void (*fp)(void);

int main(void) {
    fp functionPointer = function_a;
    fp();  //prints "a"
    functionPointer = function_b;
    fp();  //prints "b"
}

_________________
 
 View user's profile Send private message  
Reply with quote Back to top
The_Dutchman
PostPosted: Feb 24, 2012 - 03:57 PM
Newbie


Joined: Nov 15, 2011
Posts: 19


I can't post
 
 View user's profile Send private message  
Reply with quote Back to top
clawson
PostPosted: Feb 24, 2012 - 03:58 PM
10k+ Postman


Joined: Jul 18, 2005
Posts: 62348
Location: (using avr-gcc in) Finchingfield, Essex, England

You are trying to post % signs - replace them with % instead.

_________________
 
 View user's profile Send private message  
Reply with quote Back to top
skeeve
PostPosted: Feb 24, 2012 - 03:58 PM
Raving lunatic


Joined: Oct 29, 2006
Posts: 2654


Does avrfreaks have information on pseudo-resets where a beginner is likely to find it?

_________________
Michael Hennebry
Iluvatar is the better part of Valar.
 
 View user's profile Send private message  
Reply with quote Back to top
The_Dutchman
PostPosted: Feb 24, 2012 - 04:06 PM
Newbie


Joined: Nov 15, 2011
Posts: 19


Ok pastebin then..
I use an ATXmega256A3B and the project settings are correct. I'm using AVRstudio 5 and the JTAGiceMK2 debugger.
As mentioned the application is a touchscreen. In my action routine I want to input settings, So detecting key presses and building the pressed number. When I leave the function fillwithspaces commented, it works. When I uncomment fillwithspaces the reset occurs.

Action function
http://pastebin.com/DUpp16Sg

Fill with spaces function
http://pastebin.com/CEgn08KH

Thanks in advance.
 
 View user's profile Send private message  
Reply with quote Back to top
clawson
PostPosted: Feb 24, 2012 - 04:13 PM
10k+ Postman


Joined: Jul 18, 2005
Posts: 62348
Location: (using avr-gcc in) Finchingfield, Essex, England

You still haven't answered the mega128 question.

Anyway not sure what those two code snippets are supposed to show. Neither appears to be using a function pointer though I can see that the second one is one of those hugely dangerous routines designed to wreak havoc. You might want to consider including something to prevent you writing beyond the limits of whatever the char * is pointing at. Just as you can do:
Code:
char text[3];
strcpy(text, "hello world");

and wreak havoc it is very unwise to use char *'s without some kind of bounds limiting mechanism. (which is why strncpy() exists)

_________________
 
 View user's profile Send private message  
Reply with quote Back to top
The_Dutchman
PostPosted: Feb 24, 2012 - 04:24 PM
Newbie


Joined: Nov 15, 2011
Posts: 19


The number I need to make is 8 numbers wide. Always. So there isn't the problem I think. I've never heard of Mega103 mode. I use the ATXMEGA256AB I did a quick search and found that mega103 mode is for mega128 devices and is set in the fuse bits?

In the "fillwithspaces" function I give the size as second parameter. So perhaps you mean that if I give the wrong size I will overwrite other important code. I guess there could be a problem with my sizes then...
 
 View user's profile Send private message  
Reply with quote Back to top
clawson
PostPosted: Feb 24, 2012 - 04:29 PM
10k+ Postman


Joined: Jul 18, 2005
Posts: 62348
Location: (using avr-gcc in) Finchingfield, Essex, England

You are right the m64/m128/m103 thing doesn't apply but we couldn't have possibly known that until you identified the AVR. It is the main reason we see on this message board for AVR programs that can CALL but that cannot RET however.

I guess I don't win £5.

Anyway I'd still suspect you are writing through a rogue pointer and corrupting other things in memory. When one of those things is a RAM based function pointer things get very nasty (which is why MISRA won't let you use them!)

_________________
 
 View user's profile Send private message  
Reply with quote Back to top
The_Dutchman
PostPosted: Feb 24, 2012 - 04:37 PM
Newbie


Joined: Nov 15, 2011
Posts: 19


I've changed

Code:

fillwithspaces(buf,9);


To

Code:

fillwithspaces(buf,8);


And it works. Is there a quick and dirty way to never make this mistake again? Digging up the strcpy() function and looking at its protection perhaps. Or is it wrong to pass the address?
 
 View user's profile Send private message  
Reply with quote Back to top
dkinzer
PostPosted: Feb 24, 2012 - 06:15 PM
Posting Freak


Joined: Mar 12, 2004
Posts: 1205
Location: Portland, OR, USA

The_Dutchman wrote:
And it works. Is there a quick and dirty way to never make this mistake again?
The change prevented fillwithspaces() from overwriting whatever follows the buffer in RAM. You can avoid issues like this if you use the sizeof operator, e.g.:
Code:
char myBuf[9];
...
fillwithspaces(myBuf, sizeof(myBuf) - 1);
The -1 allows for the fact fillwithspaces() writes a null following the specified number of spaces.

Alternately, you could modify fillwithspaces() so that it writes one fewer space than the supplied parameter value, filling the last byte with a null.

_________________
Don Kinzer
ZBasic Microcontrollers
http://www.zbasic.net
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
clawson
PostPosted: Feb 24, 2012 - 06:23 PM
10k+ Postman


Joined: Jul 18, 2005
Posts: 62348
Location: (using avr-gcc in) Finchingfield, Essex, England

When you pass a char* (or anything* in fact)then as long as you pass the max length of the destination the routine can be written to stop before it would write beyond the valid space the pointer is pointing to.

That's how strncpy() differs from strcpy(). There's an additional parameter to say "come what may don't write more than this many bytes to the destination pointer". Inside the routine every time you p++ you dest_len-- and if it reaches 0 you return. You might also want to return a code to say "gave up early because length limit reached".

_________________
 
 View user's profile Send private message  
Reply with quote Back to top
Koshchi
PostPosted: Feb 24, 2012 - 09:24 PM
10k+ Postman


Joined: Nov 17, 2004
Posts: 13848
Location: Vancouver, BC

But you still need to pass in a valid value for the number of elements. If you tell strncpy() to copy a max of 20 bytes when the pointer only holds 10, you are still in trouble.

_________________
Regards,
Steve A.

The Board helps those that help themselves.
 
 View user's profile Send private message  
Reply with quote Back to top
Display posts from previous:     
Jump to:  
All times are GMT + 1 Hour
Post new topic   Reply to topic
View previous topic Printable version Log in to check your private messages View next topic
Powered by PNphpBB2 © 2003-2006 The PNphpBB Group
Credits