View previous topic :: View next topic |
Author |
Message |
object01
Joined: 13 May 2004 Posts: 90 Location: Nashville, TN
|
String Theory |
Posted: Mon Jun 07, 2004 2:58 pm |
|
|
This is a kind of nebulous question... I'm trying to improve my understanding of how strings are best included in a program. I've been through a lot of posts on the subject but am having trouble assimilating them all.
Part 1
Code: | char myString[] = "0123456789";
void myFunction(char stringChar) {
// ...
}
void main {
myFunction(myString);
} |
What are the RAM/ROM implications of the above? Am I correct in thinking that,
- myString is stored in RAM
- There is no considerable overhead involved in storing/reading myString
Part 2
Code: | void myFunction(char stringChar) {
// ...
}
void main {
myFunction("0123456789");
} |
Am I correct in thinking that:
- The string literal in the call to myFunction is stored in ROM
- There is a considerable overhead involved in storing/reading the string literal?
Part 3
Code: | char myString1[] = "0123456789";
char myString2[] = "9876543210";
char myStringCat[] = "0123456789\09876543210\0"; |
Am I correct in thinking that there is more overhead in storing two strings using separate declarations than in using a single declaration and referencing by offset?
Part 4
Code: | void main {
myFunction_1("0123456789");
myFunction_2("0123456789");
} |
Does the compiler consolidate the two identical string literals into one ROM location?
More as I think of it...
--
Jeff S. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Tue Jun 08, 2004 11:28 am |
|
|
The questions you ask can be answered by compiling a sample
program, and then examining the .LST file and the Program Memory
window in MPLAB. |
|
|
Ttelmah Guest
|
Re: String Theory |
Posted: Tue Jun 08, 2004 11:48 am |
|
|
object01 wrote: | This is a kind of nebulous question... I'm trying to improve my understanding of how strings are best included in a program. I've been through a lot of posts on the subject but am having trouble assimilating them all.
Part 1
Code: | char myString[] = "0123456789";
void myFunction(char stringChar) {
// ...
}
void main {
myFunction(myString);
} |
What are the RAM/ROM implications of the above? Am I correct in thinking that,
- myString is stored in RAM
- There is no considerable overhead involved in storing/reading myString
Part 2
Code: | void myFunction(char stringChar) {
// ...
}
void main {
myFunction("0123456789");
} |
Am I correct in thinking that:
- The string literal in the call to myFunction is stored in ROM
- There is a considerable overhead involved in storing/reading the string literal?
Part 3
Code: | char myString1[] = "0123456789";
char myString2[] = "9876543210";
char myStringCat[] = "0123456789\09876543210\0"; |
Am I correct in thinking that there is more overhead in storing two strings using separate declarations than in using a single declaration and referencing by offset?
Part 4
Code: | void main {
myFunction_1("0123456789");
myFunction_2("0123456789");
} |
Does the compiler consolidate the two identical string literals into one ROM location?
More as I think of it...
--
Jeff S. |
Part 1, has the data stored initially in ROM, and copied into the RAM, when the declaration instruction is reached. The overhead of reading from ROM, depends on the chip. On the latter flash chips, there is a function that allows an individual address to be read for a relatively small overhead. On the older chips, the data instead has to be stored as RETLW instructons, with a table setup and jump.
Part 2, won't work.
This involves trying to pass a string pointer to a function. Pointers are not allowed to constant strings.
You can code to send a constant string to a function, be rewriting the function to accept single characters, rather than a string. Then the compiler automatically codes to fetch each character in turn, and repeatedly call the function.
When constant strings are stored, a 'header' is attached to each string, that handles generating the offset, and fetching the character at this location.
A similar time overhead exists for RAM, when accessing using a pointer, or a variable address. However access to constant locations, is a single instruction. So:
chr=string[4];
Involves just loading the register 'chr', with the contents of a known address in memory.
chr=string[variable], or an access using pointers, involves the compiler taking the address of the start of the string in RAM, adding 'variable' to it, putting this into a processor register to give indirect addressing, and then reading the resultant byte.
Another poster, has suggested looking at the generated assembler, and this is well worth doing.
Best Wishes |
|
|
bcs99
Joined: 22 Nov 2003 Posts: 32
|
|
Posted: Wed Jun 16, 2004 10:20 am |
|
|
Ttelmah,
Sorry for interrupting but I was wondering if you could explain this statement in more detail?
Quote: |
You can code to send a constant string to a function, be rewriting the function to accept single characters, rather than a string. Then the compiler automatically codes to fetch each character in turn, and repeatedly call the function.
|
Bob |
|
|
object01
Joined: 13 May 2004 Posts: 90 Location: Nashville, TN
|
|
Posted: Wed Jun 16, 2004 10:51 am |
|
|
You can find CCS's documentation on the "feature" he's referring to in the CCS Compiler Documentation under "Function Definitions."
It's basically a workaround / special-case CCS implemented to make passing constant strings to functions a possibility.
--
Jeff S. |
|
|
burnsy
Joined: 18 Oct 2003 Posts: 35 Location: Brisbane, Australia
|
|
Posted: Thu Oct 21, 2004 8:08 pm |
|
|
This might help. A little software I wrote recently which compacts strings for storage and retrieval in PIC ROM.
http://www.ccsinfo.com/forum/viewtopic.php?t=20782
Comments appreciated.. _________________ This is the last code change until its ready.... |
|
|
BoostC
Joined: 21 Oct 2004 Posts: 2
|
Re: String Theory |
Posted: Thu Oct 21, 2004 8:34 pm |
|
|
object01 wrote: | This is a kind of nebulous question... I'm trying to improve my understanding of how strings are best included in a program. I've been through a lot of posts on the subject but am having trouble assimilating them all.
Part 1
Code: | char myString[] = "0123456789";
void myFunction(char stringChar) {
// ...
}
void main {
myFunction(myString);
} |
|
From ANSI C point this code should not compile at all since there is no conversion from 'char[11]' (or 'char*') that is used in the call to 'char' that is the actual type of the function argument. The code should look more like:
Code: | char myString[] = "0123456789";
void myFunction(char *stringChar) {
// ...
}
void main {
myFunction((char*)myString);
} |
Regards,
Pavel |
|
|
Guest
|
Re: String Theory |
Posted: Thu Oct 21, 2004 9:37 pm |
|
|
BoostC wrote: | From ANSI C point this code should not compile at all since there is no conversion from 'char[11]' (or 'char*') that is used in the call to 'char' that is the actual type of the function argument. The code should look more like: |
Well, fair enough, but ANSI also permits pointers to constant strings as function parameters, which PCH doesn't support. The construct mentioned is a workaround that they mention in their documentation.
--
Jeff S. |
|
|
|