DS3231 и CodevisionAVR

На просторах интернета не так много рабочего кода для связки DS3231 и Codevision AVR, хочу показать свой рабочий вариант.

Подключаются эти часы точно так жк как и DS1307, V+ 5в, GND, SDA, SCL.

А вот распределение памяти по ячейкам у них немного другое.

Соответственно ячейка 0х00 это секунды, 0х01 минуты, 0х03 часы и т.д.

Ну а теперь рабочий код

//**блок который нужно добавить в переменные**//
// дефайны адресов микросхемы
#define RTC_adr_write 0b11010000
#define RTC_adr_read  0b11010001
// переменные времени
unsigned char hour23;
unsigned char minute23;
unsigned char sec23;
// переменные даты
unsigned char day;
unsigned char wday;
unsigned char month;
unsigned char year;
// переменные температуры
unsigned int  temp;
unsigned char t1;
unsigned char t2;
//**блок который нужно добавить в переменные**//
/** необходимые библиотеки**/  
#include "bcd.h" //библиотека работы с BCD
#include <i2c.h> //библиотека i2c
//** необходимые библиотеки**// 
//** функции преобразования чисел (для корректного отображения значений)**/
unsigned char bcd (unsigned char data)
{
unsigned char bc;
bc=((((data&(1<<6))|(data&(1<<5))|(data&(1<<4)))*0x0A)>>4)+((data&(1<<3))|(data&(1<<2))|(data&(1<<1))|(data&0x01));
return bc;
}
unsigned char bin(unsigned char dec){
char bcd;
char n, dig, num, count;
num = dec;
count = 0;
bcd = 0;
for (n=0; n<4; n++) {
dig = num%10;
num = num/10;
bcd = (dig<<count)|bcd;
count += 4;
}
return bcd;
}
//** функции преобразования чисел (для корректного отображения значений)**//
//**функции с часами**//
// инициализация начальных установок
void RTC_init(void){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи 
i2c_write(0x0E);	        // передача адреса памяти
i2c_write(0b00100000);      // запустить преобразование температуры и выход на 1 Гц
i2c_write(0b00001000);      // разрешить выход 32 кГц
i2c_stop();                // остановка i2c
}
// получение времени и даты
void RTC_read_time(void){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x00);	     // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
sec23 = bcd(i2c_read(0));     // чтение секунд, ACK
i2c_stop();                  // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x01);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
minute23 = bcd(i2c_read(0));     // чтение минут, ACK
i2c_stop();                 // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x02);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
hour23 = bcd(i2c_read(0));     // чтение часов, ACK
i2c_stop();
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x03);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
wday = bcd(i2c_read(0));    // чтение день недели, ACK
i2c_stop();
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x04);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
day = bcd(i2c_read(0));     // чтение число, ACK
i2c_stop();
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x05);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
month = bcd(i2c_read(0));   // чтение месяц, ACK
i2c_stop();
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x06);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
year = bcd(i2c_read(1));    // чтение год, NACK
i2c_stop();
}
//**установка времени**//
void RTC_write_minute23(unsigned char min1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x01);	        // 0x01 минуты
i2c_write(bin(min1));
i2c_stop();                // остановка i2c
}
void RTC_write_hour23(unsigned char hour1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x02);	        // 0x02 часы
i2c_write(bin(hour1));
i2c_stop();                // остановка i2c
}
void RTC_write_sec23(unsigned char sec1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x00);	        // 0x00 секунды
i2c_write(bin(sec1));
i2c_stop();                // остановка i2c
}
//**установка времени**//
//** установка даты**//
void RTC_write_wday23(unsigned char wday1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x03);	        // 0x01 минуты
i2c_write(bin(wday1));
i2c_stop();                // остановка i2c
} 
void RTC_write_day23(unsigned char day1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x04);	        // 0x01 минуты
i2c_write(bin(day1));
i2c_stop();                // остановка i2c
} 
void RTC_write_month23(unsigned char month1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x05);	        // 0x01 минуты
i2c_write(bin(month1));
i2c_stop();                // остановка i2c
}  
void RTC_write_year23(unsigned char year1){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x06);	        // 0x01 минуты
i2c_write(bin(year1));
i2c_stop();                // остановка i2c
}     
//** установка даты**//
//**чтение температуры**//
void RTC_read_temper(void){
i2c_start();               // запуск i2c
i2c_write(RTC_adr_write);   // передача адреса устройства, режим записи
i2c_write(0x11);	        // передача адреса памяти
i2c_stop();                // остановка i2c
i2c_start();               // запуск i2c
i2c_write(RTC_adr_read);    // передача адреса устройства, режим чтения
t1 = i2c_read(0);           // чтение MSB температуры
t2 = i2c_read(1);           // чтение LSB температуры
i2c_stop();                // остановка i2c
t2=(t2>>7); 					// сдвигаем на 6 - точность 0,25 (2 бита)
// сдвигаем на 7 - точность 0,5 (1 бит)
t2=t2*5;
}
//**чтение температуры**//
//**функции с часами**//
//** в void main добавим инициализацию **//
RTC_init();
//** в void main добавим инициализацию **//

А тут рассмотрим примеры вызова:

RTC_read_time (); // считаем время и дату

RTC_write_hour23(X); // запишем новое значение в часы

RTC_write_minute23(X); // запишем новое значение в минуты

DS3231 и CodevisionAVR: 7 комментариев

  1. Валерий

    Добрый день сделал для визарта но не работает
    Записываю значения вот так

    RTC_write_hour23(0); // запись часов
    RTC_write_minute23(0); // запись минут
    RTC_write_sec23(0);//запись секунд

    RTC_write_wday23(0); //запись дней недели
    RTC_write_day23(0); //запись числа
    RTC_write_month23(0); //запись месяца
    RTC_write_year23(0); // запись года

    while (1)
    {
    RTC_read_time (); // выводим время и дату

  2. Валерий

    Добрый день сделал для визарта но не правильно показания и почему секунды не идут?
    Записываю значения вот так

    RTC_write_hour23(13); // запись часов
    RTC_write_minute23(55); // запись минут
    RTC_write_sec23(33);//запись секунд

    RTC_write_wday23(2); //запись дней недели
    RTC_write_day23(23); //запись числа
    RTC_write_month23(4); //запись месяца
    RTC_write_year23(19); // запись года

    while (1)
    {
    RTC_read_time (); // выводим время и дату
    }

    и зачем нужна функция

    //** функции преобразования чисел (для корректного отображения значений)**/
    unsigned char bcd (unsigned char data)
    {
    unsigned char bc;
    bc=((((data&(1<<6))|(data&(1<<5))|(data&(1<>4)+((data&(1<<3))|(data&(1<<2))|(data&(1<<1))|(data&0x01));
    return bc;
    }
    unsigned char bin(unsigned char dec){
    char bcd;
    char n, dig, num, count;
    num = dec;
    count = 0;
    bcd = 0;
    for (n=0; n<4; n++) {
    dig = num%10;
    num = num/10;
    bcd = (dig<<count)|bcd;
    count += 4;
    }
    return bcd;
    }

  3. Валерий

    дошло как сделать секунды
    надо RTC_read_time (); // выводим время и дату опрашивать в бесконечном цикле но ПОЧЕМУ СЕКУНДЫ СЧИТАЮТ ДО 90 А ПОТОМ СБРАСЫВАЮТСЯ????????????????????????????????

  4. Валерий

    Проблема с выводом
    //** функции преобразования чисел (для корректного отображения значений)**/
    unsigned char bcd (unsigned char data)

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *