Hallo zusammen,
ich möchte an eine Funktion, die strings in einer besonderen Weise
vergleicht, zwei Parameter übergeben. Und zwar einmal einen Pointer auf
ein Array von char und der andere Parameter soll direkt im Aufruf
stehen.
Leider wird der andere string nicht korrekt übergeben.
Mein Programm sieht so aus:
1
intFunktion(char*string1,char*string2)
2
{
3
charstr1[30],str2[30];
4
5
strcpy(str1,string1);
6
strcpy(str2,string2);
7
8
//hier werden str1 und str2 verarbeitet und return-Wert erzeugt
9
10
}
11
12
voidmain()
13
{
14
charinBuf[30];
15
inta;
16
17
strcpy(inBuf,"hallo");
18
19
a=Funktion(&"hallo",inBuf);
20
}
Das ganze läuft auf einem Pic mit CCS compiliert, aber das dürfte
eigentlich für das Problem egal sein.
Das Problem ist, dass die Übergabe des Konstantenarray nicht
funktioniert, in der Funktion steht in str2 dann hallo drin und str1 ist
leer.
Hat jemand eine Idee, woran das liegen kann? Wie übergibt man in C
Pointer auf implizit definierte Konstanten richtig?
Am liebsten wäre mir eine so einfache Übergabe wie an printf.
Etwa so: Funktion("hallo", inBuf);
Wie muss dann die Funktion aussehen?
Grüße,
Peter
Peter Diener wrote:
> [...] zwei Parameter übergeben. Und zwar einmal einen Pointer auf> ein Array von char
Nein, das möchtest du sicherlich nicht :-]
Du willst ja nicht den Zeiger selbst, also die 'Adressvariable' haben,
sondern das, wodrauf sie zeigt, entsprechend reicht ein einfaches
'Verzeigern'.
> Hat jemand eine Idee, woran das liegen kann? Wie übergibt man in C> Pointer auf implizit definierte Konstanten richtig?
Garnicht. In deinem Fall: Wenn du eine Konstante à la "ABC" angibst, ist
das schon ein Zeiger (naja, fast), nämlich einer, der irgendwo auf eine
Stelle im Speicher zeigt, an der ABC steht.
> Am liebsten wäre mir eine so einfache Übergabe wie an printf.> Wie muss dann die Funktion aussehen?
Genau so :-)
Den Compiler stört meiner Ansicht nach eher, dass die Konstante vom Typ
const ist, aber Funktionsparameter nicht const sein dürfen. Ich habe
auch schon ein Typcasting ausprobiert, compiliert auch, funktioniert
aber genausowenig:
Funktion( (char*) "hallo", inBuf);
Grüße,
Peter
Peter Diener wrote:
> Den Compiler stört meiner Ansicht nach eher, dass die Konstante vom Typ> const ist, aber Funktionsparameter nicht const sein dürfen.
Wo hast du denn das her?
>&"hallo"
Welche Adresse hat "hallo" denn?
>> Den Compiler stört meiner Ansicht nach eher, dass die Konstante vom Typ>> const ist, aber Funktionsparameter nicht const sein dürfen.
deine Schlußfolgerung ist falsch.
>Dann bekomme ich einen Fehler vom Compiler:>Attempt to make Pointer to a constant.
Das ist ein RAM/Flash Problem. Kenn ich vom C18.
a = Funktion("hallo", inBuf);
Übergibt vermutlich einen Zeiger auf die Konstante
"hallo" die im Flash liegt! Also anders als beim AVR-GCC
wo "hallo" im RAM liegen würde.
int Funktion (char* string1, char* string2)
Die Funktion erwartet den Zeiger im RAM!
Deshalb gibt es die Fehlermeldung.
@holger: Ja, so sehe ich das auch. Aber printf gibts ja auch beim CCS
Compiler und der Aufruf ist einfach so:
printf("Sag was...");
Irgendwie muss man die Funktion doch definieren können, dass das geht,
oder?
Peter
>@holger: Ja, so sehe ich das auch. Aber printf gibts ja auch beim CCS>Compiler und der Aufruf ist einfach so:>printf("Sag was...");>Irgendwie muss man die Funktion doch definieren können, dass das geht,
int Funktion (const char* string1, char* string2)
oder
int Funktion (const rom char* string1, char* string2)
Aber dann gibt es möglicherweise Ärger mit strcpy() :(
strcpy kann Konstanten und Variablen als source, das steht auch in der
Doku. Und const darf ich in der Funktionsdeklaration nicht erwähnen,
sonst compiliert es nicht mehr (mit irgendeiner nicht nachvollziehbaren
Fehlermeldung - identifier expected - und zeigt auf eine Stelle nach
const).
Mittlerweile hab ich es auch mit einem gcc ausprobiert und da gehts
einfach mit const in der Funktion, das hilft nur leider nicht.
Edit: ohne const, einfach so wie vorher.
Peter
>So zum Beispiel:>int addiere(int a, int b) {> return a + b;>}>>int main() {> printf("%i\n", addiere(1, 2));>}
Ja, das geht.
Aber wie wäre es mit:
1
intaddiere(constinta,constintb)
2
{
3
returna+b;
4
}
5
6
intmain()
7
{
8
printf("%i\n",addiere(1,2));
9
}
So habe ich Holgers Post verstanden...
Ich weiß nicht, ob mir da spezielles C-Wissen fehlt, aber mein Verstand
sagt mir, dass das Blödsinn ist.
Ich übergebe einer Funktion ja eine Variable, damit ich sie mit
unterschiedlichen Werten benutzen kann.
Dabei ist Funktion("Hallo",&s); ein Aufruf von vielen möglichen...
Ich weiß nicht, wie der Compiler "konstante" Strings umsetzt - ich
vermute aber, dass er aus dem konstanten Text ein char-Array macht und
dessen Pointer an die Funktion übergibt.
Vielleicht liege ich aber auch daneben (mit meiner
"const"-Parameter-Meinung). Vielleicht liegt es aber auch an Compilern
von Controllern, die ich nicht mag. (ACHTUNG! Meine persönliche
Meinung!!!)
Ich habe mittlerweile im Manual gefunden, dass es nicht geht, eine
Adresse eines Konstantenarrays zu erzeugen.
Das Problem wird beim direkten Adressieren eines Arrays
i = array[5];
durch ein Makro gelöst
und bei Funktionsaufrufen wie
printf("hallo");
mit irgendetwas, was nicht im Quellcode veröffentlicht wird.
Dass das nich geht, liegt angeblich an der Architektur vom Pic, wobei
Flash und Ram so strikt getrennt sind, dass keine Pointer auf das Flash
erzeugt werden können. Ganz nachvollziehen kann ich das allerdings
nicht, der Compiler könnte das doch mühelos erledigen, ich erwarte ja
nicht, dass das in Echtzeit passiert. Deswegen sind die Parameter ja
Konstanten, da sind die Adressen ja schon dem Compiler bekannt. Daher
verstehe ich das Problem nicht wirklich.
Es ist aber wohl so, dass die Parameter auf den Stack müssen, und der
ist nunmal im Rambereich, und wenn dort die Adresse der Daten aus dem
Flash steht, kann damit keine Adressierung durchgeführt werden. Oder so
in etwa...
Eine Alternative für meine Funktion wäre ein Makro. Weiß jemand, wie ich
in C ein Makro mit Parametern schreibe?
Grüße,
Peter