Forum: Mikrocontroller und Digitale Elektronik Atmega168: PCINT2 wird von INT0/1 gestört


von Hanno H. (hh86)


Lesenswert?

Hallo zusammen,

ich versuche mit einem Atmega168 (16 MHz) drei ungefähr zeitgleich 
ankommende CMOS Signale (CLK1-3 und DATA1-3, low-active) auf den 
fallenden Flanken der CLK Leitungen auszuwerten.
Dazu habe ich CLK1 und CLK2 auf INT0 und INT1 gelegt und die 
Flankenerkennung entsprechend eingestellt. Für CLK3 habe ich PCINT20 
verwendet und die Flankenerkennung in der ISR geregelt. Ansonsten werden 
in den entsprechenden ISR nur die Bits gesammelt.
In INT0_vect und INT1_vect erfasse ich so immer alle Bits, aber in 
PCINT20 verpasse ich jedesmal mehrere Bits. Schalte ich INT0 und INT1 
aber aus, dann kann ich in PCINT20 alle Bits erfassen.
Jetzt wäre meine Frage, wie ich auch zeitgleich alle drei Signale 
komplett erfassen kann. Müsste ich dazu zwangsläufig auf einen Mega32 
ausweichen, der ja einen zusätzlichen externen Interrupt (INT2) hat? 
Oder kann ich das ganze auch mit meinem Atmega168 (INT0, INT1 und Pin 
Change Interrupt) erreichen?
Anbei noch meine ISR, die ich so kurz wie möglich gehalten habe. Habe 
ich da irgendwelche Fehler drin, mit denen ich mir das Timing versaue?

Vielen Dank schonmal!
Hanno
1
ISR(INT0_vect)
2
{ 
3
  uint8_t x = PIND & (1 << PD5); //DATA1
4
  if (!x)
5
  {
6
    track1[counter_t1 / TRACK1_BYTELEN] |= (1 << (counter_t1 % TRACK1_BYTELEN));
7
  }
8
  counter_t1++;
9
}
10
11
ISR(INT1_vect)
12
{ 
13
  uint8_t x = PIND & (1 << PD6); //DATA2
14
  if (!x)
15
  {
16
    track2[counter_t2 / TRACK2_BYTELEN] |= (1 << (counter_t2 % TRACK2_BYTELEN));
17
  }
18
  counter_t2++;
19
}
20
21
ISR(PCINT2_vect)
22
{
23
  uint8_t x = PIND & (1 << PD7); //DATA3
24
  uint8_t state = PIND & (1 << PD4); //CLK3
25
  if (!state)
26
  {
27
    if (!x)
28
    {
29
      track3[counter_t3 / TRACK3_BYTELEN] |= (1 << (counter_t3 % TRACK3_BYTELEN));
30
    }
31
    counter_t3++;    
32
  }
33
}

von Karl H. (kbuchegg)


Lesenswert?

Regel 1:
Einen Interrupt kannst du nur dann verpassen, wenn durch die Abarbeitung 
eines anderen Interrupts das Interrupt System lange genug gesperrt ist, 
so dass zwischendurch mehrere Interrupts auflaufen können.
Das kann, durch die fixe Priorisierung auch durchaus der eigene 
Interrupt sein! Tritt der nur häufig genug auf, so dass nach Beendigung 
der ISR derselbe Interrupt schon wieder gefeurt hat, dann kommt keine 
andere ISR mehr zum Zug.


D.h.: Feuert die Interruptquelle zu häufig (bei dir sind das dann eben 
die externen Signale) dann kommt der µC nicht mehr mit. Nicht ganz 
unwesentlich dabei ist dann auch, welche Arbeit in der ISR gemacht wird. 
Daher die Regel: ISR so kurz wie möglich.

1
   ... 1 << (counter_t2 % TRACK2_BYTELEN)

ungünstig. variabler Bitshift ist etwas, was du deinem µC nicht 
unbedingt zumuten möchtest. Ein AVR hat dafür keine Instruktionen und 
muss das mit einer Schleife realisieren.

