Форум программистов, компьютерный форум, киберфорум
Наши страницы
Микроконтроллеры Atmega AVR
Войти
Регистрация
Восстановить пароль
 
GaFBich
22 / 22 / 5
Регистрация: 18.03.2010
Сообщений: 308
#1

ATtiny2313 реализация программного I2C для работы с датчиком LM75A - Atmega AVR микроконтроллер

08.11.2015, 20:20. Просмотров 1972. Ответов 8
Метки нет (Все метки)

Появилась необходимость в реализации программного I2C. Смотрел в "Вики" вроде все понятно, но в итоге должного результата получить не удалось. Буду рад если сможете объяснить что по чем.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
08.11.2015, 20:20
Я подобрал для вас темы с готовыми решениями и ответами на вопрос ATtiny2313 реализация программного I2C для работы с датчиком LM75A (Atmega AVR микроконтроллер):

ATmega8 + TWI, aka I2C (с датчиком LM75A) зависает.
Собрал термостат такой на ATmega8 с датчиком LM75A. частота шины I2C - 200 кГц....

I2C Attiny2313
Возникла необходимость воспользоваться шиной I2C. С самой шиной разобрался....

attiny2313 i2c slave
Доброго времени суток! Мне необходимо связать по шине I2C ATMEGA328 в режиме...

I2c на Attiny2313 посредством USI
Всем привет! на pinboard ll имеется еепром. Хотел бы пообщаться с ней, а в...

ATtiny2313 и алгоритм работы программы
Добрый вечер! Нужно написать алгоритм работы программы, код довольно тяжелый,...

Программа для ATtiny2313
/* * AVRGCC3.c * * Created: 02.02.2012 8:42:25 * Author: User */ ...

8
Витальич
1253 / 1164 / 172
Регистрация: 02.12.2013
Сообщений: 4,845
08.11.2015, 20:28 #2
Выкладывайте свой код, посмотрим.
0
GaFBich
22 / 22 / 5
Регистрация: 18.03.2010
Сообщений: 308
08.11.2015, 22:11  [ТС] #3
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
#define SDA_H PORTB|=(1<<PB1)
#define SDA_L PORTB&=(~(1<<PB1))
#define SCL_H PORTB|=(1<<PB2)
#define SCL_L PORTB&=(~(1<<PB2))
 
 
 
void START(void)
    {
    SCL_H;
    _delay_us(10);
    SDA_H;
    _delay_us(10);
    SDA_L;
    }
 
void STOP(void)
    {
    SCL_H;
    _delay_us(10);
    SDA_H;
    _delay_us(10);
    }
 
int I2C_Send8(unsigned char data)
    {
    DDRB|=(1<<PB1);//Output
    START();
    _delay_us(10);
        for(int i=0;i<8;i++)
            {
            if(data&0x80)
                {
                SCL_L;
                _delay_us(5);
                SDA_H;
                }
            else
                {
                SCL_L;
                _delay_us(5);
                SDA_L;
                }
            _delay_us(5);
            SCL_H;
            data<<=1;
            }
    DDRB&=(~(1<<PB1));//Input
    PORT|=(1<<PB1);//Pull_up
    _delay_us(5);
    SCL_L;
    _delay_us(5);
    SCL_H;
    if(PINB&(1<<PB1)==0)
        return 0;//ACK
    else
        return 1;//NACK
    STOP();
    }
Код примерно такой (набросал в блокноте)
0
Витальич
1253 / 1164 / 172
Регистрация: 02.12.2013
Сообщений: 4,845
08.11.2015, 22:26 #4
Где то я что то похожие видел
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
/#######################################################################################################################
//#
//# ФУНКЦИИ ОБСЛУЖИВАНИЯ ИНТЕРФЕЙСА I2C (софтовый вариант)
//#
//#######################################################################################################################
 
    //настройка порта IIC
    #define IICDDR                DDRC                /*порт управления I2C*/
    #define IICPORT                PORTC                /*порт вывода данных на линию I2C*/
    #define IICPIN                PINC                /*порт ввода данных с линий I2C*/
    #define IICData                (1<<4)                /*линия DATA*/
    #define IICClc                (1<<5)                /*линия CLC*/
 
//ФУНКЦИЯ ФОРМИРОВАНИЯ СОСТОЯНИЯ START ПО ИНТЕРФЕЙСУ IIC
void IICStart (void)
{
    IICDDR &= ~(IICData | IICClc);
    _delay_us (2);
    IICDDR |= IICData;                            //подтяжка data к нулю
    _delay_us (2);
    IICDDR |= IICClc;                            //подтяжка clc к нулю
    _delay_us (2);
}
 
 
//ФУНКЦИЯ ФОРМИРОВАНИЯ СОСТОЯНИЯ STOP ПО ИНТЕРФЕЙСУ IIC
void IICStop (void)
{
    IICDDR |= (IICData | IICClc);
    _delay_us (2);
    IICDDR &= ~IICClc;                            //подтяжка data к нулю
    _delay_us (2);
    IICDDR &= ~IICData;                            //подтяжка clc к нулю
    _delay_us (2);
}
 
