|
|
View previous topic :: View next topic |
Author |
Message |
sandyw1963
Joined: 30 Nov 2006 Posts: 7 Location: Wick, Scotland
|
INCF problem from CCS compiler listings |
Posted: Thu Nov 30, 2006 8:28 am |
|
|
Hello,
Can any body offer up any comments on the following code and why it should stop working after about 10-15 mins running time.
.................... /* ************************************************************************* *
.................... *
.................... * Name : locate_field
.................... *
.................... * Description :
.................... *
.................... * !<function>
.................... * This routine locates a field within a message. The field starts at initial,
.................... * and is ended with the separator.
.................... * !</function>
.................... *
.................... * Returns Description
.................... * ------- -----------
.................... * char * beginning of new field
.................... *
.................... * ************************************************************************* */
.................... static char *locate_field (char *initial, char separator, char terminator)
.................... {
.................... {
.................... bool valid = true;
*
2A8A: MOVLW 01
2A8C: MOVLB 8
2A8E: MOVWF xF9
.................... char *field = NULL;
2A90: CLRF xFA
2A92: CLRF xFB
....................
.................... while (*initial != separator)
.................... {
2A94: MOVFF 8F6,03
2A98: MOVFF 8F5,FE9
2A9C: MOVFF 8F6,FEA
2AA0: MOVF xF7,W
2AA2: SUBWF FEF,W
2AA4: BZ 2AC4
.................... if (*initial == terminator)
2AA6: MOVFF 8F6,03
2AAA: MOVFF 8F5,FE9
2AAE: MOVFF 8F6,FEA
2AB2: MOVF xF8,W
2AB4: SUBWF FEF,W
2AB6: BNZ 2ABC
.................... {
....................
.................... valid = false;
2AB8: CLRF xF9
....................
.................... break;
2ABA: BRA 2AC4
.................... }
.................... initial++;
2ABC: INCF xF5,F
2ABE: BTFSC FD8.2
2AC0: INCF xF6,F
.................... }
2AC2: BRA 2A94
As I understand it looking at the assembler output it works in the following way.
The value 1 is stored in the W register.
The value 8 is stored in the bank select register.
The value 1 is stored in the register 8F9 (bank select register = 8 (Thanks Ttelmah for this piece of info)).
The value in register 8F6 is stored in register 03.
The value in register 8F5 is stored in register FE9, the low byte of the FSRo register.
The value in register 8FA is stored in register FEA, the High byte of the FSRo register.
The value in register 8F7 is stored in the W register.
The W register is then subtracted form the value in the register pointed to by the high and low bytes in the FRS registers.
If result is zero goto address 2AC4 if not carry on.
The same argument follows for the next section of code upto and including address 2AB6 and at this point if the W and pointed to registers are not the same we jump to address 2ABC.
Code at address 2AB8 nd 2ABA are fairly self explanitory.
The next section is the part I have a problem with.
As I understand it ,it works as follows
.................... initial++;
2ABC: INCF xF5,F
Increment the value stored in 8F5 and store in 8F5
2ABE: BTFSC FD8.2
If the value in 8F5 <> 0 then skip one command
2AC0: INCF xF6,F
else increment the value in 8F6
2AC2: BRA 2A94
Go back to the start.
However, when I'm at location 2ABC in the code and look at the RAM location 8F5 and step through the code after INCF xF5,F operation location 8F5 does not increment no matter how many times I step round the loop. The code does work for about 10-15 mins as I've said but then stops.
Any pointers as to whats wrong??
I'm using compiler version 3.238 and CCS usb idc-u40 and there PIC18F8722 prototype board. |
|
|
Ttelmah Guest
|
|
Posted: Thu Nov 30, 2006 10:10 am |
|
|
Before looking at the problem. What are you doing with 'field'?.
CCS, does not understand, or have any handling for the idea of a 'null pointer'. 'NULL', is just defined as zero, so you are setting this pointer to '0'. Any I/O to this, will result in part of the scratch memory being overwritten...
Now that having been said (the use of this is presumably in part of the code you don't show), what compiler version, and what debugging tools?. There have been some problems in the past, with some debugging tools not reflecting what is really happening. Look at the .sym file. What address is 'initial' shown as being at?. If you are in a debugger at address 2ABC, what does the BSR hold?.
Best Wishes |
|
|
sandyw1963
Joined: 30 Nov 2006 Posts: 7 Location: Wick, Scotland
|
|
Posted: Fri Dec 08, 2006 9:57 am |
|
|
Hello ThTtelmah,
Sorry for the delay in answering your reply.
The purpose of the code is that there is a packet received in the RS232 port and this code than steps through the packet to find the start of the various fields in the packet i.e. "for", "to", "data" etc.
First point, sorry but the use of *field was in a section of code I didn't post so here's the full function
static char *locate_field (char *initial, char separator, char terminator)
{
bool valid = true;
char *field = NULL;
while (*initial != separator)
{
if (*initial == terminator)
{
valid = false;
break;
}
initial++;
}
if (valid)
{
field = initial + 1;
*initial = '\0';
}
return (field);
}
field cointains the start of the next section in the packet.
As far as I can tell "initial" is stored in locations 8F5 and 8F6 according to both the code and the .sym file.
The BSR holds the value 0x00
I'm using compiler version 3.238 and CCS usb idc-u40 and their PIC18F8722 prototype board.
thank you again for your help
Sandyw1963 |
|
|
Ttelmah Guest
|
|
Posted: Fri Dec 08, 2006 12:40 pm |
|
|
You are still not showing what you are actually _doing_ with field outside. The danger is that CCS, does not understand the 'idea' ofa NULL pointer. If such a pointer is returned, and is not trapped, any attempt to write to a NULL pointer, will destroy part of the compiler scratch area (which starts at '0'). This will kill the program.
Whay does the BSR hold 0 at 2ABC?. Step through from 2A8A, and see where it changes. Itt has been set to 8, and nothing shown should change it...
Best Wishes |
|
|
sandyw1963
Joined: 30 Nov 2006 Posts: 7 Location: Wick, Scotland
|
|
Posted: Mon Dec 11, 2006 4:29 am |
|
|
I'm not sure what you mean by "returned and not trapped". The attached section of code shows how the function is used:
message->from = locate_field (message->to, FIELD_SEPARATOR, '>');
if (message->from != NULL)
{
message->length = locate_field (message->from, FIELD_SEPARATOR, '>');
if (message->length != NULL)
{
message->command = locate_field (message->length, FIELD_SEPARATOR, '>');
if (message->command != NULL)
Also the BSR is being corrupted some where in the code but I've no idea where. It is not in the locate_field function posted previously as I've stepped through this and no where does it change the BSR. After the BSR is corrupted the INC etc in the locate_field function continues to increment the data areas pointed to by the new BSR which "appears" to be always set to 0x00.
could writing to the compilers scratch area corrupt the BSR?
Thanks again for your help. |
|
|
sandyw1963
Joined: 30 Nov 2006 Posts: 7 Location: Wick, Scotland
|
|
Posted: Mon Dec 18, 2006 3:51 am |
|
|
Problem found!
Too much computation in an interrupt handler. Basic I know but there you are.
It appears that it is corrupting the BSR. Once we moved some computation out of the isr all is well.
Thank you for your help along the way
Sandyw |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|