von Karl H. (kbuchegg)


Lesenswert?

> Habe ich da irgendwelche Fehler drin, mit denen ich mir das Timing versaue?

Über welche Frequenzen reden wir?

von Hanno H. (hh86)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Einen Interrupt kannst du nur dann verpassen, wenn durch die Abarbeitung
> eines anderen Interrupts das Interrupt System lange genug gesperrt ist,
> so dass zwischendurch mehrere Interrupts auflaufen können.
> Das kann, durch die fixe Priorisierung auch durchaus der eigene
> Interrupt sein! Tritt der nur häufig genug auf, so dass nach Beendigung
> der ISR derselbe Interrupt schon wieder gefeurt hat, dann kommt keine
> andere ISR mehr zum Zug.

Vielen Dank für die Antwort. Meine Befürchtung war eigentlich nicht, 
dass ich einen Interrupt verpasse, sondern eher, dass der Interrupt zu 
spät abgearbeitet wird und auf der Datenleitung längst ein anderer 
Zustand herrscht. Der Threadtitel war wohl ungünstig gewählt.

Zu dem Bitshift: Also sollte ich die Bits mit "vorberechneten" Masken 
reinodern??

Die drei CMOS Signale kommen von einem Magnetkartenleser von Pollin 
(ZU-M1363S1E1). Interessanterweise kann ich mit meinem Code Track1 und 
Track2 (über INT0 und INT1) gleichzeitig problemlos auslesen. Wenn ich 
aber Track1 ausschalte und Track2+Track3 gleichzeitig lesen will, dann 
klappts nichtmehr: Fehler in Track3 (PCINT20), während Track2 
einwandfrei gelesen wird. Daher auch meine Verwirrung, denn mein ISR 
Code scheint ja nicht zu komplex zu sein, sonst könnte ich Track1+Track2 
ja nicht gleichzeitig fehlerfrei erfassen?!

von Karl H. (kbuchegg)


Lesenswert?

Hanno H. schrieb:

>> der ISR derselbe Interrupt schon wieder gefeurt hat, dann kommt keine
>> andere ISR mehr zum Zug.
>
> Vielen Dank für die Antwort. Meine Befürchtung war eigentlich nicht,
> dass ich einen Interrupt verpasse, sondern eher, dass der Interrupt zu
> spät abgearbeitet wird und auf der Datenleitung längst ein anderer
> Zustand herrscht.

Das kannst aber nur du wissen!
Denn nur du weißt, wie sich das Timing deiner Signale gestaltet.


> Zu dem Bitshift: Also sollte ich die Bits mit "vorberechneten" Masken
> reinodern??

Wär eine Möglichkeit.

> Die drei CMOS Signale kommen von einem Magnetkartenleser von
> Pollin (ZU-M1363S1E1).

Und mit welcher Frequenz taktest du deinen µC? Wie hoch ist die Frequenz 
der Signale vom Leser?


Hast du dir denn schon mal deine Signale am Oszi angesehen. Immerhin 
wäre ja auch die Umkehrung denkbar: Dass das Datensignal mit der 
Clockflanke noch nicht stabil genug anliegt und du tatsächlich zu früh 
drann bist.

Im übrigen denke ich nicht, dass du mit derartigen Spielchen "diesen 
Interrupt aktivieren, jenen nicht) in irgendeiner Form weiterkommst. Die 
Aussagekraft derartiger Kombinationsspielchen ist meistens sehr gering.

von Stephan (Gast)


Lesenswert?

H. H. schrieb:
> Meine Befürchtung war eigentlich nicht,
> dass ich einen Interrupt verpasse, sondern eher, dass der Interrupt zu
> spät abgearbeitet wird und auf der Datenleitung längst ein anderer
> Zustand herrscht.

Oder Clock wieder zurückgewechselt ist und das ganze als "Fehlalarm" 
interpretiert wird.

Mach doch Kanal 2 an den PinChange. Der Kanal 2 hat laut DB ne 
niedrigere Datendichte.

von Hanno H. (hh86)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Hanno H. schrieb:
>
>>> der ISR derselbe Interrupt schon wieder gefeurt hat, dann kommt keine
>>> andere ISR mehr zum Zug.
>>
>> Vielen Dank für die Antwort. Meine Befürchtung war eigentlich nicht,
>> dass ich einen Interrupt verpasse, sondern eher, dass der Interrupt zu
>> spät abgearbeitet wird und auf der Datenleitung längst ein anderer
>> Zustand herrscht.
>
> Das kannst aber nur du wissen!
> Denn nur du weißt, wie sich das Timing deiner Signale gestaltet.
>
>
>> Zu dem Bitshift: Also sollte ich die Bits mit "vorberechneten" Masken
>> reinodern??
>
> Wär eine Möglichkeit.

Habs gerade mit fertigen Masken probiert, leider keine Verbesserung.

>> Die drei CMOS Signale kommen von einem Magnetkartenleser von
>> Pollin (ZU-M1363S1E1).
>
> Und mit welcher Frequenz taktest du deinen µC?

Mit einem 16 MHz Quarz (CKDIV8 habe ich natürlich ausgenommen :).

> Hast du dir denn schon mal deine Signale am Oszi angesehen. Immerhin
> wäre ja auch die Umkehrung denkbar: Dass das Datensignal mit der
> Clockflanke noch nicht stabil genug anliegt und du tatsächlich zu früh
> drann bist.

Ein Oszilloskop habe ich leider nicht zur Verfügung. Ich habe aber auch 
mal testweise 1-200 µs gewartet, bevor ich auf die Datenleitung geschaut 
habe. Aber da kam nur Mist raus. Eigentlich kann ich mit meinem µC auch 
nicht zu früh dran sein, denn ohne INT0/1, also nur mit PCINT20 für 
Track3 komme ich super hin und erwische alle Bits.

von Karl H. (kbuchegg)


Lesenswert?

Stephan schrieb:

> Mach doch Kanal 2 an den PinChange. Der Kanal 2 hat laut DB ne
> niedrigere Datendichte.


@Stephan

Weißt du, über welche Frequenzen wir hier reden?
Der TO scheint das ja nicht zu wissen und ich bin es mitlerweile leid, 
da ins Blaue zu raten, wie eng (zeitlich gesehen) die ganze Geschichte 
wirklich ist.

von spontan (Gast)


Lesenswert?

Wenn das irgendwie genau werden soll, so sollten die 3 Kanäle gesampelt 
werden. D.h. drei FFs speichern den Zustand der Leitungen in 
Abhängigkeit der verschiedenen Flankenwechsel.

Mit Verzögerungen über INT-Eingänge und dem Lesen der anderen Leitungen 
ist die Aussagekraft der Messung komplett weg. Da kannst Du gleich 
raten.

Wenn ichs richtig verstanden habe, willst Du einen Logiganalyser mit 
großem Speicher, aber geringen Kosten. Wenn die Messergebnisse wichtig 
sein sollten, dann kauf Dir sowas. Alles andere wird ein unsicheres 
Gebastel.

von Hanno H. (hh86)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Weißt du, über welche Frequenzen wir hier reden?
> Der TO scheint das ja nicht zu wissen und ich bin es mitlerweile leid,
> da ins Blaue zu raten, wie eng (zeitlich gesehen) die ganze Geschichte
> wirklich ist.

Bitte entschuldige! Im folgenden Frequenzbereich kommen die Signale an: 
290 bis 9950 Hz (in Abhängigkeit von der Kartengeschwindigkeit beim 
Durchziehen und der Datendichte der Tracks).

@Stephan: Den Wechsel werde ich ausprobieren, vielen Dank schonmal.

von Karl H. (kbuchegg)


Lesenswert?

Hanno H. schrieb:

> Bitte entschuldige! Im folgenden Frequenzbereich kommen die Signale an:
> 290 bis 9950 Hz (in Abhängigkeit von der Kartengeschwindigkeit beim
> Durchziehen und der Datendichte der Tracks).

Also 1K

