реклама на сайте
подробности

 
 
> Проблема с TWI
James D.
сообщение Nov 4 2005, 17:14
Сообщение #1


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Соединил 3 МК по TWI - Master передает данные на Slave 1, потом на Slave 2 (поочередно, друг за другом). Два из них общаются нормально (односторонняя передача от Master к Slave 1), а как только нужно передать от Master к Slave 2, один раз передача проходит и все зависает. Судя по всему, после этого не получается передать данные на Slave 1.
В конце каждой передачи Master осуществляет условие STOP
STOP: ldi temp,(1<<TWINT)|(1<<TWSTO)|(1<<TWEN)
out TWCR,temp,
а Slave 1/2, после приема переданных байт, просто переходят к дальнейшему выполнению основной программы, т.е. никаких стоповых функций нет. Должны ли они как-то обрабатывать функцию STOP?

Можно ли в режиме "slave приемник" узнать какой адрес передал "master передатчик", т.е. к кому в данный момент он обращается? Появляется ли этот адрес в TWDR?

Как правильно обратиться к конкретному "slave приемнику", чтобы второй "slave приемник" на вызов не реагировал?
Go to the top of the page
 
+Quote Post
19 страниц V   1 2 3 > »   
Start new topic
Ответов (1 - 14)
James D.
сообщение Nov 5 2005, 15:37
Сообщение #2


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Попробовал отключать от линии приемник, к которому сейчас нет обращения:
ldi temp,(0<<TWEA)
out TWCR,temp
Все равно где-то вся эта лабуда зависает!
У меня Мастер-передатчик - mega32, первый приемник - тоже mega32, второй приемник - mega16.
Выяснил вот что: когда мастер пытается обращаться ко второму приемнику, после посылки сигнала START, они оба зацикливаются:
wait1: in temp,TWCR
sbrs temp,TWINT
rjmp wait1
дальше этого цикла ожидания у них дело не идет. То ли мастер не может START передать, то приемник не может его получить.
В чем же тут проблема?
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Nov 6 2005, 08:18
Сообщение #3


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



Была у меня такая ситуация. Но я забыл поставить на линии резисторы на +5В. У Вас они стоят? По сколько КОм?
И если можно, выложите код, относящийся к TWI.


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 6 2005, 08:43
Сообщение #4


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Резисторы по 4.7кОм стоят на каждой линии (соединяют с +5В).
Привожу пример моих прог приема-передачи.
Передатчик - mega32, приемник - mega16. Передатчик зависает на этапе передачи адреса + W, а приемник зацикливается в цикле wait1n:
Как это все настроить?


Эта прога находится в передатчике:

;*******************************************************************
;Программа передачи байта от мастера подчиненному:

To_SR: ldi temp,$00 ;Установка скорости передачи=22727 Hz
out TWSR,temp
ldi temp,$14
out TWBR,temp

