www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Drehzahl vom Motor messen


Autor: Daniel H. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

ich komm mal wieder nicht weiter. Soll für die schule von einem Motor
die Drehzahl messen. Ich bekomme pro Umdrehung 1 impuls. Dachte mir
okey dann messe ich die Zeit zwischen 2 Impulsen mit nem Timer und
schwups schon kann ich eine vorhersage treffen auf die ganze Minuten.
Leider zeigt mir der LCD am Mic nur stuss an aber warum? Nun erstmal
das Prog:

// RS = PD0
// R/W = PD1
// E = PD2
// D4 = PD3
// D5 = PD4
// D6 = PD5
// D7 = PD6

#include <stdlib.h>
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <math.h>
#include <avr/delay.h>
#include <lcd.h>
#include <lcd.c>

uint8_t time = 0; //time = Zeit zwischen 2 impulsen
uint8_t i = 0; //zähler
char buffer[3]; //buffer


void lcd(void)
{
  itoa( time , buffer, 10); //wandle integer in string
  lcd_gotoxy(0,1); // gehe zu LCD Position X Y
  lcd_puts(buffer); //schreibe auf den LCD den Inhalt von Var buffer
  i = 0;
}

int main(void)
{
  TCCR0 |= (1<<CS00) | (1<<CS02); // Timer CPU-Takt / 1024


  DDRB = 0x00; //PORTB sind alles eingänge

  lcd_init(LCD_DISP_ON);

  lcd_clrscr();
  lcd_init(LCD_DISP_ON);

  lcd_puts("Drehzahl\n");



  for(;;)
  {
    loop_until_bit_is_set(PINB, 1);
    TCNT0 = 0;
    loop_until_bit_is_clear(PINB, 1);
    loop_until_bit_is_set(PINB, 1);
    time = TCNT0;
    i++; //zähler + 1
    if(i>100) // Schreibe auf LCD nach 100 messungen.
    {
    lcd(); // gehe in die Funktion LCD
    }

  }
}

So das ist es. Ich weiss das Loop until nicht die beste lösung ist aber
mir fehlt im mom nichts besseres ein. Für vorschläge bin ich immer
offen.

MFG
Daniel

Autor: Simon K. (simon) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn du schon den Timer benützt, würde ich das ganze auch
Interruptgesteuert machen...

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Welche Werte erwartest Du in 'time'?

Bedenke: In einem String-Array der Größe 3, kannst
du grade mal Strings mit 2 Zeichen ablegen. (2 Nutzzeichen
+ das obligatorische abschliessende '\0')

d.h. es ist sehr wahrscheinlich, dass 'time' höher zählt
als nur bis 99. Dann jedoch macht Dir der itoa ne
Menge Unsinn, da er in Speicherbereiche schreibt, die
nicht mehr zu 'buffer' gehören.
Nicht kleckern, klotzen:

char buffer[20];

Das wird auf jeden Fall ausreichen.

Übrigens: die anderen Variablen (time, i) solltest du
als volatile definieren. Der Compiler kann nämlich nicht
rausfinden, dass die quasi 'ausserhalb seiner Kontrolle'
verändert werden.


Wenn es das nicht war, dann definiere:
'Leider zeigt mir der LCD am Mic nur stuss an '
mal etwas genauer.

Autor: Daniel H. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Stuss: Ich gebe ein fast immer gleich belieben impuls mittels Frequenz
generator auf den eingang und bekomme schwankende werte. Auf dem LCD
des Generators schwankt es auch z.b. 500 Hz dann mal 505 aber mein wert
zeigt mir mal 19 an dann mal 95 dann mal 66. Das meine ich mit stuss
^^.

Erwartung: Dachte eigentlich das ich bei 500 Hz so um die 8 bekomme da
mein Atmega 8 auf 8 MHz läuft und der Presacler auf 1024.

@simon
Muss erlich zugeben hab mich noch nicht so mit interrupt beschftigt
aber würde das ein unterschied machen da der Mirc ehh nix anderes
machen soll auser die dinger zu zählen? Falls ich falsch liege lass ich
mich gerne eines besseren beleren.

Danke nochmals für die promten Antworten.

Gruß
Daniel

