Как я могу провести модульное тестирование кода Arduino?

Я хотел бы иметь возможность тестировать свой код Arduino. В идеале я мог бы запускать любые тесты без необходимости загружать код в Arduino. Какие инструменты или библиотеки могут мне в этом помочь?

В разработке находится эмулятор Arduino, который может быть полезен, но пока не кажется быть готовым к использованию.

AVR Studio от Atmel содержит симулятор микросхемы, который может оказаться полезным, но я не понимаю, как бы я использовал его в сочетании с Arduino IDE.


person Matthew Murdoch    schedule 23.04.2009    source источник
comment
Есть еще одна ветка по этому вопросу от 2011 года на arduino.cc/forum/ index.php? action = printpage; topic = 54356.0   -  person Jakob    schedule 08.01.2012
comment
Спасибо @Jakob. Симулятор Arduino, упомянутый в этом потоке (с другими потенциально полезными ссылками внизу страницы): arduino.com.au/Simulator-for-Arduino.html   -  person Matthew Murdoch    schedule 09.01.2012
comment
К сожалению, это только для Windows, я бы хотел увидеть способ просто скомпилировать и запустить код Arduino из командной строки без каких-либо закрытых исходных кодов или зависимостей от оборудования.   -  person Jakob    schedule 12.01.2012
comment
Небольшое обновление, 5 лет спустя: Simavr все еще очень активен и значительно улучшился с момента вопроса спросили, поэтому я подумал, что он заслуживает того, чтобы его подтолкнули ближе к вершине. И это может быть правильный инструмент для регрессионного тестирования, тестирования на основе сценариев и почему бы не также для модульного тестирования. Таким образом, код, который вы тестируете, будет таким же, что и код на целевом оборудовании.   -  person zmo    schedule 29.05.2015
comment
Для важных проектов подумайте о тестере оборудования; другой микроконтроллер, который не может измерять время и проверять реакцию кнопок / переключателей, время загрузки, температуру, использование v / ma, странные перестановки опций и т. д. Да, это больше оборудования для создания, но он может добавить уровень безопасности при создании изменений. многие профессиональные устройства используют jtag et al.   -  person dandavis    schedule 15.11.2016
comment
Теперь для этой цели доступно действие GitHub, автором которого является я.   -  person Ian    schedule 07.01.2021


Ответы (20)


Не запускайте модульные тесты на устройстве или эмуляторе Arduino

Дело против микроконтроллеров Device / Emulator / Sim-based tests

О том, что означает unit test, идет много дискуссий, и я не пытаюсь здесь спорить об этом. Этот пост не советует вам избегать всех практических испытаний на вашем конечном целевом оборудовании. Я пытаюсь сделать акцент на оптимизации вашего цикла обратной связи при разработке, исключив ваше целевое оборудование из ваших самых рутинных и частых тестов. Предполагается, что тестируемые блоки намного меньше всего проекта.

Цель модульного тестирования - проверить качество вашего собственного кода. Модульные тесты, как правило, никогда не должны проверять функциональность факторов, находящихся вне вашего контроля.

Подумайте об этом так: даже если бы вам пришлось протестировать функциональность библиотеки Arduino, оборудования микроконтроллера или эмулятора, было бы абсолютно невозможно, чтобы такие результаты тестирования могли сказать вам что-либо о качестве вашего Наша работа. Следовательно, гораздо более ценно и эффективно писать модульные тесты, которые не запускаются на целевом устройстве (или эмуляторе).

Частое тестирование на вашем целевом оборудовании имеет мучительно медленный цикл:

  1. Настройте свой код
  2. Скомпилировать и загрузить на устройство Arduino
  3. Наблюдайте за поведением и угадайте, выполняет ли ваш код то, что вы ожидаете.
  4. Повторить

Шаг 3 особенно неприятен, если вы ожидаете получать диагностические сообщения через последовательный порт, но сам ваш проект должен использовать единственный последовательный порт вашего Arduino. Если вы думали, что библиотека SoftwareSerial может помочь, вы должны знать, что это может нарушить любую функциональность, которая требует точного времени, например, одновременное генерирование других сигналов. Эта проблема случилась со мной.

Опять же, если вы должны были протестировать свой скетч с помощью эмулятора, и ваши критичные ко времени процедуры работали безупречно до тех пор, пока вы не загрузили его на настоящую Arduino, то единственный урок, который вы усвоите, - это то, что эмулятор ошибочен - и зная это до сих пор. не раскрывает ничего о качестве вашей собственной работы.

Если глупо тестировать на устройстве или эмуляторе, что следует делать?

Вы, вероятно, используете компьютер для работы над своим проектом Arduino. Этот компьютер на порядки быстрее микроконтроллера. Напишите тесты, которые нужно собрать и запустить на вашем компьютере.

Помните, что поведение библиотеки и микроконтроллера Arduino следует считать правильным или, по крайней мере, постоянно неправильным.