Dann brauchst du dir um Timing keine Sorgen machen. Das ist für deinen 
µC Superzeitlupe.

Also muss dein Problem wo anders liegen.
Kann es sein, dass das Clock Signal nicht sauber ist und dir den 
Interrupt mehrfach triggert?


(Bei diesen Frequenzen würd ich überhaupt nicht mit Interrupts 
rummachen, sondern auf Polling setzen. Timer aufsetzen, der in seiner 
ISR mit Hausnummer 5kHz die Eingänge überwacht und bei Flankendetektion 
den jeweiligen Zustand feststellt)

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Hanno H. schrieb:
>
1
> ISR(PCINT2_vect)
2
> {
3
>   uint8_t x = PIND & (1 << PD7); //DATA3
4
>   uint8_t state = PIND & (1 << PD4); //CLK3
5
>   if (!state)
6
>   {
7
>     if (!x)
8
>     {
9
>       track3[counter_t3 / TRACK3_BYTELEN] |= (1 << (counter_t3 %
10
> TRACK3_BYTELEN));
11
>     }
12
>     counter_t3++;
13
>   }
14
> }
15
>

Wieder mal großes Rätselraten:

Welchen Typ haben track1, track2, track3?
Welchen Typ haben counter_t1, counter_t2, counter_t1?
Welchen Wert haben TRACK1_BYTELEN, TRACK2_BYTELEN, TRACK3_BYTELEN?

Warum liest Du in PCINT2_vect überhaupt DATA3 aus, wenn Du diesen dann 
wegen falscher Flanke auf CLK3 ignorierst?

von spess53 (Gast)


Lesenswert?

Hi

>Also 1K

Eher 10k.

MfG Spess

von Karl H. (kbuchegg)


Lesenswert?

spess53 schrieb:
> Hi
>
>>Also 1K
>
> Eher 10k.
>
> MfG Spess

Ähm.
Wie war das mit der Stirn und der Tischkante. Muss ich gleich mal 
ausprobieren.

Ok, dann nehm ich die Superzeitlupe zurück und ersetze durch Zeitlupe.

von Stephan (Gast)


Lesenswert?

Hanno H. schrieb:
> Im folgenden Frequenzbereich kommen die Signale an:
> 290 bis 9950 Hz

Kommt hin. Datenblatt ist ggf. hier:
http://www.pollin.de/shop/downloads/D721519D.PDF

>1000 Instruktionen auf 3 Interruptroutinen sollten aber eigentlich mehr als genug 
Reserve sein. Auch mit ungünstigem Code.
Nach dem Timing-Diagramm sollten mindestens 25 µs nach dem Clock-Signal 
auch noch korrekt ausgelesen werden können.

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Kann auch sein, dass er einen Buffer-Overflow hat, der nur bei 
Aktivieren von DATA3 zum Tragen kommt, weil track3 bis dahin als 
zusätzliche Pufferzone für track1 und track2 dient... denn es fehlt in 
den ISRs jeglicher Check auf Überlauf der Arrays.

von MWS (Gast)


Lesenswert?

In's Blaue geraten: Du hast PCMSK2 falsch gesetzt und der PCINT triggert 
noch auf 'nen anderen Pin.

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Hat keinen Sinn, da weiter zu raten. Ohne vollständigen Quellcode ist 
alles reine Spekulation.

Wenn ich mir das Datenblatt zu dem Magenetkarten-Reader bei Pollin 
anschaue, haben die TRACKx_BYTELEN den Wert 5. Nicht gerade günstig für 
Division und Modulo-Operator. Da wäre es besser, jeweils einen Bit- und 
einen Bytezähler mitzuführen, um den Index und das Bit im Array zu 
bestimmen, welches gesetzt werden muss.

von Hanno H. (hh86)


Lesenswert?

@Karl:
Danke, ich werde es mal mit Polling versuchen. Aber aus Interesse: Wie 
könnte ich rausfinden, ob das CLK Signal unsauber ist (ohne Oszi)?

