Datum:
Ich raffs nicht ... ich erstell mir einen Zeiger aus einem FD auf ein String,
ptr=strstr(buffer, "1-0:21.7.0*255");
printf(ptr);
|
1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) Super! Aber nun will ich die Zahl in den Klammern extrahieren mit
char value[6]; strncpy(value, ptr+16, 5); |
Und egal was ich mache -> Segmentation fault. :-/
Datum:
Henrik Wellschmidt schrieb: > Ich raffs nicht ... > > ich erstell mir einen Zeiger aus einem FD auf ein String, Was ist denn ein "Zeiger aus einem FD"? > ptr=strstr(buffer, "1-0:21.7.0*255"); > printf(ptr); > > 1-0:21.7.0*255(+00023*W) > 1-0:21.7.0*255(+00023*W) > 1-0:21.7.0*255(+00023*W) > > Super! Aber nun will ich die Zahl in den Klammern extrahieren mit > > char value[6]; > strncpy(value, ptr+16, 5); > > Und egal was ich mache -> Segmentation fault. Hast du auch daran gedacht, das '\0' anzuhängen?
Datum:
welchen datentype hat ptr?
Datum:
Rolf Magnus schrieb: > Was ist denn ein "Zeiger aus einem FD"? Hallo Rolf, also ich lese mit read() aus einem 'File Fescriptor' in ein char array (buffer) ... strstr() liefert dann einen Zeiger auf die Fundstelle im char array (buffer). Das wollte ich damit sagen ;-)
Datum:
Hast Du Rolfs Frage gesehen? Rolf Magnus schrieb: >> Und egal was ich mache -> Segmentation fault. > > Hast du auch daran gedacht, das '\0' anzuhängen? Was kommt noch nach der strncpy-Anweisung, eine Ausgabe mit printf? Volkmar
Datum:
Volkmar Dierkes schrieb: > Hast Du Rolfs Frage gesehen? Ja, kann ich aber noch nicht zuordnen ... > Was kommt noch nach der strncpy-Anweisung, eine Ausgabe mit printf? Erstmal noch nischt ... ich wollte dann mit atof[] in ein Float wandeln und dann ein eine andere Funktion schicken ...
while (1) {
res = read(fd, buffer, sizeof(buffer) -1);
if (res >=0) {
buffer[res]=0;
ptr=strstr(buffer, "1-0:21.7.0*255");
char value[6];
strncpy(value, ptr+16, 5);
}
}
|
Datum:
Henrik Wellschmidt schrieb: > Volkmar Dierkes schrieb: >> Hast Du Rolfs Frage gesehen? > > Ja, kann ich aber noch nicht zuordnen ... Strings müssen nullterminiert sein. Ein strncpy kopiert zwar ein \0 des Originalstrings mit, wenn es einen kompletten String kopiert, aber wenn der Quellstring länger ist als die angegebene Maximallänge, dann hängt es keins an. >> Was kommt noch nach der strncpy-Anweisung, eine Ausgabe mit printf? > > Erstmal noch nischt ... Dann dürfte aber auch kein Segfault passieren. Der kommt erst, wenn du mangels String-Ende-Zeichen über das Ende hinaus liest.
Datum:
Rolf Magnus schrieb: > Strings müssen nullterminiert sein. Ein strncpy kopiert zwar ein \0 des > Originalstrings mit, wenn es einen kompletten String kopiert, aber wenn > der Quellstring länger ist als die angegebene Maximallänge, dann hängt > es keins an. Ahh! 1-0:21.7.0*255(+00023*W) |1|-|0|:|2|1|.|7|.|0|*|2|5|5|(|+|0|0|0|2|3|*|W|)|\0 strncpy(value, ptr+16, 5); | | | | | | | | | | | | | | | | |0|0|0|2|3| | | |\0 Fehlt also hier ^ |0|0|0|2|3| Ich wollte aber danach eigentlich gleich:
double w = atof(value);
|
ranhängen ?!
Datum:
Henrik Wellschmidt schrieb: > Fehlt also hier ^ > > |0|0|0|2|3| > > Ich wollte aber danach eigentlich gleich: > > >
> double w = atof(value);
> |
> > ranhängen ?! Na dann setz halt hinten in value ein 0 Byte ein strncpy(value, ptr+16, 5); value[5] = '\0'; Egal was strncpy gemacht hat, jetzt ist das Zeug im Array value ganz sicher ein String, weil sichergestellt ist, dass da auf jeden Fall eine 0-Terminierung existiert. Und du solltest den Pointer, den dir strstr gegeben hat, sicherheitshalber auch gegen NULL prüfen :-) PS: Wärs nicht besser und auch einfacher, nach der öffnenden Klammer '(' suchen zu lassen?
Datum:
Karl Heinz Buchegger schrieb: > > strncpy(value, ptr+16, 5); > value[5] = '\0'; > > > Egal was strncpy gemacht hat, jetzt ist das Zeug im Array value ganz > sicher ein String, weil sichergestellt ist, dass da auf jeden Fall eine > 0-Terminierung existiert. > > Und du solltest den Pointer, den dir strstr gegeben hat, > sicherheitshalber auch gegen NULL prüfen :-) > > PS: Wärs nicht besser und auch einfacher, nach der öffnenden Klammer '(' > suchen zu lassen? Hallo Karl Heinz ... Segmentation fault :(
while (1) {
res = read(fd, buffer, sizeof(buffer) -1);
if (res >=0) {
buffer[res]=0;
ptr = strstr(buffer, "1-0:21.7.0*255");
char value[10];
strncpy(value, ptr+14,5);
value[5] = '\0';
}
}
|
Ich denke das liegt an dem zeiger ptr 'strncpy(value, ptr+14,5);' In den beispielen verwenden die immer 'char arrays' keine pointer auf ein 'char arry' ... Mist.
Datum:
In deinem letzten Code: Liest read() genug Zeichen ein? Wenn read() einen Fehler zurückliefert, dann wird 'buffer' nie 0-Terminiert und du liest u.U. über das buffer ende. Findet strstr() auch wirklich den gesuchten string? Ansonsten ist ptr ein NULL pointer der beim Zugriff zu einem segfault führt.
Datum:
Henrik Wellschmidt schrieb: > Ich raffs nicht ... Tja, Stringverarbeitung war schon immer eine der besonderen Stärken von C. W.S. (dem heut abend beim Tempranillo nach Stänkern zumute ist) Apropos char* Pointer: versuche es doch mal mit strncpy(value, &buffer[16], 5); vielleicht verschafft dir das ne Erkenntnis.
Datum:
Thomas Miletich schrieb: > In deinem letzten Code: > > Liest read() genug Zeichen ein? Wenn read() einen Fehler zurückliefert, > dann wird 'buffer' nie 0-Terminiert und du liest u.U. über das buffer > ende. > > Findet strstr() auch wirklich den gesuchten string? Ansonsten ist ptr > ein NULL pointer der beim Zugriff zu einem segfault führt. Ja, das passt alles ... ich greif ja nur auf buffer zu wenn 'if (res >=0)'
res = read(fd, buffer, sizeof(buffer) -1); if (res >=0) { buffer[res]=0; |
Das kommt 5sekündlich über die Schnittstelle rein ->
/HAG5eHZ010C_EHZ1WA02 1-0:0.0.0*255(1095110000152759) 1-0:1.8.0*255(000005.2786) 1-0:96.5.5*255(82) 0-0:96.1.255*255(0000152759) 1-0:32.7.0*255(232.15*V) 1-0:52.7.0*255(232.16*V) 1-0:72.7.0*255(000.00*V) 1-0:31.7.0*255(000.10*A) 1-0:51.7.0*255(000.21*A) 1-0:71.7.0*255(000.00*A) 1-0:21.7.0*255(+00023*W) 1-0:41.7.0*255(+00042*W) 1-0:61.7.0*255(+00000*W) 1-0:96.50.0*0(67) 1-0:96.50.0*1(07CF) 1-0:96.50.0*2(19) 1-0:96.50.0*3(09) 1-0:96.50.0*4(25) 1-0:96.50.0*5(1A) 1-0:96.50.0*6(003D381B300AF9003D00490200009F80) 1-0:96.50.0*7(00) ! |
Und ptr = strstr(buffer, "1-0:21.7.0*255"); printf(ptr); sucht mir schoen das was ich brauche ...
1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) 1-0:21.7.0*255(+00023*W) |
Und dann verlässt es mich ...
Datum:
Hallo, Henrik Wellschmidt schrieb:
> char value[10]; > strncpy(value, ptr+14,5); > value[5] = '\0'; |
versuche mal das hier, achte auf das '&' bei value.
char value[10]; strncpy(&value, ptr+14,5); value[5] = '\0'; |
Wenn ich mich nicht irre, mußt Du der strncpy-Funktion ja eine Adresse übergeben, wo der String hingeschrieben werden soll. Aber da value kein Pointer ist, sondern eine Array of char, brauchst Du die Adresse davon. Volkmar
Datum:
Henrik Wellschmidt schrieb: > Und dann verlässt es mich ... Das einzige was dich verlässt ist, dass dein printf offenbar eine Sicherung gegen NULL-Pointer hat .... UND DEIN CODE NICHT ! Frag jetzt endlich mal den Pointer ab, den du von strstr kriegst. Denn das kann ich aus 300km Entfernung sehen, dass in der Hälfte deiner Daten der Suchstring gar nicht vorkommt. Und in dem Fall liefert dir strstr einen NULL-Pointer! Und mit einem NULL Pointer kannst du nicht weiter arbeiten! Bei ausnahmslos jeder Suche muss man immer damit rechnen, dass der gesuchte Wert nicht vorhanden ist! Auch du musst damit rechnen! So wie alle anderen auch! Und buffer ist hoffentlich ein char Array! (Immer diese HickHack Technik nur Ausschnitte aus einem Programm zu zeigen. Was ist da so toll drann? Ist das wirklich cool, wenn wir auf der anderen Seite des Monitors Rätselspielchen spielen müssen?)
char buffer[100]; ... while (1) { res = read(fd, buffer, sizeof(buffer) -1); if (res > 0) { buffer[res] = '\0'; printf( "received >%s<\n", buffer ); ptr = strstr( buffer, "1-0:21.7.0*255" ); if( ptr != NULL ) { char value[6]; strncpy( value, ptr + 16, 5 ); value[5] = '\0'; printf( "'%s' -> '%s'\n", buffer, value ); } } } |
Und ich schätze mal, das alles funktioniert überhaupt nicht, weil gar nicht garantiert ist, dass read immer eine komplette Zeile liefert. read() interessieren deine Zeilen nämlich nicht, der liefert was da ist, bzw. füllt dir den Buffer randvoll an. Verwende fgets. Dann bist du zumindest dieses Problem los. fgets teilt die eingehenden Daten schön in Zeilen auf und liefert dir immer eine komplette Zeile. Wenn du fgets nimmst, musst du deinen open durch einen fopen austauschen und den close gegen einen fclose.
Datum:
Volkmar Dierkes schrieb: > Hallo, > > Henrik Wellschmidt schrieb: >
> char value[10]; >> strncpy(value, ptr+14,5); >> value[5] = '\0'; > |
> > versuche mal das hier, achte auf das '&' bei value. Quatsch > übergeben, wo der String hingeschrieben werden soll. Aber da value kein > Pointer ist, sondern eine Array of char, brauchst Du die Adresse davon. Kauf dir ein C-Buch und lies mal nach wie Arrays übergeben werden.
Datum:
Henrik Wellschmidt schrieb: > Thomas Miletich schrieb: >> In deinem letzten Code: >> >> Liest read() genug Zeichen ein? Wenn read() einen Fehler zurückliefert, >> dann wird 'buffer' nie 0-Terminiert und du liest u.U. über das buffer >> ende. >> >> Findet strstr() auch wirklich den gesuchten string? Ansonsten ist ptr >> ein NULL pointer der beim Zugriff zu einem segfault führt. > > Ja, das passt alles ... ich greif ja nur auf buffer zu > wenn 'if (res >=0)' Stimmt. Hab ich aufgrund der fehlerhaften Formatierung falsch gelesen.
Datum:
Karl Heinz Buchegger schrieb: > >
> > ... > > while (1) { > > res = read(fd, buffer, sizeof(buffer) -1); > > if (res > 0) { > buffer[res] = '\0'; > > printf( "received >%s<\n", buffer ); > > ptr = strstr( buffer, "1-0:21.7.0*255" ); > if( ptr != NULL ) { > char value[6]; > strncpy( value, ptr + 16, 5 ); > value[5] = '\0'; > > printf( "'%s' -> '%s'\n", buffer, value ); > } > } > } > |
Danke Karl Heinz!!!! Das rockt!!!
00023 00023 00023 00023 00023 00023 00023 |
Karl Heinz Buchegger schrieb: >Und mit einem NULL Pointer kannst du nicht weiter arbeiten! Jetzt verstehe ich .... (null)(null)(null)(null)(null)(null)(null)(null)(null)(null)(null)(null) (null)(null)(null)(null)(null)(null)(null)(null)(null)(null)(null)1-0:21 .7.0*255(+00000*W)
Datum:
Thomas Miletich schrieb: > Stimmt. Hab ich aufgrund der fehlerhaften Formatierung falsch gelesen. Ich weiss, ich habe da grosse Differenzen zum Standard ;-)
Datum:
Es hilft alles nichts. Du brauchst ein C-Buch und musst es
durcharbeiten. Diese Try&Error Programmierung, das Zusammenkopieren von
Code, das funktioniert vielleicht bei kleinen Programmen (und auch da
nicht besonders gut), aber irgendwann ist ein Punkt erreicht, an dem man
ohne solide gelernte Grundlagen nicht weiter kommt.
> Ich weiss, ich habe da grosse Differenzen zum Standard ;-)
Und warum tust du dann nichts dagegen?
Wenigstens Einrückungen richtig zu stellen, kostet dir nichts. Die sind
aber ein solides und erprobtes Mittel um { } Fehler zu sehen und zu
finden. Erfordert Dispziplin, schon klar. Aber im Vergleich zu dem, was
dir die restliche Programmierung an Disziplin abverlangt, ist das
Pipifax.
Datum:
Karl Heinz Buchegger schrieb: > Es hilft alles nichts. Du brauchst ein C-Buch und musst es > durcharbeiten. Diese Try&Error Programmierung, das Zusammenkopieren von > Code, das funktioniert vielleicht bei kleinen Programmen (und auch da > nicht besonders gut), aber irgendwann ist ein Punkt erreicht, an dem man > ohne solide gelernte Grundlagen nicht weiter kommt. Ich habe 4 C-Bücher :-) Aber es ist halt zu verlockend sich vor den Rechner zu setzen. Ich verstehe ja ganz gut was hier geschrieben wird und lerne dabei. Klar, blind Code kopieren wäre wirlich blöde.
Beitrag #3015196 wurde vom Autor gelöscht.
Datum:
Karl Heinz Buchegger schrieb: > bzw. füllt dir den Buffer randvoll an. Verwende fgets. Dann bist du > zumindest dieses Problem los. fgets teilt die eingehenden Daten schön in > Zeilen auf und liefert dir immer eine komplette Zeile. Hallo Karl Heinz, Ich habe noch nirgens gesehen, wie man fopen() und tcsetattr() zusammen bekommt ... http://en.wikibooks.org/wiki/Serial_Programming/termios ...
Datum:
Henrik Wellschmidt schrieb: > Ich habe noch nirgens gesehen, wie man fopen() und tcsetattr() zusammen > bekommt ... Das sollte über die Funktion fileno() gehen.
Datum:
Henrik Wellschmidt schrieb: > Ich habe 4 C-Bücher :-) > > Aber es ist halt zu verlockend sich vor den Rechner zu setzen. Ich kann das ja verstehen. Aber es bringt nichts. Dafür, dass du 4 Bücher hast, schwächelst du extrem. Um es mal freundlich auszudrücken. Du musst die Dinger auch durcharbeiten! In einem guten Buch sind am Ende eines jeden Kapitels Übungen drinnen mit denen man kontrollieren kann, ob man alles verstanden hat. > Ich verstehe ja ganz gut was hier geschrieben wird und lerne dabei. Das was hier geschrieben wird, ist noch nicht mal ein matter Abklatsch dessen, was es zu den Themenkreisen Files, Strings, deren Zusammenspiel, Textparsing, Konvertierungen, Pointer, Arrays und der Zusammenhang Pointer zu Arrays, ... zu sagen gibt. Und das sind in deinem Code gerade mal 8 Zeilen, die in den Büchern aber 3 bis 5 komplette Kapitel (teilweise auch kapitelübergreifend) in Anspruch nehmen, mit allem drum und drann. In Programmiersprachen ist es oft so, dass die Dinge zusammenhängen, wie Zahnräder in einem Getriebe. Man kann ein Getriebe nicht dadurch verstehen, indem man sich jedes Zahnrad einzeln ansieht. Es ist die Gesamtheit aller Räder, die ein Getriebe ausmachen.