//ФУНКЦИЯ ЗАПИСИ БАЙТА ПО ИНТЕРФЕЙСУ IIC
//АРГУМЕНТ - байт данных для вывода по IIC
//ЗНАЧЕНИЕ - флаг подтверждения 0 (есть подтверждение) или 1 (нет подтверждения) 
char IICByteWrite (char byte)
{
    for (char i = 0; i<8; i++)
        byte = IICBit (byte);
    byte = 0x80;                                
    return IICBit (byte);                        //возвращаем бит подтверждения (0-есть бит подтверждения, 1-нет)
}
 
//ФУНКЦИЯ ЧТЕНИЯ БАЙТА ПО ИНТЕРФЕЙСУ IIC
//АРГУМЕНТ - значение бита подтверждения (0 - есть подтверждение, 1 - нет подтверждения)
//ЗНАЧЕНИЕ - принятый байт
char IICByteRead (char bit)
{
    char byte = 0xFF;
    for (char i = 0; i<8; i++)
        byte = IICBit (byte);
    bit <<= 7;
    IICBit (bit);                                //передать значение бита подтверждения
    return byte;                                //возвращаем принятый байт
}
 
//ФУНКЦИЯ ЗАПИСИ\ЧТЕНИЯ БИТА ПО ИНТЕРФЕЙСУ IIC
//выводится значение старшего бита аргумента
//принятый бит возвращается в младшем бите предварительно сдвинутого влево аргумента
char IICBit (char byte)                        
{
    if (byte & 0x80)                        //выводимый бит
        IICDDR &= ~IICData;                 //вывод 1 на линию данных
    else 
        IICDDR |= IICData;                    //вывод 0 на линию данных
    _delay_us (2);
    IICDDR &= ~IICClc;                        //старт строб импульса
    while (! (IICPIN & IICClc)){}            //ожидание формирования строба
    _delay_us (2);
    char temp;    
    if (IICPIN & IICData)                    //принимаем бит
        temp = 1;
    else
        temp = 0;
    IICDDR |= IICClc;                        //завершить строб
    byte <<= 1;
    byte |= temp;
    return byte;
}
не моё, с просторов рунета, автор утверждает что рабочий
1
GaFBich
22 / 22 / 5
Регистрация: 18.03.2010
Сообщений: 308
08.11.2015, 22:43  [ТС] #5
Хм, я вот чего понять не могу, по всей видимости в реализации данного протокола необходимо "работать" вольтдобавкой?! Вроде все просто - но мудрено!
0
Витальич
1253 / 1164 / 172
Регистрация: 02.12.2013
Сообщений: 4,845
08.11.2015, 22:46 #6
по спецификации I2C имеет открытый коллектор на обоих шинах, так что должны быть резисторы подтяжки до питания.
0
GaFBich
22 / 22 / 5
Регистрация: 18.03.2010
Сообщений: 308
08.11.2015, 22:54  [ТС] #7
Испробовал данный код, что Вы предоставили, протеус в упор не хочет показывать обмен, осциллограф молчит)))))


Сорри, про подтяжку к питанию забыл!
0
Витальич
1253 / 1164 / 172
Регистрация: 02.12.2013
Сообщений: 4,845
08.11.2015, 23:02 #8
Я не верю протеусу, хотя бы по тому что если вызвать IICStart (void), то пины щелкнут обязательно.
1. А Вы сконфигурировали пины на выход без подтяжки?
2. А какой Вы считаете адрес у LM75A?
3. А куда подключены адресные пины LM75A?
4. А что Вы подаёте после Start?
Продолжить список вопросов?
Выкладывайте пожалуйста по максимуму информацию если хотите что бы кто то смог ответить.
0
GaFBich
22 / 22 / 5
Регистрация: 18.03.2010
Сообщений: 308
08.11.2015, 23:14  [ТС] #9
Значит так, на данный момент проект на стадии разработки (хотелки в голове), ранее его собирал на Atmega16 (но запускал при помощи аппаратного TWI), все работало, адресация я с ходу не скажу, но делаю проект на DS1621 в протеусе. Выводу у меня на вход, на выход я их не делал, только к земле подтяжкой внутренней прижимает!
Адрес у DS1621, так как он один в цепи, пока один, 1001 A2 A1 A0 бит запись/чтение (0x91), далее команда 0xEE и чтение температуры 0xAA
0
08.11.2015, 23:14
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
08.11.2015, 23:14
Привет! Вот еще темы с решениями:

Инициализация USART для ATtiny2313
Здравствуйте уважаемые форумчане и доброго времени суток. Я пытался...

Контроль ШД для стеклоочистителя на базе МК Attiny2313
Здравствуйте, знатоки. Подскажите пожалуйста. Необходимо организовать подобие...

Библиотека для работы с LCD Motorola T191 (I2C) STM32F051
Привет. Давно обещал - выкладываю... Проверялась на STM32F042 и на...

Программная реализация I2C.
Всем привет. Есть необходимость в реализации софтового I2C - Мастер и Слейв...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru