Arduino硬件中断可靠性问题

时间:2017-10-30 02:26:41

标签: arduino external interrupt

这似乎是一个愚蠢的问题,也许它的描述不是我能设计的最好的。

我正在制作一个速度传感器,它使用两个红外光束来计算速度,这是根据断开两个光束所需的时间来计算的。

我有两种测试方法。

  1. 我的手(5-10米/秒)
  2. 高速加农炮(30-60米/秒)。
  3. 我已经排除了使用示波器来自IR光束的信号出现问题,当代码失败/工作时,数据在示波器上是相同的。

    我的问题是我的代码在我用手时起作用,但仍然不规则地失败,而它经常在高速下失败。两种情况下的所有条件都相同。可能是什么问题?

    #include <SPI.h>
    #include <SD.h>
    #include <LiquidCrystal.h>
    
    const int rs = 9, en = 8, d4 = 7, d5 = 6, d6 = 5, d7 = 4;
    LiquidCrystal lcd(rs, en, d4, d5, d6, d7);
    
    File root;
    int fileNo = 0;
    String currentFileName;
    const int CS = 10;
    const byte interruptPinStart = 2;
    const byte interruptPinFinish = 3;
    
    volatile unsigned long int startTimeMillis = 0;
    volatile unsigned long int stopTimeMillis = 0;
    volatile unsigned long int startTimeMicros = 0;
    volatile unsigned long int stopTimeMicros = 0;
    volatile unsigned long int microsDifference = 0;
    volatile unsigned long int millisDifference = 0;
    
    int launchNo = 0;
    float currentVelocity = 0;
    volatile boolean started = false;
    String inputString = "";       
    boolean stringComplete = false;  
    const int txLed1 = 14;
    const int statusLed1 = 15;
    const int statusLed2 = 16;
    volatile boolean triggerDone = false;
    float velocity = 0;
    String temp;
    unsigned long int lockout = 0;
    boolean lockedOut = false;
    boolean fileFail = false;
    int testNo = 0;
    
    void setup() {
      inputString.reserve(200);
      pinMode(statusLed1, OUTPUT);
      pinMode(statusLed2, OUTPUT);
      pinMode(txLed1, OUTPUT);
      Serial.begin(9600);
      while (!Serial) {
        ; 
      }
      lcd.begin(16, 2);
      pinMode(interruptPinStart, INPUT);
      attachInterrupt(digitalPinToInterrupt(interruptPinStart), startTrigger, RISING);
      pinMode(interruptPinFinish, INPUT);
      attachInterrupt(digitalPinToInterrupt(interruptPinFinish), stopTrigger, RISING);
      Serial.print("Initializing SD card...");
      if (!SD.begin(CS)) {
        Serial.println("initialization failed!");
        return;
      }
      Serial.println("initialization done.");
      root = SD.open("/");
      newDirectory(root);
      Serial.println("done!");
      lcd.clear();
      lcd.print(currentFileName);
      tone(txLed1, 38000);
    }
    
    void loop() {
      int millsDiff = millis() - stopTimeMillis;
      if (triggerDone) {
        lockedOut = true;
        Serial.print("Micros Diffrence: ");
        Serial.println(microsDifference);
        Serial.print("Millis Difference: ");
        Serial.println(millisDifference);
        float millDiff = (float) millisDifference;
        float microDiff = (float) microsDifference;
        if (microDiff > 0) {
          velocity = (float) 0.09 / (microDiff/1000000);
          testNo++;
          temp = String(launchNo) + "%" + String(microsDifference) + "%" + String(velocity);
          if (velocity > 10.0) {
            root = SD.open(currentFileName, FILE_WRITE);
            if (root) {
              root.println(temp);
              root.close();
              Serial.println(temp);
              launchNo++;
            } else {
              Serial.println("error opening file, " + currentFileName);
              fileFail = true;
            }
          }
          if (fileFail) {
            lcd.clear();
            lcd.print("File Error");
            lcd.setCursor(0, 1);
            lcd.print("Vel " + String(launchNo) + ": " + String(velocity) + " m/s");
            fileFail = false;
          } else {
            lcd.clear();
            lcd.print("Test Number: " + String(testNo));
            lcd.setCursor(0, 1);
            lcd.print("Vel " + String(launchNo) + ": " + String(velocity) + " m/s");
          }
        } 
        triggerDone = false;
        Serial.println("Test Number: " + String(testNo));
      }
      if (digitalRead(interruptPinStart) == LOW) {
        digitalWrite(statusLed1, HIGH);
      } else {
        digitalWrite(statusLed1, LOW);
      }
      if (digitalRead(interruptPinFinish) == LOW) {
        digitalWrite(statusLed2, HIGH);
      } else {
        digitalWrite(statusLed2, LOW);
      }
    }
    
    void startTrigger() {
      startTimeMicros = micros();
      startTimeMillis = millis();
      volatile int diff1 = startTimeMicros - startTimeMillis;
      volatile int diff2 = startTimeMillis - stopTimeMillis;
      if (diff2 > 200) {
        if (started == false || diff1 > 1000) {
          started = true;
          triggerDone = false;
        }
      }
    }
    
    void stopTrigger() {
      stopTimeMicros = micros();
      stopTimeMillis = millis();
      microsDifference = stopTimeMicros - startTimeMicros;
      millisDifference = stopTimeMillis - startTimeMillis;
      if ((millisDifference > 0  && millisDifference < 800) && started) {
        microsDifference = stopTimeMicros - startTimeMicros;
        millisDifference = stopTimeMillis - startTimeMillis;
        started = false;
        triggerDone = true;
      }
    }
    

0 个答案:

没有答案