Forum: Mikrocontroller und Digitale Elektronik Fat und ffwrite


von Christian P. (peterfrosta)


Lesenswert?

Hallo ihr Schlauen und Meiers ;)

vllt könnt Ihr mir helfen, dass ich nicht noch mehr Zeit vergeude.

Ich nutze die FatLib von diesem Portal umd Daten auf eine Sd zu 
schreiben

Falls das keine Lib sondern ein Bibliothek ist, lasse ich mir gerne 
erklären warum das so ist. Nur die Tatsache, dass ich den Begriff falsch 
verwende, interessiert mich weniger.

Folgendes macht Probleme:

Ich möchte einen Zahlenwert zwischen 0 und 150 in eine Datei schreiben.
Allerdings, nicht hinten anhängend sondern überschreibend.

Um das zu realisieren führe ich fogendes aus:

if ( MMC_FILE_OPENED == ffopen("test.txt",'b') ){

      ffwrites(buf);
      ffclose();

    }
    else
    {
      error--;
    }

Der Parameter "b" ist kein Fehler. ich habe die ffwrite Funktion um 
diesen Parameter ergänzt, damit die Datei in einem Abwasch erstellt oder 
gelesen wird.

Das eigentliche Problem:
Der erste String wird korrekt geschrieben.
Pro jedem weiteren Aufruf dieser Funktion, wird auch der String korrekt 
überschrieben, jedoch wird die Anzahl von Stringbytes in Leerzeichen 
angehängt. Zumindest sieht man diese im Texteditor am PC.

Beispiel:
.txt wenn 1 Mal geschrieben wurde:   "20"
.txt wenn 2 Mal geschrieben wurde:   "40  "
.txt wenn 4 Mal geschrieben wurde:   "80      "

Also die Werte kommen schon richtig an aber leider zuviel.


Meine Vermutung nun ist, dass die Variable "File.length" dafür 
verantwortlich ist. Diese wird ja automatisch inkrementiert oder?
Ich habe sie jedenfalls noch nicht selbst beschrieben.
Sorgt diese Variable vllt dafür, dass die Textdatei, entsprechend viele 
Bytes reserviert bekommt und der Editor interpretiert die freien 
reservierten Bereiche als Leerzeichen?

Falls das zutrifft, wie kann dafür sorgen, dass file.length nicht 
wächst, wenn ich immer nur die ersten 3 Bytes überschreibe?

Danke schon mal für eure Zeit!
Allerdings nur für die die konstruktiv beitragen ;)

Gruß Christian

von Karl Käfer (Gast)


Lesenswert?

Hallo Christian,

Christian P. schrieb:
> Ich nutze die FatLib von diesem Portal umd Daten auf eine Sd zu
> schreiben

Nein, tust Du nicht. Du benutzt eine von Dir selbst veränderte Version 
von irgendeiner "FatLib". Leider sagst Du wenig darüber, aus welcher 
Quelle Du diese "FatLib" hast (hier auf mikrocontroller.net sind in der 
Codesammlung ganze vier (4) FAT-Bibliontheken verlinkt, von denen leider 
keine einzige "FatLib" heißt), welche Version dieser Bibliothek den 
Änderungen zugrunde liegt, oder welche Änderungen Du daran vorgenommen 
hast.

> Falls das keine Lib sondern ein Bibliothek ist, lasse ich mir gerne
> erklären warum das so ist. Nur die Tatsache, dass ich den Begriff falsch
> verwende, interessiert mich weniger.

"Lib" ist eine (am Rande bemerkt: ähnlich bescheuerte wie "proggen" für 
"programmieren") Abkürzung für "Library", was englisch ist und übersetzt 
soviel wie "Bibliothek" bedeutet.

