Перейти к содержанию

AtTiny13 + DHT11 + TM1637. Загадочное поведение.


Krendelyok

Рекомендуемые сообщения

Написал код для работы AtTiny13, DHT11, TM1637. Всё удачно уместилось в памяти микрухи. На первый взгляд всё работает. Данные передаются без сбоев, контрольная сумма в норме. Вот видео, если кому интересно. Но обнаружилась проблема. Периодически, примерно каждые 5-6 запросов данных от датчика DHT11, показания влажности и температуры скачут. На 5 - 10 единиц могут прыгнуть. При этом рассогласования с контрольной суммой нет. Поначалу списал всё на "несерьезность" датчика, но... Залил тот же самый код в Ардуино Уно - нет никаких скачков. Цепляю датчик и дисплей обратно к тиньке - пляшут данные. Подключаю питание непосредственно от этой ардуинки - не помогает, скачут показания. Припаиваю непосредственно к датчику конденсатор по питанию 100 нФ, как рекомендуется в даташите, - бесполезно. Меняю на тиньке частоты: 1.2, 4.8, 9,6 Мгц - никакого результата. Кстати, по ходу дела, заметил еще одну странность: на 9.6 Мгц тинька в этой связке запускается только от 3 вольт, от пяти - не хочет. На дисплей при этом нужно подавать 5 вольт. В общем, у меня закончились предположения, пришел за помощью к вам. В чем подвох может быть, ведь на ардуинке с тем же питанием показания стабильны?

Код:

Скрытый текст

#define F_CPU 1200000LU
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include <avr/wdt.h> 

unsigned char word_dht = 0x00;
unsigned char time_bit[40];
unsigned char data_dht[5];
unsigned char bit_dht;


#define Clkpin 3 //Clkpin TM1637
#define Datapin 2 // Datapin TM1637
#define PIN_DHT 0 //Пин датчика DHT

#define DispPort PORTB // обзываем порт

#define  BRIGHT_LCD 7  //Яркость дисплея от 0 до 7
		
		unsigned char _PointFlag; 	//_PointFlag=1:the clock point on
		unsigned char _DispType;
		unsigned char DecPoint;
		unsigned char BlankingFlag;
	
		
static unsigned char TubeTab[10] = {0x3f,0x06,0x5b,0x4f,// знакогенератор
                           0x66,0x6d,0x7d,0x07,
                           0x7f,0x6f};//,0x77,0x7c,
                           //0x39,0x5e,0x79,0x71,
                          // 0x40,0x00};//0~9,A,b,C,d,E,F,"-"," "  

void TM1637_writeByte(char wr_data)// служебная функция записи данных по протоколу I2C, с подтверждением (ACK)
{
  unsigned char i;
    for(i=0;i<8;i++)        
  {
   DispPort &= ~(1<<Clkpin);
    if(wr_data & 0x01)
	{ DispPort |= 1<<Datapin;}
    else {DispPort &= ~(1<<Datapin);}
	_delay_us(3);
    wr_data = wr_data>>1;      
    DispPort |= 1<<Clkpin;
	_delay_us(3);  
  }  
 
  DispPort &= ~(1<<Clkpin);
  _delay_us(5);
  DDRB &= ~(1<<Datapin);// если поменяете порт на какой-то другой кроме DispPort, то тут тоже все DDRB на другие DDRx менять надо будет
  while((PINB & (1<<Datapin))); 
  DDRB |= (1<<Datapin);
  DispPort |= 1<<Clkpin;
  _delay_us(2);
  DispPort &= ~(1<<Clkpin);  
}

void TM1637_start(void) // просто функция "старт" для протокола I2C
{
   DispPort |= 1<<Clkpin; 
   DispPort |= 1<<Datapin;
 _delay_us(2);
  DispPort &= ~(1<<Datapin); 
} 

void TM1637_stop(void) // просто функция "стоп" для протокола I2C
{
  DispPort &= ~(1<<Clkpin);
 _delay_us(2);
  DispPort &= ~(1<<Datapin);
_delay_us(2);
  DispPort |= 1<<Clkpin;;
_delay_us(2);
  DispPort |= 1<<Datapin;
}