Pusk_Sr: ldi temp,(1<<TWINT)|(1<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp ;Посылка сигнала "START"

wait1r: in temp,TWCR ;Ожидаем ответ от SR-контроллера
sbrs temp,TWINT
rjmp wait1r

in temp,TWSR
andi temp,$F8
cpi temp,$08 ;Проверка подтверждения приема от SR (START)
brne Pusk_Sr

SLA_Wr: ldi temp,$04 ;Загрузка адреса SR-контроллера + "WRITE"
out TWDR,temp
ldi temp,(1<<TWINT)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

wait2r: in temp,TWCR ;Ожидаем ответ от SR-контроллера
sbrs temp,TWINT
rjmp wait2r

in temp,TWSR
andi temp,$F8
cpi temp,$18
brne SLA_Wr ;Переход, если ответ от SR неверный

;Начинаем передавать данные:

DATA_r: out TWDR,Byte ;Отправка байта данных
rcall Writer

rjmp STOP_r ;Передача данных завершена

;*******************************************************************
Writer: ldi temp,(1<<TWINT)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

wait3r: in temp,TWCR ;Ожидаем ответ от SR-контроллера
sbrs temp,TWINT
rjmp wait3r

in temp,TWSR
andi temp,$F8
cpi temp,$28
brne Writer ;Переход, если ответ от SR неверный

ret
;*******************************************************************
;Все данные переданы - STOP (линия приема/передачи переходит в высокоимпедансное состояние)

STOP_r: ldi temp,(1<<TWINT)|(0<<TWSTA)|(1<<TWSTO)|(1<<TWEN)
out TWCR,temp

;*******************************************************************



А эта прога находится в приемнике:

;*******************************************************************
;Программа приема байта от мастера:

From_MT: ldi temp,$04 ;Инициализация режима "Приемник"
out TWAR,temp

TWINT_n: ldi temp,(1<<TWINT)|(1<<TWEA)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

wait1n: in temp,TWCR ;Ожидаем вызова от MT-контроллера
sbrs temp,TWINT
rjmp wait1n

in temp,TWSR
andi temp,$F8
cpi temp,$60 ;Проверка принятого адреса от MT
brne TWINT_n

;Прием данных:

Pr_data: rcall TW_NT_n ;Прием байта
in Byte,TWDR

rjmp STOP_n

;*******************************************************************
TW_NT_n: ldi temp,(1<<TWINT)|(1<<TWEA)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

wait2n: in temp,TWCR ;Ожидаем ответа от MT-контроллера
sbrs temp,TWINT
rjmp wait2n

in temp,TWSR
andi temp,$F8
cpi temp,$80
brne TW_NT_n ;Переход, если данные от MT не получены

ret

;*******************************************************************
;Все данные приняты - STOP (линия приема/передачи переходит в высокоимпедансное состояние)

STOP_n: ldi temp,(1<<TWINT)|(1<<TWEA)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

wait4: in temp,TWCR ;Ожидаем ответа от MT-контроллера
sbrs temp,TWINT
rjmp wait4

in temp,TWSR
andi temp,$F8
cpi temp,$A0
brne STOP_n ;Переход, если STOP от MT не получен

;*******************************************************************
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Nov 6 2005, 10:41
Сообщение #5


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



Цитата
SLA_Wr: ldi temp,$04 ;Загрузка адреса SR-контроллера + "WRITE"
out TWDR,temp
ldi temp,(1<<TWINT)|(0<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp

Не нужно при передачи байта посылать условие старт, нужно заменить строку на эту:
ldi temp,(1<<TWINT)|(1<<TWEN)
это по программе в передатчике, по приемнику - не знаю.
Но советую зайти на www.atmel.com и скачать примеры (application notes), там есть несколько довольно неплохих документов. Я по ним разбирал работу модуля TWI. Кстати где-то ниже должна быть моя ветка "Проблемы TWI".


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 6 2005, 12:44
Сообщение #6


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Да примеры-то эти я уже давно все скачал и просмотрел. Но примеры там на Си, а я его не знаю...
Строку заменил, то же самое: передатчик зависает на этапе передачи адреса + W, а приемник зацикливается в цикле wait1n:
Контроллеры соединены двухжильным проводом, и находятся на расстоянии ~15см. Уже не знаю на что и грешить.
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Nov 6 2005, 14:16
Сообщение #7


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



Цитата
Pusk_Sr: ldi temp,(1<<TWINT)|(1<<TWSTA)|(0<<TWSTO)|(1<<TWEN)
out TWCR,temp ;Посылка сигнала "START"


Вы устанавливаете биты "старт" и "стоп" одновременно! так делать нелья, условие старт подается так;
Pusk_Sr: ldi temp,(1<<TWINT)|(1<<TWSTA)|(1<<TWEN)
out TWCR,temp ;Посылка сигнала "START"

Потом, условие стоп!
Цитата
;Все данные переданы - STOP (линия приема/передачи переходит в высокоимпедансное состояние)

STOP_r: ldi temp,(1<<TWINT)|(0<<TWSTA)|(1<<TWSTO)|(1<<TWEN)
out TWCR,temp


Оно (условие) не отличается от условия "СТАРТ" выше.
условие "стоп" передается так
;Все данные переданы - STOP (линия приема/передачи переходит в высокоимпедансное состояние)

STOP_r: ldi temp,(1<<TWINT)|(1<<TWSTO)|(1<<TWEN)
out TWCR,temp

Я думаю, что еще есть ошибки! В общем весь текст программы практически не верный. Нужно искать примеры в интернете на асме.

Могу посоветовать:
www.avrfreaks.net

В даташите на МК с аппаратным TWI есть вся необходимая информация. Там же есть примеры на асме, как передавать данные по этой шине. Удачи.


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 6 2005, 15:11
Сообщение #8


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Так в даташите как раз есть такая фраза:
"Для разрешения работы TWI необходимо записать лог. 1 в TWEN. Для разрешения подтверждения собственно подчиненного адреса или адреса общего вызова записывается 1 в TWEA. Битам TWSTA и TWSTO необходимо присвоить нулевое значение." Я же это не придумал.

Заходил на www.avrfreaks.net, по TWI нашел только программную реализацию всей этой лабуды, а на кой, спрашивается тогда, разработчики делали аппаратный TWI?

В энный раз просмотрел свою прогу, изменил указанные места:
STOP_r: ldi temp,(1<<TWINT)|(0<<TWSTA)|(1<<TWSTO)|(1<<TWEN)
out TWCR,temp, и т.д. все равно приемник не признает передаваемый адрес.
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 6 2005, 16:29
Сообщение #9


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Выяснилось следующее: если передавать с mega32 на mega32 - TWI работает нормально, с mega16 на mega32 - тоже, а с mega32 на mega16 - не работает.
Может тут какие-то тонкости есть?
AVR089 просмотрел, там ничего подходящего к моей ситуации нет: прерывания я не использую, спящий режим тоже.
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Nov 7 2005, 00:12
Сообщение #10


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



Цитата
STOP_r: ldi temp,(1<<TWINT)|(0<<TWSTA)|(1<<TWSTO)|(1<<TWEN)


Так нельзя сбрасывать бит TWSTA. В левой части всегда должна быть 1, т.к. она сдвигается на определенное количество разрядов. Для бита TWINT=7, еденица сдвинется на 7 разрядов влево (операция <<) и в 7 разряде будет лог. 1.

Для сброса бита можно воспользоваться инструкцией cbi.
В общем нужно разобраться с самим ассемблером. И еще в форуме тяжело объяснять такие вещи. Если хотите, можно пообщаться в аське.
Мой ICQ UIN 339085018. Я там обычно с 3-00 до 13-00 по Московскому времени. Обращайтесь!


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
rmo
сообщение Nov 7 2005, 03:24
Сообщение #11


Участник
*

Группа: Свой
Сообщений: 25
Регистрация: 25-05-05
Пользователь №: 5 364



В VMLAB в папке AVR_demo есть рабочий проект TWI на асме.
Удобно то, что на осциллографе можно просмотреть все сигналы.
Советую посмотреть.
Удачи.
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 7 2005, 05:32
Сообщение #12


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



Вы понимаете, я обнуление (например, 0<<TWSTA и пр.) везде повыкидывал, оставил только те биты, которые надо установить в 1.
Программа работает, но передача осуществляется только с mega32 на mega32 или с mega16 на mega32. А с mega32 на mega16 - не работает.
Вот в чем проблема. А программа работоспособная, на все сто.
Может там fuse биты у МК настраивать надо?

To rmo:
У меня, к сожалению, нет программы VMLAB, я был бы вам очень благодарен, если бы вы мне сказали где можно скачать полностью работоспособную версию этой проги. Я слыхал, там можно смоделировать работу двух МК - вот это мне бы подошло!
Go to the top of the page
 
+Quote Post
rmo
сообщение Nov 7 2005, 07:59
Сообщение #13


Участник
*

Группа: Свой
Сообщений: 25
Регистрация: 25-05-05
Пользователь №: 5 364



VMLAB http://www.amctools.com/download.htm
Go to the top of the page
 
+Quote Post
James D.
сообщение Nov 7 2005, 10:41
Сообщение #14


Местный
***

Группа: Участник
Сообщений: 315
Регистрация: 10-10-05
Пользователь №: 9 466



М-да, выглядит как игрушка. Сомневаюсь я насчет реального моделирования.
Да и разбираться с ней времени нет. Я как-то к AVRStudio уже привык и осваивать новую прогу неохота.
Посмотрел я пример TWI - общий алгоритм у меня такой же, только без прерываний. И, главное, моя прога-то работает, но только с mega32 на mega16 данные не передаются. А обратно - пожалуйста.
Вот в чем проблема!
Go to the top of the page
 
+Quote Post
beer_warrior
сообщение Nov 7 2005, 12:30
Сообщение #15


Профессионал
*****

Группа: Свой
Сообщений: 1 065
Регистрация: 8-10-05
Из: Kiev, UA
Пользователь №: 9 380



Ну я думаю во-первых, если не работает на разных кристаллах, проверить инициализацию меги 16.
Во-вторых, есть подозрение, что в транзакция не закрываеться
(не опознан адрес, не выставлен ACK etc)
Посему скромная рекомендация: делаем некую переменную, в которую по окончанию каждого этапа транзакции, ложим число.
По окончании всего выбрасываем это число на индикатор или в uart.
И смотрим в какой момент автомат TWI понесло не в ту сторону.


--------------------
Вони шукають те, чого нема,
Щоб довести, що його не існує.
Go to the top of the page
 
+Quote Post

19 страниц V   1 2 3 > » 
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 21st July 2025 - 01:20
Рейтинг@Mail.ru


Страница сгенерированна за 0.01479 секунд с 7
ELECTRONIX ©2004-2016