> Folgendes macht Probleme:
>
1
if ( MMC_FILE_OPENED == ffopen("test.txt",'b') ){
> Der Parameter "b" ist kein Fehler. ich habe die ffwrite Funktion um
> diesen Parameter ergänzt, damit die Datei in einem Abwasch erstellt oder
> gelesen wird.

Erstens übergibst Du diesen Parameter ausweislich des von Dir geposteten 
Code (den Code-Tags sicher lesbarer gestalten würden) nicht der Funktion 
ffwrite(), sondern der Funktion ffopen(). Und wenn Du diese um die 
Option "b" erweitert hast, dann ist das möglicherweise nicht unbedingt 
ein großer Fehler, aber jedenfalls ziemlich unglücklich -- denn "b" bei 
fopen() ist im C89-Standard für Binärdateien reserviert, und für einen 
Entwickler mit C-Erfahrung dürfte Dein "b" mit einer völlig anderen 
Funktionalität sehr verwirrend sein. Um den Positionszeiger einer Datei 
zu verschieben, gibt es im Übrigen die Funktion fseek().

Und, ach ja: fortgeschrittene Entwickler verwenden GROSSBUCHSTABEN in 
der Regel nur für #defines. Es ist sinnvoll, sich an gängige 
Codingstyles zu halten -- erstens, weil die seit Jahrzehnten etabliert 
sind und eine Auswahl der besten gebräuchlichen Praktiken sind, 
zweitens, weil man sich selbst daran gewöhnt und den Code anderer 
Entwickler besser und schneller lesen kann und drittens, weil dann auch 
andere Entwickler den eigenen Code besser lesen können -- zum Beispiel 
dann, wenn man etwas verhunzt hat und jemanden um Hilfe bitten muß.

> Meine Vermutung nun ist, dass die Variable "File.length" dafür
> verantwortlich ist.

Meine Vermutung ist, daß Du irgend etwas falsch machst. ;-) Da Du aber 
so ziemlich gar nicht beschreibst, was genau Du machst, sondern 
stattdessen viele arme, unschuldige Bytes darauf verschwendest zu sagen, 
was Du weder hören noch dazulernen willst, läßt sich bedauerlicherweise 
nicht sagen, was Du falsch machst. Wie schade.

Liebe Grüße,
Karl

von Bastler (Gast)


Lesenswert?

Ich glaube die Schlauen und die Meiers sind gerade im Urlaub, aber du 
kannst sie ja anrufen. Von der Verwandschaft hat man doch eigentlich die 
Telefonnummer, oder?

von dummy (Gast)


Lesenswert?

>Also die Werte kommen schon richtig an aber leider zuviel.

Dann wirst du vermutlich selber an der ständigen Verlängerung
des Strings schuld sein. strcat() verwendet?

von Christian P. (peterfrosta)


Lesenswert?

dummy schrieb:
>>Also die Werte kommen schon richtig an aber leider zuviel.
>
> Dann wirst du vermutlich selber an der ständigen Verlängerung
> des Strings schuld sein. strcat() verwendet?

Danke für deine Nachricht.
nein das habe ich nicht. der string kommt aus der itoa funktion und die 
schließt den string doch selbst mit "endzeichen" ab?!
Die ffwrites  ist ja widerum auch endzeichen gesteuert?!
Selbst wenn ich statt ffwrites() immer nur zwei bytes einzeln mit 
ffwrite() ausgebe entstehen diese Leerrzeichen ab des zweiten 
Schreibzugriffs.
Soll heißen:
1 Mal 2 Bytes geschrieben => .txt = "AB"
2 Mal 2 Bytes geschrieben => .txt = "AB  "

Wohl gemerkt Überschrieben soll er. Aber wieso die Leerzeichen entstehen 
weiß ich nicht.

http://www.mikrocontroller.net/articles/AVR_FAT32#Der_Status
Von hier habe ich mich mit den nltigen Datei versorgt. Wie auch immer 
man Sie hier nennen darf.


danke und gruß
christian


Anhang:
Lieber Bastler und Karl...
ich habe nicht geschrieben dass ich nicht lernen will.
Deshalb poste ich ja. Aber ich brauche Hilfe mit Bezug zum Problem und 
nicht ausschließlich Kritik zu meinem Umgang mit Mikrocontrollern (oder 
dessen was ihr davon denkt), damit ihr euch profiliert fühlt. Aber das 
bringt scheinbar nichts weil die vier Zeilen, die für euch gedacht 
waren, bei euch nicht angekommen sind. Ich würde mich freuen wenn ihr 
meinen Thread einfach in Zukunft ignorieren würdet.