Если результаты ваших тестов противоречат вашим ожиданиям, то, скорее всего, у вас есть недостаток в тестируемом коде. Если результат вашего теста соответствует вашим ожиданиям, но программа ведет себя некорректно, когда вы загружаете его в Arduino, значит, вы знаете, что ваши тесты основывались на неверных предположениях и, вероятно, у вас есть некорректный тест. В любом случае вам будет дано реальное представление о том, какими должны быть ваши следующие изменения кода. Качество вашего отзыва повышено с "что-то не работает" на "этот конкретный код не работает".

Как создавать и запускать тесты на вашем ПК

Первое, что вам нужно сделать, это определить цели тестирования. Подумайте, какие части вашего собственного кода вы хотите протестировать, а затем убедитесь, что ваша программа построена таким образом, чтобы вы могли изолировать отдельные части для тестирования.

Если части, которые вы хотите протестировать, вызывают какие-либо функции Arduino, вам нужно будет предоставить имитацию замены в вашей тестовой программе. Это намного меньше работы, чем кажется. Ваши макеты не должны ничего делать, кроме как обеспечивать предсказуемые ввод и вывод для ваших тестов.

Любой ваш собственный код, который вы собираетесь протестировать, должен существовать в исходных файлах, кроме скетча .pde. Не волнуйтесь, ваш скетч все равно будет компилироваться даже с некоторым исходным кодом за пределами скетча. Когда вы действительно приступите к делу, в файле скетча должно быть определено немного больше, чем обычная точка входа вашей программы.

Осталось только написать настоящие тесты, а затем скомпилировать их с помощью вашего любимого компилятора C ++! Вероятно, лучше всего это проиллюстрировать на примере из реальной жизни.

Реальный рабочий пример

В одном из моих любимых проектов, найденных здесь, есть несколько простых тестов, которые выполняются на ПК. Для этого ответа я просто расскажу, как я смоделировал некоторые функции библиотеки Arduino, и тесты, которые я написал для тестирования этих макетов. Это не противоречит тому, что я сказал ранее о том, что не тестировал чужой код, потому что это я написал макеты. Я хотел быть уверенным, что мои макеты верны.

Источник mock_arduino.cpp, который содержит код, который дублирует некоторые функции поддержки, предоставляемые библиотекой Arduino:

#include <sys/timeb.h>
#include "mock_arduino.h"

timeb t_start;
unsigned long millis() {
  timeb t_now;
  ftime(&t_now);
  return (t_now.time  - t_start.time) * 1000 + (t_now.millitm - t_start.millitm);
}

void delay( unsigned long ms ) {
  unsigned long start = millis();
  while(millis() - start < ms){}
}

void initialize_mock_arduino() {
  ftime(&t_start);
}

Я использую следующий макет для создания читаемого вывода, когда мой код записывает двоичные данные на аппаратное последовательное устройство.

fake_serial.h

#include <iostream>

class FakeSerial {
public:
  void begin(unsigned long);
  void end();
  size_t write(const unsigned char*, size_t);
};

extern FakeSerial Serial;

fake_serial.cpp

#include <cstring>
#include <iostream>
#include <iomanip>

#include "fake_serial.h"

void FakeSerial::begin(unsigned long speed) {
  return;
}

void FakeSerial::end() {
  return;
}

size_t FakeSerial::write( const unsigned char buf[], size_t size ) {
  using namespace std;
  ios_base::fmtflags oldFlags = cout.flags();
  streamsize oldPrec = cout.precision();
  char oldFill = cout.fill();

  cout << "Serial::write: ";
  cout << internal << setfill('0');

  for( unsigned int i = 0; i < size; i++ ){
    cout << setw(2) << hex << (unsigned int)buf[i] << " ";
  }
  cout << endl;

  cout.flags(oldFlags);
  cout.precision(oldPrec);
  cout.fill(oldFill);

  return size;
}

FakeSerial Serial;

и, наконец, собственно тестовая программа:

#include "mock_arduino.h"

using namespace std;

void millis_test() {
  unsigned long start = millis();
  cout << "millis() test start: " << start << endl;
  while( millis() - start < 10000 ) {
    cout << millis() << endl;
    sleep(1);
  }
  unsigned long end = millis();
  cout << "End of test - duration: " << end - start << "ms" << endl;
}

void delay_test() {
  unsigned long start = millis();
  cout << "delay() test start: " << start << endl;
  while( millis() - start < 10000 ) {
    cout << millis() << endl;
    delay(250);
  }
  unsigned long end = millis();
  cout << "End of test - duration: " << end - start << "ms" << endl;
}

void run_tests() {
  millis_test();
  delay_test();
}

int main(int argc, char **argv){
  initialize_mock_arduino();
  run_tests();
}

Этот пост достаточно длинный, поэтому, пожалуйста, обратитесь к моему проекту на GitHub, чтобы увидеть еще несколько тестовых примеров в действии. Я храню свои незавершенные работы в ветвях, отличных от master, поэтому проверяйте и эти ветки на предмет дополнительных тестов.

Я решил написать свои собственные облегченные процедуры тестирования, но также доступны более надежные среды модульного тестирования, такие как CppUnit.

