Forum: Mikrocontroller und Digitale Elektronik Interruptproblem mit PIC


von Stefan (Gast)


Lesenswert?

Hallo,

ich habe den Timer2 beim PIC16F873 eingeschaltet und mit Vor-/und
Nachteiler jeweils 1:16 versehen. Bei einem Takt von 4MHz müßte also
alle 64ms (PR2=250) die Interruptroutine durchlaufen werden. Dies habe
ich kontrolliert, indem ich in der Interruptroutine jeweils einen Port
umschalte und dies mit dem Oszit nachmesse. Hier komme ich auf 64ms.

Nun möchte ich aber nicht alles 64ms sondern alle 640ms einen Interrupt
haben. Deshalb habe ich eine globale Variable xy definiert und in der
Interruptroutine zähle ich diese hoch und wenn diese 10 ist, wird die
eigentliche Aktion ausgeführt. Leider funktioniert dies nicht so ganz.
Im Debugmodus von MPLAP / ICD2 mit CC5X passt es einwandfrei aber im
Realtime-Modus messe ich am Pin alle 64ms ein umschalten - unabhängig
von meiner if-Abfrage.

Was könnte das sein? Wer kann mir helfen?



===Codeausschnitt:===

char xy;

#pragma origin 4
interrupt InterruptRoutine(void)
{
  int_save_registers

  if (TMR2IF)
  {
   xy++;
    if(xy >= 10)
   {
    PORTA.0 ^= 0x01;
    TMR2IF = 0;
          aktion=1;
    timebase=0;
   }
  }

  int_restore_registers
}

von Stefan (Gast)


Lesenswert?

... timebase heißt natürlich xy!

von Steffen (Gast)


Lesenswert?

Dein Programmcode ist eigentlich in Ordnung. Könnte es evtl. sein, dass
während des Interupts die Bank-Select Bits nicht richtig gesetzt sind?

Ich kenne den CC5X nicht aber der setzt die Bits doch nicht automatisch
zurück oder wird das durch int_save_registers mit erledigt?

Wenn das Ganze mit dem ICD2 im Debugmodus richtig läuft, dann sollte es
eigentlich auch Real-Time funktionieren.

Steffen

von oksana (Gast)


Lesenswert?

Hallo Stafan, versuch mal so

char xy;

#pragma origin 4
interrupt InterruptRoutine(void)
{
  int_save_registers

  if (TMR2IE && TMR2IF)
  {
   xy++;
    if(xy >= 10)
   {
    PORTA.0 ^= 0x01;
    aktion=1;
    xy=0;
   }
   TMR2IF = 0;
  }

  int_restore_registers
}

von Stefan (Gast)


Lesenswert?

Danke oksana,

das wars - jetzt geht's. :-)
Problem war TMR2IF = 0 in der if-Schleife.

von Steffen (Gast)


Lesenswert?

Stimmt, das gehört nicht in den If-Zweig. Allerdings toggelt dann dein
Pin alle 64ms 11mal kurz hintereinander.

Steffen

von Stefan (Gast)


Lesenswert?

Wieso toggelt er?

von Steffen (Gast)


Lesenswert?

Beim Rücksprung aus der ISR werden die Interupts wieder freigegeben. Da
ja das Interuptflag nur zurückgesetzt wird, wenn xy=10 springt er
sofort wieder die ISR an. Das Ganze dann 10 mal.

Steffen

von Stefan (Gast)


Lesenswert?

Da ich jetzt doch das Interruptflag immer zurücksetze und nicht nur wenn
xy=10 dürfte ich doch dieses Problem nicht haben, oder verstehe ich da
was falsch?

von Steffen (Gast)


Lesenswert?

Das ist schon richtig. Ich meinte dein erstes Posting. So wie die ISR
jetzt ist ist das OK.

Steffen

von Stefan (Gast)


Lesenswert?

Ok, dann hab ich das auch richtig verstanden. Vielen Dank!

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.