@Frank:
Die Datentypen habe ich absichtlich nicht eingefügt. Der Code tut ja 
das, was er soll - es war nur die Frage ob er es auch schnell genug tut 
(ist ja mittlerweile geklärt :). Habe ich jetzt angehängt.
Das Auslesen habe ich beim Ausprobieren testweise vor die 
Flankendetektion geschrieben, da ich möglichst "schnell" sein wollte. 
(Jaja, das war Käse.)
Einen Buffer Overflow habe ich nicht, die sind groß genug gewählt. Das 
konnte ich im Debugger sehen. Natürlich gehört in den ISR noch ein Check 
rein, aber aus meiner (falschen) Befürchtung zu langsam zu sein, habe 
ich alles an Code entfernt, was nicht absolut nötig ist.
Den Einwand mit den Operatoren verstehe ich nicht? Ich brauche nur die 
Anzahl der gelesenen Bits und kann mit DIV und MOD bestimmen wo das 
nächste Bit hin muss. Ich schreibe jeweils 7 bzw. 5 Bits in ein Byte, 
weil ich es so später bequem in ASCII dekodieren kann.

@MWS:
Nope, im Register ist nur PCINT20 angeknipst.

Nochmal Danke an alle, für eure Hilfe :)
1
#define TRACK1_LEN 79
2
#define TRACK2_LEN 48
3
#define TRACK3_LEN 107
4
#define BUFFER 40
5
6
#define TRACK1_BYTELEN 7
7
#define TRACK2_BYTELEN 5
8
#define TRACK3_BYTELEN 5
9
10
char track1[TRACK1_LEN+BUFFER];
11
char track2[TRACK2_LEN+BUFFER];
12
char track3[TRACK3_LEN+BUFFER];
13
14
uint16_t counter_t1 = 0;
15
uint16_t counter_t2 = 0;
16
uint16_t counter_t3 = 0;

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Hanno H. schrieb:
> Einen Buffer Overflow habe ich nicht, die sind groß genug gewählt.

Nicht, wenn ein CLK-Signal "unsauber" ist und zum Beispiel "prellt". Ich 
empfehle Dir, den Check auf jeden Fall einzubauen.

> Den Einwand mit den Operatoren verstehe ich nicht? Ich brauche nur die
> Anzahl der gelesenen Bits und kann mit DIV und MOD bestimmen wo das
> nächste Bit hin muss. Ich schreibe jeweils 7 bzw. 5 Bits in ein Byte,
> weil ich es so später bequem in ASCII dekodieren kann.

Eine Division/Modulo-Operation mit 8 oder einer anderen Zweierpotenz ist 
wesentlich schneller als mit 5 oder 7, da der Compiler hier einfach Bits 
schieben kann. Das kostet ordentlich, was Du da machst. Deshalb mein 
Vorschlag, zwei Counter zu verwenden: einen für den Index (Bytecounter) 
und einen für die Bits (Bitcounter), welche Du nach Erreichen von von 
TRACKx_BYTELEN wieder zurücksetzt, um dann den Bytecounter zu 
inkrementieren. Das spart sowohl eine Division als auch den 
Modulo-Operator komplett ein.

> uint16_t counter_t1 = 0;
> uint16_t counter_t2 = 0;
> uint16_t counter_t3 = 0;

Wenn Du diese außerhalb der ISRs auch verwendest, müssen sie volatile 
deklariert sein. Wenn sie ausschließlich in den ISRs verwendet werden, 
gehören sie als static Variablen in die ISRs. Das gleiche gilt für die 
Arrays selbst. Sonst kommt da evtl. Mist raus.

Gruß,

Frank

von Karl H. (kbuchegg)


Lesenswert?

Hanno H. schrieb:
> @Karl:
> Danke, ich werde es mal mit Polling versuchen. Aber aus Interesse: Wie
> könnte ich rausfinden, ob das CLK Signal unsauber ist (ohne Oszi)?

Ohne Oszi ist natürlich schwer.
Ich würd da mal hinterher die counter ansehen, ob die plausibel sind.

von Hanno H. (hh86)


Lesenswert?