void TM1637_init()// Инициализируем дисплей. Как оказалось, можно удалить из этого блока стандартной библиотеки практически всё, кроме инициализации пинов.
{
	DDRB |= (1<<Clkpin) | (1<<Datapin);
}

//---------------------------------------------------------------------
//Здесь код для датчика DHT11. Писал полностью сам.

void start_tmr_us()
{
TCNT0 = 0x00;
TCCR0B = 0x01; //Запускаем таймер0 с частотой 1,2 Мгц
}

void start_dht()                //Отправляем приветствие датчику
{
DDRB |= (1 << PIN_DHT);
DispPort |= (1 << PIN_DHT);
DispPort &= ~(1 << PIN_DHT);
_delay_ms(18);
DDRB &= ~(1 << PIN_DHT);
DispPort |= (1 << PIN_DHT);
while(PINB & (1 << PIN_DHT)){}
while(~PINB & (1 << PIN_DHT)){}
while(PINB & (1 << PIN_DHT)){}

}

void get_data()                            //Получаем 40 бит от датчика и записываем в массив
{
for(bit_dht = 0; bit_dht < 40; bit_dht++)
{
while(~PINB & (1 << PIN_DHT)){}
start_tmr_us();
while(PINB & (1 << PIN_DHT)){}
time_bit[bit_dht] = TCNT0;
}
}

void decoder_bit(){
unsigned char bit_number = 1;
unsigned char word_number = 0;
for(bit_dht = 0; bit_dht < 40; bit_dht++){  //дербаним наш массив из 40 бит (5 байтов), в котором записана длительность каждого полученного  бита

if(time_bit[bit_dht] > 50)                //Если длительность бита больше 28 мкс,
{
word_dht = word_dht << 1;            //сдвигаем байт влево и записываем в младший разряд 1
word_dht |= (1 << 0);
}else
{
word_dht = word_dht << 1;        //Если меньше 28 мкс, сдвигаем влево байт и записываем 0
word_dht &= ~(1 << 0);
}

if(bit_number == 8){                     //Если имеем дело с восьмым битом, записываем полученный байт в массив
data_dht[word_number] = word_dht;
word_number += 1;
bit_number = 0;       
}
bit_number +=1;
}
}



ISR (WDT_vect){
TM1637_writeByte(0x40);    //Выводим на дисплей Err1
TM1637_stop();
TM1637_start();
TM1637_writeByte(0xC0);
TM1637_writeByte(0x79);
TM1637_writeByte(0x50);
TM1637_writeByte(0x50);
TM1637_writeByte(0x06);
TM1637_stop();
TM1637_start();
TM1637_writeByte(0x8F);
TM1637_stop();
}




int main(void)
{
wdt_reset();            //Запускаем вотч дог
wdt_enable(WDTO_4S);
WDTCR |= (1 << WDTIE);
sei();
TM1637_init();
_delay_ms(500);  //Зачем-то тупим немного. Иначе, вроде как, дисплей может не зажечься.
 
while(1)
{
start_dht();                         
get_data();
decoder_bit();
if((data_dht[0] + data_dht[1] + data_dht[2] + data_dht[3]) != data_dht[4])
{
	TM1637_writeByte(0x40);    //Выводим на дисплей Err0
	TM1637_stop();
	TM1637_start();
	TM1637_writeByte(0xC0);
	TM1637_writeByte(0x79);
	TM1637_writeByte(0x50);
	TM1637_writeByte(0x50);
	TM1637_writeByte(0x3f);
	TM1637_stop();
	TM1637_start();
	TM1637_writeByte(0x8F);
	TM1637_stop();
	_delay_ms(3500);
	wdt_reset();
	_delay_ms(3500);
	wdt_reset();	
}

TM1637_start();                     //Выводим на дисплей влажность.  
TM1637_writeByte(0x40);
TM1637_stop();
TM1637_start();
TM1637_writeByte(0xC0);
TM1637_writeByte(0x76);
TM1637_writeByte(0x00);
TM1637_writeByte(TubeTab[(data_dht[0] / 10) % 10]);
TM1637_writeByte(TubeTab[data_dht[0] % 10]);
TM1637_stop();
TM1637_start();
TM1637_writeByte(0x8F);
TM1637_stop();
_delay_ms(2000);
wdt_reset();

TM1637_start();                                    //Выводим на дисплей температуру
TM1637_writeByte(0x40);
TM1637_stop();
TM1637_start();
TM1637_writeByte(0xC0);
TM1637_writeByte(TubeTab[(data_dht[2] / 10) % 10]);
TM1637_writeByte(TubeTab[data_dht[2] % 10]);
TM1637_writeByte(0x63);
TM1637_writeByte(0x39);
TM1637_stop();
TM1637_start();
TM1637_writeByte(0x8F);
TM1637_stop(); 
_delay_ms(2000);
wdt_reset();
}
}

 

 

