SysInfo for Arduino

arduinec
Offline
Зарегистрирован: 01.09.2015

dimax пишет:

Я даже скетч такой писал, правда назначение было другим -расчёт точности собаки.

И где этот код можно посмотреть?

dimax пишет:

Но удобнее всего ткнуть осциллом в кварц и измерить.

Интереснее если Ардуина сама получит всю информацию о себе.
Может ещё какие-нибудь недокументированные возможности есть?

dimax
dimax аватар
Offline
Зарегистрирован: 25.12.2013

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

volatile unsigned int int_tic;
volatile unsigned long tic;
void setup(){
Serial.begin(9600);
TCCR1B = 0; TCCR1A = 0; TCNT1 = 0;
TIMSK1 = 1<<TOIE1;
TCCR1B = 1<<CS10;
WDTCSR=(1<<WDCE)|(1<<WDE); //установить биты WDCE WDE (что б разрешить запись в другие биты
WDTCSR=(1<<WDIE)|(1<<WDP2)|(1<<WDP1); // разрешение прерывания + выдержка 1 секунда(55 страница даташита)
}


ISR (TIMER1_OVF_vect) { //прерывания счёта по переполнению uint
int_tic++; //считать переполнения через 65536 тактов
}

ISR (WDT_vect){
tic= ((uint32_t)int_tic<<16)|TCNT1 ; //подсчёт тиков
Serial.print(" 1 Sec WDT= "); 
Serial.print( (float) tic * 625E-10 ,6 );
ICR1=0; int_tic=0; TCNT1=0;  
Serial.print(' ');
Serial.println("Seconds"); 
}


  
void loop(){
}

Если выводить значение tic -то это будет очень примерная частота в герцах. Зато не привязано ни к чему :)

Других интересных возможностей для самодиагностики не припомню..

arduinec
Offline
Зарегистрирован: 01.09.2015

С помощью таймера watchdog удалось получить реальную частоту кварца. Спасибо dimax!
Версия 1.03

// SysInfo for Arduino
#define Version 1.03

#include <avr/boot.h>

unsigned int tik = 0;
byte freq, count = 0;

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

  Frequency();

  Serial.print("SysInfo for Arduino version ");
  Serial.println(Version);
  Serial.println();

  Serial.print("F_CPU = ");
  Serial.println(F_CPU);

  Serial.print("Frequency = ");
  Serial.print(freq);
  Serial.println(" MHz");
  Serial.println();

  VCC();
  Fuses();
  TestPins();
}

void loop() {}

void Frequency()
{
  byte fcpu;

  TCCR1A = 0;
  TCCR1B = 1<<CS10 | 1<<CS12;  // clk/1024
  TCNT1 = 0;

  WDTCSR = (1<<WDCE) | (1<<WDE);
  WDTCSR = (1<<WDIE);  // enable WDT delay 16ms

  while(count < 3) delay(1);

  WDTCSR = (1<<WDCE);  // disable WDT

  if (tik <= 30) freq = 1;
  if ((tik > 30)  && (tik <= 100)) freq = 4;
  if ((tik > 100) && (tik <= 170)) freq = 8;
  if ((tik > 170) && (tik <= 240)) freq = 12;
  if ((tik > 240) && (tik <= 320)) freq = 16;
  if (tik > 320) freq = 20;

  fcpu = F_CPU / 1000000L;

  if ((fcpu == 16) && (freq == 8)) Serial.begin(19200);
}

ISR (WDT_vect) {
  tik = TCNT1;
  count++;
  TCNT1 = 0;
}

void VCC()
{
  #define Vref 1100
  int mvVcc;

  ADMUX = 1<<REFS0 | 0x0E;
  ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 5;
  delay(1);
  mvVcc = (1023L * Vref) / ADC;

  Serial.print("VCC = ");
  Serial.print(mvVcc);
  Serial.println(" mV");
  Serial.println();
}

void Fuses()
{
  #define SIGRD 5

  Serial.print("Signatura = ");
  Serial.print(boot_signature_byte_get(0),HEX);
  Serial.print(boot_signature_byte_get(2),HEX);
  Serial.println(boot_signature_byte_get(4),HEX);

  Serial.print("Fuses (L/H/ext) = ");
  Serial.print(boot_lock_fuse_bits_get(GET_LOW_FUSE_BITS),HEX);
  Serial.print(boot_lock_fuse_bits_get(GET_HIGH_FUSE_BITS),HEX);
  Serial.println(boot_lock_fuse_bits_get(GET_EXTENDED_FUSE_BITS),HEX);

  Serial.println();
}

void TestPins()
{
  #define FIRST_PIN 0
  #define LAST_PIN 19

  Serial.println("Test of short circuit on GND or VCC:");

  for(byte pin = FIRST_PIN; pin <= LAST_PIN; pin++)
  {
    if(pin < 10) Serial.print("Pin:  ");
    else Serial.print("Pin: ");
    Serial.print(pin);

    pinMode(pin, OUTPUT);
    digitalWrite(pin, 0);
    Serial.print("    Low: ");
    if(!digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    digitalWrite(pin, 1);
    Serial.print("  High: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    pinMode(pin, INPUT_PULLUP);
    Serial.print("  Pull Up: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    Serial.println();
    pinMode(pin, INPUT);
  }
 
  Serial.println();
}

Длительность в таймере watchdog зависит от питания и температуры, поэтому частота определяется через интервал значений.

С данным скетчем получилось заменить кварц с 16 на 8 МГц (как описано в посте 9) и вывести правильный результат (fcpu=16, freq=8) в сериал монитор, но для заливки нового скетча кварц на 16 МГц нужно возвращать обратно.

arduinec
Offline
Зарегистрирован: 01.09.2015

Добавил вывод CPU.
Версия 1.04

// SysInfo for Arduino
#define Version 1.04

#include <avr/boot.h>

unsigned int tik = 0;
byte freq, count = 0;

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

  Frequency();

  Serial.print("SysInfo for Arduino version ");
  Serial.println(Version);
  Serial.println();

  Serial.print("F_CPU = ");
  Serial.println(F_CPU);

  Serial.print("Frequency = ");
  Serial.print(freq);
  Serial.println(" MHz");
  Serial.println();

  CPU();
  VCC();
  Fuses();
  TestPins();
}

void loop() {}

void Frequency()
{
  byte fcpu;

  TCCR1A = 0;
  TCCR1B = 1<<CS10 | 1<<CS12;  // clk/1024
  TCNT1 = 0;

  WDTCSR = (1<<WDCE) | (1<<WDE);
  WDTCSR = (1<<WDIE);  // enable WDT delay 16ms

  while(count < 3) delay(1);

  WDTCSR = (1<<WDCE);  // disable WDT

  if (tik <= 30) freq = 1;
  if ((tik > 30)  && (tik <= 100)) freq = 4;
  if ((tik > 100) && (tik <= 170)) freq = 8;
  if ((tik > 170) && (tik <= 240)) freq = 12;
  if ((tik > 240) && (tik <= 320)) freq = 16;
  if (tik > 320) freq = 20;

  fcpu = F_CPU / 1000000L;

  if ((fcpu == 16) && (freq == 8)) Serial.begin(19200);
}

ISR (WDT_vect) {
  tik = TCNT1;
  count++;
  TCNT1 = 0;
}

void CPU()
{
  Serial.print("CPU = ");

  #if defined(__AVR_ATmega48__)
    Serial.println("ATmega48");
  #elif defined(__AVR_ATmega48P__)
    Serial.println("ATmega48P");
  #elif defined(__AVR_ATmega88__)
    Serial.println("ATmega88");
  #elif defined(__AVR_ATmega88P__)
    Serial.println("ATmega88P");
  #elif defined(__AVR_ATmega168__)
    Serial.println("ATmega168");
  #elif defined(__AVR_ATmega168P__)
    Serial.println("ATmega168P");
  #elif defined(__AVR_ATmega328__)
    Serial.println("ATmega328");
  #elif defined(__AVR_ATmega328P__)
    Serial.println("ATmega328P");
  #elif defined(__AVR_ATmega324__)
    Serial.println("ATmega324");
  #elif defined(__AVR_ATmega324P__)
    Serial.println("ATmega324P");
  #elif defined(__AVR_ATmega644__)
    Serial.println("ATmega644");
  #elif defined(__AVR_ATmega644P__)
    Serial.println("ATmega644P");
  #elif defined(__AVR_ATmega1284__)
    Serial.println("ATmega1284");
  #elif defined(__AVR_ATmega1284P__)
    Serial.println("ATmega1284P");
  #elif defined(__AVR_ATmega640__)
    Serial.println("ATmega640");
  #elif defined(__AVR_ATmega1280__)
    Serial.println("ATmega1280");
  #elif defined(__AVR_ATmega2560__)
    Serial.println("ATmega2560");
  #else
    Serial.println("Unknown");
  #endif

  Serial.println("");
}

void VCC()
{
  #define Vref 1100
  int mvVcc;

  ADMUX = 1<<REFS0 | 0x0E;
  ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 5;
  delay(1);
  mvVcc = (1023L * Vref) / ADC;

  Serial.print("VCC = ");
  Serial.print(mvVcc);
  Serial.println(" mV");
  Serial.println();
}

void Fuses()
{
  #define SIGRD 5

  Serial.print("Signatura = ");
  Serial.print(boot_signature_byte_get(0),HEX);
  Serial.print(boot_signature_byte_get(2),HEX);
  Serial.println(boot_signature_byte_get(4),HEX);

  Serial.print("Fuses (L/H/ext) = ");
  Serial.print(boot_lock_fuse_bits_get(GET_LOW_FUSE_BITS),HEX);
  Serial.print(boot_lock_fuse_bits_get(GET_HIGH_FUSE_BITS),HEX);
  Serial.println(boot_lock_fuse_bits_get(GET_EXTENDED_FUSE_BITS),HEX);

  Serial.println();
}

void TestPins()
{
  #define FIRST_PIN 0
  #define LAST_PIN 19

  Serial.println("Test of short circuit on GND or VCC:");

  for(byte pin = FIRST_PIN; pin <= LAST_PIN; pin++)
  {
    if(pin < 10) Serial.print("Pin:  ");
    else Serial.print("Pin: ");
    Serial.print(pin);

    pinMode(pin, OUTPUT);
    digitalWrite(pin, 0);
    Serial.print("    Low: ");
    if(!digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    digitalWrite(pin, 1);
    Serial.print("  High: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    pinMode(pin, INPUT_PULLUP);
    Serial.print("  Pull Up: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    Serial.println();
    pinMode(pin, INPUT);
  }
 
  Serial.println();
}

 

arduinec
Offline
Зарегистрирован: 01.09.2015

Добавил вывод памяти.
Версия 1.05

// SysInfo for Arduino
#define Version 1.05

#include <avr/boot.h>

unsigned int tik = 0;
byte freq, count = 0;

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

  Frequency();

  Serial.print("SysInfo for Arduino version ");
  Serial.println(Version);
  Serial.println();

  Serial.print("F_CPU = ");
  Serial.println(F_CPU);

  Serial.print("Frequency = ");
  Serial.print(freq);
  Serial.println(" MHz");
  Serial.println();

  CPU();
  Memory();
  VCC();
  Fuses();
  TestPins();
}

void loop() {}

void Frequency()
{
  byte fcpu;

  TCCR1A = 0;
  TCCR1B = 1<<CS10 | 1<<CS12;  // clk/1024
  TCNT1 = 0;

  WDTCSR = (1<<WDCE) | (1<<WDE);
  WDTCSR = (1<<WDIE);  // enable WDT delay 16ms

  while(count < 3) delay(1);

  WDTCSR = (1<<WDCE);  // disable WDT

  if (tik <= 30) freq = 1;
  if ((tik > 30)  && (tik <= 100)) freq = 4;
  if ((tik > 100) && (tik <= 170)) freq = 8;
  if ((tik > 170) && (tik <= 240)) freq = 12;
  if ((tik > 240) && (tik <= 320)) freq = 16;
  if (tik > 320) freq = 20;

  fcpu = F_CPU / 1000000L;

  if ((fcpu == 16) && (freq == 8)) Serial.begin(19200);
}

ISR (WDT_vect) {
  tik = TCNT1;
  count++;
  TCNT1 = 0;
}

void CPU()
{
  Serial.print("CPU = ");

  #if defined(__AVR_ATmega48__)
    Serial.println("ATmega48");
  #elif defined(__AVR_ATmega48P__)
    Serial.println("ATmega48P");
  #elif defined(__AVR_ATmega88__)
    Serial.println("ATmega88");
  #elif defined(__AVR_ATmega88P__)
    Serial.println("ATmega88P");
  #elif defined(__AVR_ATmega168__)
    Serial.println("ATmega168");
  #elif defined(__AVR_ATmega168P__)
    Serial.println("ATmega168P");
  #elif defined(__AVR_ATmega328__)
    Serial.println("ATmega328");
  #elif defined(__AVR_ATmega328P__)
    Serial.println("ATmega328P");
  #elif defined(__AVR_ATmega324__)
    Serial.println("ATmega324");
  #elif defined(__AVR_ATmega324P__)
    Serial.println("ATmega324P");
  #elif defined(__AVR_ATmega644__)
    Serial.println("ATmega644");
  #elif defined(__AVR_ATmega644P__)
    Serial.println("ATmega644P");
  #elif defined(__AVR_ATmega1284__)
    Serial.println("ATmega1284");
  #elif defined(__AVR_ATmega1284P__)
    Serial.println("ATmega1284P");
  #elif defined(__AVR_ATmega640__)
    Serial.println("ATmega640");
  #elif defined(__AVR_ATmega1280__)
    Serial.println("ATmega1280");
  #elif defined(__AVR_ATmega2560__)
    Serial.println("ATmega2560");
  #else
    Serial.println("Unknown");
  #endif

  Serial.println("");
}

void Memory()
{
  extern int __bss_end, *__brkval;
  int freeRam;

  Serial.print("Flash Memory = ");
  Serial.print(FLASHEND);
  Serial.println(" bytes");

  if((int)__brkval == 0)
    freeRam = ((int)&freeRam) - ((int)&__bss_end);
  else
    freeRam = ((int)&freeRam) - ((int)__brkval);

  Serial.print("Free RAM memory = ");
  Serial.print(freeRam);
  Serial.println(" bytes");

  Serial.println();
}

void VCC()
{
  #define Vref 1100
  int mvVcc;

  ADMUX = 1<<REFS0 | 0x0E;
  ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 5;
  delay(1);
  mvVcc = (1023L * Vref) / ADC;

  Serial.print("VCC = ");
  Serial.print(mvVcc);
  Serial.println(" mV");
  Serial.println();
}

void Fuses()
{
  #define SIGRD 5

  Serial.print("Signatura = ");
  Serial.print(boot_signature_byte_get(0),HEX);
  Serial.print(boot_signature_byte_get(2),HEX);
  Serial.println(boot_signature_byte_get(4),HEX);

  Serial.print("Fuses (L/H/ext) = ");
  Serial.print(boot_lock_fuse_bits_get(GET_LOW_FUSE_BITS),HEX);
  Serial.print(boot_lock_fuse_bits_get(GET_HIGH_FUSE_BITS),HEX);
  Serial.println(boot_lock_fuse_bits_get(GET_EXTENDED_FUSE_BITS),HEX);

  Serial.println();
}

void TestPins()
{
  #define FIRST_PIN 0
  #define LAST_PIN 19

  Serial.println("Test of short circuit on GND or VCC:");

  for(byte pin = FIRST_PIN; pin <= LAST_PIN; pin++)
  {
    if(pin < 10) Serial.print("Pin:  ");
    else Serial.print("Pin: ");
    Serial.print(pin);

    pinMode(pin, OUTPUT);
    digitalWrite(pin, 0);
    Serial.print("    Low: ");
    if(!digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    digitalWrite(pin, 1);
    Serial.print("  High: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    pinMode(pin, INPUT_PULLUP);
    Serial.print("  Pull Up: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    Serial.println();
    pinMode(pin, INPUT);
  }
 
  Serial.println();
}

 

Andrey12
Andrey12 аватар
Offline
Зарегистрирован: 26.12.2014

Классная штука, не на чем сейчас проверить, но потом погоняю на платах которые есть у меня.

К стати по пинам, у тебя используется 

#define FIRST_PIN 0
#define LAST_PIN 19

Но вроде как есть определенные переменные файлы с ними лежат в hardware\arduino\avr\variants

#define NUM_DIGITAL_PINS
#define NUM_ANALOG_INPUTS

Опять же проверить не могу но думаю если они работают корректно можно добваить в счетчь "кроссплатность" :)

arduinec
Offline
Зарегистрирован: 01.09.2015

Вариант с FIRST_PIN и LAST_PIN позволяет выбрать нужный диапазон для тестирования. Например пины 0 и 1 при этом тестировании всегда заняты, так как работают на сериал-монитор, поэтому их можно исключить из этого диапазона. А для Mega2560 диапазон наоборот можно расширить на все пины.

Всё не предусмотришь, но скетч позволяет подстроить его под нужные проверки.

Клапауций 232
Offline
Зарегистрирован: 05.04.2016

dimax пишет:

 Для этого есть штатные дуиновские функции.

dimax, подскажи, пожалуйста - для atmega8 выдаёт сигнатуру 406463, ожидал что-то похожее на 1E9307

спасибо.

arduinec
Offline
Зарегистрирован: 01.09.2015

Добавил вывод с внутреннего датчика температуры (http://playground.arduino.cc/Main/InternalTemperatureSensor).
Версия 1.06

// SysInfo for Arduino
#define Version 1.06

#include <avr/boot.h>

unsigned int tik = 0;
byte freq, count = 0;

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

  Frequency();

  Serial.print("SysInfo for Arduino version ");
  Serial.println(Version);
  Serial.println();

  Serial.print("F_CPU = ");
  Serial.println(F_CPU);

  Serial.print("Frequency = ");
  Serial.print(freq);
  Serial.println(" MHz");
  Serial.println();

  CPU();
  Memory();
  VCC();
  Fuses();
  Temperature();
  TestPins();
}

void loop() {}

void Frequency()
{
  byte fcpu;

  TCCR1A = 0;
  TCCR1B = 1<<CS10 | 1<<CS12;  // clk/1024
  TCNT1 = 0;

  WDTCSR = (1<<WDCE) | (1<<WDE);
  WDTCSR = (1<<WDIE);  // enable WDT delay 16ms

  while(count < 3) delay(1);

  WDTCSR = (1<<WDCE);  // disable WDT

  if (tik <= 30) freq = 1;
  if ((tik > 30)  && (tik <= 100)) freq = 4;
  if ((tik > 100) && (tik <= 170)) freq = 8;
  if ((tik > 170) && (tik <= 240)) freq = 12;
  if ((tik > 240) && (tik <= 320)) freq = 16;
  if (tik > 320) freq = 20;

  fcpu = F_CPU / 1000000L;

  if ((fcpu == 16) && (freq == 8)) Serial.begin(19200);
}

ISR (WDT_vect) {
  tik = TCNT1;
  count++;
  TCNT1 = 0;
}

void CPU()
{
  Serial.print("CPU = ");

  #if defined(__AVR_ATmega48__)
    Serial.println("ATmega48");
  #elif defined(__AVR_ATmega48P__)
    Serial.println("ATmega48P");
  #elif defined(__AVR_ATmega88__)
    Serial.println("ATmega88");
  #elif defined(__AVR_ATmega88P__)
    Serial.println("ATmega88P");
  #elif defined(__AVR_ATmega168__)
    Serial.println("ATmega168");
  #elif defined(__AVR_ATmega168P__)
    Serial.println("ATmega168P");
  #elif defined(__AVR_ATmega328__)
    Serial.println("ATmega328");
  #elif defined(__AVR_ATmega328P__)
    Serial.println("ATmega328P");
  #elif defined(__AVR_ATmega324__)
    Serial.println("ATmega324");
  #elif defined(__AVR_ATmega324P__)
    Serial.println("ATmega324P");
  #elif defined(__AVR_ATmega644__)
    Serial.println("ATmega644");
  #elif defined(__AVR_ATmega644P__)
    Serial.println("ATmega644P");
  #elif defined(__AVR_ATmega1284__)
    Serial.println("ATmega1284");
  #elif defined(__AVR_ATmega1284P__)
    Serial.println("ATmega1284P");
  #elif defined(__AVR_ATmega640__)
    Serial.println("ATmega640");
  #elif defined(__AVR_ATmega1280__)
    Serial.println("ATmega1280");
  #elif defined(__AVR_ATmega2560__)
    Serial.println("ATmega2560");
  #else
    Serial.println("Unknown");
  #endif

  Serial.println("");
}

void Memory()
{
  extern int __bss_end, *__brkval;
  int freeRam;

  Serial.print("Flash Memory = ");
  Serial.print(FLASHEND);
  Serial.println(" bytes");

  if((int)__brkval == 0)
    freeRam = ((int)&freeRam) - ((int)&__bss_end);
  else
    freeRam = ((int)&freeRam) - ((int)__brkval);

  Serial.print("Free RAM memory = ");
  Serial.print(freeRam);
  Serial.println(" bytes");

  Serial.println();
}

void VCC()
{
  #define Vref 1100
  int mvVcc;

  ADMUX = 1<<REFS0 | 0x0E;
  ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 5;
  delay(1);
  mvVcc = (1023L * Vref) / ADC;

  Serial.print("VCC = ");
  Serial.print(mvVcc);
  Serial.println(" mV");
  Serial.println();
}

void Fuses()
{
  #define SIGRD 5

  Serial.print("Signatura = ");
  Serial.print(boot_signature_byte_get(0),HEX);
  Serial.print(boot_signature_byte_get(2),HEX);
  Serial.println(boot_signature_byte_get(4),HEX);

  Serial.print("Fuses (L/H/ext) = ");
  Serial.print(boot_lock_fuse_bits_get(GET_LOW_FUSE_BITS),HEX);
  Serial.print(boot_lock_fuse_bits_get(GET_HIGH_FUSE_BITS),HEX);
  Serial.println(boot_lock_fuse_bits_get(GET_EXTENDED_FUSE_BITS),HEX);

  Serial.println();
}

void TestPins()
{
  #define FIRST_PIN 0
  #define LAST_PIN 19

  Serial.println("Test of short circuit on GND or VCC:");

  for(byte pin = FIRST_PIN; pin <= LAST_PIN; pin++)
  {
    if(pin < 10) Serial.print("Pin:  ");
    else Serial.print("Pin: ");
    Serial.print(pin);

    pinMode(pin, OUTPUT);
    digitalWrite(pin, 0);
    Serial.print("    Low: ");
    if(!digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    digitalWrite(pin, 1);
    Serial.print("  High: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    pinMode(pin, INPUT_PULLUP);
    Serial.print("  Pull Up: ");
    if(digitalRead(pin)) Serial.print("Ok  ");
    else Serial.print("Fail");

    Serial.println();
    pinMode(pin, INPUT);
  }
 
  Serial.println();
}

void Temperature()
{
  float temperature;

  ADMUX = _BV(REFS1) | _BV(REFS0) | _BV(MUX3);
  ADCSRA |= _BV(ADEN);
  delay(20);
  ADCSRA |= _BV(ADSC);
  delay(1);

  temperature = (ADC - 324.31) / 1.22;

  Serial.print("Internal Temperature = ");
  Serial.print(temperature, 1);
  Serial.println(" C");
  Serial.println();
}

 

dimax
dimax аватар
Offline
Зарегистрирован: 25.12.2013

Клапауций 232 пишет:

dimax, подскажи, пожалуйста - для atmega8 выдаёт сигнатуру 406463, ожидал что-то похожее на 1E9307

Посмотрел в даташит на мегу328 -там есть раздел "Reading the Signature Row from Software "  А в даташите на мегу 8  такого раздела нет. Похоже мега8 не поддерживает режим само-чтения сигнатуры, и считанные байтики -просто дамп первых адресов памяти.. (

Клапауций 232
Offline
Зарегистрирован: 05.04.2016

dimax пишет:

Посмотрел в даташит на мегу328 -там есть раздел "Reading the Signature Row from Software "  А в даташите на мегу 8  такого раздела нет. Похоже мега8 не поддерживает режим само-чтения сигнатуры, и считанные байтики -просто дамп первых адресов памяти.. (

ок. спасибо.

Tomasina
Tomasina аватар
Offline
Зарегистрирован: 09.03.2013

что-то на 2560 косячит.

На одной плате:

VCC = -1 mV

Signatura = 1E981
Fuses (L/H/ext) = FFD8FD

Internal Temperature = -260.1 C

На другой плате:

VCC = 1102 mV

Signatura = 1E981
Fuses (L/H/ext) = FFD8FD

Internal Temperature = -265.8 C

 

arduinec
Offline
Зарегистрирован: 01.09.2015

Tomasina пишет:

что-то на 2560 косячит.

Тоже обратил внимание на неправильные показания Mega2560, но пока не дошли руки до того, чтобы разобраться. Скорее всего другими командами нужно выставлять опорное напряжение (в Меге их два) и считывать температуру (если там есть датчик).

Хотя я и сделал вывод названия процессора, но пока так и не разобрался как Ардуина определяет какой процессор в ней: считывает какой-то код чипа или название просто записывается при прошивке. Это важно при организации ответвлений в скетче при разных процессорах.

Если есть программный код (или информация) на эти темы, то они будут с благодарностью добавлены в следующие версии скетча.

dimax
dimax аватар
Offline
Зарегистрирован: 25.12.2013

arduinec пишет:

Хотя я и сделал вывод названия процессора, но пока так и не разобрался как Ардуина определяет какой процессор в ней: считывает какой-то код чипа или название просто записывается при прошивке.

Да никак не определяет, берёт  выбранный пользователем МК из boards.txt при компиляции. Можете прикрутить настоящий детект чипа -по сигнатуре.

morfius
morfius аватар
Offline
Зарегистрирован: 06.01.2017

Доброе время. Скетчик прикольный, спасибо за труд по его написанию. Не пойму только почему у меня на платах фейлы стоят в одинаковых местах, это баг или фича?

SysInfo for Arduino version 1.06

F_CPU = 16000000
Frequency = 16 MHz

CPU = ATmega328P

Flash Memory = 32767 bytes
Free RAM memory = 1558 bytes

VCC = 5091 mV

Signatura = 1E95F
Fuses (L/H/ext) = FFDAFD

Internal Temperature = 19.4 C

Test of short circuit on GND or VCC:
Pin:  0    Low: Fail  High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Fail  Pull Up: Fail

Pin:  2    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  3    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  4    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  5    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  6    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  7    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  8    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  9    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 10    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 11    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 12    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 13    Low: Ok    High: Ok    Pull Up: Fail
Pin: 14    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 15    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 16    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 17    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 18    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 19    Low: Ok    High: Ok    Pull Up: Ok  
 

arduinec
Offline
Зарегистрирован: 01.09.2015

morfius пишет:

Доброе время. Скетчик прикольный, спасибо за труд по его написанию. Не пойму только почему у меня на платах фейлы стоят в одинаковых местах, это баг или фича?

Test of short circuit on GND or VCC:
Pin:  0    Low: Fail  High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Fail  Pull Up: Fail
Pin: 13    Low: Ok    High: Ok    Pull Up: Fail

Пины 0 и 1 относятся к Serial Port, через который Ардуина соединяется с компьютером. На пине 13 находится светодиод (на пинах 0 и 1 кстати тоже).

ua6em
ua6em аватар
Онлайн
Зарегистрирован: 17.08.2016

Клапауций 232 пишет:

__Alexander пишет:

И тогда вывод в уарт будет всегда читабельным.

ок. и, как это туда воткнуть, если мы можем узнать скорость порта только после прошивки, а для прошивки нужно знать скорость порта.

это какая-то рекурсия.

Клапауций никогда не писал реентерабельный код?

Клапауций 823
Клапауций 823 аватар
Offline
Зарегистрирован: 13.01.2017

ua6em пишет:

реентерабельный код?

шо?

morfius
morfius аватар
Offline
Зарегистрирован: 06.01.2017

Arduino Mega показывает не верную температуру:

 

SysInfo for Arduino version 1.06

F_CPU = 16000000
Frequency = 16 MHz

CPU = ATmega2560

Flash Memory = 262143 bytes
Free RAM memory = 7701 bytes

VCC = 1100 mV - ?

Signatura = 1E981
Fuses (L/H/ext) = FFD8FD

Internal Temperature = -265.8 C

Test of short circuit on GND or VCC:
Pin:  0    Low: Fail  High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Fail  Pull Up: Fail
Pin:  2    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  3    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  4    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  5    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  6    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  7    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  8    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  9    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 10    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 11    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 12    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 13    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 14    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 15    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 16    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 17    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 18    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 19    Low: Ok    High: Ok    Pull Up: Ok

ua6em
ua6em аватар
Онлайн
Зарегистрирован: 17.08.2016

Клапауций 823 пишет:

ua6em пишет:

реентерабельный код?

шо?

Открою АМЕРИКУ

arduinec
Offline
Зарегистрирован: 01.09.2015

morfius пишет:

Arduino Mega показывает не верную температуру:

См. пост 63 данной темы.

Vladal
Offline
Зарегистрирован: 19.03.2017

Tomasina пишет:

что-то на 2560 косячит.

На одной плате:

VCC = -1 mV

Signatura = 1E981
Fuses (L/H/ext) = FFD8FD

Internal Temperature = -260.1 C

На другой плате:

VCC = 1102 mV

Signatura = 1E981
Fuses (L/H/ext) = FFD8FD

Internal Temperature = -265.8 C

 


Да здесь скорее всего Mega2560 возвращает внутреннюю температуру в градусах Кельвина, а скетч считает, что это градусы Цельсия.

Можно по результатам функции CPU() определить чип и приводить показания внутреннего термометра к привычному виду.

morfius
morfius аватар
Offline
Зарегистрирован: 06.01.2017

Ну можно видеть, что если трехзначная температура - то перевести ее к соответствию, не напрягаясь тем, что за зверь тестируется. Имхо. Ну хотя бы для начала.

 

Хотя на кельвины не похоже... вот тут перевод онлайн: https://www.translatorscafe.com/unit-converter/ru/temperature/1-2/

-265.8К = 538С

arduinec
Offline
Зарегистрирован: 01.09.2015

Нашёл кучку сигнатур AVR-контроллеров: http://www.gammon.com.au/forum/?id=11633
Появилась возможность разделять код для разных контроллеров (теперь Mega2560 правильно напряжение питания показывает).
Версия 1.07

// SysInfo for Arduino
#define Version 1.07

#define SIGRD 5

#include <avr/boot.h>

typedef struct {
   byte sig[3];
   const char *desc;
} signatureType;

int foundSig = -1;
unsigned int tik = 0;
byte freq, count = 0;

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

  Frequency();

  Serial.print(F("\nSysInfo for Arduino version "));
  Serial.println(Version);
  Serial.println();

  Serial.print(F("F_CPU = "));
  Serial.println(F_CPU);

  Serial.print(F("Frequency = "));
  Serial.print(freq);
  Serial.println(F(" MHz"));
  Serial.println();

  CPU();
  Memory();
  Signature();
  VCC();
  Temperature();
  TestPins();
}

void loop() {}

void Frequency()
{
  byte fcpu;

  TCCR1A = 0;
  TCCR1B = 1<<CS10 | 1<<CS12;  // clk/1024
  TCNT1 = 0;

  WDTCSR = (1<<WDCE) | (1<<WDE);
  WDTCSR = (1<<WDIE);  // enable WDT delay 16ms

  while(count < 3) delay(1);

  WDTCSR = (1<<WDCE);  // disable WDT

  if (tik <= 30) freq = 1;
  if ((tik > 30)  && (tik <= 100)) freq = 4;
  if ((tik > 100) && (tik <= 170)) freq = 8;
  if ((tik > 170) && (tik <= 240)) freq = 12;
  if ((tik > 240) && (tik <= 320)) freq = 16;
  if (tik > 320) freq = 20;

  fcpu = F_CPU / 1000000L;

  if ((fcpu == 16) && (freq == 8)) Serial.begin(19200);
}

ISR (WDT_vect) {
  tik = TCNT1;
  count++;
  TCNT1 = 0;
}

void CPU()
{
  Serial.print(F("CPU_IDE = "));

  #if   defined(__AVR_ATmega328P__)
    Serial.println(F("ATmega328P"));
  #elif defined(__AVR_ATmega48__)
    Serial.println(F("ATmega48"));
  #elif defined(__AVR_ATmega48P__)
    Serial.println(F("ATmega48P"));
  #elif defined(__AVR_ATmega88__)
    Serial.println(F("ATmega88"));
  #elif defined(__AVR_ATmega88P__)
    Serial.println(F("ATmega88P"));
  #elif defined(__AVR_ATmega168__)
    Serial.println(F("ATmega168"));
  #elif defined(__AVR_ATmega168P__)
    Serial.println(F("ATmega168P"));
  #elif defined(__AVR_ATmega328__)
    Serial.println(F("ATmega328"));
  #elif defined(__AVR_ATmega164__)
    Serial.println(F("ATmega164"));
  #elif defined(__AVR_ATmega164P__)
    Serial.println(F("ATmega164P"));
  #elif defined(__AVR_ATmega324__)
    Serial.println(F("ATmega324"));
  #elif defined(__AVR_ATmega324P__)
    Serial.println(F("ATmega324P"));
  #elif defined(__AVR_ATmega644__)
    Serial.println(F("ATmega644"));
  #elif defined(__AVR_ATmega644P__)
    Serial.println(F("ATmega644P"));
  #elif defined(__AVR_ATmega1284__)
    Serial.println(F("ATmega1284"));
  #elif defined(__AVR_ATmega1284P__)
    Serial.println(F("ATmega1284P"));
  #elif defined(__AVR_ATmega640__)
    Serial.println(F("ATmega640"));
  #elif defined(__AVR_ATmega1280__)
    Serial.println(F("ATmega1280"));
  #elif defined(__AVR_ATmega1281__)
    Serial.println(F("ATmega1281"));
  #elif defined(__AVR_ATmega2560__)
    Serial.println(F("ATmega2560"));
  #elif defined(__AVR_ATmega2561__)
    Serial.println(F("ATmega2561"));
  #elif defined(__AVR_ATmega8U2__)
    Serial.println(F("ATmega8U2"));
  #elif defined(__AVR_ATmega16U2__)
    Serial.println(F("ATmega16U2"));
  #elif defined(__AVR_ATmega32U2__)
    Serial.println(F("ATmega32U2"));
  #elif defined(__AVR_ATmega16U4__)
    Serial.println(F("ATmega16U4"));
  #elif defined(__AVR_ATmega32U4__)
    Serial.println(F("ATmega32U4"));
  #elif defined(__AVR_AT90USB82__)
    Serial.println(F("AT90USB82"));
  #elif defined(__AVR_AT90USB162__)
    Serial.println(F("AT90USB162"));
  #elif defined(__AVR_ATtiny24__)
    Serial.println(F("ATtiny24"));
  #elif defined(__AVR_ATtiny44__)
    Serial.println(F("ATtiny44"));
  #elif defined(__AVR_ATtiny84__)
    Serial.println(F("ATtiny84"));
  #elif defined(__AVR_ATtiny25__)
    Serial.println(F("ATtiny25"));
  #elif defined(__AVR_ATtiny45__)
    Serial.println(F("ATtiny45"));
  #elif defined(__AVR_ATtiny85__)
    Serial.println(F("ATtiny85"));
  #elif defined(__AVR_ATtiny13__)
    Serial.println(F("ATtiny13"));
  #elif defined(__AVR_ATtiny13A__)
    Serial.println(F("ATtiny13A"));
  #elif defined(__AVR_ATtiny2313__)
    Serial.println(F("ATtiny2313"));
  #elif defined(__AVR_ATtiny2313A__)
    Serial.println(F("ATtiny2313A"));
  #elif defined(__AVR_ATtiny4313__)
    Serial.println(F("ATtiny4313"));
  #elif defined(__AVR_ATmega8__)
    Serial.println(F("ATmega8"));
  #elif defined(__AVR_ATmega8A__)
    Serial.println(F("ATmega8A"));
  #else
    Serial.println(F("Unknown"));
  #endif

  Serial.println();
}

void Memory()
{
  extern int __bss_end, *__brkval;
  int freeRam;

  Serial.print(F("Flash Memory = "));
  Serial.print(FLASHEND);
  Serial.println(F(" bytes"));

  if((int)__brkval == 0)
    freeRam = ((int)&freeRam) - ((int)&__bss_end);
  else
    freeRam = ((int)&freeRam) - ((int)__brkval);

  Serial.print(F("Free RAM memory = "));
  Serial.print(freeRam);
  Serial.println(F(" bytes"));

  Serial.println();
}

void Signature()
{
  const signatureType signatures [] = {
    { { 0x1E, 0x95, 0x0F }, "ATmega328P",  },    //  0
    { { 0x1E, 0x92, 0x05 }, "ATmega48A",   },    //  1
    { { 0x1E, 0x92, 0x0A }, "ATmega48PA",  },    //  2
    { { 0x1E, 0x93, 0x0A }, "ATmega88A",   },    //  3
    { { 0x1E, 0x93, 0x0F }, "ATmega88PA",  },    //  4
    { { 0x1E, 0x94, 0x06 }, "ATmega168A",  },    //  5
    { { 0x1E, 0x94, 0x0B }, "ATmega168PA", },    //  6
    { { 0x1E, 0x95, 0x14 }, "ATmega328",   },    //  7
    { { 0x1E, 0x95, 0x16 }, "ATmega328PB", },    //  8
    { { 0x1E, 0x94, 0x0A }, "ATmega164P",  },    //  9
    { { 0x1E, 0x95, 0x08 }, "ATmega324P",  },    // 10
    { { 0x1E, 0x96, 0x0A }, "ATmega644P",  },    // 11
    { { 0x1E, 0x97, 0x05 }, "ATmega1284P", },    // 12
    { { 0x1E, 0x97, 0x06 }, "ATmega1284",  },    // 13
    { { 0x1E, 0x96, 0x08 }, "ATmega640",   },    // 14
    { { 0x1E, 0x97, 0x03 }, "ATmega1280",  },    // 15
    { { 0x1E, 0x97, 0x04 }, "ATmega1281",  },    // 16
    { { 0x1E, 0x98, 0x01 }, "ATmega2560",  },    // 17
    { { 0x1E, 0x98, 0x02 }, "ATmega2561",  },    // 18
    { { 0x1E, 0x93, 0x89 }, "ATmega8U2",   },    // 19
    { { 0x1E, 0x94, 0x89 }, "ATmega16U2",  },    // 20
    { { 0x1E, 0x95, 0x8A }, "ATmega32U2",  },    // 21
    { { 0x1E, 0x94, 0x88 }, "ATmega16U4",  },    // 22
    { { 0x1E, 0x95, 0x87 }, "ATmega32U4",  },    // 23
    { { 0x1E, 0x93, 0x82 }, "At90USB82",   },    // 24
    { { 0x1E, 0x94, 0x82 }, "At90USB162",  },    // 25
    { { 0x1E, 0x91, 0x0B }, "ATtiny24",    },    // 26
    { { 0x1E, 0x92, 0x07 }, "ATtiny44",    },    // 27
    { { 0x1E, 0x93, 0x0C }, "ATtiny84",    },    // 28
    { { 0x1E, 0x91, 0x08 }, "ATtiny25",    },    // 29
    { { 0x1E, 0x92, 0x06 }, "ATtiny45",    },    // 30
    { { 0x1E, 0x93, 0x0B }, "ATtiny85",    },    // 31
    { { 0x1E, 0x91, 0x0A }, "ATtiny2313A", },    // 32
    { { 0x1E, 0x92, 0x0D }, "ATtiny4313",  },    // 33
    { { 0x1E, 0x90, 0x07 }, "ATtiny13A",   },    // 34
    { { 0x1E, 0x93, 0x07 }, "ATmega8A",    }     // 35
  };

  int flashSize, NumSig = 36;
  byte sig[3], fuse;

  Serial.print(F("Signature = "));

  sig[0] = boot_signature_byte_get(0);
  if (sig[0] < 16) Serial.print("0");
  Serial.print(sig[0],HEX);
  Serial.print(" ");

  sig[1] = boot_signature_byte_get(2);
  if (sig[1] < 16) Serial.print("0");
  Serial.print(sig[1],HEX);
  Serial.print(" ");

  sig[2] = boot_signature_byte_get(4);
  if (sig[2] < 16) Serial.print("0");
  Serial.println(sig[2],HEX);

  Serial.print(F("Fuses (Low/High/Ext/Lock) = "));

  fuse = boot_lock_fuse_bits_get(GET_LOW_FUSE_BITS);
  if (fuse < 16) Serial.print("0");
  Serial.print(fuse,HEX);
  Serial.print(" ");

  fuse = boot_lock_fuse_bits_get(GET_HIGH_FUSE_BITS);
  if (fuse < 16) Serial.print("0");
  Serial.print(fuse,HEX);
  Serial.print(" ");

  fuse = boot_lock_fuse_bits_get(GET_EXTENDED_FUSE_BITS);
  if (fuse < 16) Serial.print("0");
  Serial.print(fuse,HEX);
  Serial.print(" ");

  fuse = boot_lock_fuse_bits_get(GET_LOCK_BITS);
  if (fuse < 16) Serial.print("0");
  Serial.println(fuse,HEX);

  flashSize = 1 << (sig[1] & 0x0F);

  for (int j=0; j<NumSig; j++)
  {
    if (memcmp(sig, signatures[j].sig, 3) == 0)
    {
      foundSig = j;
      Serial.print(F("Processor = "));
      Serial.println(signatures[j].desc);

      Serial.print(F("Flash memory size = "));
      Serial.print(flashSize,DEC);
      Serial.println(F(" kB"));
      break;
    }
  }

  if (foundSig < 0) Serial.println(F("Unrecogized signature"));

  Serial.println();
}

void VCC()
{
  #define Vref 1100
  int mvVcc;

  if ((foundSig >= 0) && (foundSig <= 8)) {

    ADMUX = (1<<REFS0) | 0x0E;
    ADCSRB = 0;
    ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 0x05;
    delay(1);
    mvVcc = (1023L * Vref) / ADC;

    Serial.print(F("VCC = "));
    Serial.print(mvVcc);
    Serial.println(F(" mV"));
    Serial.println();
  }

  if ((foundSig >= 14) && (foundSig <= 18)) {

    ADMUX = (1<<REFS0) | 0x1E;
    ADCSRB = 0;
    ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 0x05;
    delay(1);
    mvVcc = (1023L * Vref) / ADC;

    Serial.print(F("VCC = "));
    Serial.print(mvVcc);
    Serial.println(F(" mV"));
    Serial.println();
  }

  if ((foundSig >= 22) && (foundSig <= 23)) {

    ADMUX = (1<<REFS0) | 0x1E;
    ADCSRB = 0;
    ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 0x05;
    delay(1);
    mvVcc = (1023L * Vref) / ADC;

    Serial.print(F("VCC = "));
    Serial.print(mvVcc);
    Serial.println(F(" mV"));
    Serial.println();
  }

  if ((foundSig >= 29) && (foundSig <= 31)) {

    ADMUX = 0x0E;
    ADCSRB = 0;
    ADCSRA = (1<<ADEN) | (1<<ADATE) | (1<<ADSC) | 0x05;
    delay(1);
    mvVcc = (1023L * Vref) / ADC;

    Serial.print(F("VCC = "));
    Serial.print(mvVcc);
    Serial.println(F(" mV"));
    Serial.println();
  }
}

void Temperature()
{
  float temperature;

  if ((foundSig >= 0) && (foundSig <= 8)) {

    ADMUX = (1<<REFS1) | (1<<REFS0) | (1<<MUX3);
    ADCSRA |= (1<<ADEN);
    delay(20);
    ADCSRA |= (1<<ADSC);
    delay(1);

    temperature = (ADC - 324.31) / 1.22;

    Serial.print(F("Internal Temperature = "));
    Serial.print(temperature, 1);
    Serial.println(F(" C"));
    Serial.println();
  }

  if ((foundSig >= 22) && (foundSig <= 23)) {

    ADMUX = (1<<REFS1) | (1<<REFS0) | 0x07;
    ADCSRB = 0x20;
    ADCSRA |= (1<<ADEN);
    delay(20);
    ADCSRA |= (1<<ADSC);
    delay(1);

    temperature = (ADC - 324.31) / 1.22;

    Serial.print(F("Internal Temperature = "));
    Serial.print(temperature, 1);
    Serial.println(F(" C"));
    Serial.println();
  }

  if ((foundSig >= 29) && (foundSig <= 31)) {

    ADMUX = (1<<REFS1) | 0x0F;
    ADCSRA |= (1<<ADEN);
    delay(20);
    ADCSRA |= (1<<ADSC);
    delay(1);

    temperature = (ADC - 324.31) / 1.22;

    Serial.print(F("Internal Temperature = "));
    Serial.print(temperature, 1);
    Serial.println(F(" C"));
    Serial.println();
  }
}

void TestPins()
{
  #define FIRST_PIN 0
  #define LAST_PIN 19

  Serial.println(F("Test of short circuit on GND or VCC:"));

  for (byte pin = FIRST_PIN; pin <= LAST_PIN; pin++)
  {
    if (pin < 10) Serial.print(F("Pin:  "));
    else Serial.print(F("Pin: "));
    Serial.print(pin);

    pinMode(pin, OUTPUT);
    digitalWrite(pin, 0);
    Serial.print(F("    Low: "));
    if (!digitalRead(pin)) Serial.print(F("Ok  "));
    else Serial.print(F("Fail"));

    digitalWrite(pin, 1);
    Serial.print(F("  High: "));
    if (digitalRead(pin)) Serial.print(F("Ok  "));
    else Serial.print(F("Fail"));

    pinMode(pin, INPUT_PULLUP);
    Serial.print(F("  Pull Up: "));
    if (digitalRead(pin)) Serial.print(F("Ok  "));
    else Serial.print(F("Fail"));

    Serial.println();
    pinMode(pin, INPUT);
  }
 
  Serial.println();
}

В скетче заложено измерение напряжения питания и внутренней температуры ATmega32U4 (Леонардо) и ATtiny85, но проверить пока не могу из-за их отсутствия.

Smith2007
Offline
Зарегистрирован: 30.10.2017

Arduino Pro Micro

Не верная температура. Больше на температуру по Фаренгейту похоже. В комнате как раз 23 градуса


SysInfo for Arduino version 1.07

F_CPU = 16000000
Frequency = 16 MHz

CPU_IDE = ATmega32U4

Flash Memory = 32767 bytes
Free RAM memory = 1638 bytes

Signature = 1E 95 87
Fuses (Low/High/Ext/Lock) = FF D8 CB EF
Processor = ATmega32U4
Flash memory size = 32 kB

VCC = 4650 mV

Internal Temperature = -10.1 C

Test of short circuit on GND or VCC:
Pin:  0    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  2    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  3    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  4    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  5    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  6    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  7    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  8    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  9    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 10    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 11    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 12    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 13    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 14    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 15    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 16    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 17    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 18    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 19    Low: Ok    High: Ok    Pull Up: Ok  

 

Smith2007
Offline
Зарегистрирован: 30.10.2017

И еще одно замечание...

На платах Leonardo в т.ч. Arduino Pro Micro скетч ни чего не выводит. 

Нужно добавить задержку в Setup() после инициализации serial порта.

Возможно это особенность всех ATmega32U4

void setup()
{
  Serial.begin(9600);
  delay(5000);

  Frequency();

 

arduinec
Offline
Зарегистрирован: 01.09.2015

Smith2007 пишет:

Arduino Pro Micro

Спасибо за информацию!

Smith2007 пишет:

Не верная температура. Больше на температуру по Фаренгейту похоже. В комнате как раз 23 градуса

В даташите ATmega32u4 нет формулы для температурного датчика, поэтому в скетче применяется формула для ATmega328p (возможно для ATmega32u4 она не подходит).

sadman41
Offline
Зарегистрирован: 19.10.2016

http://www.narkidae.com/research/atmega-core-temperature-sensor/

Микра у меня есть, при случае проверю.

arduinec
Offline
Зарегистрирован: 01.09.2015

Из статьи следует, что от полученной датчиком температуры нужно только отнять 273. Для более точного измерения к полученной температуре добавляют/отнимают температуру смещения, которая у каждого чипа своя.

sadman41
Offline
Зарегистрирован: 19.10.2016

Nano, здоровая, температура 36,6:

SysInfo for Arduino version 1.07

F_CPU = 16000000
Frequency = 16 MHz

CPU_IDE = ATmega328P

Flash Memory = 32767 bytes
Free RAM memory = 1085 bytes

MCU ID = 57 36 34 31 30 38 FF 0B 27 04 
Signature = 1E 95 0F
Fuses (Low/High/Ext/Lock) = FF DA FD FF
Processor = ATmega328P
Flash memory size = 32 kB

VCC = 5046 mV

Internal Temperature = 36.6 C

Test of short circuit on GND or VCC:
Pin:  0    Low: Fail  High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Fail  Pull Up: Fail
Pin:  2    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  3    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  4    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  5    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  6    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  7    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  8    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  9    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 10    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 11    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 12    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 13    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 14    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 15    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 16    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 17    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 18    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 19    Low: Ok    High: Ok    Pull Up: Ok  

Micro, температура ушла в минуса:

SysInfo for Arduino version 1.07

F_CPU = 16000000
Frequency = 16 MHz

CPU_IDE = ATmega32U4

Flash Memory = 32767 bytes
Free RAM memory = 1631 bytes

MCU ID = 59 34 39 32 39 35 15 0D 07 11 
Signature = 1E 95 87
Fuses (Low/High/Ext/Lock) = FF D8 FB FF
Processor = ATmega32U4
Flash memory size = 32 kB

VCC = 4957 mV

Internal Temperature = -5.2 C

Test of short circuit on GND or VCC:
Pin:  0    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  1    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  2    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  3    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  4    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  5    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  6    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  7    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  8    Low: Ok    High: Ok    Pull Up: Ok  
Pin:  9    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 10    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 11    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 12    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 13    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 14    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 15    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 16    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 17    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 18    Low: Ok    High: Ok    Pull Up: Ok  
Pin: 19    Low: Ok    High: Ok    Pull Up: Ok  

В setup() стоит добавить код, рекомендуемый для Leonardo: while (!Serial) { ; }

MCU ID документирован для ATMega328PB, но функция чтения работает и на других, только неизвестно насколько корректно. На различных 328-х ID были разные.
void ID() {
  // Note: Unique MCU ID specified ATMega328PB and may not exist or correct on other MCU's.

  // Interrupts must be disabled before boot_signature_byte_get will be called to avoid code execution break
  uint8_t i, sByte;

  Serial.print(F("MCU ID = "));
  noInterrupts();
  for (i = 0x0E ; (0x0E + 10) > i; i++) {
    sByte = boot_signature_byte_get(i);
    if (sByte < 16) Serial.print("0");
    Serial.print(sByte, HEX);
    Serial.print((char) 0x20);
  }
  interrupts();
  Serial.println();
}

P.S. Кстати, по ссылке, что выше постами, скетчем в статье температура на Micro отдается похожей на правду - 32C.

 

кудрявый
Offline
Зарегистрирован: 14.12.2017

Последняя версия в 168-ю не влазит.. в мониторе краказяберы (

Chekhov
Offline
Зарегистрирован: 30.12.2017

Я тут потуплю, конечно, и попрошу таки ответить. Может, кто для arduino DUE скетч для чтения/записи всех её портов выложит. Многие люди, купившие такую плату, перед тем, как подтвердить её получение, смогут своевременно произвести проверку покупки с помощью такого скетча. Заодно станет меньше отзывов о товаре, подобных "всё отлично. Получил, но пока не проверил. На вид всё хорошо.".

P.S.: Желающие устроить дедовщину и страждущие на нищих, новичках, студентах, и им подобных категориях людей баблишко поднять - лесом идите, - и вам спокойнее, и карму не испортите :)

 

Plasteroid
Plasteroid аватар
Offline
Зарегистрирован: 15.07.2020

Chekhov пишет:

Я тут потуплю, конечно, и попрошу таки ответить. Может, кто для arduino DUE скетч для чтения/записи всех её портов выложит. Многие люди, купившие такую плату, перед тем, как подтвердить её получение, смогут своевременно произвести проверку покупки с помощью такого скетча. Заодно станет меньше отзывов о товаре, подобных "всё отлично. Получил, но пока не проверил. На вид всё хорошо.".

P.S.: Желающие устроить дедовщину и страждущие на нищих, новичках, студентах, и им подобных категориях людей баблишко поднять - лесом идите, - и вам спокойнее, и карму не испортите :)

 

А "блинк "из примеров чем вам не подходит?

b707
Offline
Зарегистрирован: 26.05.2017

Chekhov пишет:

 Может, кто для arduino DUE скетч для чтения/записи всех её портов выложит.

Запишешь единицу в порт - а что дальше? Внешне это никак не видно. Как проверять-то будешь? К каждому пину свой светодиод припаивать?

Еще интереснее с чтением. Что читать то будем с пустых пинов?

Так что по факту, дядя, твоя задумка не только наивная (напишите мне код, хаха) - но еще и бестолковая

 

Chekhov
Offline
Зарегистрирован: 30.12.2017

b707 пишет:
Так что по факту, дядя, твоя задумка не только наивная (напишите мне код, хаха) - но еще и бестолковая
При всём уважении к вашим знаниям, предложу впредь читать пост полностью, до последнего знака препинания, а не только то, что хочется.

Возможно, с формулировкой что-то не так у меня, можно и подкорректировать было.

Смысл не понятен? - получил покупатель плату BMS 5ch, а часть ячеек аккумуляторов ещё месяца 1.5-2 в пути будут. Как проверить BMS, как вернуть свои через спор, если BMS неисправна? Никак.

В случае с платой arduino нет же нужды ждать компоненты необходимые для проверки работоспособности всех её портов, можно провести хотя-бы простой их опрос. Чьи-то амбиции, (или что там ещё обычно) не помешали появиться на этом форуме такому коду: http://arduino.ru/forum/apparatnye-voprosy/szheg-arduino-nano-est-smysl-chinit#comment-22427

 

Jeka_M
Jeka_M аватар
Offline
Зарегистрирован: 06.07.2014

Зачем ждать кого-то, возьмите да сами напишите скетч. А потом сюда выложите, людям польза будет.

Chekhov
Offline
Зарегистрирован: 30.12.2017

Jeka_M пишет:
Зачем ждать кого-то, возьмите да сами напишите скетч. А потом сюда выложите, людям польза будет.

Есть у Антона Павловича изречение, вложенное им в уста его персонажа, Дмитрия Ионовича Старцева: "Есть люди, не умеющие писать романы, и есть люди, не умеющие скрыть этого.".

Естественно выложу, когда будет такой, своими знаниями всегда стараюсь делиться с интересующимися, зачастую на безвозмездной основе. Специалист и сам часто быстрее разберется, иногда просто надо, как говаривал @Starichok снять "... с тормозов инерции мышления...", а новичок, или просто желающий повторить тот, или иной проект на arduino, в написание кода не полезет, новичку и на других этапах граблей хватит.

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

P.S.: Или я неправильно вас имел неосторожность уразуметь?

Jeka_M
Jeka_M аватар
Offline
Зарегистрирован: 06.07.2014

Это всё отмазки и отговорки. Так и скажите, что не хотите реализовать этот полезный проект и поделиться с сообществом.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Chekhov пишет:

b707 пишет:
Так что по факту, дядя, твоя задумка не только наивная (напишите мне код, хаха) - но еще и бестолковая
При всём уважении к вашим знаниям, предложу впредь читать пост полностью, до последнего знака препинания, а не только то, что хочется.

Возможно, с формулировкой что-то не так у меня, можно и подкорректировать было.

Смысл не понятен? - получил покупатель плату BMS 5ch, а часть ячеек аккумуляторов ещё месяца 1.5-2 в пути будут. Как проверить BMS, как вернуть свои через спор, если BMS неисправна? Никак.

В случае с платой arduino нет же нужды ждать компоненты необходимые для проверки работоспособности всех её портов, можно провести хотя-бы простой их опрос. Чьи-то амбиции, (или что там ещё обычно) не помешали появиться на этом форуме такому коду: http://arduino.ru/forum/apparatnye-voprosy/szheg-arduino-nano-est-smysl-chinit#comment-22427

Сэр понимает разницу между терминами port и GPIO?

Так вот, программка по ссылке занимается проверкой именно GPIO, но никак не портов.

Опять же, кто мешает воспользоваться этой программкой для Arduino Due?

Ну и, наконец, в микроконтроллере кроме GPIO есть еще масса интересных и полезных вещей:

- память оперативная,

- flash-память,

- EEPROM,

- аналогово-цифровые и цифро-аналоговые преобразователи,

- таймеры,

- контроллер прерываний,

- контроллер ПДП, 

- масса аппаратных интерфейсов: UART, I2C, SPI, CAN...

...

да даже по поводу GPIO - у меня вот есть контроллер, который на одном выводе в качестве логического нуля вместо 0.2 В выдает 1.3 В. Для КМОП логики это, вроде, безразлично, для ТТЛ - под вопросом, а для запирания транзистора - явно недостаточно. Так что эта "простейшая программка" даже GPIO полностью проверить не сможет.

 

Поэтому подтверждаю: идея наивная и бестолковая.

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

rkit
Offline
Зарегистрирован: 23.11.2016

GPIO проверить можно - нужно просто позамыкать их друг на друга + пара резисторов конденсаторов + пара месяцев на разработку (вот тут наш халявщик и пролетает). И протоколы так же можно проверить, и таймеры друг с другом сравнить и с полученным от компа сигналом, и память забить разными значениями можно. Только это еще минимум полгода.

Chekhov
Offline
Зарегистрирован: 30.12.2017

rkit пишет:

(вот тут наш халявщик и пролетает).

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

andriano пишет:

Сэр понимает разницу между терминами port и GPIO?

Так вот, программка по ссылке занимается проверкой именно GPIO, но никак не портов.

Сэров не встречал, сам из народа. Я разницу понимаю, с формулировками иногда бывает затык.

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

Итог: желающие потрындеть - вэлкам! пусть и в этой теме среди флуда и показательных Я-каний сложно станет найти полезную информацию :)

rkit
Offline
Зарегистрирован: 23.11.2016

Chekhov пишет:

rkit пишет:

(вот тут наш халявщик и пролетает).

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

Да? Замечательно! Жду коммерческого предложения.

Green
Онлайн
Зарегистрирован: 01.10.2015

andriano пишет:

Сэр понимает разницу между терминами port и GPIO?

А не один ли фиг? Что PB0, что GPIO0? Чисто терминология.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Кирпич и паровоз - тоже разница чисто терминологическая (в смысле разные термины).

Green
Онлайн
Зарегистрирован: 01.10.2015

У некоторых малоногих, где io порт всего один, его именуют GPIO, у других присваивают буковки. А вот разницы абсолютно никакой.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Нет никакой разницы между логическим устройством и физическим?

nik182
Offline
Зарегистрирован: 04.05.2015

andriano пишет:

... Сэр понимает разницу между терминами port и GPIO?  ...

Как индийские программисты назовут в их мануалах так и будет. Открываем мануал AVR читаем I/O-Ports ...All AVR ports have true Read-Modify-Write functionality... Открываем STM32 мануал : GPIOs (general-purpose inputs/outputs)... Each of the GPIO pins can be configured by software as output (push-pull or open-drain), as input (with or without pull-up or pull-down) or as peripheral alternate function. 

Ну в чем разница? Ноги процессора. Функционал почти одинаков. Названия разные. 

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

nik182 пишет:

andriano пишет:

... Сэр понимает разницу между терминами port и GPIO?  ...

Как индийские программисты назовут в их мануалах так и будет. Открываем мануал AVR читаем 

1.

Цитата:
I/O-Ports ...All AVR ports have true Read-Modify-Write functionality...

Открываем STM32 мануал : 

2.

Цитата:
GPIOs (general-purpose inputs/outputs)... Each of the GPIO pins can be configured by software as output (push-pull or open-drain), as input (with or without pull-up or pull-down) or as peripheral alternate function.

Ну в чем разница? Ноги процессора. Функционал почти одинаков. Названия разные. 

А ничего, что в первом случае речь идет о портах (т.е. логических устройствах, находящихся в адресном пространстве портов ввода-вывода процессора), а во втором - о пинах (аппаратных выводах микросхемы, которые могут служить электрическими входами или выходами)?

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

nik182
Offline
Зарегистрирован: 04.05.2015

Идем дальше, цитата AVR : Each port pin consists of three register bits: DDxn, PORTxn, and PINxn. As shown in the Register Description, the DDxn bits are accessed at the DDRx I/O address, the PORTxn bits at the PORTx I/O address, and the PINxn bits at the PINx I/O address.

Достаточно было Each port pin consists of three register bits... и для STM : Each of the GPIO pins can be configured by software. 

Так где разница? И там и там пины, которые конфигурятся регистрами. Только одни называют этот конгломерат регистров и железных ног портом , а другие входами-выходами общего назначения. 

Назовите хоть один порт, который управляет таймерами? 

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

nik182 пишет:

Назовите хоть один порт, который управляет таймерами? 

TIMx_CR1, TIMxCR2, TIMx_DIER...