Hallo, ich bin gerade dabei für ein Projekt eine Servosteuerung zu basteln. Ich möchte dazu den Timer1 von meinem Atmel Mega8 über den Uart ansprechen. Der soll mir dann entsprechend des gesendeten Werts ein PWM Signal an den Servo schicken. Bis jetzt hab ich mir ein kleines C Programm geschrieben. Leider funktioniert das ganze nicht so wie ich mir das vorstelle, denn der Servo fängt nur an zu pfeifen. Ich hab auch kein Oszilloskop zu Hause und kann deshalb auch nicht das ausgegebene Signal überprüfen. Es wär nett wenn mir jemand ein Tipp geben könnte woran es liegt oder wenigstens sagen ob ich ganz auf dem Holzweg bin. Die Kommunikation über den Uart hab ich schon mit einem kleinen Programm getestet. Sie sollte also funktionieren. Nicht meckern, dass das ganze so zusammengestückelt ist. Ich hab nicht wirklich Ahnung vom Programieren...
Jens W. schrieb: > Nicht meckern, dass das ganze so zusammengestückelt ist. Ich hab nicht > wirklich Ahnung vom Programieren... Meckern werde ich nicht, aber bitte such dir erst einmal ein grundlegendes Buch über C-Programmierung, und lies dir zumindestens die Basics an. Ganz ohne Ahnung wird das sonst nichts. Oliver
Hallo Nur mal so als Hinweis: Schau dir mal die letzte while-Schleife an. Ist das, was du da machst, wirklich das, was du zu tun beabsichtigst? Und Oliver hat recht, kauf dir ein Buch! Gruß Joachim
Joachim schrieb: > Hallo > > Nur mal so als Hinweis: > Schau dir mal die letzte while-Schleife an. > Ist das, was du da machst, wirklich das, was du zu tun beabsichtigst? Und noch ein Hinweis: Einrückungen sind nicht nur Zierde, sondern erfüllen eine vitale Funktion für den Menschen um sich Abhängigkeiten visuell einzuprägen. Dem Compiler hingegen sind die Einrückungen wurscht. Daher ist es essentiell, dass die Einrückungen so gemacht werden, dass sie mit dem übereinstimmen, was der Compiler anhand der C Regeln an Abhängigkeiten sieht.
Hmm ja ihr habt da sicher Recht, dass ich da richtig in die Materie eintauchen muss. Ich hab nur gehofft dass ich nach meinen "Einführung in C++" Kurs wenigstens schon mal n bischen was hinbekomm.. Möcht mich auch gleich entschuldigen, wenn ich hier so ein Verbrechen gepostet habe... @Joachim: Ich hab gedacht, dass ich dort mehr oder weniger permanent mit uart_gets in die Funktion springe und die mir dann den Buffer in das "Daten"feld schreibt. Das wollte ich dann zum Integer konvertieren und in das OCR1A Register schreiben. Damit sollte dann der Vergleichswert des Zählers bei dem der Zustand an Pin OC1A von High nach Low wechselt aktualisiert werden. So siehts zumindest in meinem Kopf aus ;) Aber alle Theorie ist grau. Bin ich denn abgesehen von meinem nicht Können in C auf dem richtigen Weg? Gruß Jens
Jens W. schrieb: > Hmm ja ihr habt da sicher Recht, dass ich da richtig in die Materie > eintauchen muss. Ich hab nur gehofft dass ich nach meinen "Einführung in > C++" Kurs wenigstens schon mal n bischen was hinbekomm.. Dann sollte dir aber der Unterschied zwischen
1 | while(1) |
2 | uart_gets(Daten); |
3 | wert=atoi(Daten); |
4 | OCR1A=wert; |
und
1 | while(1) |
2 | {
|
3 | uart_gets(Daten); |
4 | wert=atoi(Daten); |
5 | OCR1A=wert; |
6 | }
|
klar sein. Deine Version sieht der Compiler so:
1 | while(1) |
2 | uart_gets(Daten); |
3 | |
4 | wert=atoi(Daten); |
5 | OCR1A=wert; |
Nur das uart_gets ist in der Schleife und wird ständig wiederholt. Die anderen beiden Anweisungen sind nicht in der Schleife und da es sich bei der Schleife um eine Endlosschleife handelt, werden sie in der Tat überhaupt nie ausgeführt. (Und mit einer konsequenten vernünftigen Einrückstruktur kann man das als Mensch sogar sehen :-) Ausserdem solltest du dir mal überlegen, welchen Wert OCR1A eigentlich hat, solange du ihm keinen Wert über die UART zuweist. Das Programm startet und .... von der Seriellen kommt einfach nix. Was soll dann passieren? Es wird ja wohl nicht Sinn der Sache sein, dass das Servo dann keine vernünftige Position einnimmt, weil es keinen vernünftig definierten Servopuls bekommt.
Jens W. schrieb: > Bin ich denn abgesehen von meinem nicht Können in C auf dem richtigen > Weg? Nur dann, wenn Du die o.g. Vorschläge liest und berücksichtigst, insbesondere den von Joachim (ich stoße Dich jetzt mal mit der Nase drauf, indem ich die Klammern so setze, dass Du siehst, was Dein Code macht):
1 | while(1) { |
2 | uart_gets(Daten); |
3 | }
|
Entschuldigung, ich hatte während des Schreibens telefoniert und so den Beitrag von Karl Heinz übersehen!
Nach einem einführenden Kurs in C++ sollte man eigentlich auch verstanden haben, daß man Funktiona nicht nur hinschreiben, sondern auch aufrufen muß, wenn sie etwas tun sollen. uart_init wäre solch ein Kandidat. Und dein mit Sicherheit zu kleines Daten-Feld wird das Programm bei der ersten Eingabe vonmehr als zwei Zeichen ins Nirwana schicken. Jens W. schrieb: > Bin ich denn abgesehen von meinem nicht Können in C auf dem richtigen > Weg? Schwer zu sagen. Eine faire Antwort wäre vermutlich: Nein. Nicht, weil du auf dem falschen Weg bist, sondern weil dir (noch) die Voraussetzungen fehlen, überhaupt einen Weg von einem Nicht-Weg zu unterschieden. Aber "learning by doing" ist schonmal ein richtiger Weg ;-) Oliver
Ahh ok Danke! Ich seh schon das war natürlich n bischen stupid von mir. Da wär ich vieleicht mit ner vernünftigen Einrückung auch selbst drauf gekommen. Und Klammern vergessen gilt an der Uni noch als Formfehler... Leider funktioniert das ganze immernoch nicht deswegen wär es nett, wenn mir jemand sagen könnte ob ich die Signalgenerierung für den Servo über den Timer1 überhaupt richtig angehe.
Danke erstmal für eure Anregungen ich werd mich heut Nachmittag nochmal hinsetzen und das ganze ein wenig überarbeiten. Da es ja doch an mehreren Ecken mangelt.
So etwas
1 | char Daten[3]; |
2 | |
3 | ...
|
4 | |
5 | uart_gets(Daten); |
ist immer eine etwas haarige Sache. uart_gets kann sich nicht dagegen wehren, dass zu viele Zeichen über die UART hereinkommen. Dazu müsste es die Länge des Arrays kennen, was es nicht tut. Man müsste ihm die Länge mitgeben. Das mindeste was du aber tun solltest ist, an dieser Stelle nicht kleckern sondern klotzen! Wenn du davon ausgehst, dass dein Benutzer nicht mit dem Kopf auf die Tastatur fällt und dir so eine Eingabezeile rüberschickt 1234444444444444444444444444444444444444444444444444444444444444 dann solltest du dich zumindest auf einfache Fehlbedienungen einstellen. Einem Benutzer zu sagen: Deine Eingabe darf nur 3 Zeichen umfassen, nämlich #34 und dann ein einen String im Programm zu benutzen, der maximal 2 Nutzzeichen fassen kann, geht zwar in diesem Fall gut (weil du ja den # wegwirfst), aber spätestens dann, wenn dein Benutzer #487 eingibt, nur um zu sehen was passiert, dann krachts in deinem Programm ganz gewaltig. "487" passt nun mal nicht mehr in einen char[3]. Hier also lieber etwas vorsichtig und defensiv sein und die String-Arrays etwas größer dimensionieren. Das ein Benutzer schon mal #87654 eingibt, sollte dein Programm auf jeden Fall abkönnen auch wenn es mit dem Super-GAU Fall "Baby drückt wahllos auf der Tastatur" heillos überfordert ist (und ja: ein gutes Programm kommt auch damit klar, aber von einem Anfänger erwarte ich sowas nicht)
Jens W. schrieb:
> Und Klammern vergessen gilt an der Uni noch als Formfehler...
Diese Regel solltest du für dich als allererstes gleich über Bord
werfen. Eine ansprechende, übersichtliche Form ist wesentlicher
Bestandteil eines guten Programms. Sie hat nicht nur optisch dekorativen
Zweck, sondern kann tatsächlich den Unterschied zwischen einem wartbarem
und weitgehend fehlerfreiem Programm und einem unlösbaren
Spaghettihaufen ausmachen.
Fehlerverseuchte Programme sind meistens auch die, die wie ein Haufen
hingerotzter Code aussehen.
Genauso wie die Umkehrung:
Schüler sucht verzweifelt seit Stunden nach einem Fehler. Lehrer geht zu
ihm und formatiert den Code als allererstes neu nach konsistenten,
durchgehenden Regeln (welche das im Detail sind, ist erst mal egal). 5
Minuten später greift sich der Schüler ans Hirn: Er hat den Fehler
selbst gesehen. Spätestens wenn so etwas das 5te mal passiert, hat auch
der dümmste Schüler begriffen, dass er sich mit dem 'Weglassen der
Formatierung' im Grunde nur selbst ein Bein stellt.
Genau deswegen sind sauber strukturierte Programme im Schnitt mit
weniger Fehlern beladen. Man sieht Fehler einfach besser. Die Ausrede:
Das kann ich später immer noch machen, gilt einfach nicht. Gewöhn dir
von Anfang an an, eine saubere Form zu schreiben. Dazu gehören:
Einrückungen. Dazu gehören: ein einheitliches { } Schema
Jens W. schrieb:
> Und Klammern vergessen gilt an der Uni noch als Formfehler...
Das bezweifele ich aber sehr stark. Klammern sind nunmal ein wichtiger
Bestandteil in der C- und C++-Syntax, ohne die überhaupt kein gültiger
oder gar funktionierender C-Code erstellt werden kann.
Oliver
Ihr könnt mir ruhig glauben, dass Klammern vergessen, zumindest in meiner Abschlußklausur (mit Stift und Zettel), als Formfehler galt. Ich will damit nicht sagen, dass ich der Ansicht bin, dass dies richtig ist. Da wie schon gesagt: ohne Klammern läufts halt nicht. Trotz alledem hab ich mein Programm nun zum Laufen gekriegt. Das Hauptproblem lag darin, dass ich den Uart nicht richtig initialisiert hatte. Jetzt läuft aber alles und ich kann mein Servo über Matlab steuern und damit auch mein Versuchsschiff über Bluetooth. Wenn ich wieder zu Hause bin poste ich noch das fertige Programm falls interesse besteht. Vielen Dank nochmal für die Hilfe vorallem an Karl heinz Buchegger! mfg Jens
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.