Frank M. schrieb:
> Nicht, wenn ein CLK-Signal "unsauber" ist und zum Beispiel "prellt". Ich
> empfehle Dir, den Check auf jeden Fall einzubauen.

Ja, der Check wird auch eingebaut. Aber wenn die CLK Line prellt, dann 
sind die gesammelten Bits sowieso für die Katz (und ein BO wäre mir bei 
Testzwecken mehr oder minder egal).

> Eine Division/Modulo-Operation mit 8 oder einer anderen Zweierpotenz ist
> wesentlich schneller als mit 5 oder 7, da der Compiler hier einfach Bits
> schieben kann. Das kostet ordentlich, was Du da machst. Deshalb mein
> Vorschlag, zwei Counter zu verwenden: einen für den Index (Bytecounter)
> und einen für die Bits (Bitcounter), welche Du nach Erreichen von von
> TRACKx_BYTELEN wieder zurücksetzt, um dann den Bytecounter zu
> inkrementieren. Das spart sowohl eine Division als auch den
> Modulo-Operator komplett ein.

Das klingt sinnvoll, sofern die beiden Counter dann als Register und 
nicht im RAM vorliegen. Wäre sicher eine weitere Optimierung, aber ist 
wohl nicht ursächlich für mein Problem (Timing wurde ja ausgeschlossen).

Also falls noch jemand Ideen hat, wie ich eine prellende CLK Line 
feststellen und beheben könnte (ohne Oszi) oder sonst noch Anregungen 
hat, bin ich immer offen :)

von Karl H. (kbuchegg)


Lesenswert?

Hanno H. schrieb:

> Die Datentypen habe ich absichtlich nicht eingefügt. Der Code tut ja
> das, was er soll - es war nur die Frage ob er es auch schnell genug tut
> (ist ja mittlerweile geklärt :).

Ich denke: schnell genug wird es schon noch sein.
Aber mit Bit/Bytezählern bzw. entsprechenden Masken entlastest du deine 
ISR ungeschaut um einen Faktor 8 bis 10 (wenn nicht noch mehr. Sind ja 
schliesslich Division und Modulo)