person Iron Savior    schedule 11.07.2012
comment
Это отличный ответ! Спасибо! - person Jonathan Arkell; 04.07.2014
comment
Это можно было бы прочитать не тестировать ни в одной системе. Любое реальное устройство (встроенное или нет) не является чистым, поэтому мы должны тестировать только символьное / математическое доказательство? Модульные тесты тестового кода в контексте выбора (язык, компилятор, флаги, библиотеки), все из которых влияют на правильность. Посмотрите, как я разработал и протестировал правильный код, но не для компилятора и платформы, которые мы выбрали для проекта. летает с вашим менеджером проекта, прежде чем станет слишком консервативным при тестировании. ArduinoUnit поддерживает модульное тестирование на Arduinos, но его нужно где-то запускать или моделировать. - person Warren MacEvoy; 26.05.2015
comment
@WarrenMacEvoy Опять же, я думаю, вы последовали моему совету и превратили его в то, чем он не является. Вы обязательно должны протестировать свой код в его реальной среде НЕКОТОРЫЕ ТОЧКИ. Я считаю, что вы не должны делать это каждый день и, конечно же, не должны называть это модульным тестом. - person Iron Savior; 27.07.2015
comment
Можете ли вы запускать вещи «изначально», гарантируя, что типы имеют тот же размер, что и на вашем Arduino? Это может маскировать проблемы переполнения / недостаточного заполнения, которые могут возникнуть на оборудовании Arduino, если в вашей тестовой среде по умолчанию используются большие типы? - person NeilenMarais; 03.05.2016
comment
@NeilenMarais, это тоже зависимость, которую можно высмеять. Вы можете закончить использование специфичных для компилятора функций, чтобы гарантировать определенное поведение при тестировании, но это должно быть ограничено кодом вашей тестовой установки. - person Iron Savior; 03.05.2016
comment
Первая часть ответа немного странная. Так как тест на устройстве может быть не таким эффективным, как на других платформах, не делайте этого. Модульный тест, запущенный на устройстве, должен работать без проблем, особенно если тестовый вывод идет на другой последовательный порт. - person toasted_flakes; 21.05.2016
comment
@toasted_flakes Я не уверен, откуда у вас эта цитата, но я не сказал этого. Модульные тесты, запущенные на устройстве, имеют множество проблем - очень медленный цикл обратной связи, у вас может не быть никаких последовательных портов или каких-либо других средств ввода-вывода для вашего целевого устройства, и они имеют очень ограниченную емкость, которая может повлиять на объем ваш набор тестов. - person Iron Savior; 25.05.2016
comment
@IronSavior Это было впечатление, которое у меня сложилось после прочтения первой части вашего ответа, но ваш комментарий проясняет это. Спасибо! - person toasted_flakes; 25.05.2016
comment
Не согласен, категорически! Во встроенном коде может возникнуть множество проблем, которые можно найти только на реальном оборудовании. Аргументы в пользу скорости верны. Но ответ не должен заключаться в том, что не тестируйте на реальном оборудовании. Ответ должен заключаться в том, чтобы писать тесты, которые работают на реальном оборудовании, но также не требуют для работы реального оборудования. Запускайте их на ПК по ходу работы с интервалом в несколько секунд и на устройстве изредка / почти всегда. Любой, кто работает над критически важными системами, в которых задействованы деньги, безопасность или даже жизнь и последует совету в этом ответе, подвергнет свой проект серьезным рискам. - person Christian Hujer; 14.01.2018
comment
@ChristianHujer Вы, безусловно, должны тестировать на реальном оборудовании - никто не говорит, что вы никогда не должны тестировать на целевом оборудовании. Моя статья посвящена ужесточению вашего ежедневного цикла обратной связи при разработке с помощью модульного тестирования на вашей машине разработки. Таким образом, ваши накладные расходы на тестирование сводятся к минимуму, потому что вы будете тестировать целевое оборудование только тогда, когда это необходимо. - person Iron Savior; 15.01.2018
comment
Отличный ответ, имхо. Аналогичный подход можно применить и к тестированию для iPhone. Вместо того, чтобы запускать тесты на реальном устройстве или даже на симуляторе, создавайте тесты, которые просто запускаются на машине разработки, вообще не требуя среды iOS. Тогда они становятся чрезвычайно быстрыми для тестирования. Они не позволяют легко все протестировать, но предоставляют обширный охват. - person Benjohn; 17.01.2018
comment
… Пытаюсь применить это на практике! :-) Вы упоминаете pde файлы и скетчи. Я быстро find . -n "*.pde" сделал в папке с набросками, и ничего не обнаружил. Я использую инструмент разработчика Arduino. Можете ли вы посоветовать, как структурировать проект, чтобы разбивать файлы на части, чтобы их было легко протестировать? Ссылки хватило бы. Спасибо! - person Benjohn; 17.01.2018
comment
Исходные файлы скетчей @Benjohn Arduino раньше имели расширение pde, даже если они C ++. arduino.cc/en/Guide/Environment#toc1 - person Iron Savior; 19.01.2018
comment
Хорошо спасибо. Я разбил большую часть своего эскиза в библиотеку, поэтому я надеюсь, что смогу просто поместить файл make в папку библиотеки и запускать тесты из него в командной строке. - person Benjohn; 19.01.2018
comment
Для всех, кто выбрал этот подход, он отлично сработал для меня и помог мне удалить кучу ошибок в моих графических алгоритмах Arduino (ну, алгоритмы свечения светодиодов, если честно). Я использовал структуру модульного тестирования catch и хотел бы призвать всех, кто попробует это проверить, из. Его невероятно легко запустить и запустить, и это делает написание тестов тривиальным и понятным. Определенно стоит попробовать. - person Benjohn; 23.01.2018
comment
нет абсолютно никакого смысла в написании модульных тестов, запускаемых на устройстве, что является близорукой перспективой. Ценность заключается в информации, которую он предоставляет пользователю. Только пользователь решает это сам. Вы не можете утверждать это как факт. Информация, которую вы получаете с его помощью, заключается в том, что вы знаете, как работает определенный код на устройстве. Например, воссоздание задач с помощью FreeRTOS вызовет фрагментацию памяти и вызовет проблемы. Вы не испытаете этого в Windows. Вы должны понимать слова «модульные тесты» за то, что они означают, а не за то, как вы их применяете. Они тестируют единицу, вот и все. - person Mike de Klerk; 19.11.2018
comment
@MikedeKlerk Вы описываете интеграционные тесты, а не модульные тесты. Возможно, абсолютно нет смысла переоценивать случай в целом, но я имею в виду это в контексте быстрого модульного тестирования. - person Iron Savior; 19.11.2018
comment
@IronSavior Мне любопытно получить ваши комментарии к моей библиотеке arduino_ci (упомянутой в мой ответ), который, по-видимому, соответствует вашим критериям: (1) работает на ПК, а не на устройстве (2) имеет широкие возможности имитации для встроенных функции и (3) могут работать как часть службы CI, такой как Travis или Appveyor. - person Ian; 22.02.2019
comment
Если вы не убедите свой компилятор использовать модель данных IP16 на ПК, вы рискуете получить некоторые сюрпризы. Попробуйте это: unsigned short x = 42; Serial.println(-x>0 ? "This is Arduino" : "This is PC");. - person Edgar Bonet; 30.05.2020
comment
@EdgarBonet Верно. Невозможно полностью воспроизвести все производственные условия в тестовых средах. Вы все равно должны помнить о таких краях. - person Iron Savior; 31.05.2020
comment
@IronSavior, ссылка еще действительна? Я не могу найти образец кода на GitHub. - person James Foster; 07.09.2020

Ввиду отсутствия каких-либо ранее существовавших сред модульного тестирования для Arduino я создал ArduinoUnit. Вот простой скетч Arduino, демонстрирующий его использование:

#include <ArduinoUnit.h>

// Create test suite
TestSuite suite;

void setup() {
    Serial.begin(9600);    
}

// Create a test called 'addition' in the test suite
test(addition) {
    assertEquals(3, 1 + 2);
}

void loop() {
    // Run test suite, printing results to the serial port
    suite.run();
}
person Matthew Murdoch    schedule 26.04.2009
comment
Кажется, что тесты запускаются только на Arduino, поэтому вы не можете выполнять их автоматически на своей машине разработки. Основная идея модульных тестов состоит в том, чтобы запускать их автоматически, поэтому текущий дизайн больше похож на инструмент отладки, а не на настоящую среду модульного тестирования. - person Jakob; 08.01.2012
comment
Ты прав. Чтобы иметь возможность запускать их на ПК, кроме того, потребуется эмулятор Arduino или AVR. В библиотеках Arduino (на данный момент) нет реального уровня аппаратной абстракции, а эмуляторы AVR, когда я смотрел, все еще находились в разработке. Если сейчас что-то сдвинулось с мертвой точки, то в принципе это можно было бы сделать. - person Matthew Murdoch; 09.01.2012
comment
@MatthewMurdoch Я думаю, это отличная идея. Я знаю, что меня заинтересует нечто подобное, когда выйдет подходящий эмулятор AVR. - person fulvio; 09.02.2012
comment
@MatthewMurdoch Какой смысл запускать модульные тесты на микроконтроллере? Вы ведь должны тестировать свой собственный код, а не саму Arduino. - person Iron Savior; 30.05.2013
comment
@IronSavior По той же причине, по которой вы запускаете модульные тесты для настольного приложения на настольном компьютере. Они подтверждают, что написанный вами код правильно работает в предполагаемой среде. - person Matthew Murdoch; 31.05.2013
comment
@MatthewMurdoch Боюсь, вы ошибаетесь. По определению, модульные тесты никогда не запускаются в целевой среде. Фактически, сама идея модульного тестирования состоит в том, чтобы полностью исключить целевую среду из тестирования. Они всегда выполняются в лабораторной среде, которая имитирует все действия, внешние по отношению к тестируемому модулю, чтобы гарантировать, что успех или неудача теста отражаются ТОЛЬКО на тестируемом модуле. Это одна из основных причин, по которой люди используют концепцию инверсии управления в сложных проектах. - person Iron Savior; 31.05.2013
comment
То, что вы предлагаете, можно назвать тестированием, но вы не можете называть это модульным тестированием. - person Iron Savior; 31.05.2013
comment
Интересная идея @IronSavior Savior. Вы предлагаете, чтобы классы C ++ и их тесты были скомпилированы в соответствии с архитектурой, на которой работает Arduino IDE, и протестированы там? - person marcv81; 01.10.2014
comment
@ marcv81 Нет, вы бы использовали компилятор для своей системы разработки. - person Iron Savior; 01.10.2014
comment
@IronSavior Я думаю, это то, что я имел в виду. Итак, если вы запускаете модульные тесты в среде разработки, а не в целевой, как насчет архитектурно-зависимого кода? Например, что, если тест полагается на размер целочисленных типов, который не указан в C ++, но может быть установлен для целевой среды и может варьироваться в зависимости от среды разработки (потому что вы никогда не знаете, кто может форкнуть ваш проект)? - person marcv81; 01.10.2014
comment
@ marcv81 Области, в которых существуют такие проблемы с переносимостью, скорее всего, не станут предметом модульного тестирования. Помните, что модульные тесты должны проверять только ВАШ код, поэтому ограничьте их объем соответствующим образом. Учитывая огромную разницу в аппаратном обеспечении, о которой мы здесь говорим, я могу согласиться с тем, что некоторые такие обстоятельства могут быть неизбежны. В таких случаях инженер должен сохранять бдительность и принимать меры по смягчению последствий. Это может означать изменение вашего дизайна для улучшения тестируемости или даже что-то столь же простое, как просто документирование соответствующих фактов. - person Iron Savior; 01.10.2014
comment
@Iron Savior модульный тест проверяет ваш код, но ваш код где-то работает. Если этот контекст является контекстом Arduino или имитирует его; тогда ArdunoUnit поможет вам написать модульные тесты. Если вы посмотрите на проект ArduinoUnit, мета-тестирование фреймворка автоматически загружается, запускается и проверяет результаты теста на кроссплатформенной цели. Как и в случае с другими кроссплатформенными целями. Ваша точка зрения является оправданием того, что вы не тестируете код во встроенной среде, где правильность имеет такое же, если не часто, большее значение, чем в других контекстах. - person Warren MacEvoy; 26.05.2015
comment
@WarrenMacEvoy Вы объединяете модульные тесты с другими видами тестирования. - person Iron Savior; 26.05.2015
comment
@Iron Savior - я подчеркиваю, что настоящий чистейший модульный тест почти бесполезен. Ваш мир просто всегда включает (например) ALU. Я использовал компиляторы C, где short означало 1 бит. Какая часть вашего кода будет там работать? Весь код написан в контексте предположений. Если не считать символических доказательств правильности (чистейший модульный тест), все ваши тесты выполнялись с набором предположений (даже в символическом доказательстве на самом деле будут предположения). И вы считаете их юнит-тестами. - person Warren MacEvoy; 17.07.2015
comment
@WarrenMacEvoy Вы находитесь во власти компилятора только в том случае, если позволяете себе это делать. Условия, специфичные для Arch, также являются допустимыми объектами автоматического тестирования. Не похоже, что вы ничего не можете поделать с условиями, зависящими от архитектуры. Если бы это было так, тогда не было бы много кросс-архитектурного кода, написанного на C (и он есть). Я думаю, вы все еще не понимаете, о чем я говорю. Я не говорю о TDD - я говорю об автоматическом тестировании и ни о чем другом. - person Iron Savior; 27.07.2015
comment
@IronSavior Я опирался на работу, которую проделал Мэтью Мердок, и сделал возможным запускать модульные тесты на ПК, а не в целевой среде (Arduino). Мой ответ здесь, и я буду признателен за ваши мысли. - person Ian; 08.03.2018
comment
Есть способ использовать ArduinoUnit с помощью Emulare, эмулятора Arduino. Следовательно, нам не нужно развертывать его на реальном устройстве. И это очень хорошо работает с Emulare. Спасибо Мэтью за создание ArduinoUnit. - person newbie programmerz; 29.03.2018

Я добился значительного успеха в модульном тестировании моего кода PIC, абстрагируя доступ к оборудованию и имитируя его в своих тестах.

Например, я абстрагирую ПОРТУ с помощью

#define SetPortA(v) {PORTA = v;}

Тогда SetPortA можно будет легко смоделировать без добавления служебного кода в PIC-версию.

После того, как аппаратная абстракция была протестирована некоторое время, я вскоре обнаружил, что обычно код переходит с тестовой установки на PIC и работает с первого раза.

Обновление:

Я использую шов #include для кода модуля, # включение кода модуля в файл C ++ для тестовой установки и файл C для целевого кода.

В качестве примера я хочу мультиплексировать четыре 7-сегментных дисплея, один порт управляет сегментами, а второй выбирает дисплей. Код дисплея взаимодействует с дисплеями через SetSegmentData(char) и SetDisplay(char). Я могу поиздеваться над ними на своем тестовом стенде C ++ и проверить, получаю ли я ожидаемые данные. Для цели я использую #define, чтобы получить прямое назначение без накладных расходов на вызов функции.

#define SetSegmentData(x) {PORTA = x;}
person David Sykes    schedule 23.04.2009
comment
Я в принципе вижу, как можно использовать «шов» препроцессора для модульного тестирования. Однако я не уверен, как я могу это сделать, не имея эмулятора для запуска тестов или компилятора, совместимого с avr-gcc, который выводит (в моем случае) двоичные файлы Windows ... - person Matthew Murdoch; 24.04.2009
comment
Спасибо за обновления. Вы выполняете модульные тесты на PIC или на своем ПК? - person Matthew Murdoch; 24.04.2009
comment
Модульные тесты запускаются на Mac с использованием Xcode. Чтобы запустить их на Pic, вероятно, потребуется какой-то эмулятор. Абстрагирование от него, чтобы он работал на Mac, значительно упрощает переключение процессоров. - person David Sykes; 24.04.2009
comment
В среде Arduino используется компилятор avr-gcc, который имеет некоторые особенности, которые означают, что компиляция с помощью gcc (или другого компилятора C ++) и запуск на ПК может не означать, что код также будет компилироваться на avr-gcc. - person Matthew Murdoch; 01.09.2009
comment
О какой разнице ты говоришь? Это вещи, с которыми нельзя справиться с помощью каких-то директив препроцессора? - person Joseph Lisee; 15.03.2010
comment
Дэвид, спасибо, что поделился, это именно то, что я искал. Можете ли вы поделиться репозиторием с образцом примера, показывающим этот подход к тестированию, возможно, один rhar модульного теста тестирует функцию в файле c, которая зависит от API-интерфейсов устройства. - person Glenn Block; 04.12.2016
comment
@GlennBlock Извини, Гленн, прошло какое-то время с тех пор, как этот код был в рабочем состоянии - person David Sykes; 05.12.2016

Кажется, что emulino отлично справится с этой задачей.

Emulino - это эмулятор платформы Arduino от Грега Хьюгилла. (Источник)

репозиторий GitHub

person Gonzo    schedule 20.11.2009

simavr - это симулятор AVR, использующий avr-gcc.

Он уже поддерживает несколько микроконтроллеров ATTiny и ATMega, и, по словам автора, легко добавить еще несколько.

В примерах находится simduino, эмулятор Arduino. Он поддерживает запуск загрузчика Arduino и может быть запрограммирован с помощью avrdude через Socat (модифицированный Netcat).

person Gonzo    schedule 01.02.2010

Вы можете выполнить модульное тестирование на Python с моим проектом PySimAVR. Arscons используется для построения, а simavr - для моделирования.

Пример:

from pysimavr.sim import ArduinoSim    
def test_atmega88():
    mcu = 'atmega88'
    snippet = 'Serial.print("hello");'

    output = ArduinoSim(snippet=snippet, mcu=mcu, timespan=0.01).get_serial()
    assert output == 'hello'

Начать тест:

$ nosetests pysimavr/examples/test_example.py
pysimavr.examples.test_example.test_atmega88 ... ok
person ponty    schedule 24.10.2011

Я не знаю ни одной платформы, которая может тестировать код Arduino.

Однако существует платформа Fritzing, которую вы можете использовать для моделирования оборудования и позже. экспортировать схемы печатных плат и прочее.

Стоит проверить.

person Yuval Adam    schedule 23.04.2009

Мы используем платы Arduino для сбора данных в большом научном эксперименте. Впоследствии нам придется поддерживать несколько плат Arduino с разными реализациями. Я написал утилиты Python для динамической загрузки шестнадцатеричных изображений Arduino во время модульного тестирования. Код, указанный по ссылке ниже, поддерживает Windows и Mac OS X через файл конфигурации. Чтобы узнать, где ваши шестнадцатеричные изображения размещаются в среде Arduino IDE, нажмите клавишу Shift, прежде чем нажимать кнопку сборки (воспроизведения). Нажмите клавишу Shift во время загрузки, чтобы узнать, где находится ваш avrdude (утилита загрузки из командной строки) в вашей системе / версии Arduino. В качестве альтернативы вы можете просмотреть включенные файлы конфигурации и использовать место установки (в настоящее время на Arduino 0020).

http://github.com/toddstavish/Python-Arduino-Unit-Testing

person toddstavish    schedule 04.10.2010
comment
+1 Отличный материал! У вас есть какая-либо информация о том, как вы проводили модульное тестирование после загрузки изображений? - person Matthew Murdoch; 11.10.2010
comment
Мы использовали носовые тесты для запуска наших модульных тестов на стороне Python. Настройка для каждого теста загружает правильное шестнадцатеричное изображение для этого теста. Мы начинаем с малого, а затем переходим к более всестороннему тестированию. Убедитесь, что последовательная связь работает, убедитесь, что последовательная интеграция с пользовательским интерфейсом работает, проверьте интеграцию последовательного порта с БД и т. Д. Analog_read_speed pde и py показывают основы этого (см. Ссылку на github выше). В конце концов, мы откроем исходный код всего проекта, поэтому, пожалуйста, следите за обновлениями. :) - person toddstavish; 12.10.2010

