|
|
View previous topic :: View next topic |
Author |
Message |
gokul.ftpl
Joined: 05 May 2006 Posts: 6
|
Error:attempt to create a pointer to a constant |
Posted: Thu Nov 02, 2006 5:13 am |
|
|
This code generates an error but that works fine in an ansi c complaint compiler
Code: |
void Test(char *str){
char Next_Line='\n';
char Prev_Line='\p';
char Tab_Space='\t';
unsigned int i;
while(*str!='\0'){
if(*str == Next_Line){
str++;
printf("\n Found Next_line");
}
else if (*str == Prev_Line){
printf("\n Found prev_Line");
str++;
}
else if (*str == Tab_Space){
printf("\n Found Tab Space");
str++;
}
printf("%c",*str);
str++;
}
return;
}
int main()
{
Test("Hello \n \p \t");
return 0;
}
|
but this one works fine
Code: |
int main()
{
char str[] ="Hello \n \p \t";
Test(str);
return 0;
}
|
can any one tell me why this happens
[/quote]
|
|
|
Ttelmah Guest
|
|
Posted: Thu Nov 02, 2006 5:46 am |
|
|
Worth reading the manual...
A search under 'constant', or 'pointer to constant', will find a description of this.
The key is that the PIC, has a Hoffman memory architecture, with separate memory 'spaces' for the code memory, and the variable memory. Now on the older PICs, the code memory is not even accessible for data storage by the program, so if you define a 'constant' string, it is implemented as a program to return the data, rather than as addressable storage locations, and cannot be directly accessed. CCS, elected on this basis, to have no provision to access this memory, and 'pointers' only access the variable memory. Latter chips do allow the memory to be accessed, but as yet the old restriction remains in place for CCS code.
When you declare:
"This is a test"
This is constant data. The declaration:
char fred[]="This is a test";
Actually creates program to return the data string, and the code to call this, and copy it into the RAM storage addressed by 'fred'. Once the data is in this RAM, it can then be accessed by a pointer.
You can also use the 'strcpy' function to access such constants, so once one RAM string area is defined, you can use:
strcpy(fred,"Another");
To put a different message into the same area, and save RAM.
As an 'aside', CCS, have an extra 'shortcut', that can be used to avoid the need to copy the data into RAM for such accesses. If you have an output function like 'putc', which accepts single characters, you can use:
putc("This is a test");
and the compiler will automatically call the program to retrieve the bytes, and then send these sequentially to the output program.
The decision not to allow pointer access to the ROM, reduces code size, and pointer sizes. Allowing this is a feature that is due to be 'added' to the latest compilers (with an option to turn it on/off), but does not yet work properly.
Best Wishes |
|
|
gokul.ftpl
Joined: 05 May 2006 Posts: 6
|
Re:Error:attempt to create a pointer to a constant |
Posted: Thu Nov 02, 2006 7:21 am |
|
|
Thank you for your reply i tried with the alternative shortcut which you have specified and it was working fine |
|
|
jimbo Guest
|
Re:Error:attempt to create a pointer to a constant |
Posted: Tue Nov 07, 2006 3:44 pm |
|
|
I like your tip on turning a char routine into a string.
I used it as follows:
serPutByte("Hello World");
Q1: But my problem is: The NULL comes out. Is there a way to avoid that?
Q2: Is strcpy() written in assembly? what I need is a strcat() that works like strcpy(). Eg takes a constant...
strcpy(buf,"Hello ");
strcat(buf,"World"); //Attempt to make a pointer to a constant
Any ideas? I tried the manual (ccsc.exe/? If that is what you mean?).
Rgds,
Jim Pruett |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Tue Nov 07, 2006 5:27 pm |
|
|
Quote: | serPutByte("Hello World");
Q1: But my problem is: The NULL comes out. Is there a way to avoid that? |
The code does not send the null. Look at the ASM code from the .LST
file below. The code looks for the null (0x00) at the end of the string.
When it finds the null, it exits from the loop. It doesn't send the null.
Code: | ... serPutByte("Hello World");
002D: CLRF 21 // Set index = 0
002E: MOVF 21,W // Put index into W
002F: CALL 004 // Call routine to get chars
0030: IORLW 00 // OR the char with 0x00
0031: BTFSC 03.2 // Is the char == 0 ?
0032: GOTO 037 // Jump to 037 if so
0033: INCF 21,F // If not, increment the index
0034: MOVWF 22 // Put char in temp variable
0035: GOTO 014 // Call routine to transmit char
0036: GOTO 02E // Go back to start of loop |
|
|
|
carterson2
Joined: 27 Aug 2006 Posts: 5 Location: Memphis
|
|
Posted: Wed Nov 08, 2006 8:16 am |
|
|
Thanks for that. I still think an extra char comes out, but your snippet says no. hmmm.
Anywho, what I learned from this thread is:
printf() has a very very small footprint. I just replaced all strcat's with it!!!!
I love it!
Historically I never even considered using stdio.h (until now!) Its always a big clunky libc.a or such. NOW I WILL! Thanks CCS!
(I approve this message ;-)... |
|
|
|
|
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
|