Karl Käfer schrieb:
> Und, ach ja: fortgeschrittene Entwickler verwenden GROSSBUCHSTABEN in
> der Regel nur für #defines.

Was stellt deiner Meinung denn MMC_FILE_OPENED dar? es ist an der 
entsprechenden Stelle definiert und das ist Code der unter der oben 
stehenden URL  downloadbar ist.  Aber selbst wenn deine Verbesserung 
richtig wäre... Hilft mir das nicht.

Und zur File.length lässt sich bestimmt konstruktiver Stellung nehmen 
als mit diesen vielen nutzlosen Bytes die du mir zur Verfügung gestellt 
hast...

von Karl H. (kbuchegg)


Lesenswert?

Christian P. schrieb:

> Und zur File.length lässt sich bestimmt konstruktiver Stellung nehmen

Nein, da lässt sich nicht Stellung nehmen.
Zum einen weiß keiner welche Lib du tatsächlich benutzt.
Zum anderen weiß keiner, welche Änderungen du gemacht hast.
Zum dritten ist es wahrscheinlicher, dass du selbst dir einen Hund 
reingehauen hast. Entweder mit deiner Änderung im Filesystem, oder 
irgendwo im verwendenden Code. Den aber kennt hier auch keiner.

Es ist natürlich möglich, dass im Originalcode noch ein Bug lauert, der 
noch keinem aufgefallen ist. Aber die Erfahrung lehrt, das es meistens 
nicht so ist. Gerade bei Code, den viele unteschiedliche Entwickler 
einsetzen, fallen solche Dinge schnell mal auf.

von Christian P. (peterfrosta)


Lesenswert?

