Arduino e interruzioni: modo rapido per ottenere valori pin


11

Uso un Arduino Uno e l' ho già configurato per funzionare con interruzioni sui pin digitali 2, 3, 4 e 5 secondo una spiegazione 1 che ho trovato.

void setup() contiene il seguente codice per impostare gli interrupt.

  //Endable Interrupts for PCIE2 Arduino Pins (D0-7)
  PCICR |= (1<<PCIE2);

  //Setup pins 2,3,4,5
  PCMSK2 |= (1<<PCINT18);
  PCMSK2 |= (1<<PCINT19);
  PCMSK2 |= (1<<PCINT20);
  PCMSK2 |= (1<<PCINT21);

  //Trigger Interrupt on rising edge
  MCUCR = (1<<ISC01) | (1<<ISC01);

E ora, la funzione ISR (PCINT2_vect) viene attivata ad ogni interruzione. Funziona come un fascino. La mia domanda è: qual è il modo migliore / più veloce per scoprire quale pin è stato attivato?

Ho trovato qualcosa in Re: è meglio usare ISR (PCINT2_vect) o attachInterrupt sui pin 2, 3? , ma non capisco il codice e non funziona immediatamente. Ma sembra impressionante ...

Qual'è la soluzione?

[2] http://arduino.cc/forum/index.php/topic.72496.15.html#lastPost

Modificare:

Al momento, sto leggendo lo stato del pin dal registro pin di input:

  if (PIND & 0b00000100)
    Serial.println( "PIN 2" );
  if (PIND & 0b00001000)
    Serial.println( "PIN 3" );
  if (PIND & 0b00010000)
    Serial.println( "PIN 4" );
  if (PIND & 0b00100000)
    Serial.println( "PIN 5" );

Alla fine, voglio contare gli interrupt sui pin. Ma come posso assicurare che non ci siano conteggi due volte?


All'elettronica, probabilmente più persone si sono date da fare con Arduinos e altre cose elettroniche.
Earlz,

Se pensi, la domanda dovrebbe essere laggiù, segnalala. Ho risolto i miei problemi di accesso.
madc,

3
@Earlz: questa è una domanda di programmazione, quindi è in argomento . Il fatto che sia per una piattaforma di hobbisti è irrilevante; vedi le centinaia di altre domande su Arduino su StackOverflow come riferimento.
BlueRaja - Danny Pflughoeft,

Risposte:


4

Anch'io ho una prima soluzione, ma non ho potuto testare l'affidabilità poiché l'hardware non è finito.

Per prima cosa ho aggiunto oldPins e tickCount come variabili globali:

static byte oldPins = 0;
volatile unsigned int tickCount[4] = { 0, 0, 0, 0 };

Ed è così che ho risolto l'ISR al momento. Le soluzioni migliori sono più che benvenute.

ISR( PCINT2_vect ) {
  //Read values from digital pins 2 to 7
  const byte actPins = PIND;
  //Match this values agaist the oldPins bitmask (XOR and AND for raising edge)
  const byte setPins = (oldPins ^ actPins) & actPins;

  if (setPins & 0b00000100)
    tickCount[0]++;
  if (setPins & 0b00001000)
    tickCount[1]++;
  if (setPins & 0b00010000)
    tickCount[2]++;
  if (setPins & 0b00100000)
    tickCount[3]++;

  oldPins = actPins;
}

1
Se si aggiorna tickCount [] in un ISR, è necessario dichiararlo con il qualificatore di tipo "volatile".
Icarus74,

Ho aggiornato il codice all'interno della risposta. Per maggiori informazioni consultare la documentazione di arduino: arduino.cc/en/Reference/Volatile
madc
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.