Arduino และอินเตอร์รัปต์: วิธีที่รวดเร็วในการรับค่าพิน


11

ฉันใช้Arduino Unoแล้วตั้งค่าให้ทำงานกับการขัดจังหวะบนพินดิจิตอล 2, 3, 4 และ 5 ตามคำอธิบายที่1 ที่ฉันพบ

void setup() มีรหัสต่อไปนี้เพื่อตั้งค่าอินเตอร์รัปต์

  //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);

และตอนนี้ฟังก์ชั่น ISR (PCINT2_vect) จะถูกเรียกใช้ในการขัดจังหวะทุกครั้ง มันใช้งานได้เหมือนมีเสน่ห์ คำถามของฉันคืออะไรวิธีที่ดีที่สุด / เร็วที่สุดในการค้นหาว่าพินใดถูกเรียกใช้

ฉันพบบางอย่างในRe: ดีกว่าที่จะใช้ ISR (PCINT2_vect) หรือแนบติดขัดบนพิน 2, 3? แต่ฉันไม่เข้าใจรหัสและมันไม่ทำงานนอกกรอบ แต่มันดูน่าประทับใจ ...

ทางออกคืออะไร?

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

แก้ไข:

ในขณะนี้ฉันกำลังอ่านสถานะพินจากการลงทะเบียนพิน:

  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" );

ในท้ายที่สุดฉันต้องการนับการขัดจังหวะบนหมุด แต่ฉันจะมั่นใจได้อย่างไรว่าไม่มีการนับสองครั้ง?


ที่อิเล็กทรอนิกส์ผู้คนจำนวนมากอาจยุ่งกับ Arduinos และสิ่งอื่น ๆ อิเล็กทรอนิกส์
Earlz

หากคุณคิดว่าคำถามควรอยู่ที่นั่นทำเครื่องหมายไว้ ฉันแก้ไขปัญหาการเข้าสู่ระบบของฉัน
madc

3
@Earlz: นี่เป็นคำถามที่การเขียนโปรแกรมเพื่อให้มันอยู่ในหัวข้อ ความจริงที่ว่าสำหรับแพลตฟอร์มงานอดิเรกนั้นไม่เกี่ยวข้อง ดูคำถาม arduino อื่น ๆ อีกหลายร้อยรายการใน stackoverflowสำหรับการอ้างอิง
BlueRaja - Danny Pflughoeft

คำตอบ:


4

ฉันมีวิธีแก้ปัญหาแรกด้วยตัวเอง แต่ฉันไม่สามารถทดสอบความน่าเชื่อถือได้เนื่องจากฮาร์ดแวร์ยังไม่เสร็จเจ็ท

ครั้งแรกที่ฉันเพิ่ม oldPins และ tickCount เป็นตัวแปรทั่วโลก:

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

และนั่นคือวิธีที่ฉันแก้ไข ISR ในขณะนี้ ทางออกที่ดีกว่ายินดีต้อนรับ

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
หากคุณกำลังอัพเดต tickCount [] ใน ISR คุณควรจะประกาศด้วยตัวระบุประเภท 'ระเหย'
icarus74

ฉันอัปเดตรหัสภายในคำตอบ สำหรับข้อมูลเพิ่มเติมดูเอกสารประกอบของ arduino: arduino.cc/en/Reference/Volatile
madc
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.