Autor: Kojote (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vielleicht is es für mich noch zu früh am Morgen und ich seh es net,
aber wo hast du deinen Stackpointer initialisert?

gruß Kojote

Autor: Sven Günther (s705081)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Kojote: das must du doch gar nicht wenn man den AVR-GCC benutzt.

Gruss Sven

Autor: Rahul (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Stackpointer in C? Das macht der Compiler...
@Daniel:
Wenn du schon 100 Messungen machst, solltest du darüber auch einen
Mittelwert bilden; sonst zeigst du nur die letzte Messung an.

Autor: Rahul (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Noch was vergessen:
Die neueren ATMegas haben einen InputCapture-Eingang, mit dem sich
solche Probleme in Hardware lösen lassen...

Autor: Kojote (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Sven Günther
sry mein Fehler, ich nehme alles zurück... is wohl doch noch zu früh*g*

Autor: Daniel H. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Leider kommen immernoch die falschen werte raus. Hab jetzt noch ein 470k
Wiederstand parralel zum eingang und zur masse gelötet damit es keine
undefinierten Zustände gibt.

Es stimmt eigentlich alles. Und doch sitzt irgendwo der Floh.

Wäre ja ok wenn wenigsten falsche Plausible werte kommen würden aber
warum zeigt er mir bei einem 8 Bit Timer auf dem lcd einen wert von 858
das versteh ich nicht.

Noch jemand eine Idee?

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Zeig noch mal Dein momentanes Programm.

Autor: Daniel H. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
// RS = PD0
// R/W = PD1
// E = PD2
// D4 = PD3
// D5 = PD4
// D6 = PD5
// D7 = PD6

#include <stdlib.h>
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <math.h>
#include <avr/delay.h>
#include <lcd.h>
#include <lcd.c>

uint8_t time = 0; //time = Zeit zwischen 2 impulsen
uint8_t i = 0; //zähler
uint16_t gesamt = 0; //Alles
char buffer[20]; //buffer


void lcd(void)
{
  itoa( time , buffer, 10); //wandle integer in string
  lcd_gotoxy(0,1); // gehe zu LCD Position X Y
  lcd_puts(buffer); //schreibe auf den LCD den Inhalt von Var buffer
  i = 0;
}

int main(void)
{
  TCCR0 |= (1<<CS00) | (1<<CS02); // Timer CPU-Takt / 1024


  DDRB = 0x00; //PORTB sind alles eingänge

  lcd_init(LCD_DISP_ON);

  lcd_clrscr();
  lcd_init(LCD_DISP_ON);

  lcd_puts("Drehzahl\n");



  for(;;)
  {
    loop_until_bit_is_set(PINB, 1);
    TCNT0 = 0;
    loop_until_bit_is_clear(PINB, 1);
    loop_until_bit_is_set(PINB, 1);
    time = TCNT0;
    //loop_until_bit_is_clear(PINB, 1);
    i++; //zähler + 1
    if(i>50) // Schreibe auf LCD nach 50 messungen.
    {
    lcd(); // gehe in die Funktion LCD
    }

  }
}



Das ist der aktuelle Code. Komisch finde ich ja das er falsche Werte
anzeigt. Bei einem 8 Bit Timer gibt es keine 858.

Danke schonmal für deine Zeit Karl.

Gruß
Daniel

Autor: vorbeigeschlendert (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich zitiere mal Rahul: '...Die neueren ATMegas haben einen
InputCapture-Eingang, mit dem sich solche Probleme in Hardware lösen
lassen...'

das ist der entscheidende Hinweis... kuck dir das mal in Datenblatt an
und ich bin sicher du schreibst dein Programm um

Grüße

Autor: Christian Rötzer (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Daniel

Stelle Dir nur mal vor, wenn Deine Messung erst 118 und dann 85 ergibt.
Was steht dann am Display?

Autor: Daniel H. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Der geheimnisvolle fremde & Rahul

Wo ihr recht habt habt ihr recht. Hab mir das ganze mal angesehen und
wenn ich es richtig verstaden habe ist das genau das was ich eigentlich
haben will.

Werde mal morgen ein ganz neues Board Ätzen und dann schaue ich mir mal
das ganze mit dem Input Capture an.

Hat jemand ein Sample File dafür wie man das anwendet dann geht es
wesentlich einfacher beim lernen da ich ein funktionierendes Beispiel
habe?

MFG
Daniel

Autor: Sven (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>das ganze mit dem Input Capture an.

>Hat jemand ein Sample File dafür wie man das anwendet dann geht es
>wesentlich einfacher beim lernen da ich ein funktionierendes Beispiel
>habe?

guckst Du hier:

http://www.matwei.de/doku.php?id=de:elektronik:dre...

Gruß Sven

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.