Изменено пользователем Krendelyok
Опечатки
Ссылка на комментарий
Поделиться на другие сайты

Реклама: ООО ТД Промэлектроника, ИНН: 6659197470, Тел: 8 (800) 1000-321

   Здравствуйте!  Зашел на вашу тему чтоб набраться опыта, и не претендую на осознания всего вашего кода, но с моей колокольни бросается в глаза обозначение частоты кварца, F_CPU 1200000LU.  Для меня сочетание  LU ново, может это то чего я еще не знаю, но обычно в просматриваемых  мной кодах частота обозначается (в вашем случае), F_CPU 1200000UL.

Ссылка на комментарий
Поделиться на другие сайты

20% скидка на весь каталог электронных компонентов в ТМ Электроникс!

Акция "Лето ближе - цены ниже", успей сделать выгодные покупки!

Плюс весь апрель действует скидка 10% по промокоду APREL24 + 15% кэшбэк и бесплатная доставка!

Перейти на страницу акции

Реклама: ООО ТМ ЭЛЕКТРОНИКС, ИНН: 7806548420, info@tmelectronics.ru, +7(812)4094849

В 15.07.2015 в 03:07, codecity сказал:

 

Это да. Скорее всего, я что-то перепутал. Но компилятор, видимо, справляется  с этой ошибкой) Частота правильно работает.

Ссылка на комментарий
Поделиться на другие сайты

Выбираем схему BMS для корректной работы литий-железофосфатных (LiFePO4) аккумуляторов

 Обязательным условием долгой и стабильной работы Li-FePO4-аккумуляторов, в том числе и производства EVE Energy, является применение специализированных BMS-микросхем. Литий-железофосфатные АКБ отличаются такими характеристиками, как высокая многократность циклов заряда-разряда, безопасность, возможность быстрой зарядки, устойчивость к буферному режиму работы и приемлемая стоимость. Но для этих АКБ, также как и для других, очень важен контроль процесса заряда и разряда, а специализированных микросхем для этого вида аккумуляторов не так много. Инженеры КОМПЭЛ подготовили список имеющихся микросхем и возможных решений от разных производителей. Подробнее>>

Реклама: АО КОМПЭЛ, ИНН: 7713005406, ОГРН: 1027700032161

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

Ссылка на комментарий
Поделиться на другие сайты

22 часа назад, Alex сказал:

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

Я просто на нескольких форумах советуюсь. Вопрос то сложный. Не для таких, как ты, неучей)

Изменено пользователем Krendelyok
Ссылка на комментарий
Поделиться на другие сайты

1 минуту назад, andryxa сказал:

И ты думаешь после этого тебе кто-то будет помогать?

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

Изменено пользователем Krendelyok
Ссылка на комментарий
Поделиться на другие сайты

Ну давай, обосри и этот форум, до кучи :) Что тебе тут никто не помогает и никто тебя не понимает...

Вопросы нужно нормально задавать, тогда и ответы будут нормальными.
 

1 час назад, Krendelyok сказал:

Вопрос то сложный

Какой вопрос сложный, "В чем подвох может быть ?" ? 
Такие вопросы могут задавать только подобные тебе безмозглые существа :)
 

Ссылка на комментарий
Поделиться на другие сайты

Гость
Эта тема закрыта для публикации ответов.
  • Последние посетители   0 пользователей онлайн

    • Ни одного зарегистрированного пользователя не просматривает данную страницу
×
×
  • Создать...