Arduino 崩溃或挂起的 7 种方式及如何防止

news2024/11/25 6:44:29

Arduino 崩溃或挂起的 7 种方式(以及如何防止它发生)

作者:Chris in Arduino

查看原文

为了帮助防止Arduino崩溃或挂起,我进行了一系列实验,以确定Arduino崩溃,挂起,重置,冻结,停止运行代码或做一些奇怪的事情的所有方式。我把这些实验的结果放在一起,作为Arduino如何崩溃或挂起的指南,以及如何防止这种情况发生在你身上。

1. 调用太多函数

调用太多函数(例如在递归循环中)可能会导致 Arduino 崩溃和重置。根据实验,这可能在大约 300 次函数调用后发生。避免调用具有更多局部变量或更大局部变量的函数的调用次数,会减少 Arduino 重置次数。函数的递归循环是达到此函数限制的最可能原因。

// Recursive loop - a function that calls itself
reFunction(int a) {
  if (a > 10000) return; // how to end the recursion
  reFunction(a++); // recursion
}

每个函数调用都会消耗一些 Arduino 的内存;一旦Arduino耗尽了功能内存,它通常会重置(就像按下外部重置按钮一样)并再次运行setup()

在Arduino UNO上对此进行了测试。构建了一个具有 1 个参数和 1 个局部变量的小函数。通过递归中的参数递增,我可以看到在 Arduino 重置之前递归发生了多少次。在这个Arduino模型上,大约360次调用这个函数。

在这里插入图片描述

我用来用完所有地址的代码。Arduino在调用此功能大约360次后崩溃。

具有更多内存的 Arduino 可能会允许更多的函数调用;内存较少的Arduino可能允许较少的函数调用。

为了防止 Arduino 因函数调用过多而崩溃:

  • 如果使用递归函数,请确保结束递归的条件不会运行太长时间
  • 考虑使用 foror while循环,大多数 Arduino 应用程序不需要递归函数
  • 减少函数中局部变量的数量;如果必须使用递归函数,减少局部变量的数量将允许更多的函数调用以适应Arduino内存。

2. 分配过多内存

如果 Arduino 内存不足,它可能会崩溃、卡住或以不可预测的方式运行。Adruino 内存不足的最简单方法是为变量分配太多变量或太多空间,例如使用malloc()函数。也可能使用函数调用耗尽内存(如上所述)。

我做了一个实验,我分配了Arduino(UNO WiFi Rev 2)上的所有内存,看看Arduino的行为。分配所有内存后,任何进一步的内存请求都将不起作用,但函数调用仍然有效。我还发现Arduino上没有内存保护,我可以引用任何我想要的地址。

要防止 Arduino 崩溃耗尽内存,请执行以下操作:

  • 准备程序时在函数中声明变量,对于大多数Arduino项目,可以计算编写代码时所需的变量;如果这些变得太大,编译器会警告您;
  • 避免使用malloc()
  • 如果使用malloc()是不可避免的,则使用程序free(),尽管使用了`free()仍然可能耗尽内存,但可能性较小。

如果您需要在Arduino上存储更多数据,我写了一整本指南,列出了使用Arduino存储数据的一系列不同方法(从几千字节到数百千字节。在这里查看: chipwired.com/arduino-store-data/

3. 陷入无限循环

如果Arduino卡在无限循环中,阻止它执行其他代码,则Arduino可能会显示为挂起。这通常是在代码检查始终以 true 结尾的循环条件时引起的。

// Accidental infinite loop
int a = 0;
while(a == 3){
  a = returnThree(); // a function that always returns 3
}

从技术上讲,Arduino总是运行无限循环void loop()(函数),但是如果Arduino卡在你不想要的循环中,它可能会显得挂起。与PC不同,Arduino通常不能同时执行两个程序。这意味着如果程序卡在循环中,整个Arduino通常会停止执行任何其他任务。

上面提到的递归函数也是一种无限循环。除了函数调用自身的递归之外,函数也可以在循环中相互调用。

// Accidental infinite loop with functions
function x() {
  y();
}

function y() {
  x();
}

要防止无限循环,请执行以下操作:

  • 通读代码流并确保退出无限循环的条件
  • 计划调用函数的条件,尽量避免函数的无限循环
  • 使用回调函数和中断,而不是在循环中等待,直到发生某些事情(请参阅下面的中断处理

如果使用无限循环来等待输入,则可以在等待时运行其他代码。我发现了这个任务调度程序库,它允许Arduino同时执行程序的多个部分。它似乎有点难以设置,但它似乎确实适用于各种Arduino板。

4. 等待函数返回

Arduino 在等待库函数执行时可能会显示为挂起。当Arduino等待函数执行时,它通常无法处理其他代码(除非使用我上面提到的任务调度库之类的东西)。这通常是因为这些函数正在执行此列表中的其他操作,导致Arduino挂起或崩溃(例如,它们陷入无限循环)。

我看到这种情况发生的最常见功能是Serial.available()。我经常看到人们将其用作循环条件,这意味着 Arduino 将卡在循环中,直到串行连接可用;如果没有连接可用,Arduino将不会执行任何其他代码。

void setup(){
  Serial.begin(9600);
  while(!Serial.available()); // wait for the serial connection
}

void loop() {
  // do stuff
}

在上面的示例中,如果没有任何可用内容可从串行连接读取,则Arduino将在启动时挂起。虽然我没有深度研究过Serial.available() ,但我想它是等待数据可用的无限循环。

要降低函数调用崩溃或挂起 Arduino 的可能性,请执行以下操作:

  • 确保您的 Arduino 可以退出无限循环,例如在上面的示例中,为要读取的数据提供串行连接;
  • 考虑一下函数在调用它们时所做的“promise”库函数,函数的这个承诺(例如,串行可用意味着询问串行连接是否有可用)是否意味着它可以进入无限循环。如果不确定,请查看 Arduino 参考或库的文档。

5. 中断处理不正确

如果Arduino不断提供中断而不是执行其主代码,则它可能显示为挂起。如果处理器不断跳转以中断服务例程,它将无法完成其他任务,因此似乎挂起。

中断的典型执行流程为:

  1. setup()函数中将中断处理函数注册到特定事件(当事件发生时,此函数将由处理器执行);
  2. Arduino 执行其loop()
  3. 事件发生,Arduino去执行中断处理功能;
  4. Arduino 返回执行loop()

如果 Arduino 在完成处理中断之前就被中断淹没,它可能永远无法完成处理它们,并且看起来会挂起。我使用此页面作为Arduino中断处理的参考。

为了尽量减少处理中断时 Arduino 挂起的可能性:

  • 尽可能少地处理中断,最大限度地减少中断处理函数中的代码;
  • 在处理中断时考虑修改变量的**atomicity* *,可以用相同的中断处理程序(我知道这很混乱!
  • 与其打开和关闭中断,不如考虑保存处理器寄存器的状态,关闭中断,然后恢复寄存器的状态 - 这可以防止在中断应该关闭时意外打开中断(由另一个处理程序)

6. 电源掉电

如果输入电压降至一定水平以下,Arduino 将崩溃并重置。可以将警告配置为在电压开始下降时开始执行中断处理功能;一旦达到掉电级别,Arduino 就会崩溃并重置。

当电源电压显着且持续下降时,通常会发生掉电,超出 Arduino 的容差水平。这可能是由以下原因引起的:

  • 如果 Arduino 使用电池运行,则电池电量耗尽
  • 电源发出严重噪音或中断
  • 另一个设备突然消耗电流,该设备错误地配置为与 Arduino 共享电源(例如,配置不良的电机)

电压输入电平因 Arduino 型号而异:例如,UNO 系列通常为 7V 至 12V(或 USB 5V),而 MKR 系列为 5V。

大多数Arduino板,当然是Arduino自己生产的板,在板中内置了质量不错的电源管理电路(如稳压器)。我发现,只要您遵守数据手册上的电压要求,并提供足够的电流,就不会有问题。

要避免由于掉电而导致 Arduino 重置,请执行以下操作:

  • 提供稳定的电源,大多数商用电源设备(包括手机充电器)在兼容规格内应能工作;
  • 小心将使用大量电流的电路组件(例如电机)连接到Arduino使用的同一电压源,突然的电流消耗可能会中断Arduino的电源。

在这里插入图片描述

我的UNO WiFi Rev 2由标准USB手机充电器供电*

7. 看门狗定时器配置不正确

如果看门狗计时器已启用并且到达其倒计时期结束时,Arduino 将重置,而代码未清除。如果 Arduino 未能在时间用完之前清除看门狗计时器,则看门狗将重新启动 Arduino。

忘记在代码中清除看门狗计时器,或者不够频繁地清除,可能会导致Arduino崩溃。

查看此处的示例程序,以了解有关如何配置看门狗计时器的更多信息,以便它不会意外崩溃您的 Arduino。

如何知道您的Arduino是否还活着

为了证明 Arduino 仍在正确执行代码,通常使用检测信号例程。Arduino 的心跳是 LED 通过固定模式闪烁,因此可以观察到,如果 LED 未能遵循该模式,则 Arduino 没有正确执行代码。

如果心跳 LED 已编码但未闪烁,则 Arduino 已崩溃或挂起。闪光灯的模式很重要,因为卡在重启循环中的Arduino(例如,由于看门狗定时器)可能仍然闪烁LED,但模式错误。

下面是一个示例检测信号例程:

void loop() {
  do_stuff();
  heartbeat();
  delay(200);
}

void heartbeat(){
  //toggle LED
}

我更喜欢这种切换方法,这样您就可以看到Arduino是否需要很长时间来处理事情。如果检测信号变得不均匀,则意味着 花费的时间过长,或者处理器正在处理大量中断。do_stuff()

引用

在整理本指南时,我使用了一些参考资料。如果您有兴趣阅读有关这些内容的更多信息,请查看下面的列表:

  • 中断
  • 我的 Arduino 核心处理器的数据表(UNO WiFi Rev 2)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/86665.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

5.大型电商项目之创建前端展示模板并调用

1. templates前端模板的使用 1.1 templates前端模板的创建 首先,我们页面很多地方是相似的,这里就创建一个基础模板,不同的地方,对模板内容的block进行修改即可;对于相同的地方,我们就使用include包含即可…

B. Hossam and Friends #837 div2

Problem - B - Codeforces 题意就是给你m个数对,这两个人不是好朋友,其他的所有人都是好朋友,问1~n里面有多少个区间里面所有数都是好朋友 分析: 这题我分析的没错,但是在计算区间的时候,想的复杂了,用模…

JS中,a标签里的javascript:;和 javascript:void(0)还有##

目录 1. javascript:;【常用】点击链接之后不会刷新页面,不会跳转链接,也不会传递参数 2. javascript:void(0) 【少用】点击链接后不会刷新页面,不会跳转链接,也不会传递参数 3. a标签中的# 点击链接后会刷新页面…

Spring Batch批处理-作业Job简介

引言 书接上篇Spring Batch 批处理入门案例解析,上篇带小伙伴们写了一个Spring Batch 入门案例解析,本篇就开始批处理正文啦,今天先对作业Job做个全面了解。 作业介绍 目前很多项目都流程的概念,比如web应用,集成应…

Java基础03_数据类型

数据类型 强类型语言 要求变量的使用要严格符合规定,所有的变量必须先定义后使用;安全性高但是速度低; 弱类型语言 例如:‘12’ 3 123 或者 ‘12’ 3 ‘123’ 在强类型语言中是有明显的区别的。而在弱类型语言中是不区分的…

算符优先分析器的构造

一、实验目的 (1)理解自底向上的语法分析的基本思想。 (2)理解算符优先文法的概念。 (4)掌握算符优先分析器的工作原理和工作流程。 (3)掌握算符分析表和优先函数的构造。 二、实验…

函数式接口

Lambda表达式的本质:作为函数式接口的实例 如果一个接口中,只声明一个抽象方法,则此接口就称为函数式接口 FunctionalInnterface public interface MyInterface{void method1(); }要想用Lambda表达式就一定要在函数式接口的条件下使用 相当于…

微信小程序直播状态接口如何获取

现如今,小程序直播非常的红火,越来越多的商家开通了微信小程序直播,但是在直播的过程中,偶尔会出现一些小问题,如禁播,异常状态等等,下面小编就来介绍一下微信小程序直播状态接口如何获取。 一、…

echarts5.4立体柱状图

资源下载&#xff1a;https://www.jsdelivr.com/package/npm/echarts 效果图&#xff1a; 借鉴资源&#xff1a;echarts 如何绘制三维 3D 立体柱状图 - 简书 代码示例&#xff1a; <!DOCTYPE html> <head><meta charset"utf-8"><title>ECh…

基于51单片机的智能小车系统设计

原理图&#xff1a; 程序运行图&#xff1a; 部分程序&#xff1a; /******************************************************************************* * 文件名称&#xff1a;main.c * 说明&#xff1a;本文件为小车控制的主函数 * 功能&…

分布式websocket探索

单体式架构 根据基于golang的gin框架开发的web项目所展开 如果一个Web项目采用单体式架构且配备了websocket通讯的功能&#xff0c;那么在单个实例中是能够正常运行的 在我的项目中&#xff0c;用户可以通过websocket来进行实时通讯和实时消息通知&#xff0c;同时如果在web业务…

AcrelEMS-IDC数据中心综合能效管理系统解决方案-Susie 周

1、概述 安科瑞电气紧跟数据中心发展形式&#xff0c;推出AcrelEMS-IDC数据中心综合能效管理解决方案&#xff0c;包含有电力监控、动环监控、消防监控、能耗统计分析、智能照明控制以及新能源监测几个子系统。集成了变配电监测、电源备自投、电气接点测温、智能照明控制、电能…

yearning搭建及使用

yearning搭建及使用 数据库审计管理&#xff0c;是数据安全规范中不可或缺的一环&#xff0c;通过审计管理我们能够把控、追溯sql执行情况。yearning作为一款开源的数据库审计软件&#xff0c;是我们开发运维工作中经常打交道的一个“伙伴”。 yearning提供的核心功能就是sql…

mysql 自增字段、属性

mysql自增属性 参考文章 https://www.php.cn/mysql-tutorials-489209.html https://blog.csdn.net/qq_41045806/article/details/108310772 在Mysql中&#xff0c;可以为某一属性设置自增属性&#xff0c;可以很好地为我们解决属性值重复的问题。 在mysql中&#xff0c;使用au…

DevExpress Universal全面的软件开发包

DevExpress Universal全面的软件开发包 DevExpress Universal帮助您使用所有DevExpress单平台控件等为Windows、Web、移动和平板电脑构建应用程序。它包括桌面控件(WinForms、WPF、UWP和桌面报告)、Web控件(ASP.NET、ASP.NET MVC和Core、Bootstrap Web Forms、JavaScript-jQuer…

第十章用Python获取sqlite、MySQL、Excel、csv、json中的数据

这里写目录标题项目背景获取sqlite3中的数据sqlite3库获取sqlite数据pandas库获取sqlite数据获取MySQL中的数据pymsql库获取MySQL数据pandas库获取mysql数据获取Excel中的数据xlrd库获取Excel数据pandas库获取Excel数据获取csv中的数据csv库读取csv数据pandas读取csv数据获取js…

Docker02(数据卷)

目录 一、宿主机与容器之间的文件拷贝 二、数据卷 三、数据卷容器 四、Dockerfile Dockerfile简介 自定义centos&#xff0c;具备vim及ifconfig作用 自定义tomcat8 一、宿主机与容器之间的文件拷贝 在生产环境中使用 Docker &#xff0c;往往需要对数据进行持久化&#…

Spring Cloud微服务治理框架深度解析

在学习一个技术之前&#xff0c;首先我们要了解它是做什么的&#xff0c;我们为什么要用它。不然看再多资料都理解不了&#xff0c;因此我们先来讲解下Spring Cloud Spring Cloud是一套微服务治理框架&#xff0c;几乎考虑到了微服务治理的方方面面。那么接下来具体说下 Spring…

WebRTC客户端主要流程分析

1.通信过程 因为WebRTC规范里没有包含信令协议&#xff0c;所以像OWT、mediasoup等支持WebRTC的开源项目&#xff0c;其通信两端建立连接的过程中的信令逻辑各不相同。但是&#xff0c;总体上来说&#xff0c;其通信过程必然会包括以下过程。 发起端创建本地的PeerConnection&…

基于微信小程序的校友录系统-计算机毕业设计

项目介绍 本系统采用微信开发者开发、结合后台java语言以及Mysql数据库等技术。系统主要分为管理员和用户、校友三部分&#xff0c;管理员服务端&#xff1a;首页、个人中心、用户管理、校友管理、校友风采管理、校友视频管理、视频分类管理、班级信息管理、留言板管理、论坛交…