(Ich wusste bisher nicht, dass da keine 2-er Potenzen im SPiel sind, 
drum hab ich weiter oben "ja" zu einem Maskenarray gesagt. Aber so ist 
das für den µC noch viel simpler.

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Hanno H. schrieb:
> Also falls noch jemand Ideen hat, [...]

Du hast Dich leider nicht zur volatile-Deklaration Deiner in dne ISRs 
benutzten Variablen geäußert. Das könnte bei Dir schon das Problem 
beseitigen. Ja, volatile ist hier zwingend notwendig.

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Karl Heinz Buchegger schrieb:
> (Ich wusste bisher nicht, dass da keine 2-er Potenzen im SPiel sind,
> drum hab ich weiter oben "ja" zu einem Maskenarray gesagt. Aber so ist
> das für den µC noch viel simpler.

Tja, wie so oft: Der TO lässt für ihn unwichtig erscheinende Infos 
(sogar bewusst) weg, die sich aber im nachhinein als durchaus 
ausschlaggebend für das Problem entpuppen können.

von Hanno H. (hh86)


Lesenswert?

Frank M. schrieb:
> Tja, wie so oft: Der TO lässt für ihn unwichtig erscheinende Infos
> (sogar bewusst) weg, die sich aber im nachhinein als durchaus
> ausschlaggebend für das Problem entpuppen können.

War keine Absicht. Hatte den Überblick verloren. Jedenfalls ist es mit 
als volatile deklarierten Variablen auch nicht gelöst.
In die ISR habe ich jetzt einen zweiten Counter (temp_count) eingefügt, 
um die CLK Line zu beobachten. Dabei ist mir aufgefallen, dass 
counter_t3 nicht genau halb so groß ist wie temp_count, sondern um 
5-10 abweicht. Das würde ja für eine prellende CLK Leitung sprechen, 
oder?
(Wenn ich allerdings nur Track3 lese, dann ist counter_t3 immer exakt 
die Hälfte von temp_count.)
1
#define TRACK1_BYTELEN 7
2
#define TRACK2_BYTELEN 5
3
#define TRACK3_BYTELEN 5
4
#define TRACK1_LEN 79
5
#define TRACK2_LEN 48
6
#define TRACK3_LEN 107
7
#define BUFFER 40
8
9
volatile const uint8_t mask[7] = { 0b0000001, 0b0000010, 0b0000100, 0b0001000, 0b0010000, 0b0100000, 0b1000000 };
10
11
volatile char track1[TRACK1_LEN+BUFFER];
12
volatile char track2[TRACK2_LEN+BUFFER];
13
volatile char track3[TRACK3_LEN+BUFFER];
14
15
volatile uint16_t counter_t1 = 0;
16
volatile uint16_t counter_t2 = 0;
17
volatile uint16_t counter_t3 = 0;
18
19
volatile uint16_t temp_count = 0
20
21
ISR(PCINT2_vect)
22
{
23
  uint8_t x = PIND & (1 << PD7);
24
  uint8_t s = PIND & (1 << PD4);
25
  if (!s)
26
  {
27
    if (!x)
28
    {
29
      //track3[counter_t3 / TRACK3_BYTELEN] |= (1 << (counter_t3 % TRACK3_BYTELEN));
30
      track3[counter_t3 / TRACK3_BYTELEN] |= mask[counter_t3 % TRACK3_BYTELEN];
31
    }
32
    counter_t3++;    
33
  }
34
  temp_count++;
35
}

von Karl H. (kbuchegg)


Lesenswert?

Hanno H. schrieb:

> um die CLK Line zu beobachten. Dabei ist mir aufgefallen, dass
> counter_t3 nicht genau halb so groß ist wie temp_count, sondern um
> 5-10 abweicht.

größer oder kleiner?
Hast du zuviele Pulse oder zu wenige gezählt?

von Karl H. (kbuchegg)


Lesenswert?

1
ISR(PCINT2_vect)
2
{
3
  uint8_t x = PIND & (1 << PD7);
4
  uint8_t s = PIND & (1 << PD4);
5
  if (!s)
6
  {
7
    if (!x)
8
    {
9
      //track3[counter_t3 / TRACK3_BYTELEN] |= (1 << (counter_t3 % TRACK3_BYTELEN));
10
      //track3[counter_t3 / TRACK3_BYTELEN] |= mask[counter_t3 % TRACK3_BYTELEN];
11
12
      track3[byteCount_t3] |= bitmask_t3;
13
    }
14
    bitMask_t3 <<= 1;
15
16
    bitCount_t3++;
17
    if (bitCount_t3 == TRACK3_BYTELEN)
18
    {
19
      bitMask_t3 = 0x01;
20
      bitCount_t3 = 0;
21
      byteCount_t3++;
22
    }
23
24
    counter_t3++;    
25
  }
26
  temp_count++;
27
}

von Hanno H. (hh86)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Hanno H. schrieb:
>
>> um die CLK Line zu beobachten. Dabei ist mir aufgefallen, dass
>> counter_t3 nicht genau halb so groß ist wie temp_count, sondern um
>> 5-10 abweicht.
>
> größer oder kleiner?
> Hast du zuviele Pulse oder zu wenige gezählt?

Also bei den fehlerhaften Swipes ist 2*counter_t3 < temp_count mit einer 
Differenz von 5-10. Bei guten Swipes ist 2*counter_t3 == temp_count.
1
vier fehlerhafte Swipes:
2
Swipe    1.     2.     3.     4.
3
tmp   0x569  0x56b  0x569  0x56b
4
t3    0x2b0  0x2b1  0x2b0  0x2b3
5
6
zwei "gute" Swipes wo ich nur Track3 lese:
7
Swipe    1.     2.    
8
tmp   0x570  0x536
9
t3    0x2b8  0x29b

Deinen Code habe ich eingefügt. Allerdings wurde dadurch auch das 
Problem nicht behoben.
Nochmals Danke an alle! :)

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.