mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik ICP-Pulsdauer


Autor: Lukas (Gast)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

Ich muss die Pulsdauer eines Rechtecksignals messen über den ICP - Pin.
Mein Problem ist, dass ich zum testen ein Oszi an einen Ausgang gehängt 
habe und in der Interrupt routine jedes mal wenn der ICP - PIn ausgelöst 
wird den Pin Ein und Ausschalte. Aber es wird nur blödsinn am 
OSzilloskop angezeigt.

Habe im Anhang meinen Programmcode vllt. kann mal jemand schaun ob ich 
iwas flasch initialisiert habe.

System: Atmega32 @1Mhz intern

Lg

Lukas

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

Each half period of the external clock applied must be longer than one
system clock cycle to ensure correct sampling. The external clock must 
be
guaranteed to have less than half the system
clock frequency (fExtClk < fclk_I/O/2) given a 50/50% duty cycle.

MfG Spess

Autor: Lukas (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
My System Clock is as far as i know 1Mhz and de Frquenzy @ ICP - Pin is 
between 300Hz and 1300Hz. The Prescaler of the Timer is 8.

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>   PORTD |= (1 << ICP_PIN);        //Input Capture Pin als Eingang

Der Kommentar stimmt nicht. Du schaltest damit den Pullup ein. 
Verkraftet das Signal den Pullup?

>        StartTime = ICR1;        //  Timerwert wird in StartTime gesichert
>        EndTime = ICR1;                //End Wert sicehrn

Du kannst der Empfehlung von Atmel ("ICR1 so früh wie möglich lesen") 
besser nachkommen, wenn du ICR1 vor dem If-then-else liest und später 
auf StartTime und EndTime aufteilst.

> if (TCCR1B & (1<<ICES1))

Du kannst das beschleunigen, wenn du das Bit ohne Abfragen einfach 
toggelst. Du weisst ja, wie du gestartet bist. Dito PA0 ans PORTA.

>       TIFR |= (1 << ICF1 );       // Interrupt Flag löschen

Das würde ich nicht machen. Die ISR alleine löscht schon ihr 
Interruptflag. Wenn du reinfummelst, löschst du vielleicht den nachsten 
anstehenden ICP IRQ. Bei 300Hz and 1300Hz und 1 MHz/8 vielleicht 
unkritisch, bei schnelleren Signalen vielleicht tödlich.

> Aber es wird nur Blödsinn am OSzilloskop angezeigt.

Das hört sich nach einem Bedienerfehler an. Masseleitung vergessen? 
Oszilloskop falsch eingestellt?

Autor: Lukas (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Stefan B. schrieb:
> Der Kommentar stimmt nicht. Du schaltest damit den Pullup ein.
> Verkraftet das Signal den Pullup?

Hy, also ich schließe an den ICP - Pin derzeit einen Rechteckgenerator 
an. Wie meinst du ob der den PUllup verkraftet? Sollte ich diese Zeile 
komplett löschen?


Also beim Oszilloskop habe ich die Massen verbunden und wenn ich mich 
mit dem Oszi auf den Rechteckgenerator hänge bekomme ich auch das 
korrekte Signal.

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Lukas schrieb:

> Hy, also ich schließe an den ICP - Pin derzeit einen Rechteckgenerator
> an. Wie meinst du ob der den PUllup verkraftet? Sollte ich diese Zeile
> komplett löschen?

Schafft es deine Signalquelle gegen einen Pullup-Widerstand zu arbeiten?

                         Vcc
                          |
                          #
                          # Pullup-Widerstand
                          |
Rechteckgenerator o-------+-------o Oszi
              GND o---------------o GND


Wenn ein Pullup-Widerstand in der Größenordnung der internen Pullups 
deines AVR vorhanden sind: Sind die Rechtecke noch Rechtecke und werden 
die Kenndaten der LOW/HIGH Pegel aus dem AVR Datenblatt noch erreicht? 
Wenn nicht, internen Pullup des AVRs nicht einschalten. Wenn ja, dann 
schadet die Zeile nicht.

> Also beim Oszilloskop habe ich die Massen verbunden und wenn ich mich
> mit dem Oszi auf den Rechteckgenerator hänge bekomme ich auch das
> korrekte Signal.

Du kannst am PA0 Pin beobachten:

1. ein regelmäßiges (im Bezug aufs Eingangssignal) LOW/HIGH - die ICP 
ISR arbeitet

2. ein konstantes LOW -  der AVR arbeitet, aber deine ICP ISR wird nie 
angesprungen.

3. ein konstantes HIGH -  der AVR arbeitet, aber deine ICP ISR wurde nur 
einmal angesprungen.

4. ein unregelmäßiges LOW/HIGH - die ICP ISR arbeitet falsch oder der 
AVR resettet sich regelmäßig.

5. Keine LOW/HIGH Signale - Rauschen. Elektrische Verbindung fehlerhaft. 
AVR konstant im RESET (PA0 Tristate)

Autor: Lukas (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

Ich habe jetzt die Zeile:

 PORTD |= (1 << ICP_PIN);

weggegeben. D.h der Rechteckgenerator hängt jetzt dirket am Eingang ICP.

Die Register für den ICP Eingang habe ich folgendermaßen gesetzt:

int main()
{
  DDRD   =  0x00;
  DDRA   =  0xff;


Wenn ich nun in der ISR alles auskommentiere und nur folgenden Code 
einfüge:

ISR( TIMER1_CAPT_vect )
{

  PORTA  = 0xff ;
  TIFR |= (1 << ICF1 );
}


bekomme ich nur ein Rauschen am Oszilloskop. Heißt das, dass er gar 
nicht in die ISR hineinkommt bzw. kannst du mir sagen wie ich es sonst 
Lösen könnte bzw. testen.

VIELEN DANK FÜR DEINE HILFE.

LG

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Lukas schrieb:

> bekomme ich nur ein Rauschen am Oszilloskop. Heißt das, dass er gar
> nicht in die ISR hineinkommt bzw. kannst du mir sagen wie ich es sonst
> Lösen könnte bzw. testen.

>> 5. Keine LOW/HIGH Signale - Rauschen. Elektrische Verbindung fehlerhaft.
>> AVR konstant im RESET (PA0 Tristate)

#include <avr/io.h>
#include <util/delay.h>

int main(void)
{
  DDRA = (1<<PA0); //PA0 als Testausgang
  while(1)
  {
    _delay_us(500);
    PORTA ^= (1<<PA0);
  }
}

sollte ein 1 kHz Rechtecksignal auf dem Oszi ergeben. Wenn das nicht 
funktioniert, liegt es nicht an ICP_Measure.c

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

>ISR( TIMER1_CAPT_vect )
>{
>  PORTA  = 0xff ;
>  TIFR |= (1 << ICF1 );
>}

>bekomme ich nur ein Rauschen am Oszilloskop. Heißt das, dass er gar
>nicht in die ISR hineinkommt bzw. kannst du mir sagen wie ich es sonst
>Lösen könnte bzw. testen.

Beim ersten Interrupt werden die Ausgänge H. Und da bleiben sie auch

>TIFR |= (1 << ICF1 );

Die Zeile ist überflüssig.

Ein sei() hast du aber noch im Programm?

MfG Spess

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Kontrolliere am Atmega32 auch, ob GND (Pin 31) und AVcc (Pin 30) 
angeschlossen sind. Ohne die arbeitet PORTA nicht richtig!

Den

    _delay_us(500);
    PORTA ^= (1<<PA0);

Block kannst du mit einem anderen Testpin ruhig im ICP Programm drin 
lassen. Den brauchst du beim späteren Debuggen vielleicht noch als 
"Pulsschlag", ob der AVR regelmäßig durch die Hauptschleife rattert.

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.