if ( MMC_FILE_OPENED == ffopen("test.txt",'b') ){
> Der Parameter "b" ist kein Fehler. ich habe die ffwrite Funktion um
> diesen Parameter ergänzt, damit die Datei in einem Abwasch erstellt oder
> gelesen wird.


as ist in der tat flasch ausgedrückt!
richtig ist:


if ( MMC_FILE_OPENED == ffopen("test.txt",'b') ){
...
 Der Parameter "b" ist kein Fehler. ich habe die ffopen() Funktion um
 diesen Parameter ergänzt, damit die Datei in einem Abwasch erstellt 
und/oder
 geoeffnet wird.

von Karl H. (kbuchegg)


Lesenswert?

Christian P. schrieb:

> if ( MMC_FILE_OPENED == ffopen("test.txt",'b') ){
> ...
>  Der Parameter "b" ist kein Fehler. ich habe die ffopen() Funktion um
>  diesen Parameter ergänzt, damit die Datei in einem Abwasch erstellt
> und/oder
>  geoeffnet wird.

was immer das 'in einem Abwasch' auch heissen soll.
EIn 'b' an dieser Stelle in einem call der fopen (oder sö ähnlich) 
heisst, ist einfach nur der Schreibmodus. Ein 'b' bedeutet 'binär 
schreiben' und bedeutet, dass sich das Filesystem aus einer Umsetzung 
von zb. \n zu \r\n raushalten soll. Alle Bytes werden genau so 
geschrieben, wie sie im Call zu den diversen write calls angegeben sind.

von Christian P. (peterfrosta)


Lesenswert?

Karl Heinz schrieb:
> Christian P. schrieb:
>
>> Und zur File.length lässt sich bestimmt konstruktiver Stellung nehmen
>
> Nein, da lässt sich nicht Stellung nehmen.
> Zum einen weiß keiner welche Lib du tatsächlich benutzt.
> Zum anderen Weiß keiner, welche Änderungen du gemacht hast.
> Zum dritten ist es wahrscheinlicher, dass du selbst dir einen Hund
> reingehauen hast. Entweder mit deiner Änderung im Filesystem, oder
> irgendwo im verwendenden Code. Den aber kennt hier auch keiner.

Doch lässt es sich. Ich habe ein veremutung auchgestellt bzgl der 
automatischen Hochzählung dieser Variable. Welche Files ich genommen 
habe, kann man zumindest jetzt  sehen (siehe link).

Ich habe nicht geändert von diesen Files AUSSER die Funktion ffopen() um 
einen Parameter ergänzt.
Im Innern wurde lediglich eine weitere Abfrage angelegt.
Und diese Funktion kann ich ja zur Verfügung stellen. Es tut mir sehr 
leid wenn ich nciht auf Anhieb weiß, was alles relavant zum hochladen 
ist. Zumal ich dachte, dass diese ffopen() nicht relvant ist.
Die datei wird ja erstellt oder geöffnet.

von Christian P. (peterfrosta)


Angehängte Dateien:

Lesenswert?

hier die funktion ffopen()

von Christian P. (peterfrosta)


Lesenswert?

alles andere ist in den datein (file und fat) ist unberührt

von Bastler (Gast)


Lesenswert?

Ich würde die simple Logic "OpenForRead versuchen und im Fehlerfall 
OpenForWrite durchführen" zuerst mal lokal in eine Funktion packen. 
Damit kann man klar zwischen "Fehler in der Lib" und "Fehler 
hausgemacht" unterscheiden.
Wenn's dann funktioniert, kann man immer noch die Lib erweitern. 
Vorzugsweise hier im Forum, dann haben alle was davon.
Na zufrieden mit der "Nochmaleinmischung"?

von Karl H. (kbuchegg)


Lesenswert?

Die 'Erweiterung' ist für mich unlogisch.

Eine Datei ist entweder zum Lesen oder zum Schreiben geöffnet.
Gerade bei den erzwungenermassen vereinfachten Filesystemen auf einem 
kleinen µc würde ich da nicht unbedingt erwarten, dass ich auf eine 
Datei, die zum Lesen geöffnet ist auch schreiben kann, ohne dass es da 
Fehler gibt.
Deine Erweiterung macht:
Wenn die Datei existiert, wird sie zum Lesen geöffnet.
Wenn die Datei nicht existiert, wird sie zum Schreiben geöffent.

Du beschreibst die Datei aber immer, egal ob sie zum Lesen oder zum 
Schreiben geöffnet wurde.

Und so wie die praktische Erfahrung anscheinend zeigt, funktioniert das 
nun mal nicht.

Falls ich da jetzt nichts übersehen habe, dann hast du lediglich 
programmiert
1
uint8_t myOpen( const char* name )
2
{
3
  uint8_t result = ffopen( name, 'r' );
4
  if( result == MMC_FILE_ERROR )
5
    result = ffopen( name, 'c' );
6
7
  return result;
8
}
d.h. nach einem Aufruf von myOpen weißt du nicht, in welchem Modus die 
Datei geöffnet wurde.
Gibts in deiner Lib keinen ffunlink(), der die Datei einfach löscht, 
indem er die Directory Einträge (und damit die FAT Einträge) frei gibt?

von Karl H. (kbuchegg)


Lesenswert?

Ich versteh das 'Problem' immer noch nicht.

Wenn ich die Aufgabenstellung aus dem Eröffnungsposting einigermassen 
richtig erfasst habe UND das Beispiel im Link einigermassen aktuell ist, 
dann lässt du in
1
....
2
  // Datei existiert, also anhaengen !
3
  if (TRUE == ffileExsists(file_name))
4
  {
5
            ffopen (file_name, 'c');
6
      // Spult bis zum Dateiende vor um anzuhaengen.
7
      // Geht auch ohne Option MMC_OVER_WRITE
8
      ffseek (file.length);
9
 
10
      // Schreibt String.
11
      ffwrites(str);
12
 
13
....
einfach den ffseek weg und der ffwrites beginnt die Datei von vorne weg 
zu beschreiben. Und das war ja doch das Ziel der Übung, oder nicht.

von Bastler (Gast)


Lesenswert?

Alternativ, ohne in der Lib zu ändern, einfach nach dem open() ein 
seek(0).

von Christian P. (peterfrosta)


Lesenswert?

Karl Heinz schrieb:
> einfach den ffseek weg und der ffwrites beginnt die Datei von vorne weg
> zu beschreiben. Und das war ja doch das Ziel der Übung, oder nicht.

Siehe erste Post. Da steht zwischen ffopen() und ffwrite() kein 
ffseek()!
Das ist ja warum ich den Post gestartet habe...  kein ffseek() oder 
ffseek(0) sorgen dafür das ich an den Anfang der Datei schreibe aber es 
kommen leerzeichen dazu!

steht aber auch im ersten und dritten post
Christian P. schrieb:
> Beispiel:
> .txt wenn 1 Mal geschrieben wurde:   "20"
> .txt wenn 2 Mal geschrieben wurde:   "40  "
> .txt wenn 4 Mal geschrieben wurde:   "80      "

Warum habe ich ffopen() erweitert?!
Weil wenn der Funktion "r" übergeben wird, die Datei nur geöffnet wird 
wenn vorhanden ABER keine erstellt wird.
Wenn der Funktion ffop() "c" übergeben wird, wird sie zwar erstellt 
(falls nciht vorhandn) aber nicht geöffnet.

mein Übergabeparameter "b" den ich mir frei ausgesucht habe, und 
zwischen "r" wie "read" und "c" wie "create", fande ich passt "b" wie 
"both" oder "beides". Warum das "b" in dieser Funktion fuer binäre 
sachen reserviert bleiben sollte ist mir schleierhaft. Dürfte ich den 
ein "B" verwenden??


also

Bastler schrieb:
> Ich würde die simple Logic "OpenForRead versuchen und im Fehlerfall
> OpenForWrite durchführen" zuerst mal lokal in eine Funktion packen.
> Damit kann man klar zwischen "Fehler in der Lib" und "Fehler
> hausgemacht" unterscheiden.

Naja... jedefalls ist die motivation nun eine andere! Danke. aber ganz 
verstehen tue ich dich nicht. siend das nun  pseudo funktinen, die ich 
mir stuzen soll?

also datein und ordner erstellen oder löschen macht keine probleme... 
ich habe probleme mit dem inhalt der datei... und zwar wächst der mit 
jedem geschriebenen byte. auch wenn überschrieben wird.

Daher würde ich gerne noch mal das augenmerk auf file.length lenken. 
Vllt kennt sich damit jemand aus.

am besten wenn ich heute abend nch mal drann sitz, werde ich versuchen 
file.length einfach mit zu beschreiben. vllt löst das mein Problem.

mfg
christian

von Karl H. (kbuchegg)


Lesenswert?

Christian P. schrieb:
> Karl Heinz schrieb:
>> einfach den ffseek weg und der ffwrites beginnt die Datei von vorne weg
>> zu beschreiben. Und das war ja doch das Ziel der Übung, oder nicht.
>
> Siehe erste Post. Da steht zwischen ffopen() und ffwrite() kein
> ffseek()!

Das war aber auch dein modifizierter ffopen.
Was der alles für Konsequenzen hat, kann ich nicht wirklich abschätzen.

Laut Doku und Beispiel in dem Link, müsste das von dir gewünschte 
komplett ohne MOdifikation der Lib funktionieren.

> Weil wenn der Funktion "r" übergeben wird, die Datei nur geöffnet wird wenn 
vorhanden ABER keine erstellt wird.

Ja. Das ist auch der Normalfall. Wenn man eine Datei zum Lesen öffnen 
will, und die Datei existiert nicht, dann ist das ein Fehler. Alle 
Dateisysteme, die ich kenne behandeln das so.

> Wenn der Funktion ffop() "c" übergeben wird, wird sie zwar erstellt (falls nciht 
vorhandn) aber nicht geöffnet.

Das wage ich dann doch zu bezweifeln. GIbst du c (für create) an, dann 
wird sie zum Schreiben geöffnet. Das 'zum Schreiben' ist implizit, denn 
das man aus einer neu erstellten Datei nichts lesen kann, ist 
unmittelbar klar.


Ich denke, du solltest dir mal klar machen, das das 'r' für 'read' steht 
und das 'c' für 'write (and create if not existing)'. In deinem 
Zusammenhang macht die Verwendung von 'r' überhaupt keinen Sinn, denn du 
willst ja nach eigenem Bekunden und nach dem geposteten Code zu gehen, 
in die Datei schreiben. Also ist alls was mit 'r' zusammen hängt schon 
mal komplett aussen vor. Ob diese Lib in der Lage ist, im laufenden 
Betrieb ein geöffnetes File von 'Lesen' auf 'Schreiben' umzustellen, 
weiß ich nicht. Da da aber Aufwand dahinter steckt und man auf einem 
kleinen µC eher selten eine Datei schreibt nur um sie gleich danach auf 
dem µC wieder einzulesen, denke ich mal eher, das die Lib das nicht 
unterstützt. In deinem Fall brauchst du das auch nicht. Um eine Datei zu 
überschreiben braucht man sie nicht lesen. Einfach jedesmal neu die 
Datei mit 'c' aufmachen und alles was bisher da drinn stand, wird 
komplett gelöscht bzw. mit den nächsten fwrite(s) von Beginn der Datei 
weg überschrieben. Du legst mir da viel zu viel Augenmerk auf 'create'. 
Du öffnest mit 'c' in erster Linie die Datei zum Beschreiben. Der Call 
ist das Pedant zu
http://www.thinkage.ca/english/gcos/expl/c/lib/creat.html

Einen gezielten 'Append' Modus, in dem eine vorhandene Datei beim 
erneuten Öffnen zum Schreiben nicht implizit gelöscht wird, scheint 
diese Lib nicht zu haben.

Was passiert denn bei
1
  if ( MMC_FILE_OPENED == ffopen("test.txt", 'c') ){
2
    ffwrites(buf);
3
    ffclose();
4
  }
5
  else
6
  {
7
    error--;
8
  }

Wenn dann beim Schreiben immer noch Fehler in der Datei sind, dann ist 
da wohl ein Fehler in der Lib.

von Bastler (Gast)


Lesenswert?

Solangsam komm ich dahinter, was dein Problem ist.
Ich würde vermuten, daß einfach noch niemand den Fall "Datei 
überschreiben" genutzt hat. "Anhängen" ist eben die gängigere Variant 
zum Loggen von Irgendwas. Ja, es sieht alles danach aus, daß beim 
ffwrite für den Fall "Schreibposition<File-Größe" versehentlich die 
File-Größe hochzählt. Leider hab ich aktuell keinen Zugang zu der Source 
(iPad spinnt rum)

von Rolf Magnus (Gast)


Lesenswert?

Christian P. schrieb:
> Warum das "b" in dieser Funktion fuer binäre sachen reserviert bleiben
> sollte ist mir schleierhaft.

Weil es in der Standard-C-Funktion fopen(), an die dieses ffopen() 
offenbar angelehnt ist, für binary steht. Entsprechend denkt natürlich 
jeder erstmal, daß das da auch so ist.

von Christian P. (peterfrosta)


Lesenswert?

Karl Heinz schrieb:
> Ich denke, du solltest dir mal klar machen, das das 'r' für 'read' steht
> und das 'c' für 'write (and create if not existing)'. In deinem
> Zusammenhang macht die Verwendung von 'r' überhaupt keinen Sinn, denn du
> willst ja nach eigenem Bekunden und nach dem geposteten Code zu gehen,

aha. ich hatte das dann vllt falsch verstanden.  aber wenn ich mir die 
if-abfragen in ffopen() anschau, komme ich auf eine andere Deutung.

die erste if wird nur betreten, wenn "r" übergeben wird und die Datei 
existiert. wenn ich das richtig verstehe, kann ich die datei dann nur 
lesen. Ich will sie aber vor allem auch beschreiben (überschreiben).

die zweite if wird betreten wenn "c" übergeben wird und die Datei noch 
NICHT existiert. Dann wird sie erstellet.

ALso der Fall: die Datei ist vorhanden und ich öffne Sie zum schreiben, 
scheint nicht abgedeckt.
Und um eine Datei anzulegen und zu danach sofort zu beschrieben wären 
auch mehere schritte nötig. Da Parameter "c" nur abgefragt wird, wenn 
die Datei nicht existiert. also kann das nicht zum schreiben gedacht 
sein. Wohl gemerkt der hier runtergeladene Code.

Daher verstehe ich nciht, warum du dich an meiner erweiterung so 
aufhängst.

Dateien öffnen und erstellen, funktioniert, wie schonmal erwähnt 
ziemlich gut.

Ob es die Datei gibt oder nicht. mit parameter"b" gibt es sie, sie ist 
geöffnet und beschreibar.

Wenn ich das falsch verstanden habe, klär mich bitte auf. a

Karl Heinz schrieb:
> Was passiert denn bei  if ( MMC_FILE_OPENED == ffopen("test.txt", 'c')
> ){
>     ffwrites(buf);
>     ffclose();
>....

laut code dürfte garnichts passieren. weil wie ebend beschrieben bei 
Paramnerer "c" auch die Datei nicht existent sein muss. Du pflaumst mich 
hier von anfang an wegen kleinkram an und guckst slebst nicht sehr genau 
hin karl.
Deshalb gibt es meine Erweiterung. Was da raus kommt steht oben schon 
ein paar mal. Mit "c" wird die Datei nicht überschrieben.

Rolf Magnus schrieb:
> Weil es in der Standard-C-Funktion fopen(), an die dieses ffopen()
> offenbar angelehnt ist, für binary steht. Entsprechend denkt natürlich
> jeder erstmal, daß das da auch so ist.

das wusste ich nicht. welches Zeichen wäre denn erlaubt?

Bastler schrieb:
> Solangsam komm ich dahinter, was dein Problem ist.
> Ich würde vermuten, daß einfach noch niemand den Fall "Datei
> überschreiben" genutzt hat. "Anhängen" ist eben die gängigere Variant
> zum Loggen von Irgendwas. Ja, es sieht alles danach aus, daß beim
> ffwrite für den Fall "Schreibposition<File-Größe" versehentlich die
> File-Größe hochzählt. Leider hab ich aktuell keinen Zugang zu der Source
> (iPad spinnt rum)

Mit dieser einmüschung bin ich nun sehr zufrieden ;) vllt könntest du 
dahin gehend ja noch etwas zeit investieren. ich hoffe das dort der 
Fehler steckt. ich bin bin hoffentlich auch in einer stunde wieder 
drann.


gruß Christain

von holger (Gast)


Lesenswert?

Hast du dies in der config eingestellt?

#define MMC_OVER_WRITE     TRUE

Wenn nicht dann mach das mal. Deine Änderungen solltest
du dann aber erst mal wieder raus nehmen.

von Christian P. (peterfrosta)


Lesenswert?

holger schrieb:
> Hast du dies in der config eingestellt?
>
> #define MMC_OVER_WRITE     TRUE

Ja das hatte ich bisweilen aktiv.
also meinst du wenn das auf TRUE ist, brauche ich meine Erweiterung 
nicht.
weil mir Paramter "c" die Datei entweder angelegt wird oder - falls 
schon vorhanden - geöffnet wird und ich sie dann beschreiben kann?
Dann wäre die Erweiterung wirklich überflüssig.

Aber ob das die File.length geschicht behebt muss ich ausprobieren.

danke
gruß
christian

von Karl H. (kbuchegg)


Lesenswert?

Christian P. schrieb:
> Karl Heinz schrieb:
>> Ich denke, du solltest dir mal klar machen, das das 'r' für 'read' steht
>> und das 'c' für 'write (and create if not existing)'. In deinem
>> Zusammenhang macht die Verwendung von 'r' überhaupt keinen Sinn, denn du
>> willst ja nach eigenem Bekunden und nach dem geposteten Code zu gehen,
>
> aha. ich hatte das dann vllt falsch verstanden.  aber wenn ich mir die
> if-abfragen in ffopen() anschau, komme ich auf eine andere Deutung.
>
> die erste if wird nur betreten, wenn "r" übergeben wird und die Datei
> existiert. wenn ich das richtig verstehe, kann ich die datei dann nur
> lesen.

richtig.
WEnn du dir den Code in diesem Fall ansiehst, sind da auch Calls drinn, 
die diverse Lesebuffer befüllen, von wo dann die diversen read 
Funktionen anfangen zu lesen.

> die zweite if wird betreten wenn "c" übergeben wird und die Datei noch
> NICHT existiert. Dann wird sie erstellet.

Auch richtig.
Aber:
Davor kommt ja auch noch ein
1
  uint8_t file_flag = fat_loadFileDataFromDir(name);
ganz am Anfang. Dem müsste man jetzt mal nachgehen, was der so macht. So 
wie der Code in ffopen geschrieben ist, macht dieser loadFileDataFromDir 
alles was notwendig ist, damit unmittelbar mit dem SChreiben auf eine 
Datei begonnen werden kann. Sofern die Datei schon existiert.

> Daher verstehe ich nciht, warum du dich an meiner erweiterung so
> aufhängst.

Weil sie unnötig ist und im wesentlichen einfach nur aus sinnlosem 
Kopieren zweir Codestellen besteht, von der du  nicht im mindesten 
überlegt bzw. analysiert hast, was die eigentlich machen.

> Ob es die Datei gibt oder nicht. mit parameter"b" gibt es sie, sie ist geöffnet 
und beschreibar.

Ok. Klartext. Dein Paramater 'b' samt Implementierung ist hirnlos 
zusammenkopierter Mumpitz.


Ich muss jetzt weg. Aber ich werd mich da mal drann setzten und einen 
UNterbau unter das Filesystem legen, mit dem ich am PC nachsehen kann, 
was da wirklich passiert. Eventuell ist ja wirklich ein Bug in der 
Längenbehandlung. Aber eigentlich denke ich, dass da noch ein weiteres 
Problem wartet. Die Lib unterscheidet offenbar nicht die Fälle 'neues 
File schreiben' und 'an bestehendes File anhängen'. Im regulären C fopen 
gibt es diese 3 Fälle und warum der Autor dieser Lib nicht dieser 
einfachen Strategie gefolgt ist, ist mir nicht ganz klar.
1
FILE * fopen ( const char * filename, const char * mode );
2
3
....
4
5
"r"  read: Open file for input operations. The file must exist.
6
"w"  write: Create an empty file for output operations. If a file with
7
the same name already exists, its contents are discarded and the file is treated as a new empty file.
8
"a"  append: Open file for output at the end of a file. Output
9
operations always write data at the end of the file, expanding it.
10
Repositioning operations (fseek, fsetpos, rewind) are ignored. The file is
11
created if it does not exist.

Es wäre die einfachste und klarste Lösung gewesen, mit der jeder C 
Programmierer unmittelbar hätte umgehen können.


Im Zweifelsfall besteht immer noch die Möglichkeit in deinem Filesystem 
die Datei zuerst runterzulöschen und dann eine neue Datei mittels 'c' zu 
erstellen. Den call ffrm gibt es ja dafür.

von Christian P. (peterfrosta)


Lesenswert?

so ich sietzt gerade daran.

den Parameter von "b" auf "c" zu ändern, hat mehr Probleme gemacht.
Mein "b" Parameter scheint es zu meiner Zufriedenheit zu erledigen.

Hab dann folgendes gemacht.
1
// ****************************************************
2
    // if file exists, it will be opened and if not it will creat and open
3
    if ( MMC_FILE_OPENED == ffopen("Guthaben.txt",'b') ){
4
      
5
      ffwrites(buf);
6
      if(aufbuchwert >10)
7
        file.length = 1;
8
      else if(aufbuchwert<9 && aufbuchwert <100)
9
        file.length = 2;
10
      else
11
        file.length = 3;
12
        
13
      ffclose();
14
      
15
    }
16
    else
17
    {
18
      error--;
19
    }

 Dies behebt mein Problem.
ist sicherlich keine allgmein anwendbare Variante aber für meine 
Anwendung passt es nun.
Der Curser wandert nicht mehr sonder ist maximal 3 Byte vom Startplatz 
entfernt.

mfg
christian

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.