Эта программа позволяет автоматически запускать несколько модульных тестов Arduino. Процесс тестирования запускается на ПК, но тесты выполняются на реальном оборудовании Arduino. Один набор модульных тестов обычно используется для тестирования одной библиотеки Arduino. (это

Форум Arduino: http://arduino.cc/forum/index.php?topic=140027.0 < / а>

Страница проекта GitHub: http://jeroendoggen.github.com/Arduino-TestSuite

Страница в указателе пакетов Python: http://pypi.python.org/pypi/arduino_testsuite

Модульные тесты написаны с помощью «Библиотеки модульного тестирования Arduino»: http://code.google.com/p/arduinounit

Для каждого набора модульных тестов выполняются следующие шаги:

  • Прочтите файл конфигурации, чтобы узнать, какие тесты запускать
  • Скрипт компилирует и загружает скетч Arduino, содержащий код модульного тестирования.
  • Модульные тесты выполняются на плате Arduino.
  • Результаты теста распечатываются через последовательный порт и анализируются скриптом Python.
  • Сценарий запускает следующий тест, повторяя вышеуказанные шаги для всех тестов, запрошенных в файле конфигурации.
  • Сценарий распечатывает сводку, показывающую обзор всех неудачных / пройденных тестов в полном комплекте тестов.
person jeroendoggen    schedule 11.01.2013

Для этой цели я создал arduino_ci. Хотя он ограничен тестированием библиотек Arduino (а не отдельных скетчей), он позволяет запускать модульные тесты либо локально, либо в системе CI (например, Travis CI или Appveyor).

Рассмотрим очень простую библиотеку в каталоге вашей библиотеки Arduino под названием DoSomething с do-something.cpp:

#include <Arduino.h>
#include "do-something.h"

int doSomething(void) {
  return 4;
};

Вы должны выполнить модульное тестирование следующим образом (с тестовым файлом с именем test/is_four.cpp или каким-то другим):

#include <ArduinoUnitTests.h>
#include "../do-something.h"

unittest(library_does_something)
{
  assertEqual(4, doSomething());
}

unittest_main()  // this is a macro for main().  just go with it.

Это все. Если этот assertEqual синтаксис и структура теста кажутся знакомыми, то это потому, что я принял некоторые из библиотеки ArduinoUnit Мэтью Мердока, поэтому он упоминается в его ответе.

Дополнительную информацию о модульном тестировании I / Контакты O, часы, последовательные порты и т. Д.

Эти модульные тесты компилируются и запускаются с использованием скрипта, содержащегося в рубиновом геме. Примеры того, как это настроить, см. В README.md или просто скопируйте один из этих примеров:

person Ian    schedule 07.03.2018
comment
Это выглядит интересно, но я не уверен, что он правильно тестирует код Arduino. Судя по опубликованному вами выводу, он компилируется в архитектуру x86_64, которая, очевидно, не используется для Arduino. Это может привести к ошибкам, вызванным конфликтами между реализациями типов. - person Cerin; 11.07.2018
comment
Такая ошибка, безусловно, возможна. У вас есть пример, который я мог бы использовать в качестве тестового примера? - person Ian; 12.07.2018

Храните программный код отдельно или абстрагированно от остального, чтобы вы могли тестировать и отлаживать этот более крупный «отдых» на любой платформе, для которой у вас есть хорошие инструменты и с которой вы знакомы больше всего.

По сути, постарайтесь собрать как можно больше окончательного кода из как можно большего числа известных в работе строительных блоков. Оставшаяся работа, связанная с оборудованием, будет намного проще и быстрее. Вы можете завершить его, используя существующие эмуляторы и / или эмулируя устройства самостоятельно. И тогда, конечно, вам нужно как-то проверить настоящую вещь. В зависимости от обстоятельств, это может быть или не очень хорошо автоматизировать (то есть кто или что будет нажимать кнопки и предоставлять другие входные данные? Кто или что будет наблюдать и интерпретировать различные индикаторы и выходы?).

person Alexey Frunze    schedule 24.10.2011

Джеймс В. Греннинг пишет отличные книги, и эта посвящена модульному тестированию встроенного кода C Разработка через тестирование для встроенного C.

person Rafael Vega    schedule 30.11.2010

Я использую Searduino при написании кода Arduino. Searduino - это симулятор Arduino и среда разработки (Makefiles, код C ...), которая упрощает взлом на C / C ++ с помощью вашего любимого редактора. Вы можете импортировать эскизы Arduino и запускать их в симуляторе.

Снимок экрана Searduino 0.8: http://searduino.files.wordpress.com/2014/01/jearduino-0-8.png

Будет выпущен Searduino 0.9, и видео будет записано, как только будут проведены последние тесты ... через день или два.

Тестирование на симуляторе не следует рассматривать как настоящие тесты, но оно, безусловно, очень помогло мне в поиске глупых / логических ошибок (забвение сделать pinMode(xx, OUTPUT) и т. Д.).

Кстати: Я один из разработчиков Searduino.

person user3183814    schedule 10.01.2014

Существует проект под названием ncore, который предоставляет собственное ядро ​​для Arduino. И позволяет писать тесты для кода Arduino.

Из описания проекта

Собственное ядро ​​позволяет компилировать и запускать скетчи Arduino на ПК, как правило, без каких-либо изменений. Он предоставляет собственные версии стандартных функций Arduino и интерфейс командной строки для ввода данных в ваш эскиз, которые обычно поступают от самого оборудования.

Также в разделе "что мне нужно для его использования"

Если вы хотите создать тесты, вам понадобится cxxtest из http://cxxtest.tigris.org. NCORE был протестирован cxxtest 3.10.1.

person Sudar    schedule 06.08.2012
comment
Это интересный проект. К сожалению, похоже, что теперь он мертв, так как не продвигался в течение 6 лет. - person Cerin; 10.07.2018

Если вы хотите провести модульное тестирование кода вне MCU (на настольном компьютере), проверьте libcheck: https://libcheck.github.io/check/

Я использовал его для тестирования собственного встроенного кода несколько раз. Это довольно надежный фреймворк.

person ezaquarii    schedule 19.08.2017
comment
Единственным недостатком является то, что он не поддерживает g ++, что делает его бесполезным для тестирования большинства библиотек Arduino, использующих функции C ++. - person Cerin; 11.07.2018

Вы можете использовать emulare - вы можете перетащить микроконтроллер на диаграмму и запустить свой код в Eclipse. В документации на веб-сайте рассказывается, как его настроить.

person Imre    schedule 23.05.2012

Используйте Proteus VSM с библиотекой Arduino для отладки или тестирования кода.

Это лучшая практика, прежде чем вводить свой код на борт, но обязательно укажите время, потому что симуляция не запускается в реальном времени, поскольку они запускаются на плате.

person sathish    schedule 17.04.2017

Попробуйте Симулятор схем Autodesk. Это позволяет тестировать код и схемы Arduino со многими другими аппаратными компонентами.

person Sidhant Goyal    schedule 03.01.2017

В основном Arduino пишется на C и C ++, даже библиотеки arduino написаны на C и C ++. Итак, простыми словами, просто обрабатывайте код как C и C ++ и попробуйте выполнить модульное тестирование. Под словом «дескриптор» я подразумеваю, что вы изменили весь базовый синтаксис, например, serial.println на sysout, pinmode на varaibles, цикл void на цикл while (), который прерывается либо в ключевой таблице, либо после некоторой итерации.

Я знаю, что это немного долгий и непростой процесс. По моему личному опыту, как только вы начнете с ним делать, это окажется более надежным.

-Nandha_Frost

person Nandha Frost    schedule 23.11.2018

Если вы заинтересованы в запуске эскиза INO и проверке последовательного вывода, у меня есть рабочая реализация этого в моем Контрольная сумма Arduino NMEA.

Следующий сценарий берет файл и использует интерфейс командной строки Arduino для компиляции его в файл HEX, который затем загружается в SimAVR, который оценивает его и распечатывает последовательный вывод. Поскольку все программы Arduino работают вечно, не имея возможности убить себя (exit(0) не работает), я позволяю скетчу работать в течение нескольких секунд, а затем сравниваю захваченный результат с ожидаемым результатом.

Загрузите и извлеките Arduino CLI (в данном случае версия 0.5.0 - последняя на момент написания):

curl -L https://github.com/arduino/arduino-cli/releases/download/0.5.0/arduino-cli_0.5.0_Linux_64bit.tar.gz -o arduino-cli.tar.gz
tar -xvzf arduino-cli.tar.gz

Теперь вы можете обновить индекс и установить соответствующее ядро:

./arduino-cli core update-index
./arduino-cli core install arduino:avr

Предполагая, что ваш скетч называется nmea-checksum.ino, чтобы получить ELF и HEX, запустите:

./arduino-cli compile -b arduino:avr:uno nmea-checksum.ino

Затем SimAVR для запуска HEX (или ELF) - я собираю из исходников, потому что последний выпуск у меня не работал:

sudo apt-get update
sudo apt-get install -y build-essential libelf-dev avr-libc gcc-avr freeglut3-dev libncurses5-dev pkg-config
git clone https://github.com/buserror/simavr.git
cd simavr
make

Успешная компиляция даст вам simavr/run_avr, который вы можете использовать для запуска скетча. Как я уже сказал, timeout иначе он никогда не завершится:

cd simavr
timeout 10 ./run_avr -m atmega168 -f 16000000 ../../nmea-checksum.ino.arduino.avr.uno.elf &> nmea-checksum.ino.clog || true

Сгенерированный файл будет содержать управляющие символы цветового кода ANSI, обертывающие последовательный вывод, чтобы избавиться от них:

cat nmea-checksum.ino.clog | sed -r "s/\x1B\[([0-9]{1,2}(;[0-9]{1,2})?)?[mGK]//g" > nmea-checksum.ino.log
cat nmea-checksum.ino.log

Теперь все, что вам нужно сделать, это сравнить этот файл с заведомо исправным файлом:

diff nmea-checksum.ino.log ../../nmea-checksum.ino.test

Если нет различий, diff выйдет с кодом 0, иначе сценарий завершится ошибкой.

person Tomáš Hübelbauer    schedule 14.09.2019