hallo,
hier mal meine fat16/fat32 lib für atmel atmegas.
noch ich sag mal im alpha 2 status ;)
was geht ist:
- auslesen eines MBR ( muss im code eingestellt werden...)
- datei anlegen open('w',rstr);
- datei schreiben ffwrite(c);
- datei anhängen open('a',rstr);
- datei lesen c=ffread();
- datei löschen ffrm(fileName);
- direktory wechseln ffcd(dirName); (immer nur eins nach dem anderen)
- direktory anzeigen ffls();
- datei seek ffseek(234); (ab stelle 0, nur beim lesen)
- commando promt hier kann komplette funktionalität getestet werden !
- umwandeln von "t.txt" -> "T TXT" fat_str("t.txt);
mit einem atmega168 @ 20 mhz schafft man lesend ~ 220.000 bytes/sec,
mit einem atmega32 @ 8 mhz schafft man lesend ~ 20.000 bytes/sec,
bei fat 32 mit größeren clustern wird es immer schneller ;)
würde mich über anregungen, oder verbesserungsvorschläge freuen !
ps: hab Ulrich Radigs mmc.h/mmc.c etwas erweiter, an dieser stelle danke
für die veröffentlichung dieser dateien.
grüße daniel
hallo, einige bug-fixes sind gemacht, eine lib zum einlesen von tastatureingaben, über eine at-tastatur ist jetzt dabei. nur falls es jemanden interessiert ;)
g das thema interessiert doch immer. wie sieht es mit dem speicherbedarf aus? funktioniert der code auch - read only - auf einem atmega16 (1kb ram)?
Gast
#930780
mich würde nicht nur der quelltext, sondern auch deine quellen interessieren, gerade spezifikation, umsetzung mit atmega etc.
hallo, @ Alexander D. würde sogar mit write funktionieren, man müsste nur in der main auf ein paar sachen verzichten, wie den commando prompt und so. nur die fat-0.x.c und file-0.x.c sind auch super so zu gebrauchen. @ gast quellen sind einmal die Fatgen103.pdf spezifikationen von MS gewesen und https://www.pjrc.com/tech/8051/ide/fat32.html entickelt hab ich das ganze mit linux. habe mir raw images von mmc/sd karten gemacht und das mit low-level-datei-lese funktionen mit linux gcc geschrieben, da kann man dann schön debugen. zu dem code, das einzige problem, warum read und write nich z.b. auf einem atmega8 läuft ist, weil nicht genügend flash da ist, ram würde locker reichen.
hallo, neue optimierungen und bugs beseitigt beim schreiben ! fat16 schreiben von 60.000 bytes in 1,421 sec -> 41KB fat16 lesen von 60.000 bytes in 0,823 sec -> 71KB fat32 schreiben von 60.000 bytes in 1,249 sec -> 46KB fat32 lesen von 60.000 bytes in 0,747 sec -> 78KB die werte, mit atmega32 @ 8 mhz (interner takt). status: ist jetzt voll funktionsfähig ! grüße daniel
Gast
#932903
Hallo Habs zwar noch nicht testen können, sieht aber Klasse aus !! Tolle Arbeit !!! Noch einen schönen Abend Gruß Siegmar
Gast
#932953
>#include "fat-0.3.c" >#include "file-0.3.c" Das macht man nicht ;) Gibt nur Probleme. Bastel dir mal eine fat.h und file.h.
hallo, @ Siegmar danke, hört man gerne :) wenn du zum testen kommst, laß doch mal hören wo es hinkt, wenn es hinkt ;) @ holger ja werd ich machen. nur noch keine lust gehabt... ist mir auch noch ein kleines rätsel warum das unbedingt nötig ist. würde es reichen nur die funktionen in einer *.h datei "bekannt" zu machen, die von anderen *.c dateien aus aufgerufen werden ? das würde für mich am meisten sinn machen. wäre dann quasi sowas wie private oder public. also private nur in der *.c selber als prototyp, public in der *.h...
Gast
#933016
Da ich mich momentan auch gerade mit dem Thema befasse, werde ich die Library mal ausprobieren. Ich hab aber gehört, dass FAT32 auf SD-Karten nicht funktioniert ? Oder ist nur ein Gerücht ?
hallo, @ kalhou es kommt auf die größe der karte an. manche sind zu klein um sie mit fat32 zu formatieren. andere wieder sind zu groß um sie mit fat 16 zu formatieren... welchen controller willst du denn benutzen und wie willst du die karte anschließen? grüße daniel
hallo, kleinere änderungen, grad der optimierung erhöht. ohne lcd, tastatur und benchmark teil, jetzt 709 bytes statischer ram (bei lesen und schreiben mit commando prompt) und 10127 bytes an flash speicher verbrauch. mit allem 740 ram und 11796 flash. compiler optimierung 2 besser als s... grüße daniel
Gast
#933183
Die Karte hängt an einem atmega128 momentan ist sie über hardware spi angeschlossen... d.h. 1Gb sollte mit FAT32 funktionieren ?
Gast
#933373
So... hab jetzt die Library mal ausprobiert. Zuerst hatte ich Probleme, da ich das Ganze in AVR-Studio probierte und daher kein Makefile verwendete, dass mir Studio diverse Fehler zurückgab, die sich mit der Einbindung eines Makefiles praktisch in Luft auflösten. Trotzdem wäre es von Vorteil wenn es auch ohne die Einbindung eines externen Makefiles funktionieren würde ;) Weiter habe ich dann probiert ein paar Zeichen aus einer Datei zu lesen.
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
28 | |
29 | |
30 | |
31 | |
32 | |
33 | |
34 | |
35 | |
36 | |
37 | |
38 | |
39 | |
40 | |
41 | |
42 | |
43 | |
44 | |
45 | |
46 | |
47 | |
48 | |
49 | |
50 | |
51 | |
52 | |
53 | |
54 | |
55 | |
56 | |
57 | |
Das Init Zeugs hat funktioniert und wurde mir auch schön auf der UART angezeigt. Scheint das lesen der Datei nicht zu funktionieren. Was ich noch vermisse ist eine Funktion zum beschreiben der Dateien, sowie eine Funktion zum lesen ganzer Strings ;)
hallo, @ kalhou also beschreiben einer datei würde wie folgt laufen:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
-1 die funktion ffopen erwartet als datei bezeichnung einen string im
8.3 format, alles großgeschrieben ! man kann zum wandeln von z.b.
delme.txt" die funktion fat_str nutzen, die macht aus "delme.txt" "DELME
TXT".
-2 str enthält 22 bytes die auf die karte sollen, i ist nur ein index
zähler für den str
-3 in der schleife wird auf die karte geschrieben, der ganze string
-4 schließt die datei (erst hier wird die datei tatsächlich angelegt,
vorher werden nur die daten der datei auf die karte geschrieben)
noch zu 1:
es gibt auch noch ffopen('a',"DELME TXT"); das würde die datei zum
anhängen öffnen, wird dann ab letztem zeichen weiter geschrieben.
nur öffnen zum lesen wäre ffopen('r',"DELME TXT"); und dein obiger
code
Gast
#933930
Zum Verständniss: verwendet habe ich die aktuellste Version "mmc-0.3.1.zip" dort findet sich leider keine Funktion "fat_str"
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
28 | |
29 | |
30 | |
31 | |
32 | |
33 | |
34 | |
35 | |
36 | |
37 | |
38 | |
39 | |
40 | |
41 | |
42 | |
43 | |
44 | |
45 | |
46 | |
47 | |
48 | |
49 | |
50 | |
51 | |
52 | |
53 | |
54 | |
55 | |
56 | |
57 | |
58 | |
59 | |
60 | |
61 | |
62 | |
63 | |
Das Beispiel hier funktioniert nur soweit ich keine Datei auf der Karte habe die "delme.txt" heisst! Wenn ich eine Datei "delme.txt" auf der Karte habe und dann mit dem Modus 'a' den String dranhängen will, klappt das nicht und der Kontroller bleibt hängen (zu sehen an den LEDS (PORTA) die nie angehen. Das lesen schlug in beiden fällen Fehl. 1. Heisst das also, dass man soweit nur Files in Grossbuchstaben ablegen kann ? 2. Warum wurde die fat_str Funktion nicht direkt in fopen integriert ? 3. Wird es in naher Zukunft noch Funktionen geben zum direkten Lesen/Schreiben von Strings ? 4. Wird es ebenfalls in naher Zukunft die Möglichkeit geben mehrere Dateien zu öffnen ? Wäre ja eigentlich keine Sache, da man nur bei fopen eine File Struktur zurückgeben und bei jeder Funktion wie fread auf den Zeiger auf diese Struktur zugreifen müsste :)
hallo, sieh dir mal mit einem hex editor die daten auf der karte an. da wirst du sehen, dass dort 8.3 einträge und lange datei namen drauf sind. bei allen 8.3 datei namen werden großbuchstaben sein. wenn der datei name bzw. die endung nicht 8 bzw 3 zeichen haben, wird mit leerzeichen aufgefüllt, bis 8.3 erfüllt ist! wenn du mit dem pc eine datei auf der karte anlegst, dann wird es bei dem beispiel "delme.txt" einen 8.3 eintrag geben der "DELME TXT" lautet. nur mit diesen 8.3 namen arbeitet die library. fat_str ist aus dem grund nicht in ffopen integriert, weil es auch ohne läuft und ich das ganze so schrumpfen möchte, das es irgendwann auf einen mega8 passt. -1. egal was für eine datei du anlegst, es wird immer ein großbuchstaben 8.3 name mit angelegt. von jedem betriebssystem, dass ich kenne. -3. da ist die funktion zum schreiben von strings...
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
nur so aus dem kopf, sollte aber gehn :) -4. mehrere dateien wird es erstmal nicht geben, aus ram gründen. aber du hast doch schon einen weg aufgezeigt wie es gehen könnte. wenn du es änderst, poste doch einfach mal eine ergebnisse :) zu dem problem mit dem anhängen, werd ich später mal ausprobieren...
hallo, bei mir gibt es mit folgendem code keine probleme:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
benutzt wird die ffwirteString von siehe oben... wegen dem einlesen von strings kannst du dir ja nach dem beispiel was basteln... grüße daniel
Gast
#934329
lesen und schreiben habe ich jetzt soweit geschafft.. werde morgen mal weiter schauen... eine letzte frage bleibt: bei langen dateinamen < 8 zeichen wird das ja mit ~1 gemacht.. also z.b. aus "langer-dateiname" wird "langer~1.txt" wie funktioniert das allerdings wenn ich zwei "ähnliche" dateinamen habe ? also z.b. "langedatei1" und "langedatei2" würden ja dann beide mit "langed~1" abgekürzt... geht das überhaupt ?
daraus wird dann: langed~1, langed~2 usw... ist dann etwas unübersichtlich ;) vorallem wenn es so etwas ist wie langedatei-wichtig-von-chef.txt und langedatei-wichtig-von-frau.txt weil daraus auch langed~1 und langed~2 wird
Gast
#934467
also wenn ich jetzt "langedatei-wichtig-von-chef.txt" und "langedatei-wichtig-von-frau.txt" auf der sd habe wie weiss ich dann welche datei ich mit "langed~1" resp. "langed~2" anspreche ? gruss
Gast
#934554
> wie weiss ich dann > welche datei ich mit "langed~1" resp. "langed~2" anspreche ? Öffnen und nachgucken?
Dürfte wohl für den Controller weniger einfach werden, anhand des Inhaltes einer Datei darauf zu schliessen, wie der originale Dateiname lautet. Es sei denn der originale Dateiname steht versteckt irgendwo in der Datei, was ich mir aber nicht vorstellen kann! Das Problem ist ja, dass wenn ich die Datei "langedatei-wichtig-von-frau.txt" öffnen will, nicht beide Dateien "langed~1" und "langed~2" aufmachen sollte, um herauszufinden welche der beiden jetzt die Datei ist die ich brauche.
Gast
#934633
Auf lange Dateinamen sollte man beim uC grundsätzlich verzichten. Die Auswertung benötigt eine Menge RAM. Man kommt mit den 8.3 Dateinamen eigentlich immer klar. Unter DOS war das früher auch nicht anders ;)
Das Problem ist nur, wenn ich auf meinem MP3-Player eine Datei in Form von "Interpret - Titel" ablege, bekomme ich schon mächtig Probleme, da z.b. ein Album 10 Lieder drauf hat "Interp~1...10" wird schon ein wenig schwierig zum auslesen.
Gast
#934665
>wenn ich auf meinem MP3-Player eine Datei
Ich wusste das du das sagen würdest!
Gut, da macht das Sinn. Welcher 8.3 Name zum
langen Dateinamen gehört ist relativ einfach
rauszufinden: Der 8.3 Eintrag steht direkt hinter
den Einträgen des langen Dateinamens.
Gast
#934854
oder id3-tags auslesen ;)
Gast
#935340
das problem bei den id3 tags ist nur, dass sie unterschiedlicher nicht sein könnten. die einen stehen am anfang, die anderen am ende.. di einen beginnen mit TAG, die anderen mit id3 etc. das tag auszuwerten ist ja noch einfach, da immer 30 bytes reserviert sind.... werds wohl trotzdem irgendwie versuchen alle möglichkeiten auszulesen :o
hallo, das problem von langen dateinamen ist das die auch mal 255 zeichen lang sein können. ich finde, wenn man z.b. einen mp3 player baut, sollte der auch die id3 tags anzeigen wenn er die lieder spielt. es git doch pc programme, die die mp3 sammlungen sortieren und ordentlich tagen... grüße daniel
Gast
#936090
So, hab jetzt ein bisschen mit der Library herumexpermientiert. Was ich probiere zu machen ist z.b. mit ffls(); alle Dateien eines Verzeichnisses auszulesen und statt mit uart an den PC zu senden, die Dateinamen in einer weiteren Datei zwischenzuspeichern. Ist sowas theoretisch möglich oder müsste ich dafür mehrere Files offen haben ? Hab schon ein wenig probiert die Funktionen auf mehrere Files umzuschreiben, aber zu der File Struktur die ich jedesmal als Zeiger übergeben muss kommt auch noch die Fat Struktur dazu, die ja atm. auch statisch ist und welche ich wohl auch irgendwie über einen Zeiger mitgeben müsste, aber um das umzuschreiben bin ich mir zu wenig mit dem FAT Dateisystem vertraut... Jemand eine Idee ? Gruss
hallo, die funktion "lsRowsOfClust(unsigned long int start_sec)" in file-0.3.c bekommt einen start sektor eines clusters übergeben und arbeitet dann selbständig den cluster ab (also die sektoren). und in dieser funktion benutzt du einfach anstatt der uart ausgaben, einen teil in dem du die namen oder was auch immer dich interessiert von der datei woanders speicherst. in dem teil wo die uart ausgaben sind ist die aktuelle datei auf dem struct:file zu finden, mit allen möglichen angaben. in dem struct:fat ist der aktuell geladenen sektor zu finden. macht zusammen: name, attribut, reihe in sektor, den sektor selber, größe, länge, 1.cluster. also alles was man zur weiteren verarbeitung braucht. hilft das? güße daniel
Gast
#936248
Das Problem ist nur, dass wenn ich dort wo die UART Ausgaben gemacht werden, probiere ein anderes File zu öffnen, dies nicht zu funktionieren scheint da er wohl immernoch etwas in der Fat struct am rumschreiben ist und ffopen ja schliesslich auch auf diese zugreift ? Was mir gerade vorhin aufgefallen ist, dass die ffls Funktion mir die Dateien mehrmals ausgibt wenns mehr als nur ein paar auf der Karte hat. z.b. habe ich 3 Ordner gemacht und er hat mir diese 3 Ordner einige Male aufgelistet und dazwischen immer Punkte ausgegeben z.b. wie folgt ORDNER1 ORDNER2 ORDNER3 . . .. .. . ORDNER1 ORDNER2 ORDNER3 . . .. .. . etc.
1) In eine Codesammlung gehört fertiger, funktionsfähiger Code. Sagt ja der Name schon. 2) Gute Programmierkenntnisse der verwendeten Sprache sind dafür zwingend erforderlich.(#include "fat-0.3.c") 3) Es gibt bereits (erprobte) Libs hier in dieser Codesammlung die SD/MMC + FAT unterstützen. Wozu das Rad neu erfinden?
hallo, @ Torsten S. sieh mal in meinen ersten post, 4. zeile... #include "fat-0.3.c" funktioniert doch oder? übersichtlicher ist das auslagern von prototypen in *.h dateien auf jeden fall nicht ! c standart ist, dass jede datei auch einzelnd compilierbar sein soll. ist doch so auch gegeben. warum das rad neu erfinden? weil ich mein eigenes rad will! zudem hat ja wohl selber machen noch den größten lerneffekt. so wie theorie und praxis halt ! @ kalhou schick mir ein image von der karte und dem von dir verwendeten code, dann kann ich dir genau sagen woran es liegt. sonst must bischen selber probieren. bei mir läuft es, das einzige problem sind mit linux formatierte karten, weil die komischerweise das root dir, wenn es nur 1 cluster groß ist mit 0x0ffffff8 als ende markiert haben... und dachte es ist eindeutig, man kann IMMER nur eine datei zum lesen/schreiben/anhängen öffnen! man kann aber durchaus mehrere nacheinander öffnen usw...
Daniel Platte wrote: > warum das rad neu erfinden? weil ich mein eigenes rad will! zudem hat ja > wohl selber machen noch den größten lerneffekt. so wie theorie und > praxis halt ! OK. Warum nicht. Aber bitte erst wenns fertig ist in die Codesammlung. > #include "fat-0.3.c" funktioniert doch oder? übersichtlicher ist das > auslagern von prototypen in *.h dateien auf jeden fall nicht ! Ein großer Fehler, diplomatisch ausgedrückt. Sei froh, das noch keiner von den C-Experten seinen Senf dazugegeben hat. Bitte meine Posting nicht als rumnörgeln betrachten, sondern als konstruktive Kritik um Dich auf den "richtigen" Weg zu bringen. Torsten
hm, meiner meinung nach ist der code schon durchaus brauchbar. vielleicht im falschen forum, mag sein. dann möge es bitte jemand verschieben. bei der letzten version mmc-0.3.zip läuft bei mir mit verschieden formatierungen und cluster größen alles gut. warum sind *.h dateien denn so wichtig? bzw der richtige weg (hatte es ja auch schon geändert..)? bin offen für verbesserungen und anregungen, ist ja der sinn weshalb der code hier öffentlich rumsteht :) güße daniel
Gast
#936451
Könnte ich Morgen mal machen.. hab den code allerdings ein wenig abgeändert. Man sollte allerdings rausfinden was es ist. Zu dem Prototypen: Hab es auch so gelernt, dass man die Prototypen in das Headerfile auslagert und im zugehörigen c File dann einfach das Headerfile dazunimmt. Was wirklich richtig ist weiss ich auch nicht. Vielmehr stört micht, das wenn ich in einem c File z.b. strings.h benutze und im main-File dann eine Funktion aus diesem c File aufrufen will ich dann nochmals strings.h includen muss.
Hier ist mein Beispielcode! Habe gewisse Anpassungen an den Libraries vorgenommen z.b. die Struktur für Fat und File im Headerfile definiert etc. aber der Code sollte allgemein verständlich sein. Auf der SD Karte hatte ich lediglich 3 Ordner (ORDNER1,2,3). Die Karte ist eine 1GB SanDisk und ist mit FAT32 formatiert. Der Code wurde im AVRStudio compiliert, daher stammt auch das Makefile, welches noch im Ordner enthalten ist. Gruss [EDIT] hab gerade gesehen, dass die Karte mit FAT16 mit Vista formatiert war. Hab sie dann FAT32 formatiert und ging gleich. Allerdings bleibt mein Problem das ich während der Funktion ffls(); statt der UART Ausgabe eine Datei und dann den Namen der aktuellen Datei dort reinschreiben will ;)
hallo, werd mir deinen code und den fehler bei fat16-ffls mal ansehen, allerdings leider erst sonntag. bin übers wochenende weg.. grüße daniel
hallo,
hab mir den code angesehen, läuft bei mir problemlos. schade das du kein
image von der karte gemacht hast, mit der es nicht ging. so ist der
fehler für mich nicht reproduzierbar.
zu deinem problem, was du möchtes ist eine datei suchen um dann etwas
damit zu machen oder?
wenn ja:
die funktion ffopen gibt 0 zurück wenn die datei die du lesen/anhängen
willst in dem aktuellen verzeichniss vorhanden ist. wenn 0 zurück kommt,
ist die datei auch schon fürs lesen oder anhängen "vorbereitet", also
mit ffread() / ffwrite() zugänglich. kommt 1 bei ffopen('w',dateiName")
zurück ist die datei vorhanden und muss gelöscht werden vor dem
schreiben.
wenn nein:
hab ich keine ahnung was du machen willst ;)
dann erkläre es mal...
grundsätzlich sollten die datei-operation funktionen in file-0.x.c nur
extern genutzt werden, da so sicher gestellt ist, das alle flags und
structs richtig geladen/gesetzt sind. das war nämlich das problem bei
dem was du wolltest...
z.b. wenn man file.name benutzen will aber dann ffopen aufruft, läd
ffopen was neues auf file.name, weil ffopen eben auch ein dir auf eine
datei durchsucht, und alles mögiche auf file.name landet bevor man das
hat was man will...
grüße daniel
genau gesagt möchte ich alle files eines ordner auslesen und statt dann die filenamen über usart auszugeben, würde ich gerne den filenamen in eine liste eintragen, die dann etwa so aussieht " DATEI1 MP3; Interpret1; Titel1 DATEI2 MP3; Interpret2; Titel2 DATEI3 MP3; Interpret3; Titel3 DATEI4 MP3; Interpret4; Titel4 " das ganze wäre z.b. in einer txt datei eingetragen: Also soll er eigentlich jedes File in dieser Form in eine Liste eintragen (ID3 Tag Erkennung habe ich schon gemacht) wenn ich mehrere Files offen haben könnte wäre das ja kein Problem, da aber die Funktion lsRowsOfClust() selbst auf die File/Fat Struktur zugreifft gibt es ein Problem solange ich nur eine Datei offen haben kann. Was mir in diesem Zusammenhang aufgefallen ist: Du hast ja anfänglich gesagt du würdest kein Support für mehrere Files die offen sind anbieten, da damit möglichst wenig Ressourcen gebraucht werden, allerdings sieht es so aus als wäre in fat-0.x.c eine statische Variable
1 | |
vorhanden die immer 512bytes Platz wegnimmt, ob man nun eine Datei offen hat, oder nicht..
hallo, wieso willst du so eine datei anlegen? ist doch doppelt, weil es diese struktur doch eigentlich schon in dem ordner gibt... man könnte das ganze so erweitern, dass id3 tags ausgelesen werden und mit angezeit werden, anstatt z.b. die länge der datei. ps: hab grade getestet, läuft auch problemlos auf atmegas die nur 1kB ram haben.
Gast
#942212
Hallo, kann man mit der Lib auch formatieren?
hallo, nein kann man nicht und wird man auch erstmal nicht.
Gast
#942855
Daniel Platte (zerrome) Danke für Deine Beiträge in Groß-/Kleinschreibung.
Gast
#942943
> Danke für Deine Beiträge in Groß-/Kleinschreibung.
Da klemmen noch mehr Tasten. Beispiel:1 | |
Gast
#943123
"sUpEr Kommentare"
Gast
#943139
Warum fehlen in so vielen Libs die Formatier-Routinen? Sind die so aufwendig? Kann doch jedes Handy/Kamera außerdem erspart man sich damit die "Kompatibilitätsprobleme" mit Windows etc.
hm, hab mir ehrlich gesagt noch nie gedanken darum gemacht eine formatier routine zu schreiben, wäre sicher nicht besonders schwer. gut, bei gelegenheit mach ich das mal :) groß/kleinschreibung ist einfach nur nervig. ich schreibe außerdem sehr viel jeden tag, da bin ich froh wenn ich mal meine kleinen finger etwas schonen kann (die betätigen shift bei 10 finger tippen).
1 | |
mit einem gecasteten void pointer byteweise auf 4 byte große variablen zu schreiben ist bis jetzt noch die eleganteste lösung meiner meinung nach... güße daniel
Gast
#944289
> Warum fehlen in so vielen Libs die Formatier-Routinen? > Sind die so aufwendig? Man muss für jede Kartenkapazität die passenden Werte (Clustergröße etc.) festlegen. Windows benutzt hierzu noch aus den alten DOS-Zeiten entstandene Werte. Nimmt man willkürlich andere Kombinationen, kann es Kompatibilitätsprobleme mit Windows geben. Deshalb ist es besser, gleich auf einem PC zu formatieren. Außerdem sind alle SD-Karten werkseitig mit FAT16/32 vorformatiert. > Kann doch jedes Handy/Kamera Handy und Kameras können viel. Zum Beispiel auch nette Bildchen und Menüs auf Displays anzeigen. Ist aber kein Problem. Gib einem Mikrocontrollerfreak 0,01 Cent für jedes je verkaufte Handy oder jede Kamera, und er wird Dir jede erdenkliche Funktion in der Lib implementieren ;-) Ich selbst habe z.B. noch nie eine Karte in einer Kamera formatiert. Wozu soll das gut sein? (Fotografiere sehr viel mit Canon EOS 20D) > außerdem erspart man sich damit die "Kompatibilitätsprobleme" mit Windows etc. Wenn man selbst formatiert und nicht alles genau richtig macht, fangen die Kompatibilitätsprobleme mit Windows etc. erst an! Joachim
hallo, hier nochmal eine etwas verbesserte version. bug in run_cmd behoben. benchmark teil kann mit #define benchmark 0 oder 1 ein oder aus geschaltet werden. grüße daniel
bug beim leere datei lesen beseitigt. so das wäre es dann erstmal.
hallo, die neuste version ist erweitert um: ffmkdir - legt verzeichniss in aktuellem verzeichniss an. ffrm - kann jetzt auch ordner löschen. löscht rekursiv ! in der fat-0.3.h ist ein define : #define smallFatSys 1 wird es auf #define smallFatSys 0 gesetzt, dann passt der code in einen atmega8 , mit schreib und lese unterstüzung und kommando prompt ! falls jemand fehler findet, bitte melden !
bugfix in ffrm...
Gast
#946791
Hallo Daniel, erst einmal Danke für die Arbeit die du dir machst. Allerdings habe ich noch ein Problem: (Vorneweg: Ich benutze die Version 0.3.1 und den CodeVisionAVR-Compiler. Ich habe also den Code an einigen Stellen angepasst. Dies betraf in den meisten Fällen jedoch nur Variablendeklaration u.ä..) Also: Ich erstelle eine Datei mit
1 | |
, was auch wunderbar funktioniert. Nun möchte ich an diese Datei jeweils verschiedene Daten (Strings) anhängen (z.B. Datum Uhrzeit ...) und die TXT-Datei später im PC auslesen.
1 | |
2 | |
3 | |
4 | |
Das funktioniert auch noch, allerdings nur bis die Datei eine Größe von 512Byte überschreitet. Lese ich nun die Datei im PC aus, sehe ich nur die Zeichen, die auf den neuen Sektor geschrieben wurden. Dies ist bei allen Vielfachen von 512 der Fall. (Also bei jedem neuen Sektor?) Nun würde mich mal interessieren, ob das ein allgemeiner Fehler ist oder ob ich beim Anpassen an CodeVision einen Fehler gemacht habe. Wenn das der Fall ist, wäre ich für Tips dankbar, wo ich zu suchen habe. ;)
hallo, ja danke. dicker bug in ffwrite und was blödes in ffopen. ist geändert ! och als arbeit würde ich das nicht umbedingt bezeichnen ;) macht doch spass
Gast
#947275
Ok, schon mal Danke fürs Ändern. Mit meinem CodeVision bekomme ich nun leider in so fern Probleme, das beim Linken die Fehlermeldung: "Error(s) occured" during assembly." erscheint. Könntest du mir sagen, an welchen Funktionen Du für die Version 0.4.2 etwas geändert hast, damit ich nicht alles noch mal portieren muss?! also in ffopen, ffwrite & fat_setCluster hab ich schon was gefunden.. schon mal vielen Dank...
Mir ist nun mein ForumPW wieder eingefallen, deswegen nicht mehr Timo,
sondern nun LoLiPoPer.
Ich habe nun einfach noch mal die komplette Version 0.4.2 nach CV
portiert.
Jetzt klappt es schon besser. Aber es läuft noch nicht ganz rund.
Jetzt steht in der Datei, die ich wie oben beschrieben anlege, der erste
Teil (die ersten 512 Bytes) drin, dann ist eine Pause von 512 Byte(nur
Leerzeichen)und ab hier gibt es noch kleine Fehler jeweils wenn die
Vielfachen von 512Bytes erreicht werden.
Kleine Fehler in so fern, dass immer ein paar Zeichen verloren gehen.
Das ganze sieht in der TXT in etwa so aus:
<----512Byte----><----512Byte----><----512Byte----><----512Byte----><---
--...
"text text text "" ""text text tex" "text text t"
| | |
große Lücke kleine Lücke kl. Lücke
Wenn du da noch mal schauen könntest, wäre das klasse..
Macht ja Spaß ;)
hallo, eben erst zurück gekommen... da ist wohl noch eine variable falsch gesetzt gewesen. danke für deine mithlife und geduld. bin selbst die ganze zeit schon am bugs suchen, aber je mehr mitmachen umso besser wird es werden. ist ein wenig umständlich hier nur den auszug zu posten, deshalb als anhang die geänderte file-0.3.c geändert nur eine zeile in ffopen in dem teil:
1 | |
und zwar fehlte die angabe(nach zeile 94):
1 | |
die für ffwrite nötig ist, um zu wissen in welchem sektor des clusters man sich grade befindet. die berechnung ist da auch noch etwas umständlich, wie auch in ffseek...
Servus..
bei der Menge an Code ist es ja ganz klar, dass man mal ne Kleinigkeit
übersieht. Alles klein Problem..
Die von mir beschriebene "große Lücke" ist nun weg. Die kleinen gibt es
allerdings immer noch.
Ich hänge als Anhang mal die Textdatei an, damit du dir selbst n Bild
machen kannst.
In der Datei werden immer Datensätze in dieser Form:
#;NUMMER;DATUM;UHRZEIT;MESSWERT (für Import in Excel)
aneinandergereit. An einigen Stellen fehlen eben einige Daten.
(Wenn du die Datei mit Excel öffnest ist das auch ganz gut zu erkennen.)
Was mir noch aufgefallen ist:
Wenn ich mit ffopen('w',"DATEINAMTXT"); eine Datei anlegen will, diese
jedoch schon existiert, bekommen ich von ffopen nicht immer den
Rückgabewert 1 geliefert. d.h. die Datei wird neu angelegt und befindet
sich dann zwei mal auf der SD-Karte. Die Inhalte sind jeweils die
gleichen und es geht auch nix verloren. Schön is das aber nicht. ;)
Ab und zu ist der Rückgabewert aber korrekterweise auch 0.
So, das sollte erst mal genug sein.. ;)
hallo,
woher kommen die daten die auf die karten sollen denn? sind die auf
jeden fall korrekt? werde morgen nochmal exzessiv testen mit großen
datenmengen und hin und her kopieren von dateien usw...
hattest du die karte neu formatiert, als du den neuen code verwendet
hattest?
wenn nicht könnten so sachen mit ffopen('w',"DATEINAMTXT"); passieren.
werde ich mir morgen aber auch nochmal genau anschauen.
güße daniel
hallo, kann die bugs nicht bestätigen. habe mehrere dateien mit w erstellt, mit a sachen angehangen in verschiedenen größe (vielfachache von 512 usw). läuft immer alles ok. kommen deine daten über den uart? poste doch mal die funktionsaufrufe wie du sie machst. vielleicht werd ich daraus schlauer. als anhang nochmal das aktuellste programm
hmm.. wenns bei dir so läuft, kann es ja eigentlich nur an mir liegen.
Ich poste mal die Funktionsaufrufe, evtl. ist ja dort ein Schnitzer
drin.
Ansonsten kann es ja immer noch sein, dass beim Portieren nach CV was
falsch gelaufen ist.
Vorweg: Die SD-Karte ist eine ScanDisk 512MB.
Formatiert habe ich diese mit WindowsXP Prof. als FAT und auch
mal
als FAT32. (Ich formatiere die Karte auch bei ca. jedem 2.
Versuch
neu.)
Hier jetzt die Aufrufe:1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
28 | |
29 | |
30 | |
31 | |
32 | |
33 | |
34 | |
35 | |
36 | |
dazu die Funktion DV_MESSDATATXTerstellen();
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
Diese Funktion wird in der mainloop jede Sekunde aufgerufen:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
28 | |
29 | |
30 | |
31 | |
32 | |
33 | |
34 | |
35 | |
36 | |
37 | |
38 | |
39 | |
40 | |
41 | |
42 | |
43 | |
44 | |
45 | |
46 | |
47 | |
48 | |
Die Variablen Sekunde_ASCII, usw. sind globale Variablen, die aus einem RTC-Chip stammen. Die Variablen gebe ich im mainloop jeweils zur Kontrolle per UART aus.(Da stimmen die Daten immer.) messdatatxt ist ein globaler String:char* messdatatxt="MESSDATATXT"; Ich hab jetzt noch mal rumprobiert. Folgende Fehler treten auf: - Ein Datenblock 512Byte fehlt ganz(kommt sehr selten vor). - Einige Datensätze fehlen teilweise. - MESSDATA.TXT wird mehrfach erstellt Hoffentlich hab ich hier was falsch gemacht. Sonst wirds ungemütlich..
hallo, also die karte sollte nur dann abgezogen werden, wenn ganz sicher keine schreib/anhäng operation gemacht wird. also besser einen pin mit schalter versehen und erst nachdem der schalter gedrückt wurden und sicher ist, dass die karte nichts mehr macht raus ziehen. oder irgnedwie anders sicher stellen, dass keine operation läuft während man den strom wegnimmt. grundsätzlich sieht dein code ok aus. benutzt du die letzte version der lib? habe mit: fat32 und 4 sektoren pro cluster fat16 und 1 sektor pro cluster fat16 und 4 sektoren pro cluster, getestet. hab über das programm dateien auf die karte geschrieben, angehangen, ausgelesen usw. alles ohne probleme. kannst du evtl. noch fat und file *.c dateien posten, dann schau ich mir mal die änderungen dort an. hast du ein delay in der main, um DV_MessungSpeichern aufzurufen, oder mit timer? güße daniel
moin moin... jipp, den Taster hab ich drin. Bevor ich die Karte abziehe setze ich über einen Taster SD_ONLINE = 0; und DV_MessungSpeichern(); kann nur bei SD_ONLINE ==1; aufgerufen werden.
1 | |
2 | |
3 | |
Ich hab jetzt mal etwas umprogrammiert. Und zwar beim EXTINT6 mit einigem Erfolg:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
sprich: Ich mache die Abfrage, ob eine Datei schon vorhanden ist, indem
ich versuche sie zu lesen.
Was merkwürdig ist: Auch wenn die Datei vorhanden ist, liefert
ffopen('r',..); anscheinend immer 1 zurück.
Damit wird DV_MESSDATATXTerstellen(); jedesmal ausgeführt. ABER:
Es bleibt bei EINER Datei!! (verstehe im mom nicht wirklich warum, aber
das Ergebnis ist das Erwünschte!)
Das Problem reduziert somit auf einen einzigen Fehler:
Wenn ich weniger als 1024Bytes in eine TXT-Datei schreibe klappt alles
wunderbar. SChreibe ich jedoch mehr als 1024Byte in die Datei fehlen die
2. 512Bytes (bzw sind diese mit Nullen(Leerzeichen) aufgefüllt). Danach
ist wieder alles OK.
DIe Lib ist die 0.4.2!
Ahja, und DV_MessungSpeichern(); wird nach einem delay aufgerufen.
(Das auch nur zur Probe. Später soll das dann per Taster laufen.)
Im Anhang sind noch die File.c & die FAT.c. Allerdings in einer
TXT-Datei, da ich den Code erst mal einfach in die MAIN.c geknallt habe.
Hoffe, du musst nich zu viel Aufwand betreiben..
ALso schon mal Danke..
hallo,
ich kanns nicht sehen, aber du sorgst doch dafür, dass bei programmstart
file_flag mit 0 initialisiert wird(ein ffclose macht das auch..)? es
gibt nämlich nur 3 möglichkeiten warum ffopen('r',datname); 1 zurück
gibt.
1. wenn file_flag nicht 0 ist.
2. wenn die datei nicht im aktuellen verzeichniss gefunden wurde.
3. wenn das laden des 1. sektors der datei fehl schlägt.
ich habe in der option bei ffopen im write teil etwas geändert,
erscheint mir sicherer, änder das auch noch grad.
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
warum bei daten größer 1024 dieser bug bei dir auftritt ist mir grad noch ein rätsel, schau ich mir aber noch genau an. nach dem delay hatte ich nur gefragt, um sicher sein zu können, dass da kein interrupt irgendwo reinpfuscht :) für mich wäre noch interessant, wieviele sektoren pro cluster hat die karte mit fat32 formatiert? wenn du das so grad nicht nachsehen kannst, mach einfach mal sowas nach der fat init:
1 | |
2 | |
3 | |
4 | |
ach was mir grad noch einfällt, wie ist die karte an den avr angeschlossen? da können auch mal ein paar bytes verloren gehen wenn die kabel zu lang oder so. bin selber jetzt auch auf einen 74hc4050 umgestiegen um die karte zuverlässiger anzuschließen (kostet 40 cent). grüße daniel
Mal wieder Hallo!;)
Das file_flag hatte ich nicht expliziet mit 0 initialisiert. Ich dachte,
sowas läuft über die Initialisierung von fat_initfat();
Probiert hab ich das jetzt aber mal (auch mit ffclose(); beim
Programmstart), bringt aber keine Änderung.
Den Teil in ffopen hab ich aktualisiert.
Am Anschluss der Karte kann es eigentlich nicht liegen, da ich das
"Savvy128"-Board von chip45.com verwende.
Interrupt verwende ich schon, allerdings schalte ich die bei jedem
Zugriff auf die Karte mit #asm('cli'); aus.
(Ext. Interrupt vom RTC-Chip)
Deinen Code zur Sektorenbestimmung liefert bei FAT32 den Wert "8" und
bei FAT den Wert "16".
hmm.. mit dem Umweg über ffopen('r',..); zur Dateienerstellung kann ich
leben, nur das Löschen der Daten wenn ich mehr als 1024 Byte schreibe
stört schon.
also, nach nochmaligem debugen kann ich einen fehler da aussließen. wichtig ist einfach nur die reihenfolge: 1. ffopen 2. ffwrite/ffread 3. ffclose dann kann da nix schief gehen. irgendwo fehlt warscheinlich eine kleinigkteit in deinem code, irgend eine änderung die ich gemacht habe, die du aber nicht gemacht hast. probier mal einfach so in einem test programm, die funktionalität der fat-lib (neuste version mmc-0.4.3.zip). so kommst du vielleicht auf den fehler. hab auch nicht deinen ganzen code um mir das mal anzusehen. z.b. hast du
1 | |
2 | |
3 | |
4 | |
5 | |
das so geändert. da wird beim schreiben von einem byte immer direkt auch eine unnötige long int operation gemacht (4 byte operation), das ist ungünstig. die von dir beschriebene lücke klingt für mich so, als wenn da ffclose irgendwo falsch aufgerufen wird. grüße daniel
hallo, als anhang mal eine ganz einfache nutzung der lib. erstellt eine datei, schreibt daten rein und hängt daten an. erstellt einen ordner und erstellt die datei nochmal darin. grüße daniel
Hallo, saubere Arbeit! Vielleicht wäre es bald übersichtlicher einen wiki Artikel zu schreiben, wo auch Minimal und Optimalschaltplan drin sind und immer die neuste Version drin steht. Eine SD Lib für Codevision wäre super, poste also bitte mal den Code sobald er läuft. Viel Spaß noch Kai
hallo, @ Lolipop Er wie siehts denn jetzt aus bei dir? läuft es oder nicht? wenn es dir nichts ausmacht, poste doch auch mal so eine mini version mit den änderungen für codevision. falls das noch nicht läuft, können ja vielleicht auch andere mal mitschauen. @ Kai Franke zum thema wiki, hab ich noch nie gemacht. interesse scheint auch nicht allzu groß zu sein. übersichtilicher wäre es allerdings schon ;) grüße daniel
hey Daniel, jetzt rennt er!! ;) Ich habe noch mal die Version 0.4.3 neu portiert. Anscheinend war die Kleinigkeit, die Du da geändert hast ausschlaggebend. Bevor ich das online stelle, möchte ich noch mal ein bisle mit den Ordneroperationen rumspielen um zu sehen ob das auch fehlerfrei funktioniert. Und alles n bisle ordentlich machen. (also *.c - & *.h files erstellen.) Müsste ich bis heut Abend hinbekommen. bis dann..
hallo, äh ja, ordner operationen da gibt es noch was... tritt selten auf, aber hier der bugfix, sorry. muss man denn viel ändern zu codevision? ist doch auch ein standart c compiler, oder?
Da ich bis zum 15. meinen Artikel für den Artikelwettbewerb fertig haben muss, werde ich wohl bis dahin auch wissen wie man einen wiki Artikel erstellt und biete an auch für diesen Artikel einen zu erstellen. Ich sage dann nochmal Bescheid, dann könnt ihr mir ja beide eure Errungenschaften schicken und ich vereine sie im wiki. Editieren und hinzufügen wird ja jeder hinbekommen :P Gruß Kai
Soo.. denn stelle ich mal den Code online. So viel ist nicht zu ändern für CV. Hauptsächlich die Variablendeklarationen. Ist aber schon immer etwas Aufwand. Aber nun hab ichs noch mal mit der V0.4.4 gemacht. (Allerdings hab ich die Funktionen nicht noch mal sauber formatiert.) Wenn da noch irgendwo was zukommt, änder ichs auch gern noch mal.(Wäre natürlich schöner, wenn ich wüßte in welchem Teil was geändert wurde, dann muss ich nicht alles neu machen.) Der Code wurde auch nicht in irgendeiner Weise extrem optimiert. Wichtig war mir in erster Linie, dass alles einwandfrei funktioniert und das ist, soweit ich weiß, auch gegeben. @Daniel: Wenn Fehler gemeldet werden, wäre es klasse, wenn du da mit nachschauen könntest und ich übernehme die Änderungen für CV.
hallo, @ Kai Franke fänd ich super, wenn du daraus einen wiki artikel machen würdest. ich schreibe gerne ein paar allgemeine sachen zur fat oder auch speziell zu dem code oder so... @ Lolipop Er werde die änderungen die ich jetzt ab version 0.4.4 mache in den dateien dokumentieren. angepeilt ist so ab version 0.5.x dass die statische variable sector[512] dynamisch übergeben wird. so könnte man, wenn das programm grade nicht den fat teil nutzt, 512 bytes ram sparen. werde mir später mal deine umsetzung ansehen. grüße und danke für die aktive teilnahme daniel
Gast
#961036
Hi. Leider funktioniert das schreiben nicht bei mir. Er hängt sich immer bei ffopen auf... Was ist da los? Gruß Flo
hallo, seltsam, also die initialisierung klappt? was benutzt du für eine karte und wie ist die karte angeschlossen? wie lautet der genaue aufruf von ffopen, also mit welchen parametern usw. du benutzt die aktuelle version (mmc-0.4.4.zip)? grüße daniel
Gast
#961179
Ich benutze version 0.4.4.
Habe den ATMega128.
Die SD karte ist am Hardware SPI interface angeschlossen.
ffopen gibt 1 zurück.
//**********************************************************************
*******************************************
int main(void){
lcd_init();
lcd_string("Computer start",0);
RoteLED();
set_cursor(0, 3);
lcd_string("0%",0);
//----------sd-karte initialisieren----------
if(mmc_init() !=0)
{
lcd_clear();
lcd_string("Keine SD-Karte ist eingesteckt.",0);
while(1);
}
//----------sd-karte initialisieren----------
set_cursor(0, 2);
for(int i=0;i<16;i++)
{
lcd_data(0xff);
_delay_ms(10);
}
set_cursor(0, 3);
lcd_string("100%",0);
_delay_ms(1000);
lcd_clear();
//----------fat initialisieren----------
if(fat_initfat()!=0)
{
lcd_clear();
lcd_string("Fat konnte nicht gelesen werden!",0);
while(1);
}
//----------fat initialisieren----------
lcd_string("FAT-16 gelesen",0);
if(ffopen('w',"DELME TXT")==1)
{
lcd_clear();
lcd_string("File konnte nicht angelegt werden!",0);
while(1);
}
//2
unsigned char str[22]="das soll auf die karte";
unsigned char i=0;
//3
do{
ffwrite(str[i]);
i++;
}while(str[i]!='\0');
//4
ffclose();
set_cursor(0, 2);
lcd_string("Fertig",0);
while(1);
return 0;
}
Ist da was falsch?
Gruß Flo
hm, ffopen mit option 'w' gibt auch 1 zurück wenn die datei schon vorhanden ist. versuch mal ein
1 | |
vor dem öffnen mit ffopen. das würde die datei löschen für den fall das sie da ist. sieht sonst richtig aus...
ach was ich grad sehe, der code von dir ist teilweise aus einem blöden beispiel... der string str[22] müsste 23 zeichen lang sein, weil "das soll auf die karte" sind 22 zeichen.
Gast
#961217
Also habe den Code nun geändert. Jetzt geht das Programm glatt durch (ohne Fehlermeldungen). Doch auf dem PC wird keine datei angezeigt. (Auch im Hex-editor sehe ich keine neuen einträge!) Irgendwas stimmt da nicht... Gruß Flo
hm das ist mal komisch. ist die karte vielleicht partitioniert? dann muss man das umstellen auf: #define superfloppy 0 in der fat-0.4.h standartmäßig ist das so eingestellt, das die karte unpartitioniert ist. würde erklären warum der pc keine daten sieht, aber die initialisierung der karte am mc durchläuft und auch geschrieben werden kann. bei fat_initfat() wird nicht auf sinnigkeit der ausgelesenen daten geprüft. ergo landen die daten an merkwürdigen stellen der karte, weil die bereiche der fat falsch ausgelesen werden...
Gast
#961941
JUHUHUHU es klappt. Genau der Fehler war es... ^ Einfach #define superfloppy auf 0 stellen und ich kann lesen und schreiben!! Vielen Dank. Gruß Flo
hallo, schön das es klappt. muss mir mal überlegen wie ich erkennen kann ob im sektor 0 ein mbr steht oder der erste sektor der fat, dann könnte man das automatisieren... grüße daniel
ein neues update. die änderungen sind in den *.c dateien dokumentiert. änderungen nur in der fat-0.4.c und file-0.4.c. grüße daniel
äh hier auch noch die dateien...
Gast
#971735
Hallo, mich würde interessieren ob ihr auch solche Probleme mit dem Compiler habt in AVR-Studio. Mit jedem Fehlermeldung die ich beseitige, erscheinen 10 andere. Das ist ja nichts besonderes :D aber irgendwann war ich mit meinem Latein am Ende... Hat einer von euch eine fehlerfreie AVR-Studio version? lg alex
Gast
#971812
Ich nochmal, das Problem mit den mit AVR-Studio lag wohl am Projekt an sich. Nach einem Computer-Neustart und eines neuen Projekts hat das compiling fehlerfrei funktioniert. Bei meinem ATmega88 bedeutet das mit -0s Program: 7498 bytes (91.5% Full) mit smallFileSys 0. Habe noch zwei Fragen: 1. Wie wirkt sich smallFileSys auf den Funktionsumfang aus? 2. Gibt es ein switch für NUR Schreibzugriff? Bzw. welche Funktionen kann ich weglassen um mehr Programmspeicher zu haben. lg alex
hallo,
bei "smallFileSys 0" fällt das löschen von dateien und das rekursive
löschen von ordnern weg, das anlegen von ordnern und das wechseln in
einen höheren ordner auch ("cd.." quasi). der rest ist dabei.
einen schalter um nur schreib bzw lese zugriffe zu machen hatte ich auch
schon vor. werd ich auch die tage noch machen. das problem dabei ist,
dass einige funktionen die zum lesen gebraucht werden auch zum schreiben
gebraucht werden, ich kann grad nicht so abschätzen wieviel kleiner das
wird. nur lesen wird man wohl auf weniger als 3 kByte bekommen.
bei mir gab -O2 den kleinsten code
gruß daniel
also, ich bekomme eine nur lesen version auf 3618 bytes code gedrückt, ohne weitere optimierungen und ohne tolle ff-funktionen wie ffseek usw. eine nur schreiben variante wird aber nicht viel kleiner werden können als 5990 bytes an code. das liegt daran, dass man ja auf jeden fall auch das dateisystem lesen muss um schreiben zu können... will man ein verzeichniss wechseln können, muss der ganze lese kram mit rein... möchte man nur einen daten logger bauen, so wird wohl ein atmega88 oder 8 mit 8 kBytes flash reichen, will man da mehr, braucht mann mehr flash. grüße daniel
Gast
#972840
Hallo, das hört sich ja sehr gut an :D Ich bin an der nur schreiben variante interessiert, wäre nett wenn du das mal bei gelegenheit zu verfügung stellst. viele Grüße alex
hallo, sorry hat etwas gedauert... die änderungen sind nicht wild... avr-size main_.hex mit den schaltern (nur schreiben ohne große datei funktionen) :
1 | |
2 | |
gibt nach dem kompilieren 6538 bytes an code an. sind doch 500 mehr, weil ich übersehen hatte das man beim schreiben auf jeden fall auch noch ffseek braucht. mit den schaltern (komplette unterstützung):
1 | |
2 | |
wird der code 8228 bytes groß. mit den schaltern (minimal system, nur lesend):
1 | |
2 | |
wird der code 3618 bytes groß. güße daniel
Gast
#980616
Hallo!
Danke für die Bibliothek!
Insgesamt laufen die Funktionen ganz gut. Mit 2 Sachen habe ich jedoch
noch einige Probleme:
1. Die Funktion ffopen('w', ...) braucht bestimmt 10 Sekunden um zu
Entscheiden, dass die Datei nicht vorhanden ist, und eine neue angelegt
werden muss. Ist das normal? ffopen('a', ...) braucht nämlich nur wenige
ms.
2. Die Funktion ffopen('a', ...), bzw. das zugehörige ffclose schließt
die Datei nicht korrekt, sodass sie anschließend am PC (oder MAC) mit
1,32 GB Größe angezeigt wird. Eine Idee, wodran das liegen könnte?
(Atmega 2560 mit 2GB SD und 64MB MMC Karte).
MfG Thomas
hallo, -1 nein das ist alles andere als normal. es sei denn man möchte eine datei in einem ordner anlegen in dem es schon sehr sehr viele dateien/ordner gibt. -2 poste doch mal eine funktionsaufrufe damit ich mir ein bild davon machen kann woran es liegt. wie sind die karten formatiert, also mit fat32 oder fat16? mit welchem betriebssystem sind die karten formatiert worden? hast du sie vor der benutzung der lib neu formatiert? klingt ein bischen so als würde fat_loadFileDataFromDir irgendwie ne macke haben, weil alle drei optionen/funktionen diese funktion nutzen, also ffopen (w/a) und ffclose auch, wenn mit ffopen(a) geöffnet war... schau ich mir mal genauer an...
Gast
#980906
Hey, der ganze Aufruf sieht in etwa so aus:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
Ich benutze die KArten mit FAT16, mit FAT32 funktioniert es nicht. Formatiert mit Windows, jedoch formatiere ich die Karten nicht nach jedem Versuch neu. (Ist ja eigentlich auch nicht der Sinn der Sache) Einstellung für:
1 | |
2 | |
Ansonsten arbeite ich mit Version 0.4.4, da die Änderung zu 0.4.5 nicht groß genug schienen. Habe relativ viel an den Header Dateien geändert, um sie schön einzubinden. (Von wegen - wer darf was sehen, und warum / warum nicht) - komme von Java, und da ist das alles etwas schöner.
hm, die header dateien sind relativ egal denke ich. es kann sein das wegen der partition irgendwo ein bug ist. versuch mal die karte unpartitioniert zu benutzen, dass sollte auf jeden fall problemlos funktionieren. ich komme erst später heute abend zum testen... ich gehe mal davon aus das nur die header dateien geändert wurden, falls nicht, müsste ich mal den ganzen code sehen. güße daniel
hallo, es gab keine bugs in dem partitions bereich, hätte mich sonst vorher mal gemeldet. hier trozdem mal eine neue version, ist schneller geworden, aber auch etwas gefährlicher ;) es ist jetzt umbedingt erforderlich zu prüfen ob richtig geöffnet wurde bevor man schreibt ! ein beispiel:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
nur wenn ffopen null zurück gibt wird ffwrite aufgerufen. ffwrite prüft nicht mehr ob öffnen erfolgreich war. zudem ist ffwrite und ffread inline geworden. code ist allgemein kleiner geworden durch vielfache optimierungen ! durchschnittswerte mit einem atmega168 @ 16 mhz: 165 kByte lesend 146 kByte schreibend
...
hier mal noch der erste wiki versuch... http://www.mikrocontroller.net/articles/FAT32 werde da noch weiter daran arbeiten. jeder der zu fat etwas beitragen kann/möchte ist eingeladen dort mitzuarbeiten... grüße daniel
Gast
#994837
Hallo Daniel Ich finde deinen Quelltext für die SD-Karte eine gute Idee. Habe allerdings aber auch meine Probleme damit. Ich verwende: AVR-Studio ATmega32 mmc-0.3.1.zip Mein Problem: Trotz intensiver Fehlersuche habe ich es bis jetzt nicht schaffen können ein Hexfile mit deinem Quelltext zu erstellen. Habe die 0.3.1 Version genommen weil dort auch die Routine für ein LCD dabei ist. Ich bekommen immer Fehlermeldungen. Habe deinen Quelltext nicht verändert. Die Fehlermeldungen habe ich in den Anhang gepackt. Wäre nett wenn du oder jemand anderes sie mal anschauen könnte. Weiß gerade nicht mehr weiter, ist bestimmt nur ein dummer Fehler aber steh da jetzt auf dem Schlauch. Gruß Alex
hallo, ja hm das avr-studio... hab da letztens auch mal die dateien kompilieren wollen, ging aber nicht. irgendwie löst das die c abhänigkeiten nicht alleine?!?. am einfachsten ist es wenn du das makefile das bei meiner lib babei ist benutzt. beim avr-studio kann man in den projekt eigenschaften ein externes makefile angeben. dann gehts. außerdem ist dringend davon abzuraten eine ältere version als 0.4.5 zu nutzen (besser 4.5.6), da doch noch einige fehler in den vorherigen versionen waren. um ein lcd zu nutzen, könntest du einfach die lcd routinen mit übernehmen... güße daniel
Gast
#994986
Danke Werde ich gleich mal ausprobieren. Gruß Alex
Gast
#994997
In file-0.4.h >extern unsigned char ffmkdir(char name[]); // legt ordner in >aktuellem verzeichniss an. > >#include "file-0.4.c" So etwas tut man nicht! *.c Dateien sollte man nicht per #include einfügen.
also über das makefile oder wie? bist du Holger Klabunde?
Gast
#995079
Naja zumindest habe ich jetzt nicht mehr so viele Fehlermeldungen aber. Aber er erstellt mir kein Hexfile. Woran kann das denn liegen? Hab mal mein ganzes Prog angefügt vieleicht weißt du ja Rat. (alles Unveränderte Dateien von dir) Danke für deine Bemühungen Gruß Alex
hallo, hab grad kein windows da um avr-studio zu starten. aber ich meine mich zu erinnern, dass ein projekt und die haupt c datei gleich heißen müssen. also solltest du ein projekt namens main_ erstellen und da dann alle dateien einfügen... gruß daniel
Gast
#995098
Ne hat leider auch nicht funktioniert. Trotzdem danke Versuche noch ein bischen rum wenn ich ne Lösung finde poste ich die. Alex
Gast
#995108
probier mal das hier. wenn das nicht geht ist dein avr-studio schrott
Gast
#995200
hm, nee seh grad mit meinem avr-studio projekt kann das auch nicht gehn, weil der pfad zu den dateien nicht stimmt und der pfad zum kompiler warscheinlich auch nicht. na ja was auf jeden fall geht ist ein neues projekt mit namen main_ zu erstellen, dann avr-studio schließen und die dateien main_.c usw in das projekt verzeichniss kopieren, dort die vom avr-studio erstellte datei main_.c überschreiben. dann das studio wieder starten. eventuell noch das externe makefile einstellen.
Gast
#997546
So hab noch lange rumprobiert aber leider keinen Erfolg gehabt. Mit der Version 0.4.6 lässt sich kein Hex File erstellen. Jedoch mit der Version 0.3.1 ist dies kein Problem. Wieso das so ist weiß ich nicht und kann ich mir auch schlecht erklären. Hab die AVR Progs extra neu runtergeladen und neu installiert, sogar auf anderen PC´s probiert. Leider alles ohne erfolg vielleicht hat ja jemand anders noch nen Rat. Würde ja gerne wissen was das Problem genau ist. Gruß Alex
hab jetzt mal die header dateien so umgebaut wie die portierbarkeit wohl am größten ist. leider zu lasten der ausführungsgeschwindigkeit. alleine durch die header dateien gehen 20KBytes pro sekunde lesend verloren...seltsamerweise wird der code kleiner aber auch langsamer... @ Alex probier mal die neue version, damit sollte es besser klappen. ich denke es liegt nicht am code der 0.4.6 sondern am einbinden im avr-studio, daher könnte es mit der 0.4.7 einfacher sein. grüße daniel
Gast
#997863
Die wenigsten werden WinAVR unter /opt/cross installiert haben ;) CC = /opt/cross/bin/avr-gcc OBJCOPY = /opt/cross/bin/avr-objcopy OBJDUMP = /opt/cross/bin/avr-objdump SIZE = /opt/cross/bin/avr-size NM = /opt/cross/bin/avr-nm
Gast
#997899
hmmm... 20kB/s weniger ist schon interessant. Wahrscheinlich konnte der Compiler bei deiner ersten Version (wo er ja alles in einer einzigen Datei bekommt) besser optimieren durch z. B. Inlining (was den größeren Code erklärt). Durch die Aufteilung ist es jetzt allerdings besser in die Verwaltung von IDEs wie dem AVRStudio einzubeziehen. Btw. Super Sache, dass du deinen Code zur Verfügung stellst. Steffen.
Gast
#998650
hab das Makefile mal umgeschrieben und volgendes verändert # Define programs and commands. SHELL = sh CC = /WinAVR/bin/avr-gcc #OBJCOPY = /WinAVR/bin/avr-objcopy #OBJDUMP = /WinAVR/bin/avr-objdump #SIZE = /WinAVR/bin/avr-size #NM = /WinAVR/bin/avr-nm AVRDUDE = avrdude REMOVE = rm -f COPY = cp so kriege ich auch ein hexfile erstellt aber ob das jetzt auf dem atmega läuft werde ich dann später erst sehn. Oder könnte es sein das es ohne die auskommentierten Pfade nur so scheint als sollte es Funktionieren? Warte noch auf den uc momentan hab ich leider keinen da. Danke für eure Hilfe. Gruß Alex
Gast
#998822
geht das nicht auch so? # Define programs and commands. SHELL = cmd.exe CC = /WinAVR/bin/avr-gcc.exe OBJCOPY = /WinAVR/bin/avr-objcopy.exe OBJDUMP = /WinAVR/bin/avr-objdump.exe SIZE = /WinAVR/bin/avr-size.exe NM = /WinAVR/bin/avr-nm.exe AVRDUDE = avrdude.exe REMOVE = del -f COPY = copy bei "del -f" bin ich mir nicht sicher ob del den parameter f kennt, warscheinlich nicht, da müsste man mal nach adequatem ersatz suchen. "rm -f" -> "Löschen. Ignorieren nicht vorhandener Dateien, keine Nachfragen." copy müsste aber so gehn gehn.. grüße daniel
lol moment bei windows wird das warscheinlich eher c:\WinAVR\bin\avr-gcc.exe heißen... mit optimierung s wird der code jetzt wieder kleiner als mit 2 und der geschwindigkeitsverlust geht auf 10KBytes /sec zurück. also von 165 auf 155KB damit kann ich leben (atmega 168 @ 16mhz).
Gast
#1000221
Der Pfad zu Winavr wird doch in die Path-Variable eingetragen, sollte es nicht reichen die *.exe anzugeben? Er wird sich dann schon einen Pfad suchen... Hab es nicht probiert! Steffen.
neue version kleine änderungen. mit windows und linux makefiles usw..
Moin Daniel, wollte mich heute auch mal näher mit deinem SD-Code beschäftigen, nachdem meine Platine ansonsten funktioniert. Die Funktionsweise sieht verständlich aus. Was mich momentan am Einsatz hindert ist, dass SPI, Usart wie auch die Command-Shell fest mit dem eigentlichen Code verbunden ist. Da ich hierfür bereits eigene Bibliotheken habe.... wie kann ich diese auf Dauer am besten einbinden und zwar so, dass der Wartungsaufwand bei einer Codeaktualisierung deinerseits nicht zu umständlich wird? Oder hast du schon einmal überlegt, die ganzen relevanten #defines in eine Config.h auszulagern. Hierin könnten z. B. Methodennamen für Usart und SPI definiert sein oder auch, ob file.h->methode() auf den Usart ausgeben soll.... Und diese Datei wäre dann problemlos anpassbar durch einen anderen Anwender. Anders gefragt - wenn ich dir einen entsprechenden Patch schicke würde, hättest du Interesse? cu, Michael
Ich nochmal.... anbei als zip eine kleine Abwandlung deiner Lib mit einem globalem Config-Header-File. Es kompiliert; ausprobiert habe ich es aber nicht. Zur Idee: In mmc_defs.h werden für uart, spi und spi hardware die entsprechenden Methodennamen als #define angegeben. Beispiel Uart:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
Möchte ich einen anderen Uart-Code verwenden, so include ich die entsprechende Header-Datei und passe die Methodennamen an. - ugets wird z. Zt. nicht verwendet. - Die SPI Methoden sollte man nochmal überdenken... da wollte ich dein Feedback abwarten bevor ich deinen Code vollständig verstehen will Somit kann ich flexibel unterschiedliche Basisfunktionen für die Peripherieansteuerung verwenden (buffered, unbuffered usart; hardware spi, software spi; evtl. debug Lösungen) und bin deutlich flexibler, was die gesamte Konfigurierbarkeit anbetrifft. Die restlichen Code-Dateieen enthalten jetzt nur noch die SD-Card-Logik allein. Was hälst du davon? Michael
hallo Michael, gute idee das so zu ändern, dass man unterschiedliche "unterbauten" nehmen kann, würde es auch einfacher machen das ganze auf andere controller zu portieren. eine globale "hardware" header datei zu machen, wo die funktionen vom spi und die funktionen des uart, also der hardware anbindung der karte und der ausgabe, definiert werden ist eine gute lösung. die von dir beschriebenen vorteile sind es wert. leider komme ich vor freitag wohl kaum zur umsetzung, weil ich umziehe und lernen mich voll in beschlag nimmt. bis spätestens sonntag sollte es aber ohne probleme drin sein, wie im einzelnen, werde ich mir noch überlegen. weitere ideen sind sehr willkommen ! grüße daniel
Moin Daniel,
Das klingt ja sehr schön :-) Wenn du Zeit hast, dann schau dir meine
Abwandlung mal an... vielleicht sind ja ein paar brauchbare Ideen drin.
Eine "globale" Hardware-header-Datei würde ich zuerst mal auf die
mmc-lib beschränken. Warum? Viele dürften für die Ansteuerung der
peripherie etc. bereits eigene Code-Sammlungen haben. Die mmc-lib müsste
dann nur noch an diese Libs angedockt werden.
Die SPI Ports und Pins könnte man auch nochmal in eine weitere
Config-Datei auslagern. So habe ich es jedenfalls bei mir gemacht, siehe
Attachement SpiDefs.h
Zweite Idee: Ein Debug-Switch. Ist dieser gesetzt, so wird an eine
ebenfalls frei definierbare Debug-Funktion die aktuelle Aktion (open
file, read directory etc.) gesendet. Sowas kann man schön so
programmieren:
#define MMC_DEBUG 0
#if defined(MMC_DEBUG)
logDebug("bla");
#endif
Anyway, denn erstmal viel Erfolg beim Lernen und Umziehen....
Michael
Gast
#1028708
Hallo, interessant wäre, wenn der SPI-Teil umgearbeitet wird, gleich zu überlegen, ob nicht eine "universellere" Variante erarbeitet wird. Ziel könnte sein, dass mehrere Komponenten am SPI (-Bus) hängen und nicht SS sondern ein Portpin für CS verwendet wird. Beim Senden und Empfangen muss dann zusätzlich noch mitgeliefert werden, welche SPI-Peripherie angesprochen werden soll (SPI-Parameter müssen für jeden Baustein gespeichert werden und evtl. vor dem Senden/Empfangen neu angepasst werden). So könnte z.B. ein zusätzlicher CAN-Baustein oder HC595 angeschlossen werden ohne eine Software-SPI zu benötigen. Besonders, wenn einzelne SPI-Komponenten nur selten benötigt werden (Config.ini auf SD Karte nur zum Start notwendig, HC595 für Relaisansteuerung einmal pro Sekunde...). Steffen.
Moin! Wieso sollte dies ein Problem sein? In der MMC-Config kannst du imho frei definieren, welchen Pin du als SS-Pin verwenden willst. Ob dies nun der "offizielle" SS-Pin des AVRs oder ein anderer Pin ist spielt hierbei keine Rolle. Somit kannst du auch problemlos mehere SPI-Chips oder -Geräte an den AVR anschließen solange du die gleiche Ansteuerungslogik (send_byte etc.) verwendest. Aufwändiger wird es allerdings, wenn du unterschiedliche Busgeschwindigkeiten fahren willst. Da hast du recht. Michael
Gast
#1029030
>Aufwändiger wird es allerdings, wenn du unterschiedliche >Busgeschwindigkeiten fahren willst. Da hast du recht. Genau dort sehe ich der Herausforderung. An der Stelle ist es wahrscheinlich sinnvoll "eine" SPI-Routine zu verwenden. Dann kann man sich merken, ob eine Parameteränderung durchgeführt werden muss oder nicht.
Gast
#1029215
>#define MMC_DEBUG 0 > >#if defined(MMC_DEBUG) > logDebug("bla"); >#endif Das geht auch noch eleganter. In der Headerdatei:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
Im C-Code:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
So kann man mehrere Debugausgaben einzeln gezielt ein und ausschalten. Es wird eben nur das benutzt was man gerade benötigt. Das was man nicht haben möchte einfach in der Headerdatei auskommentieren:
1 | |
Im C Code spart man sich dann auch das
#if defined(MMC_DEBUG)
Ausgabe("text");
#endif
Die Debugausgabe benötigt nur eine Zeile Code statt drei.
MMC_DEBUG("text");
hallo, leider hab ich doch extrem weniger zeit als ich dachte. bugs würden geändert werden, aber mehr ist momentan nicht drin, sorry. nächste woche hab ich wohl etwas mehr zeit, hoffe ich... grüße daniel
Gast
#1049219
Hi Forum, ich hab das nun auch mal ausprobiert mit dem FAT-Treiber... Das Init funktioniert noch einwandfrei - danach geht nicht mehr viel: z.B. ffls() - da hängt er ziemlich lange in einer Schleife, der Grund ist, dass die Variable fat.dataDirSec bei mir auf -2 steht... Wie ist das bei Euch? Ich hab meine Karte unter Win mit FAT16 und FAT32 formatiert - jedesmal mit dem selben Ergebnis... Habt Ihr eine Idee an was das liegen kann? Die eine Karte ist eine MMC 512 MB von Transcend, bei der anderen Karte (Sandisk 2GB) steht in der FAT-Strukur nur Käse - liegt wohl an der Grösse... Schon mal danke für Eure Tipps... Andi
Gast
#1049579
hallo, ist die karte partitioniert? wenn ja musst du #define superfloppy ändern (in der fat.h). -2 ist auch ein komischer wert für einen unsigned long int... grüße daniel
Daniel, hast du inzwischen ein bisschen Zeit gefunden, die Debug- und sonstigen Änderungen einzuarbeiten? Dann könnte ich meine selbstgestrickten Dinge verwerfen und zurück zu deinem Code wechseln :-) Michael
hallo, bin momentan bis oben hin zu mit arbeit... ich hab auch die karten meist selber nur mit linux gedebugt, da hatte ich mir auch eine kleine mmc.c und mmc.h geschrieben, der rest code ist platformunabhänig... das ist die bequemste art den code zu testen. zudem kann man mit programmen wie WinHex auch images von datenträger machen und so kann man sogar ganz ohne mmc karten code debugen und testen. einfach immer eine mmc.c und mmc.h an die hardwaremäßige plattform anpassen, schon ist die lib portiert (sofern standart c darauf läuft). daher tendiere ich momentan dazu die debug geschichte erst in den semesterferien mal anzusehen (wie gesagt, debug mit linux ich wesentlich komfortabler). den rest, also die uart und die mmc/spi geschichte so umzubauen, dass andere bibliotheken genutzt werden können mach ich über weihnachten, als kleines present ;) spass beiseite, da werd ich wohl endlich ein wenig zeit haben mich meinem hobby zu widmen... grüße daniel
Hi, ich versuche gerade die Dateien aus mmc-0.4.8.zip unter Linux zu kompilieren. Das geht auch Problemlos, nur wenn ich den Schalter write auf 1 (read only) setze bekomme ich folgende Fehlermeldungen:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
Ist das ein Bug oder habe ich etwas übersehen. Bei "read only" werden diese Funktionen natürlich nicht gebraucht, aber ich dachte der write Schalter berücksichtigt diese Option. Danke Andi
hallo, besser spät als nie ^^ also, in der main_.c wird auf die schreib funktionen zugegriffen, genauso wie in der command.c . den schalter auf nur lesend setzen funktioniert nicht, wenn man dann doch auf die schreib funktionen zugreift. in der bibliothek selber stimmt das soweit alles. wenn du nur lesen möchtest, musst du dir eine main schreiben und nur auf die lesen funktionen zugreifen... grüße daniel
Gast
#1183754
Hallo, da ich BMPs auf meinem S65-Display ausgeben möchte, die auf der SD_Card liegen, wäre es für mich auch interessant direkt auf sector[] zuzugreifen. Die Funktion ffread() ist dafür zu umständlich. Wie könnte man dies realisieren? Güße Martin
Hallo, also du könntest z.B. aus der fat.c direkt die Funktion:
1 | |
aufrufen. Als Parameter bekommt die Funktion den zu ladenden Sektor übergeben. Danach ist der Sektor auf sector[]. Setzt allerdings Voraus, dass du den Sektor kennst. Wenn du damit BMP's lesen möchtest, muss du ja auch die folge Sektoren kennen. Deshalb ist die ffread etwas umständlicher. Im Regelfall, gibt es aber ja aber nur einen Index der erhöht wird und eine Abfrage... erst wenn man 512 Bytes gelesen hat wird es etwas umständlicher, wegen dem Problem der folge Sektoren. Grüße Daniel
Gast
#1184307
Hallo Daniel, wenn ich Dich recht verstehe, habe ich die Datei *.BMP mit ffopen() zu öffnen. Der der erste Sector befindet sich nun in sector[]. Da die größe der Datei bekannt ist, kann man mit sec++ und fat_loadSector(sec) den nächsten Sector in den Buffer sector[] laden. Dies wiederholt man, bis die ganze Datei geladen ist und schließt die Datei mit ffclose(). P.S Danke für die schnelle Antwort Gruß Martin
Also Prinzipiell schon, aber es kann mehrere Sektoren in einem Cluster geben, diese Cluster können auch nicht aufeinanderfolgen. Deshalb muss man zwischendurch in der Fat nach dem folge Cluster suchen, diesen auf Sektoren umrechnen und dann weiter lesen... Wenn Du das alles beachtest, bist Du genau bei dem was ffread macht. Das Prinzip wie Fat funktioniert habe ich versucht im Wiki Artikel FAT32 zu erklären. PS: Ist Dir ffread nicht schnell genug? Wieso willst Du da was selber machen? Grüße Daniel
Gast
#1184820
Hallo Daniel, ich hatte am Anfang vermutet, dass ffread zu langsam sei. Inzwischen habe ich die Funktion aber benutzt und musste feststellen, das sie für den Bildaufbau schnell genug ist. Dieser dauert für die 176x132 Pixel (1Pixel=2Byte) ca. 1 Sekunde (gefühlt). Mit dieser Geschwindigkeit kann ich leben. Was mir aber noch Sorgen bereitet ist das Schreiben auf SD-Card. Dabei wird die FAT so verändert, dass man die Dateien in Windows zwar noch angezeigt bekommt aber das Löschen wird verweigert. Gruß Martin
Hi Martin, das mit der 1 Sekunde ist seltsam wenn du mit 16 Mhz @ Avr arbeitest, weil mit Deiner Angabe komm ich auf 371712 Bit, ist ja 46464 Byte/Bild, da sollte wesentlich mehr drin sein, oder hab ich mich verrechnet? Zu dem Windows, welches benutzt Du? Vista? Ich bin da nicht ganz Spezifikations-konform, weil normalerweise müsste man die Uhrzeit der Zugriffszeiten (erstellen/lesen...) richtig eintragen. Der Einfachheit halber schreib ich Nullen rein... Hatte beim Testen aber dieses Problem auch nie. Würde Vista ähnlich sehen, beim Datum 00-00-0000 nicht klar zukommen ^^ Güße Daniel
Gast
#1185164
Hallo Daniel, da ich mit 3,3V Versorgungsspannung arbeite, zwecks der einfacheren Anbindung von SD-Card und Display, läuft mein m32 nur mit 12MHz. Nachdem ich zwei Byte von SD-Card gelesen habe muß ich sie in ein Integer umwandeln und noch zum Display schicken, das kostet zusätzlich Zeit. Meine Zeitangabe ist auch nur eine grobe Schätzung, der Bereich ist irgendwo zwischen 0,5 und 1s. Zur SD-Card: Ich habe es mit XP und Linux getestet. Beide behaupten die Karten seinen schreibgeschützt. Das habe ich mit 3 unterschiedlichen Readern getestet, auf die richtige Einstellung des mechanischen Schreibschutz habe ich auch geachtet. Die Dateien die mit 'a' beschrieben wurden seien 1,5GB groß, das behauten beide BS, obwohl die Karten nur 256 bzw. 512MB groß sind. Als Software benutze ich Deine mmc-0.4.8. Hardwareprobleme kann ich zu 90% ausschliessen, da das Lesen einwandfrei funktioniert, das einmalige schreiben auch. Nur das anhängen von Daten an eine bestehende Datei produziert den Fehler. Das Anhängen muß ich aber nochmal genau überprüfen, wenn mir weitere SD-Cards zu Verfügung stehen. Mit meiner letzten mache ich nur noch Lesetests. Gruß Martin
Hallo, nur um mal abzuklopfen, Du hast den Code nicht geändert oder so und Du achtest darauf, dass ffclose() aufgerufen wurde bevor du den Strom von der Karte nimmst, bzw. diese aus der Halterung ziehst (beim schreiben, beim lesen egal). Mich würde dann auch der Aufruf und so interessieren, um abschätzen zu können wo da vielleicht der Fehler liegt. Hab den Code so in der 0.4.8 Version selber im Gebrauch und mit Datei Größen noch nie Probleme gehabt. Grüße Daniel
Gast
#1185621
Hallo Daniel, ich habe Deine Version komplett übernommen und mit meinen Funktionen erweitert. So im nachhinein betrachtet kann ich aber das Abziehen der Stromversorgung bevor ein ffclose stattgefunden hat nicht ausschliesen. Das geht halt in der Softwareentwicklnugsphase nicht immer. Ein reaktivieren der SD-Cards unter Windows blieb bis jetzt erfolglos, Windows meldet immer einen aktivierten Schreibschutz oder behauptet das die Datei text.txt ein Verzeichnis sei. Meine letzte Hoffnung ist nun Linux. Ich könnte auch mal probieren, die Datei mit ffrm() zu löschen. Gruß Martin
Hallo, also auch beim Versuch die Karten zu Formatieren gibt es Fehlermeldungen? Generell ist das sehr seltsam. Eigentlich geht Schreibschutz über Software nur mit einem bestimmten Kommando an die Karte, was aber auch nicht jede Karte unterstützt... Einen Versuch die Datei mit ffrm() zu löschen ist es auf jeden Fall wert. Schlimmstenfalls bleibt ein bisschen Datenmüll in der Fat über. Sollte aber mit einem Scandisk Tool zu beheben sein. Ich vermute, dass im Dateieintrag der Datei irgendwas steht was keinen Sinn macht. Hast Du einen Hex-Editor mit dem Du Dir die Rohdaten auf der Karte ansehen kannst? Davon ein Screenshot wäre super :) Um soetwas zu verhindern, könnte man einen Taster anschließen, der einen Interrupt auslöst und ffclose() aufruft.
Gast
#1187210
Hallo, ich habe es nun mit Linux probiert, alles ohne Erfog. Fdisk und mkfs.msdos werden zwar augeführt (ohne Fehlermeldung) aber danach ist alles beim Alten. Die Dateien sind also noch vorhanden, selbst ein dd if=/dev/zerro of=/dev/sdb brachte keinen Erfolg. Es sieht für mich so aus, als ob der Speichercontroler auf der SD-Karte auf read only steht. Das Komische ist nur, dass es bei zwei unterschiedlichen SD-Cards aufgetreten ist. Einen Hex-Editor habe ich natürlich, was genau soll ich Dir übermitteln? Auf die Idee mit der Interruptroutiene bin ich auch schon gekommen, die wird mir aber nur was bringen, wenn das Programm in einer Endlosschleife fest sitzt. Bei einem Zugriff auf eine falsche Speicherstelle und der nachfolgende Sprung ins Nirvana wird mir die ISR die SD-Card nicht schützen können, weil sie wahrscheinlich nicht mehr ausgeführt wird. Gruß Martin
Hi, also das mit dem Sprung ins Nirvana versteh ich nicht. Wenn Du sagen wir mal konstant Daten wegspeicherst, und ein ffclose wird aufgerufen, wird halt nur die Datei ordentlich geschlossen, also die aktuelle Größe usw. geschrieben. Macht jedes Betriebssystem ähnlich... Also Daten Direkt schreiben und den Fat und Datenbereich zum Schluss aktualisieren. Deshalb kann man bei Usb-Sticks die einfach so herausgezogen wurden (beim schreiben) die Daten meist recovern. Da Du keinen Code gepostet hast, kann ich nicht genau sagen wo der Fehler eigentlich liegen kann... Rechne Dir das mal durch, wie oft man eine Zelle beschreiben kann und wie oft du Tatsächlich schreibst. Interessant wäre für mich der Sektor des Ordners in dem der Dateieintrag steht. Die einzige Möglichkeit eine Karte mit der Lib zu zerstören wird zu oft schreiben auf die Karte sein, dass ist definitiv sicher. Wäre aber auch mit einem großen Betriebssystem nicht anders ! Wenn Du mit Linux und mkfs keinen Erfolg beim Formatieren der Karten hast ist da was ganz anderes im argen. Aber interessehalber, schick mir mal eine. Dann schau ich da nach. Das glaub ich nämlich irgendwie nicht, formatieren mit Linux und dann sind da noch Daten so lesbar?!? Güße Daniel
Gast
#1187307
Hallo, die Screeshots sind noch in der Mache. Habe soeben feststellen müssen, dass WinHex keine Screenshots zulässt. Schicken kann ich Dir auch eine, ich habe schlieslich zwei Defekte. Ich bräuchte halt nur die Adresse. Zum Nirvana: Wenn der Prozessor eine falsche Speicherstelle liest und versucht den Befehl dann auszuführen, wird eine Exception ausgelöst, fals der Befehl nicht bekannt ist. Schlimmer ist es aber, wenn an dieser Stelle ein ausführbarer Befehl steht, der aber nichts mit dem Programm zu tun hat. Das kann den Programmcounter und den Stack verändern. Der Prozessor befindet sich dann in einem nicht definierten Zustand. Wenn jetzt ein Interrupt ausgelöst wird kann alles mögliche passieren, aber bestimmt etwas sinnfreies. Nach dem Formatieren unter Linux habe ich auch ganz blöd aus der Wäsche geschaut, als ich die Dateien wieder gesehen habe. Der Fortschrittsbalken beim Formatieren unter Windows bewegt sich auch bis zum Ende und dann meldet Windows erst einen Fehler. Sinngemäss "Befehl konnte nicht zum Abschluß gebracht werden". Ich denke das war der verify. Ich such mir jetzt einen besseren HexEditor und mache die Screenshots. Kannst Du einen empfehlen? Gruß Martin
Also ich nehm auch immer winhex. Musste halt nen gesamt Screenshot machen... Was hat der Prozessor mit der mmc/sd karte zu tun? Die ganze Geschichte kommuniziert ja über SPI, also AVR <-> mmc/sd Karte. Da hat keiner direkten Zugriff auf Stack oder so des anderen.. Schick mir ne Mail an zerrome aT gmail PunKt com, dann schick ich Dir meine Adresse. Meinst du mit Daten gesehen, dass Du die Daten mit dem Hex-Editor gesehen hast? Wäre klar, weil Formatieren nur den Fat Bereich ändert, sonst müsste ja immer die Ganze Karte platt gemacht werden. Grüße Daniel
Gast
#1187564
Hi, der Screenshot [Alt]+[Druck] bzw. nur [Druck] legt bei mir unter WinHex nichts in der Zwischenablage ab, also nichts mit cut and paste! Der Prozessor arbeit doch wohl die Befehle ab, somit auch die, die für das lesen und schreiben auf SD-Card zuständig sind. Der Stack ist der letzte Speicherbereich im Ram. Dieser wird benutzt um Daten, die einer Funktion übergeben werden sollen aufzunehmen, aber auch die Rücksprungadresse um wieder ins Hauptprogramm oder in die aufrufende Funktion zurückzukehren. Der Stackpointer enthält die letzte benutzte Adresse auf dem Stack. Nachdem ich einen Dateibrowser geöffnet habe, hat mir dieser die Dateien und Verzeichnisse wieder angezeigt. Das sollte nach einer Formatierung eigentlich nicht so sein.top Die Mail schreibe ich heute Abend. Gruß Martin
Hallo, jetzt versteh ich glaube ich endlich was Du mit dem Nirvana meinst... Klar, nach der ISR nochmal ins normale Programm zu springen macht in dem Fall keinen Sinn. Da wäre dann in der ISR ein exit() oder so angebracht. Wenn Du einen Screenshot vom gesamten Bildschirm machst wenn Winhex offen ist geht nichts in die Zwischenablage? Versuchs mal mit dem tool Printkey... Grüße Daniel
Gast
#1196007
Hallo Daniel, ich bin nun so weit, dass mein "AVR-Portable" BMPs mit 24Bit Farbtiefe dank Deiner Lib lesen und auch auf dem Display des S65 anzeigen kann. Ein einfaches Spiel (Pong) habe ich auch schon am Laufen. Was ich nun gerne noch realisieren möchte, ist das Abspeichern von Spielständen. Nun zu meiner Frage: Gibt es eine Möglichkeit mit ffread den Namen eines Spielers auszulesen um den Pointer auf die richtige Stelle hinter dem Namen zu positionieren und dann mit ffwrite den Spielstand zu speichern? Gruß Martin
Hallo, ich glaube ich würde das an Deiner Stelle so machen, ein struct anlegen mit Spielername, Score usw. Für sagen wir, die Top 10. Jetzt aus einer Datei die Daten auslesen und ins struct schreiben. Wenn jetzt ein Spiel vorbei ist, einfach den Score überprüfen und wenn nötig einen aus den Top 10 rauswerfen und den aktuellen Spieler ins struct schreiben. Zuletzt noch das aktualisierte struct wieder in die Datei schreiben. Das Problem ist ja, dass man lese und schreib Vorgänge trennen muss, weil nur eine Datei zum schreiben oder lesen geöffnet werden kann. Wäre mit dem oben beschriebenen Beispiel kein Problem. Denkbar wären auch noch andere Möglichkeiten, solange man lesen und schreiben trennt... Werde mir da mal was überlegen, weil es ja schon schick wäre, eine Datei zu öffnen und dann lesen und schreiben zu können... muss man halt bisschen aufpassen was man macht ^^ Das Problem ist ja nicht das überschreiben von alten Daten (da ändert sich ja nix am Datei Eintrag in FAT und Ordner), sondern wenn über das alte Datei Ende hinweg neu geschrieben wird. Da muss dann ne menge mehr gemacht werden... Grüße Daniel
Hallo, deine SD Karten sind angekommen. Die Controller darauf sind OK. Aber es sind massenhaft kaputte Sektoren. Zu viele. Ich vermute ja bei so billig Herstellern, dass die keine Algorithmen zum mappen von logischen auf physikalische Sektoren einbauen... mkdosfs wirft in der Standart ausgabe (Konsole) keine Fehler, aber dmesg liefert die ganzen Fehler... Die eine Karte kann man sogar an manchen stellen noch beschreiben, die andere weigert sich einfach. Ist eindeutig kaputter Flash, weil die Controller sich noch ordnungsgemäß verhalten. Bin gerade an einer neuen Version der Lib... die 0.5, da wird es große Änderungen geben. Es wird dann auch möglich sein zu lesen und schreiben auf einer geöffneten Datei. Muss aber viel umbauen dafür... Grüße Daniel
Gast
#1203120
Hallo Daniel, die SD-Cards kannst Du behalten, die brauche ich nicht mehr. Was aber komisch ist, sind die haufenweise def. Sektoren, denn die Teile wurden kaum benutzt. Ich bin schon gespannt auf die neue Lib. und stelle mich gerne als Betatester zur Verfügung. (So lange ich noch SD-Cards zum Schießen habe ;-) ) Gruß Martin
Hallo Martin, wenn du magst kann ich die Karten auch zurück schicken, dann kannste Dir die vielleicht auch nochmal ansehen. Mit Massenhaft kaputten Sektoren meinte ich, dass so bei 10 gemeckert wurde. Das ist schon viel, weil eine gute Karte normalerweise noch Reserven hat, die benutzt werden wenn wenn defekte entdeckt werden. Es ist auf jeden Fall Vorsicht geboten bei Flash Speicher.. Die Lib ist jetzt soweit fertig. Bin am testen und Debuggen. Es entfällt der Parameter beim öffnen einer Datei. Also 'w','r', und 'a' sind nun überflüssig. Es wird entweder die vorhandene Datei geöffnet oder wenn nicht vorhanden eine erstellt. Diese kann man dann lesen und beschreiben. Will man an eine Datei etwas anhängen, wird diese einfach geöffnet und mit ffseek(file.length) ans ende gespult. Dann einfach schreiben... Dazu und zu anderen neuen Aspekten aber noch Code Beispiele. Denke ich werde Sonntag die Version mmc-0.5 Posten können. Grüße Daniel
Es gibt noch Probleme bei fragmentierten Fat-Tabellen. Wenn ich das in den Griff bekommen habe ists fertig :) Im Idealfall, wo die FAT unfragmentiert voliegt, kann man 256000 Byte-Blöcke in einem Rutsch lesen. Sollte also auch alles schneller werden. Beim schreiben ähnlich...
Gast
#1212245
Hallo Daniel, wie gesagt, Du kannst die SD-Cards behalten. Ich denke die kannst Du in der Testphase ganz gut gebrauchen. Das hört sich ja schon sehr vielversprechend an. Wie heisst es doch so schön:" Gut Ding will Weile haben!". In diesem Sinne wünsche ich Dir viel Spass und natürlich auch Erfolg. Gruss Martin
Hallo, also wenn ich teste, dann eh nur mit images von Karten, nie mit den Karten selber... Wäre auch viel zu umständlich da immer neu zu Formatieren und Dateien drauf zu kopieren um auf einen definierten Zustand zu kommen. So is das ne Sache von 2 Sekunden... Grüße Daniel edit: Man stelle sich vor, eine schleife läuft Amok und das über mehrere Sekunden/Minuten oder so -> defekte Karte...
Gast
#1213383
Hallo Daniel, das mit den Images von Karten habe ich nicht verstanden, wo laufen die den? Klär mich auf! Gruß Martin
Hallo, also ich mache ein Image von einer Karte (z.B. mit winhex), also von allen Sektoren. Dieses Image öffne ich in meinem c-Programm als Datei (c-Programm auf PC). Diese Datei hat ja die Struktur der Karte und kann somit genau so benutzt werden. Jetzt braucht man nur noch eine angepasste mmc.c und schon kann man problemlos Testen, ohne Karten zu gefährden und bequem am PC. Abschließende Tests mit realer Hardware kommen dann natürlich dazu, aber da geht es nicht mehr so darum ob der Code das macht was er soll... Grüße Daniel
Sooo, ist fertig. Ist gut geworden, schneller und kleiner... Viel Spaß damit. Werde morgen oder so mal das Wiki mit bisschen Doku undso füttern. Wer den Link noch nicht kennt: http://www.mikrocontroller.net/articles/FAT32 Grüße Daniel
Hi, ich bin blutiger Anfänger, zumindest was SD-Karten angeht. Deswegen auch nen Anfängerfrage :) Wie beschalte ich denn so eine SD-Karte? Kann mir mal jemand nen Schaltplan hochladen? Wär total nett! Gruß Matze
Gast
#1219244
Hallo, hab grad keinen Schaltplan da. Das Problem ist ja meistens, dass die Karte 3,3 V braucht und so ein MC meist mit 5 V läuft. Da muss man also Level shiften. Ich mache das immer mit nem HC4050, ist ein Digital IC, dass wenn man es mit 3,3 Volt betreibt auch 3,3 Volt an den Ausgängen hat. Ist aber bis 15 V Tolerant an den Eingängen. Ein Eingang hängt mit einem Ausgang zusammen. Geht glaub ich bis 20 Mhz Frequenz und kostet 20 Cent. Den Ausgang der Karte kann man direkt an den MC machen, da 3,3 V reichen für logisch 1. mc -> hc4050 -> karte (für SCLK,DI,CS) karte -> mc (für DO) Grüße Daniel PS: hab da in der ffmkdir() etwas übersehen, also noch bisschen Vorsicht beim Ordner anlegen...fix kommt bald...
aller besten dank für die hilfee bei der beschaltung! ich habe zwar keine ordner operationen vor, aber ich werde aufpassen :) was den einstieg vielleicht für alle anfänger erleichern würde, wäre ein beispielprogramm, in dem die meisten / wichtigsten funktionen einmal durchlaufen werden (Datei erstellen und öffnen, daten hinein schreiben und anhängen, etc (natürlich auch für ordner)). ähnlich wie die libraries von fleury und seine testprogramme - muß aber nich soo ausführlich und allumspannend sein. ich denke, ein atmega8 hat jeder zuhause rumfliegen... ich muß nämlich gestehen, daß die fülle von dateien und die auf den ersten blick recht kryptischen befehlsnamen einen echt abschrecken können :) gruß, matze
Gast
#1219348
Ja kann ich verstehen, sieht wahrscheinlich echt seltsam aus wenn man sich die fat.c oder so ansieht (und erst der ganze doku Text ^^)... habe da für mich möglichst sprechende und lange Namen genommen... Letztendlich sollen ja für einen normalen Anwender nur die Funktionen aus der file.c sein. Wie ffopen, ffclose, ffseek, ffwrite usw... Ah nicht zu vergessen noch zwei elementare Funktionen mmc_init und fat_initfat, sonst nur Funktionen aus file.c... Mache morgen oder eher Dienstag so ein Mini Beispiel. Bin für Anregungen immer zu haben. Wollte im Rahmen der Dokumentation auch noch eine Beschaltung von MMC/SD Karten (Schaltplan und Fotos) machen. Leider fehlt mir momentan die Zeit um mich richtig aus zu leben in meinem Hobby ^^ Grüße Daniel
Das klingt doch gut. Ich muß nämlich für die Uni Messwerte auf eine SD-Karte bannen und deine Library ist goldwert. - aber einen kleinen Denkanstoß brauche ich wohl noch :) Ich habe vielleicht auch gleich noch eine Anmerkung (bitte versteh mich nicht falsch, ich finde deine Arbeit klasse und ziehe den Hut!): So wie ich das verstehe, kann die Funktion ffwrite nur ein einzelnes Zeichen auf die Karte schreiben. Für viele Anwendungen ist es aber häufig nötig gleich einen ganzen String zu schreiben. Man müßte also jeden "Buchstaben" einzeln anweisen. Wäre es nicht pfiffiger einfach eine Funktion alla:
1 | |
2 | |
3 | |
4 | |
5 | |
zu schreiben bzw.in die file.c zu packen?! gruß matze
Gast
#1219768
Hallo Daniel, ich habe die neue LIB in meine alten Programme eingebaut. Alle funktionierten auf Anhieb. Zum intensieveren Testen komme ich in den nächsten Tagen. Tolle Arbeit, Danke dafür! Gruß Martin
Hallo zusammen, danke das ihr mit testet. Die angesprochene Funktion ffwrites ist aufgenommen. Zudem ist in der fat.c noch eine Funktion fat_str hinzu gekommen, die sonst immer woanders untergebracht war. Mit dieser Funktion kann man einen String von "test.txt" in "TEST TXT" wandeln, so muss ja schließlich alles auf die karte... Anbei sind jetzt, wie ich denke einfache Beispiele zur Benutzung der Lib, für einen atmega8. Der is leider ein bisschen zu klein für den vollen Umfang der Lib (z.B. Ordner Rekursiv löschen und anlegen). Der Bug in ffmkdir ist behoben. Keine weiteren Bugs bekannt... Was mich noch stört, ist die Tatsache, dass mehr als 100 KBytes schreiben möglich wären, aber durch einen blöden Vergleich von zwei unsigned long int (ist nötig wegen der überschreiben Funktionalität) nur 80-85 KBytes geschrieben werden... Muss mal sehen ob das nicht einfacher geht... Grüße Daniel
Hi, ich verzweifel langsam. ich komm einfach nicht durch die mmc_init. ich denke, es liegt an meiner verkabelung. hier eine kleine ascii-skizze :) (ATmega162) --------\ 09 (NC) \ 01 (CS) | ---------- (PB1) 02 (DI) | ---------- MOSI (PB6) 03 (GND) | -------------------------- (-) 04 (VCC) | -------------------------- (+) 05 (CLK) | ---------- SCK (PB7) 06 (GND) | -------------------------- (-) 07 (DO) | ---------- MISO (PB5) 08 (NC) | --------- Ich habe den ATmega162 mit 3,3V laufen, daher kein HC4050 dazwischen. Ich hoffe, daß ist soweit richtig und ich habe nur ein brett vorm kopf. Als quellcode habe ich das beispiel von "mmc_0.5.1" genommen. oder mache ich was falsch, wenn ich mein ISP kabel, das ja die selben ports benutzt, dranlasse? ich komm echt nicht weiter und brauche wirklich hilfe! gruß und danke, matze
Gast
#1224575
Hi, bist du sicher, das überhaupt das Programm drauf ist? Ist ISP nicht mit 5 Volt? Sieht nämlich sonst Ok aus. Wie lang sind die Kabel vom MC zur Karte? Und ja, besser ISP Stecker abmachen. Grüße Daniel
So, habe den fehler nach langem probieren gefunden. irgendwie hat der uart nicht geklappt, wenn der isp nicht angeschlossen war. ich habe jetzt als work-around einfach die masse, an der es lag, von PC zum uC extra gezogen. jetzt geht alles. aber wie zum kuckkuck mach ich nen zeilenumbruch? ich hab schon alles probiert: \n und \r sogar schon den 0x0D (ascii code für zeilenumbruch). hilfe. danke, matze
Hallo,
schön das es jetzt klappt.
Zeilenumbruch wo? Im Terminal Programm?
Je nachdem welches du benutzt musst du das auf vt100 oder so
umstellen... dann sollte uputc('\n') oder uputs("\n") auf jeden Fall
gehen.
Anbei ein Funktionsübersichts Diagramm der ganzen Lib.
Krieg leider die Größe nicht in den Griff. Also hier die Warnung: 2412 x
7946 Pixel :)
ne, im terminalprogramm weiß ich das (ich mach das immer mit 0x0D). aber in der*.txt auf der SD karte. Ich kriegs einfach nicht hin. gruß matze
Gast
#1225336
Hallo, also mein hex Editor sagt bei Windows Zeilenumbruch: 0x0D 0x0A für neue Zeile... Das ist der Hex Code
1 | |
für
1 | |
2 | |
3 | |
Grüße Daniel
Update, bei Linux ist ein Zeilenumbruch nur 0x0A...
Gast
#1226103
Ich möchte jedemenge einfache Bytes in eine Textdatei schreiben. Das klappt auch alles gut, ich mache mir nur gedanken um die Lebensdauer der Karte. Wäre es besser, wenn ich die Bytes nicht direkt mit ffwrite(byte); auf die Karte schreibe, sonderen erstmal in einem großen String speichere und diesen dann später komplett auf die Karte übertrage, oder macht das keinen unterschied? Ich benutzte einen MEGA32, RAM wäre noch genug dar, um z.B. 512Bytes zupuffern.
Hallo, nee das ist kein Problem, da ja schon 512 Bytes gepuffert werden. Halt ein Sektor, bevor geschrieben wird. Was allerdings schlecht wäre, ist nach dem schreiben immer direkt ein ffclose (obwohl man später eigentlich noch mehr schreiben will), weil dabei die Datei Daten ein Update erfahren. Dies bedeutet, dass einmal der Sektor wo der Dateieintrag drin steht neu geschrieben wird und evlt. muss auch die FAT geupdatet werden (wenn mehr Bytes geschrieben wurden als über Cluster schon verkettet sind). Und natürlich der Sektor in dem man gerade geschrieben hat auch. Also einfach öffnen und dann immer mal wieder schreiben ist überhaupt kein problem... Ein Problem könnte sein, wenn man oft innerhalb einer Datei hin und her springt. Beispiel: Ich schreibe in Sektor 1928 ein Byte, jetzt springe ich (mit ffseek) zu Sektor 1929 und schreibe wieder ein Byte, weil ich aber Sektor 1928 verlasse und dieser geändert wurde, muss er vorher geschrieben werden. Wenn ich jetzt zurück springe, passiert das gleiche wie vorher mit Sektor 1928 jetzt mit Sektor 1929. Das ist der schlimmste Fall, weil für nur 1 geändertes Byte immer ein ganzer Sektor geschrieben wird... Würde also 512 Sektor schreib Vorgange (also 512*512 Bytes) für 512 Bytes machen. Das wäre schlecht und langsam... Wenn eine Datei angelegt wird, gibt es mindestens 3 Sektor schreib Operationen. 1. Anlegen des Datei Eintrags im Ordner. 2. Mindestens einen Sektor mit Daten beschreiben (auch wenn weniger Bytes geschrieben werden). 3. Update des Datei Eintrags (Größe usw.). Macht 3 beschriebene Sektoren. Das wird so gemacht, weil wenn schon mal ein Datei Eintrag besteht, kann man mit Recovery-Tools möglicherweise bei Datenverlust Daten retten. Dient also rein der Sicherheit. Nötig wären nur 2 Sektor schreib Operationen... Da ein Sektor (512 Bytes) die kleinste Einheit ist die man auf eine Karte schreiben kann werden ja eben 512 Bytes gepuffert. Grüße Daniel
Gast
#1226600
Ok, vielen Dank dafür!! Das mit dem ffclose werde ich berücksichtigen. Gruß Christian
Hi, ich habe noch einen kleinen Zusatz zur file.c (ist vielleicht etwa übertrieben, aber vielleicht als Addon nicht schlech): Wenn man z.B. Messwerte aufnehmen will, macht ein Zeilenumbruch recht viel sinn. Ich habe in meine file.c daher hinzugefügt:
1 | |
2 | |
3 | |
4 | |
5 | |
Macht zugegebener Maßen nicht in jeder Anwendung sinn, bei mir allerdings schon und ich denke auch bei so mach anderem. Gruß, ein Fan dieser Speicherfressenden Library :) Matze
Gast
#1231436
Hallo Daniel, ich habe nun die LIB ausfuehrlich getestet und muss sagen, dass alles rund laeuft. Meine HireScore-Liste laeuft nun auch und wartet auf die Besten. Gruss Martin
Gast
#1232732
Hallo, ich hab heute die Souce-Files mit WinAVR (ohne mitgelieferte makefile) compiliert und es kommt tatsächlich ein Hex-File. uc=atmega8 optimierung= -Os smallFileSys 0 write 0 superfloppy 1 Program: 7826 bytes (95.5% Full) (.text + .data + .bootloader) Data: 656 bytes (64.1% Full) (.data + .bss + .noinit) Als hab ich den parameter smallFileSys 1 gesetzt. Die Größe ist aber bei den 7826 byte geblieben. Ich weiß, dass das Problem bekannt ist. Gibt es dazu schon eine Lösung? Viele Grüße C.Alex PS: Die mitgelieferte makefile hat auch keine abhilfe gebracht.
Gast
#1233495
Hallo, bin leider noch nicht dazu gekommen, die beiden Optionen von smallFileSys und write wieder einzubauen... Nur superfloppy funktioniert bis jetzt. Wird wohl auch noch ein wenig dauern, weil ich auch alles auf dynamischen Ram verbrauch am umbauen bin... Grüße Daniel
Gast
#1233636
Hallo, das erklärt natürlich einiges :) Ich dachte AVRStudio würde wieder rumspinnen. Ich muss auch zugeben, ich hab nicht alle 180 Beiträge oben gelesen... Was aber trotzdem interessant ist: Ich wollte den Code für ATmega88 compilieren und auf einmal hat er nicht mehr draufgepasst (500byte zu groß). Laut Datenblatt sind aber atmega8 und atmega88 von den Speichern her gleich groß. Tja Sachen gibts... Danke für die Info Viele Grüße C.Alex
Hallo zusammen. Jetzt sind wieder alle 3 Schalter in der Lib zu benutzbar. Zudem einige Verbesserungen. Lesend ist bis zu 230 KBytes/s möglich. Beim Roh lesen, also ohne Dateisystem kommt man ungefähr auf 300 KBytes/s. Das ist nur ein relativ geringer Overhead. Schreiben geht jetzt bis zu 140 KBytes/s trotz überschreiben-Funktionalität. Bisschen Doku gibts auch hier : http://www.mikrocontroller.net/articles/AVR_FAT32 PS: Die Zeilenumbruch Funktion wird erstmal nicht aufgenommen, allerdings sind weitere Anregungen erwünscht. Viel Spaß damit :) Grüße Daniel
Gast
#1238482
Hallo Daniel, die neue Version passt mit 94% Flash-Auslastung wunderbar auf dem atmega88. Beim ersten Compilieren hat er mit smallFileSys 1 die Funktion fat_str(datei) nicht gefunden. Ich hab dann einfach die Präprozessoranweisung in fat.c geänder in:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
Viele Grüße C.Alex
Gast
#1240825
Hallo, mit welchem Programm muss ich meine SD-Karte formatieren, damit ich sicher gehen kann, dass es fehlerfrei formatiert ist. Hintergrund ist, dass ich ein LowLevel-Format gemacht hab um den Speichervorgang nachvollziehen zu können. Anschließen mit Windows formatiert in FAT16. Seit dem schlägt die Fat-Initialisierung fehl. Also: Boot... Vorher ging es.
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | |
19 | |
20 | |
21 | |
22 | |
23 | |
24 | |
25 | |
26 | |
27 | |
28 | |
29 | |
30 | |
31 | |
32 | |
33 | |
34 | |
35 | |
36 | |
37 | |
38 | |
39 | |
40 | |
41 | |
42 | |
43 | |
44 | |
45 | |
46 | |
47 | |
48 | |
49 | |
50 | |
51 | |
52 | |
53 | |
54 | |
55 | |
56 | |
57 | |
Ich hab doch im Prinzip nichts falsch gemacht? oder? C.Alex
Gast
#1240947
Hallo @Daniel weiter oben schreibst Du, dass Du einen HC4050 als Levelshifter verwendest. Ist der wirklich geignet? Im Datenblatt steht das VCC -0,5 bis 7V sein kann (also VCC=3,3V). DC Input Voltage -0,5V to Vcc+0,5V. Das wären dann aber bis 3,8V, also keine 5 V. Das der das eventuell ohne kaputt zu gehen kann ist ne andere Sache! Oder habe ich da was falsch verstanden? Danke für ne Klärung Achim
Hallo zusammen. @Alex Wahrscheinlich ist die Karte jetzt nicht mehr partitioniert, du musst also in der fat.h "superfloppy 1" ändern. @sucher Ausschnitt Datenblatt: "The 74HC4050 provides six non-inverting buffers with a modified input protection structure, which has no diode connected to VCC. Input voltages of up to 15 V may therefore be used. This feature enables the non-inverting buffers to be used as logic level translators, which will convert high level logic to low level logic, while operating from a low voltage power supply. For example 15 V logic (“4000B series”) can be converted down to 2 V logic." Das verstehe ich so, dass da eine irgendwie geartete Eingangssicherung besteht, damit der Eingang nicht kaputt geht. Deshalb kann man bis zu 15V auf den Eingang machen selbst wenn das Ding nur mit 2V betrieben wird. Rest vom Datenblatt gibt das auch so her... Grüße Daniel
Gast
#1241084
Hallo @Daniel, Danke für die Antwort. Es gibt da wohl verschieden Datenblätter ( Deins ist Philips?). Bei Reichelt könnte man das nich rauslesen http://www.reichelt.de/?;ACTION=6;LA=3;ARTICLE=3228;GROUPID=2933;GROUP=A2235;SID=31XMMj3qwQAR8AAApHlEkae535059485831c5f64f055c1b01bd7a (Thomson) Es geht mir nicht ums rechthaben, sondern ich möchte es verstehen. MfG Achim
Gast
#1241182
Hallo Daniel, die Initialisierung der Karte und FAT funktionieren jetzt wieder, allerdings bleibt das Beilspielprogramm gleich in dem ersten Funktionsaufruf hängen. Also bei:
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
Daraufhin hab ich die Signalwandlung mit dem SN74LS07 geprüft, es ist aber alles OK. Hast du eine Idee warum der uC da hängen bleibt? Gleiche Reaktion mit 2 versch. Karten. Danke! C.Alex
Hallo. @Achim Tatsache, in dem Datenblatt von Thomson steht nur ein schlanker Satz dazu, im Rest der Daten finde ich das auch nicht so bestätigt.. "The VCC side diodes are designed to allow logic-level convertion from high-level voltages (up to 15 V) to low-level voltages." @C.Alex So wie es aussieht, gibt es möglicherweise Probleme mit FAT16 und nur einem Sektor pro Cluster... hatte ich nicht getestet, sorry. Werd ich aber schleunigst beheben. Bis zum erbrechen hatte ich FAT32 mit mehreren Sektoren pro Cluster getestet... Als workaround, meine Empfehlung: FAT32 mit mehreren Sektoren pro Cluster. Grüße Daniel
Gast
#1241895
Hallo Daniel, ich habe beide Karten mit FAT32 formatiert; kein Unterschied zu vorher. Bedenken habe ich im Zusammenhang mit der Formatierung der Karten. Kann man davon ausgehen, dass das Windows Formatier-Tool alles richtig macht? Weil: ich hab die Karte mit Windows formatiert und hatte danach das Problem, dass es nicht mehr gebootet hat :Boot... Daraufhin hab ich es in meine Digicam reingesteckt, der kein System erkannt hat und formatieren wollte, und siehe da: Boot...OK Ich kenn mich nur zuwenig mit FAT aus um dem auf den Grund zu gehen. C.Alex
Hallo, also das einzige Problem ist die Formatierung mit Linux, da dabei, warum auch immer, das root-Dir wenn es nur 1 Cluster groß ist als Ende Markierung nicht 0xfffffff0 erhält, sondern 0xffffff80. Ich hatte einfach keine Lust mich mit 3 Ende Markierungen herumzuschlagen. Windows ist manchmal etwas eigen beim Formatieren, da wird schon mal aus einer partitionierten Karte eine unpartitionierte ohne Kommentar ^^ Muss man nachsehen und in der Lib umstellen. Andere Probleme gibt es eigentlich nicht im Zusammenhang mit Formatierungen. Was haben die Karten, die nicht durch den Boot Vorgang kommen, denn für Eckdaten? MB Größe, Sektoren/Cluster und partitioniert oder unpartitioniert? Grüße Daniel
Gast
#1242083
Hallo, da wäre: Lexar Media File System: FAT16 Total capacity: 127.090.176 byte Sector count: 248.223 Bytes per Sector: 512 Bytes per Cluster: 2.048 Total Clusters: 61.925 Lexar Platinum II File System: FAT16 Total capacity: 512.880.128 byte Sector count: 1.001.719 Bytes per Sector: 512 Bytes per Cluster: 8.192 Total Clusters: 62.574 Woran kann ich erkennen, ob nach dem formatieren eine Karte partinioniert ist oder nicht? C.Alex
Also einmal steht im Sektor 0 die Partitionstabelle oder die Fat Daten. Bei beiden von Dir geposteten Karten sollte angesprochenes Problem mit nur einem Sektor pro Cluster nicht auftreten. Bleibt nur noch die Partitionierung und das Formatieren mit Linux. Das mit der Partitionierung ist schnell getestet... einfach mal umstellen in der Lib und schauen ob es geht. Allerdings besser nur ein lese Test (also auch kein ffrm !). Es kann auch vorkommen, dass die Initialisierung der Fat durchläuft, aber keine sinnvollen Daten enthält. Dann würde sich z.B. ffrm ziemlich aufhängen. Würde zu Deinem Problem Passen. Wäre aber zurückzuführen auf die Falsche Vorgabe des Schalters "superfloppy" in fat.h Grüße Daniel
Gast
#1246249
Hallo Daniel, ich hab den Parameter SUPERFLOPPY mit beiden Einstellungen ausprobiert und versucht einer vorher unter Windows erstelle TEST.TXT nur zu lesen und auf dem Terminal darzustellen. Bei einer Einstellung ist der Bootvorgang nicht beendet worden: Boot... und es wurde auch nichts weiteres angezeigt. Mit der anderen Einstellung wurde der Bootvorgang abgeschlossen und das ganze Terminal wurde mit irgendwelchen Daten vollgeschrieben. Unter Linux hab ich noch nicht formatiert. C.Alex
Hallo, kann ich absolut nicht bestätigen. Hast du irgendwo den Code geändert? Habe nochmal alles durchgesehen und getestet, dabei ist mir noch ein anderer Bug aufgefallen..in Zusammenhang mit ffseek und dem überschreiben von Daten. Sonst ist da alles im grünen Bereich ! Grüße Daniel
Hallo! Ich bin begeistert von der Lib! Wer hätte gedacht, dass das SD-benutzen so einfach wird? =) Alles funktioniert soweit ok. Zum Testen habe ich eine AgfaPhoto 1GB genommen. Ich schreibe mit einem Delay von 10ms 2000 uint_16t Werte und ihre Nummer als String auf eine Textdatei. Geht sauber und schnell. Allerdings scheint es so, dass ich nochmal warten muss (ich hab jetzt 100ms) bevor ich ffclose aufrufe, da sonst die Datei nicht vollständig ist. Vermutlich wegens des Hardware SPI? Vielleicht könnte ffclose selbst solange warten, bis die Datei komplett ist! Bei mir gings auch auf einer 16MB FAT12 Karte, aber da gab es Probleme mit dem Schreiben (hatte keinen delay vor ffclose(), aber es fehlten am Ende 400 Werte!). Zudem wurden andere Dateien durch das Schreiben der Werte verändert. Ich kann ja mal das Image schicken, wenn Interesse für FAT12 Support besteht. (Und mir jemand erklärt, vo unter dev die Datei für meinen SD-Leser steht...) Danke für deine Mühen! StrangeMan PS: Verwende 0.5.2
Gast
#1261068
Hallo, also die SPI Routinen sind blockend geschrieben, die warten solange bis das Byte das geschrieben werden soll auch raus ist. Deshalb ist ein delay unnötig. Wenn es aber mit einem delay klappt, klingt das für mich eher so, als ob die SPI Strecke anfällig ist. Vielleicht schwingt da was mit oder so (und beruhigt sich bei einem delay?!?)... Wie steuerst Du die Karten an? Direkt oder über irgendwelche Pegelwandler? Komme momentan nicht richtig zum weiter entwickeln. Was aber definitiv geht ist einfaches lesen und schreiben ohne die etwas ausgefalleneren Funktionalitäten wie ffseek() und überschreiben von Daten. Wobei ffseek() an sich tadellos funktioniert, nur in Zusammenhang mit ffwrite() und dem überschreiben welches über einen Sektor hinaus geht gibt es Probleme, da dann ja der Sektor in dem man jetzt weiter überschreiben möchte noch geladen werden muss... Grüße Daniel
Gast
#1262369
Noch zum Thema Zeilenumbruch: Wichtig ist das die Angabe der Zeichenanzahl beim Schreiben auf die SD-Karte!!!! "\r\n" sind nur 2 Zeichen nicht 4!!!!! Bei der Angabe, das es 4 Zeichen sind, werden die letzten 2 Zeichen (nach dem Zeilenumbruch)irgendwelcher Käse. Meist sind da 4ecke enthalten, oder der Inhalt anderer Daten.
Antwort schreiben
Bitte melde dich an, um einen Beitrag zu schreiben.