【问题标题】:Arduino yun Stops working after a few hoursArduino yun 几个小时后停止工作
【发布时间】:2017-02-24 17:02:25
【问题描述】:

我正在尝试使用 arduino yun 将机器生产的零件数量输出到谷歌电子表格。通过我的设置,我可以暂时将数据输出到电子表格。然而,过了一段时间,云停止了工作。我用来指示代码正在运行的红色 LED 熄灭了,我再也看不到端口列表中的 arduino。 32u4芯片复位导致LED重新亮起,表示代码正在运行,但板子仍然没有出现在端口菜单中。

我已经在我们的车间对其进行了测试,它已经运行了 7-12 个小时,完全没有问题。只有当我们把它带到生产车间时,我们才开始遇到这些问题。有谁知道问题可能是什么?这是代码中最相关的部分:

#include <elapsedMillis.h>
#include <Process.h>
#include <Bridge.h>
#include "TimeLib.h"

// On Arduino:  0 - 1023 maps to 0 - 5 voltsf
#define VOLTAGE_MAX 5.0
#define VOLTAGE_MAXCOUNTS 1023.0

unsigned int buttonCount = 0;
float voltage = 0;
elapsedMillis timeSinceLastCycle = 0;
elapsedMillis transmitData = 0;
int pressFlag = 0;
Process date;
int hours, minutes, seconds;
int lastSecond = -1;
Process sendData;

String printDate() {

  // String currTime = String(hours) + ":" + String(minutes) + ":" + String(seconds);

  if (lastSecond != seconds) { // if a second has passed
    // print the time:
    if (hours <= 9) {
      Console.print("0");  // adjust for 0-9
    }
    Console.print(hours);
    Console.print(":");
    if (minutes <= 9) {
      Console.print("0");  // adjust for 0-9
    }
    Console.print(minutes);
    Console.print(":");
    if (seconds <= 9) {
      Console.print("0");  // adjust for 0-9
    }
    Console.println(seconds);

    // restart the date process:
    if (!date.running()) {
      date.begin("date");
      date.addParameter("+%T");
      date.run();
    }
  }

  //if there's a result from the date process, parse it:
  while (date.available() > 0) {
    // get the result of the date process (should be hh:mm:ss):
    String timeString = date.readString();

    // find the colons:
    int firstColon = timeString.indexOf(":");
    int secondColon = timeString.lastIndexOf(":");

    // get the substrings for hour, minute second:
    String hourString = timeString.substring(0, firstColon);
    String minString = timeString.substring(firstColon + 1, secondColon);
    String secString = timeString.substring(secondColon + 1);


    // convert to ints,saving the previous second:
    hours = hourString.toInt();
    minutes = minString.toInt();
    lastSecond = seconds;          // save to do a time comparison
    seconds = secString.toInt();
    String currTime = hourString + ":" + minString + ":" + String(seconds);
    return currTime;
  }
}

void checkVoltage() {

  int sensorValue = analogRead(A0);
  voltage = sensorValue * (VOLTAGE_MAX / VOLTAGE_MAXCOUNTS);

  Console.println(voltage);
  delay(50);
  if (voltage >= 4.9 && pressFlag == 0) {

    Console.println("Delaying");
    sensorValue = analogRead(A0);
    voltage = sensorValue * (VOLTAGE_MAX / VOLTAGE_MAXCOUNTS);

    if (pressFlag == 0 && voltage >= 4.9) {

      unsigned long int intCycleTime = timeSinceLastCycle;
      timeSinceLastCycle = 0;
      digitalWrite(LED_BUILTIN, LOW);   // turn the LED on (HIGH is the voltage level)

      printDate();
      String pressTime = printDate();

      Console.print("PressTime is ");
      Console.println(pressTime);

      buttonCount++;
      Console.println(buttonCount);

      pressFlag = 1;



      String part1 = "curl -X POST -H \"Content-Type: application/json\" -d '{\"value1\":\"";
      String timeString = pressTime;
      Console.print(timeString + " seconds");
      String part2 = "\",\"value2\":\"";
      String numParts = String(buttonCount);
      String part3 = "\",\"value3\":\"";
      String strCycleTime = String(intCycleTime / 1000); // + " seconds";
      String part4 = "\"}' https://maker.ifttt.com/trigger/arduino2Request/with/key/gL8YmxeaUChOMJvmwpdXp -k";
      //curl -X POST -H "Content-Type: application/json" -d '{"value1":"1","value2":"2","value3":"3"}' https://maker.ifttt.com/trigger/arduino2Request/with/key/gL8YmxeaUChOMJvmwpdXp

      String curlString = part1 + timeString + part2 + numParts + part3 + strCycleTime + part4;

      // The curl string sends data to oue excel spreadhsheet using the IFTTT web service

      sendData.runShellCommandAsynchronously(curlString);

      elapsedMillis breakTimer = 0;
      /*while(sendData.running()){

          if(breakTimer > 5*1000){
            break;
          }
        } */


      Console.print("Data Available: "); // A value of 32 indicates a successful transmission of data, 0 also works if run asynchronously.
      Console.println(sendData.available());

      digitalWrite(LED_BUILTIN, HIGH);   // turn the LED on (HIGH is the voltage level)

    }

  }
  else if (voltage < 2.5) {
    pressFlag = 0;
  }

}

void setup() {

  Bridge.begin();
  Console.begin();
  pinMode(LED_BUILTIN, OUTPUT);
  digitalWrite(LED_BUILTIN, HIGH);   // turn the LED on (HIGH is the voltage level)

  // run an initial date process. Should return:
  // hh:mm:ss :
  if (!date.running()) {
    date.begin("date");
    date.addParameter("+%T");
    date.run();
  }
}

void loop() {

  checkVoltage();

  if ((timeSinceLastCycle > 300000) && (transmitData > 300000)) { // If 5 minutes have elapsed without a part being produced, output that the arduino is transmitting even if not part is available
    sendData.runShellCommand("curl -X POST -H \"Content-Type: application/json\" -d '{\"value1\":\"1\",\"value2\":\"Arduino Transmitting\"}' https://maker.ifttt.com/trigger/transmitData/with/key/gKRo-zSur5rj6rD5rviCaV2RHI5g56Dy0Vc0S_XJ-oO -k");
    transmitData = 0;
  }
}

更新:我在 checkVoltage 函数中添加了一系列打印语句。上面的代码已更新以反映这一点。我发现它在尝试使用 sendData.runShellCommandAsynchronously 时挂起。输出看起来像

1.58
1.54
5.00
Delaying
PressTime is n" -d 
3

尝试运行ShellCommand 时网络连接中断会导致此问题吗?

【问题讨论】:

  • 我可以看到随着时间的推移出错的事情之一是buttonCount 溢出。反正代码是不完整的。
  • 问题是,在溢出成为问题之前,它会失败很长一段时间。此外,我并不关心 buttonCount 的确切值,因为我的数据处理脚本只检查是否有一个数字并自己再次计算条目。这可以防止机器在短时间内断电并且值重置为 0 时出现错误计数。我已更新代码以包含完整代码。
  • 有一些明显的差距,特别是在 printDate 函数中,因为我之前有打印语句。我把它们拿出来希望缩小代码可以解决我的问题,但没有运气
  • 我喜欢这个问题。与生产线相比,您在车间用多少个项目进行了测试?我要检查的第一件事是动态内存,它被String 及其+ 运算符隐式使用。您可以更有效地使用闪存中的单个静态分配的 char[] 缓冲区 + sprintf() + 存储在 PROGMEM 中的单个格式字符串(请参阅:this)。您可以使用存储值限制轻松计算命令的最大长度。
  • printDate() 的签名说它返回一个char *,但是,有一条通过代码的路径不返回任何内容。 (当没有输入while() 时。编译器应该会抱怨。编译时,始终启用所有警告,然后修复这些警告。(对于gcc,至少使用:-Wall -Wextra -pedantic 我也使用:@987654333 @)

标签: c arduino arduino-yun


【解决方案1】:

所以按照 user3629249 的解决方案后,这个问题似乎得到了解决。现在已经有数周的无错误运行时间。 user3629249,如果您想重新发布您的建议作为答案,我会接受。感谢 user3629249 和 Patrick Trentin 的帮助!

我的更新 ProcessDate 函数现在包含:

if(date.available() >0){
  while (date.available() > 0) {
  // get the result of the date process (should be hh:mm:ss):
  String timeString = date.readString();

  // find the colons:
  int firstColon = timeString.indexOf(":");
  int secondColon = timeString.lastIndexOf(":");

  // get the substrings for hour, minute second:
  String hourString = timeString.substring(0, firstColon);
  String minString = timeString.substring(firstColon + 1, secondColon);
  String secString = timeString.substring(secondColon + 1);


  // convert to ints,saving the previous second:
  lastSecond = seconds;          // save to do a time comparison
  lastMinute = minutes;
  lastHour = hours;
  hours = hourString.toInt();
  minutes = minString.toInt();
  seconds = secString.toInt();
  String currTime = hourString + ":" + minString + ":" + String(seconds);
  return currTime;
} 
else{
        String currTime = ""; // If there is no result from the date process, return nothing. Should not happen.
        return currTime;
      }
    }

【讨论】:

    猜你喜欢
    • 2014-09-23
    • 2020-02-27
    • 2018-12-19
    • 1970-01-01
    • 1970-01-01
    • 2012-12-20
    • 2018-02-20
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多