- LiTime Speicher und Akkus         
Seite 1 von 3 123 LetzteLetzte
Ergebnis 1 bis 10 von 21

Thema: 100us an/aus signal?

  1. #1
    Benutzer Stammmitglied
    Registriert seit
    19.02.2005
    Beiträge
    39

    100us an/aus signal?

    Anzeige

    Praxistest und DIY Projekte
    wie kann ich mit einem timer an einem ausgang nen signal mit 100us an und 100us aus herstellen?

    hab das so gemacht ( sind aber keine 100us irgendwie ):
    Ddrb.2 = 1
    Portb.2 = 0

    Xport Alias Portb.2

    Dim Tcounter As Byte
    Tcounter = 0

    On Timer0 Ontimer0
    Config Timer0 = Timer , Prescale = 8

    ...

    Ontimer0:
    Tcounter = Tcounter + 1
    If Tcounter = 46 Then
    If Xport = 0 Then
    Xport = 1
    Else
    Xport = 0
    end if
    end if
    return

    mein gedankengang war dabei:
    ich habe einen quarz mit 3686400hz
    takt = 3686400/8 = 460800

    alle 2.17us löst der Ontimer0 aus
    da ich aber nur eine genauigkeit von 100us brauche das ganze * 46


    gedanken fehler? rechenfehler? oder geht das so nicht ?

    mfg

  2. #2
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    09.06.2004
    Ort
    Aachen
    Beiträge
    2.674
    alle 2.17us löst der Ontimer0 aus
    da ich aber nur eine genauigkeit von 100us brauche das ganze * 46
    Müsste Funktionieren, ABER:

    Du musst Tcounter wieder auf 0 setzen, wenn er bei 46 war!
    Hast du das Signal mal gemessen, ich würde vermuten, dass es bei ca 557 uS liegt. Vielleicht ist ja die Zeit 2,71 uS an, der Rest aus zu kurz? Was willst du für einen Duty cycle. Warum nicht 50:50?

    If Tcounter >= 23 then
    xport = 1
    else
    xport = 0
    end if

    if Tcouner = 46 then
    Tcounter = 0
    end if

    MFG Moritz

  3. #3
    Benutzer Stammmitglied
    Registriert seit
    19.02.2005
    Beiträge
    39
    jojo das mit dem auf 0 setzten habe ich ... (nur vergessen zu posten)

    zum cycle:
    emm ich möchte das das deingen 100us AN macht und dann nach 100us AUS...

    aber wieso sollte das signal bei 557us liegen, wenn ich das so mache?

    will damit nen fahrtenregler ansprechen...

    ich poste einfach mal das komplette dingen...
    Code:
     $regfile = "2313def.dat"
     $crystal = 3686400
     $baud = 9600
    
     Ddrb.2 = 1                                                 'X
     Ddrb.3 = 1                                                 'Y
     Ddrb.4 = 1                                                 'Z
    
     Portb.2 = 0
     Portb.3 = 0
     Portb.4 = 0
    
     Xport Alias Portb.2
     Yport Alias Portb.3
     Zport Alias Portb.4
    
    
     Dim Tcounter As Byte
    
     Dim Xcounter As Byte
     Dim Ycounter As Byte
     Dim Zcounter As Byte
    
     Dim Ximpulse As Byte
     Dim Yimpulse As Byte
     Dim Zimpulse As Byte
     Dim Intervallength As Byte
    
     Tcounter = 0
    
     Xcounter = 0
     Ycounter = 0
     Zcounter = 0
    
     Ximpulse = 10                                              '=>1000usek
     Yimpulse = 10                                              '=>1000usek
     Zimpulse = 10                                              '=>1000usek
     Intervallength = 20                                        '=>2000usek
    
     On Timer0 Ontimer0
     Config Timer0 = Timer , Prescale = 8                       'Takt: Quarz/8 => 460800 => Tick alle 2.17usek
    
     Enable Timer0
     Enable Interrupts                                          'Interrupts global
    
    
    
    'Hauptprogramm
     Do
     Loop
    
     End
    
    'Ontimer0
     Ontimer0:
       Tcounter = Tcounter + 1
       If Tcounter = 46 Then                                    ' Tick alle 100usek
         Xcounter = Xcounter + 1
         Ycounter = Ycounter + 1
         Zcounter = Zcounter + 1
    
         If Xcounter <= Ximpulse Then
           Xport = 1
         End If
         If Xcounter > Ximpulse Then
           Xport = 0
         End If
         If Xcounter = Intervallength Then
           Xcounter = 0
         End If
    
         If Ycounter <= Yimpulse Then
           Yport = 1
         End If
         If Ycounter > Yimpulse Then
           Yport = 0
         End If
         If Ycounter = Intervallength Then
           Ycounter = 0
         End If
    
         If Zcounter <= Zimpulse Then
           Zport = 1
         End If
         If Zcounter > Zimpulse Then
           Zport = 0
         End If
         If Zcounter = Intervallength Then
           Zcounter = 0
         End If
    
         Tcounter = 0
       End If
     Return
    nach dem dingen sollte das signal 1000usek AN/1000usek AUS sein oder?
    an meinem led sieht das aber eher nach 1sek AN/1sek AUS aus... (hab kein oziloskop womit ich das testen könnte...)

  4. #4
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    09.06.2004
    Ort
    Aachen
    Beiträge
    2.674
    zum cycle:
    emm ich möchte das das deingen 100us AN macht und dann nach 100us AUS...
    Dein Interrupt erzeugt alle 2.17 uS einen Interrupt.
    Dann wird Tcounter 1 hochgezählt. Bis jetzt ist xport nur im Falle tcounter = 46 an. Wenn es kleiner oder größer ist aus. Du erzeugst aleo keinen Wechsel damit! Du hast einen Cycle (wenn wir mal davon ausgehen, dass es nut von 0 bis 46 geht) von 47 zu 1!

    Und 2. dein Script erzeugt (wemm es mur von 0 bis 46 geht) alle 100 us 2 Wechsel und nciht nur einen. Bei dir wäre 01 100us lang. Gewünscht ist aber 01 = 200us (etwas blöd ausgedrückt).

    Verstanden?!

    Mach es so:
    Tcounter = Tcounter + 1
    If Tcounter = 46 then
    toggle xport
    Tcounter = 0
    End if

    MFG Moritz

  5. #5
    Benutzer Stammmitglied
    Registriert seit
    19.02.2005
    Beiträge
    39
    öm
    und was ist wenn ich nu eine längeres AN als Aus haben möchte?

  6. #6
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    09.06.2004
    Ort
    Aachen
    Beiträge
    2.674
    Ähm, mir fällt gerade was auf, du hast die Frequenz nicht zufällig mal gemessen? Du hast bei deinem Code was ganz wesentliches übersehen!

    Takt: Quarz/8 => 460800 => Tick alle 2.17usek
    Das stimmt leider überhaupt nicht. Alle 2.17 uS wird der Timer0 um ein erhöht. Er läuft aber erst bei 256 über und löst erst dann einen Interrupt aus! Ich hab mich leider vorher immer auf die Angabe 2,17 uS verlassen.
    OnTimer wird also nur alle 556 uS ausgelöst!
    Du musst vermutlich nen kleineres Prescaler nehmen (1).
    Und den Timer vorladen.
    Leider ist es sehr schwer da, der Timer nach 3,6864 Takten überlaufen müsste, damit er jede uS überläuft.
    Wenn wir uns die Zahl mal anschauen, fällt uns was aus! Das ist im Grunde die Quarzfrequenz/1 Mio
    Könntst du also ein anderen Quarz nehmen?
    4 Mhz oder 8 wären gut. Da das Timing sehr viele Resourcen frisst, wäre ein 16 Mhz Qurz natürlich am besten.


    Fragen?!

    MFG Moritz

  7. #7
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    02.09.2004
    Beiträge
    124
    Hallo,

    warum das ganze im Hauptprogramm laufen lassen?

    Falls der verwendete AVR eine Time-Compare-Unit besitzt (z.B. in Timer2)...
    46 ins Timer-Compare Register laden.

    Config Timer2 = Timer, Prescale = 8, Compare = Toggle(*), Clear Timer = 1
    OCR2 = 46
    (*) toggelt OC2-Pin, andere Pins im OC-Int toggeln.


    Falls nicht, Timer mit 256-46 voreinstellen und den Portpin in der Overflow-Interruptroutine toggeln.

    On Timer0 OVF_Int
    Config Timer0 = Timer, Prescale = 8
    Timer0 = 210
    ...

    OVF_Int:
    Timer0 = 210
    Toggle PortX.Y
    Return


    Ist nur eine Überlegung, getestet hab ich das nicht.

    Ciao,
    Werner

  8. #8
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    09.06.2004
    Ort
    Aachen
    Beiträge
    2.674
    Beim ersten Beispiel blick ich nciht ganz durch, aber as 2. ist klar.
    Es sind aber halt schon Fehler im Ansatz. Du hast es jetzt richtig gemacht aber wir wollen ja noch versuchen den cycle einzustellen. Dafür wäre vermutlich ein kleinere Prescaler und ein anderes Quarz sinnvoll. Natürlich nur, wenn das ganze so fein eingestellt werden soll.

    MFG Moritz

  9. #9
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    02.09.2004
    Beiträge
    124
    Beim ersten Beispiel bin ich mir auch nicht sicher. Speziell ob Clear Timer = 1 wirklich den Timer beim Aufruf des Compare Interupt löscht.

    Ansonsten nutzt das 2.Beispiel einfach die Möglichkeit der Timer 1 & 2 bei einem beliebigen Zählerstand einen Interupt auszulösen. Timer 0 besitzt diese Funktion leider nicht.

    Ciao,
    Werner

    P.S. Der in BASCON integrierte Simulator scheint bei den neuen AVRs nicht ganz fehlerfrei zu sein. Wenn interne Register der Timer nicht oder nicht wie erwartet gesetzt werden, lohnt es sich das Programm noch mal im AVR Studio zu testen. Z.B. die CAPTURE Funktion von Timer 1 funktionierte bei mir im BASCON Simulator nicht. Simulier ich den erzeugten Code im Studio klappt es, und was wichtiger ist auch auf dem Zielsystem funktioniert es.

  10. #10
    Benutzer Stammmitglied
    Registriert seit
    19.02.2005
    Beiträge
    39
    ich kann maximal nen 10mhz quarz nehmen weil der at90s2313 nur max 10mhz kann... aber ich glaube das wäre schon eine verbesserung oder?

Seite 1 von 3 123 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiTime Speicher und Akkus