String parsen -> strcmp funktioniert nicht

OP #1076846
Hallo Leute,

ich möchte einen String parsen, der z.B. in der Form "$first=88\r99" 
vorliegen kann. Merkwürdiger Weise kann die nachfolgende Funktion den 
teil zwischen $ und = (hier: "first") sehr gut herausfinden und auch der 
Wert (hier: 88) wird korrekt herausgeparst. Wenn ich tmpstr1 oder 
tmpstr2 in timerbuffer schreibe, erhalte ich den gewünschten Teilstring. 
Es gibt nur ein Problem mit strcmp --> Dort geht er nämlich nicht rein! 
Hat jemand eine Idee, woran das liegen könnte?
1
void extract_data(char *str)
2
{
3
  uint8_t     cnt = 0;
4
  int8_t      equalspos = -1;
5
  char       tmpstr1[20];
6
  char       tmpstr2[20];
7
  
8
  if (str[0] == '$') {   // command
9
    while(str[cnt] != '=' && cnt < strlen(str))
10
    {
11
      cnt++;
12
    }
13
    if (str[cnt] == '=') {
14
      equalspos = cnt;
15
      
16
      // command
17
      for (cnt=1; cnt<equalspos; cnt++)
18
      {
19
        tmpstr1[cnt-1] = str[cnt];
20
      }
21
      tmpstr1[equalspos-1] = '\0';
22
      
23
      // value
24
      cnt=equalspos+1;
25
      while(str[cnt] != '\r' && cnt < strlen(str))
26
      {
27
        tmpstr2[cnt-equalspos-1] = str[cnt];
28
        cnt++;
29
      }
30
      tmpstr2[cnt-equalspos-1] = '\0';
31
      
32
      if (newdata == 0) {
33
        newdata = 1;
34
        strcpy(timerbuffer, tmpstr1);
35
      }
36
      
37
      
38
      if(strcmp(tmpstr1, "first") == 0) {
39
        uart_putc('1');
40
      }
41
      if(strcmp(tmpstr1, "second") == 0) {
42
        uart_putc('2');
43
      }  
44
    }
45
    else {
46
      
47
    }
48
    
49
  }
50
  else {          // data
51
    uart_puts("No Order\r");
52
  }
53
}

(Edit: Sorry, dass es in "Mikrocontroller und Elektronik" gelandet ist - 
habe nach der Forensuche nicht mehr darauf geachtet, in welchem Bereich 
ich gerade bin --> würde eher in GCC passen)
Gast
Hab mir den code nicht ganz genau angeguckt, kenn das Problem aber gut. 
Probier mal strncmp, da du ja eh nur auf "first" und "second" abfragst, 
kannst du einfach fuer "first" die 5, und fuer "second" die 6 Zeichen 
vergleichen. Dann sollte es hinhauen.
1
      if(strncmp(tmpstr1, "first", 5) == 0) {
2
        uart_putc('1');
3
      }
4
      if(strncmp(tmpstr1, "second", 6) == 0) {
5
        uart_putc('2');
Gast
Also dafür würde ich persönlich strtok() nehmen. Damit lässt sich
ao ein String prima zerlegen (wenn man weiss, wie die Funktion
funktioniert ;-) )
Nichtsdestotrotz ist der Code eigentlich korrekt. Das uart_putc sollte 
aufgerufen werden (und in der Simulation wird es das auch). Daraus 
ergeben sich für mich 3 Möglichkeiten:

1) Der gepostete Code stimmt nicht genau mit dem verwendeten Code 
überein.

2) uart_putc verhält sich unerwartet, so dass es nur so aussieht, als ob 
es nicht aufgerufen wird.

3) Du hast irgendein "globales" Problem, z.B. dass der Stack in den 
Data-Bereich wächst.
Gast
strcmp arbeitet soweit ich weiss bis zum erkennen des String-End 
zeichens \0. Wenn man aber Strings zerpflueckt, geht das \0 dabei unter 
Umstaenden verloren. Moeglicherweise funktioniert der gepostete code 
deswegen ja nicht.
OP
Danke für die nützlichen Tipps! Es lag scheinbar wirklich an einem 
globalen Problem, so wie es Stefan Ernst auch schon vermutet hatte. 
Nachdem ich einige Funktionen, die ich zum Test eingebaut hatte, 
gelöscht hatte, lief es.

Trotzdem habe ich einige Tipps wie die von Helmut Lenzen und Matthias 
umgesetzt, welche natürlich auch prima funktionieren. Die Idee mit 
strtok() werde ich in Zukunft sicherlich verfolgen, aber da meine 
Parsefunktion momentan gut funktioniert, habe ich das erst mal so 
gelassen.

>> Problem gelöst - vielen Dank!

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 17 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.