Forum: Mikrocontroller und Digitale Elektronik Wartezeit mit 32-Bit-Timer


von Chris (Gast)


Lesenswert?

Hallo,

ich möchte eine Wartezeit mit einem 32-Bit-Timer mit dem uC 
PIC24FJ128GB204 programmieren. (Ich möchte kein Delay verwenden, da 
andere Funktionen abgearbeitet werden sollen, während die Zeit 
hochgezählt wird).

Da ich in der uC-Programmiererei relativ neu bin, ist es für mich etwas 
schwierig einen solchen Timer zu konfigurieren.
Der Mikrokontroller arbeitet mit einer Quarzfrequenz von 32MHz.

Nun möchte ich eine Warteschleife von 1min haben. Hierfür habe ich mir 
das zusätzliche Datenblatt angesehen: “dsPIC33/PIC24 Family Reference
Manual”, “Timers” (DS39704)

In diesem ist auch ein Beispiel für die Konfiguration eines 
32-Bit-Timers vorhanden, welcher wie folgt aussieht:
1
/* The following code example will enable Timer3 interrupts, load the
2
    Timer3:Timer2 Period Register and start the 32-bit timer module
3
    consisting of Timer3 and Timer2.
4
    When a 32-bit period match interrupt occurs, the user must clear the
5
    Timer3 interrupt status flag in software.
6
    */
7
    T2CON = 0x00; //Stops any 16/32-bit Timer2 operation
8
    T3CON = 0x00; //Stops any 16-bit Timer3 operation
9
    TMR3 = 0x00; //Clear contents of the timer3 register
10
    TMR2 = 0x00; //Clear contents of the timer2 register
11
    PR3 = 0xFFFF; //Load the Period register3 with the value 0xFFFF
12
    PR2 = 0xFFFF; //Load the Period register2 with the value 0xFFFF
13
    IPC2bits.T3IP = 0x01; //Setup Timer3 interrupt for desired priority level
14
    //(this example assigns level 1 priority)
15
    IFS0bits.T3IF = 0; //Clear the Timer3 interrupt status flag
16
    IEC0bits.T3IE = 1; //Enable Timer3 interrupts
17
    T2CONbits.T32 = 1; //Enable 32-bit Timer operation
18
    T2CONbits.TON = 1; //Start 32-bit timer with prescaler
19
    //settings at 1:1 and clock source set to
20
    //the internal instruction cycle
21
    void __attribute__((__interrupt__, __shadow__)) _T3Interrupt(void)
22
    {
23
    /* Interrupt Service Routine code goes here */
24
        IFS0bits.T3IF = 0; //Reset Timer1 interrupt flag and Return from ISR
25
    }


Und in diesem Code blicke ich mich leider nicht durch. Was muss ich hier 
modifizieren, damit ich eine Wartezeit von 1min erhalte?

Vielen, vielen Dank im Voraus!

von Nop (Gast)


Lesenswert?

Chris schrieb:
> Was muss ich hier
> modifizieren, damit ich eine Wartezeit von 1min erhalte?

Also wie die Kommentare im Code sagen, ist die 32bit-Periode aus PR3:PR2 
aufgebaut. Da beide auf 0xFFFF sind, ist die derzeitige Periode 
0xFFFFFFFF, oder in dezimal etwa 4.3*10^9. Das ist der Ausgangswert, von 
dem aus runtergezählt wird.

Dann steht in den Kommentaren, daß als Takt dafür der CPU-Takt direkt 
dient. Das sind bei Dir 32MHz. Also 32*10^6 Takte pro Sekunde.

Wenn das bei 0 ankommt, gibt's den Interrupt. Das ist somit nach 
4.3*10^9/32*10^6 = 134 Sekunden der Fall.

Will man nun 60 Sekunden statt 134 Sekunden, dann sind es 60*32*10^6 
Takte, also 1.92*10^9. Wandelt man das in hexadezimal um, erhält man 
0x7270E000. Die obere Hälfte davon soll in PR3, die untere in PR2.

Mithin muß aus:
PR3 = 0xFFFF;
PR2 = 0xFFFF;
dann werden:
PR3 = 0x7270;
PR2 = 0xE000;

So würde ich das jedenfalls erstmal versuchen.

von neuer PIC Freund (Gast)


Lesenswert?

f_osc == 32 MHz

f_tc = (f_osc / 2) / PRESCALER

mit PRESCALER = 1:1

f_tc = 16 MHz    =>   T_tc = 62.5ns


D.h. im Vollgasmodus wird der Zähler alle 62.5ns um eins erhöht. Also 
muss man 60 s / 62.5 ns Ticks warten, entsprechend ist PR auf 0x39387000 
zu setzen.

von Nop (Gast)


Lesenswert?

neuer PIC Freund schrieb im Beitrag #4817831:
> f_tc = (f_osc / 2)

Ah den hatte ich nicht drin, dann würde mein Vorschlag 120 Sekunden 
warten.

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
Noch kein Account? Hier anmelden.