Kruftin
May 13 2012, 11:18
Добрый день!
Возникла проблема при подключении к мк атмега32 компаса HMC5883. Устанавливаю состояние старт, а вот затем посылаю адрес для записи, в ответ на который получаю состояние регистра статуса twi равное 0х20, что означает: данные переданы, получен Not ack. Вот такие дела. Причем коды состояния я получаю только лишь при работе на частоте 1 МГц, на 8Мгц не могу получить даже состояние старт.
Код прилагаю даже в двух вариантах. Также в архив положил даташит на компас.
Вот участок кода где я проверяю статус:
Код
void HMC5843(void)
{
//unsigned char xh, xl, yh, yl, zh, zl;
long xo, yo, zo;
i2cSendStart();
i2cWaitForComplete();
i2cWrite_Address(0x3C); //write to HMC
i2cWaitForComplete();
status_er = i2cGetStatus();
i2cWrite_Data(0x02); //mode register
i2cWaitForComplete();
i2cWrite_Data(0x00); //continuous measurement mode
i2cWaitForComplete();
//status_er = i2cGetStatus();
//i2cCheckForMT_SLA();
i2cSendStop();
Полезные ссылки:
1)http://www.seeedstudio.com/wiki/index.php?title=Twig_-_3-axis_Compass_v1.0b
ILYAUL
May 13 2012, 14:24
А где Вы устанавливаете скорость передачи?
Kruftin
May 13 2012, 18:01
В архиве компас есть полный код программы(для CVAVR), так вот там есть функция:
1-й вариант
CODE
void i2cSetBitrate(unsigned short bitrateKHz)
{
//unsigned char bitrate_div;
// set i2c bitrate
// SCL freq = F_CPU/(16+2*TWBR*4^TWPS))
//TWSR &= ~(1<<TWPS0); //set zero for TWPS = 1
//TWSR &= ~(1<<TWPS1);
//calculate bitrate division
//bitrate_div = ((F_CPU/4000l)/bitrateKHz);
//if(bitrate_div >= 16)
// bitrate_div = (bitrate_div-16)/2;
//TWBR = bitrate_div;
unsigned char bitrate_div;
// set i2c bitrate
// SCL freq = F_CPU/(16+2*TWBR))
//#ifdef TWPS0
// for processors with additional bitrate division (mega128)
// SCL freq = F_CPU/(16+2*TWBR*4^TWPS)
// set TWPS to zero
cbi(TWSR, TWPS0);
cbi(TWSR, TWPS1);
//#endif
// calculate bitrate division
bitrate_div = ((F_CPU/4000l)/bitrateKHz);
if(bitrate_div >= 16)
bitrate_div = (bitrate_div-16)/2;
outb(TWBR, bitrate_div);
}
2-й вариант
Код
TWBR=0x01; // Bit rate
TWSR=(0<<TWPS1)|(0<<TWPS0); // Setting prescalar bits
// SCL freq= F_CPU/(16+2(TWBR).4^TWPS)
А сама установка скорости в основной программе называется i2cInit():
CODE
void i2cInit(void)
{
// set i2c bit rate to 40KHz
i2cSetBitrate(100);
// enable TWI (two-wire interface)
//TWCR = 1<<TWEN; // Enable TWI
sbi(TWCR, TWEN);
}
void main(void)
{
i2cInit();
delay_ms(100);
USART_Init();
#asm("sei");
while(1)
{
HMC5843();
delay_ms(200); //at least 100ms interval between measurements
if (1){
USART_SendChar('p'); //отвечаем компу
USART_SendChar('r');
USART_SendChar('i');
USART_SendChar('v');
USART_SendChar('e');
USART_SendChar('t');
USART_SendChar(zl);
USART_SendChar(zh);
USART_SendChar(error);
USART_SendChar(status_er);
delay_ms(200);
}
}
}
ILYAUL
May 13 2012, 18:31
Как всё сложно- то . Moжет проще TWBR=SYSCLK/(2*SCL_Freq)-8
Kruftin
May 13 2012, 19:41
Можно и так. Но вот при частоте тактирования 1МГц я доходил до успешного выставления старта на линии. А при частоте 8МГц у мк атмега32 я даже старт не могу поставить, в статусе 0xF8 вылазит. Ну не знаю может поставить наименьшую скорость на i2c, или килогерц эдак 5-10 попробовать? Даже не знаю в чем дело. Старт прошел пусть только и на 1МГц, данные отправлены, а ответ not ack. Хотя в даташите на компас написано и 100 и 400 килогерц он поддерживает(ну т.е. 400КГц максимум). К компасу припаялся, кидаю на него питание 3.3 вольта(правда это минимум по даташиту), на линии SDA, SCL тоже через резисторы 10Ком напряжение идет 3.3 на выводах компаса.
ILYAUL
May 13 2012, 21:30
Цитата(Kruftin @ May 13 2012, 23:41)

К компасу припаялся, кидаю на него питание 3.3 вольта(правда это минимум по даташиту), на линии SDA, SCL тоже через резисторы 10Ком напряжение идет 3.3 на выводах компаса.
Т.е всё подключено согласно этой схеме
Kruftin
May 14 2012, 08:48
Именно так.
ILYAUL
May 14 2012, 10:16
Уменя складывается впечатление , что у Вас проблема с SCL , пока Вы работаете на 1 мгц Вы где-то на грани попадания в частотную полосу . Чуть выше и всё микросхема Вас не понимает. Можете посмотреть какие значения пишутся в регистр TWBR при 1 и 8 мгц и пересчитать на SCL?
Navovvol
May 14 2012, 11:08
с I2C не сталкивался, но пытаясь разобраться вот на что наткнулся:
Код
bitrate_div = ((F_CPU/4000l)/bitrateKHz);
if(bitrate_div >= 16)
bitrate_div = (bitrate_div-16)/2;
outb(TWBR, bitrate_div);
допустим F_CPU= 1 000 000 , тогда
1000000/4000=250, 250/100 = 2.5
bitrate_div=2
если F_CPU = 8 000 000, тогда
8000000/4000=2000, 2000/100 = 20
20 >=16 истина, тогда
20-16=4, 4/2= 2
bitrate_div =2.
Т.О. при любой частоте запишется число 2. Или я чего то не учел ?
Kruftin
May 14 2012, 11:46
Дак а почему тогда вариант номер 2 не катит?
Код
TWBR=0x01; // Bit rate
TWSR=(0<<TWPS1)|(0<<TWPS0); // Setting prescalar bits
// SCL freq= F_CPU/(16+2(TWBR).4^TWPS)
Первый вариант взят из примера для компаса HMC5843, он по моему с точки зрения кода ничем не отличается особо.
Ну мы устанавливаем частоту передачи на i2c, по даташиту на компас она может быть до 400КГц. Дак вот не все равно что я запишу в TWBR?
Пусть TWBR = 1, тогда Частота f_SCL = 1000000/(16 +2*1*4) = 41666Гц, ну и 41666<400000,
Пусть частота будет 8Мгц, тогда 41666*8 = 333328, что тоже меньше 400000.
Navovvol
May 14 2012, 12:07
нашел вот такое примечание в даташите, правда на мегу 128
"Прим.: TWBR должен быть равен не менее 10, если TWI работает в ведущем режиме. Если TWBR меньше 10, то ведущий может генерировать некорректное состояние на линиях SDA и SCL. Проблема возникает при работе в ведущем режиме при передаче условий СТАРТ+ПОДЧИН_АДР+ ЧТЕНИЕ/ЗАПИСЬ подчиненному."
Kruftin
May 14 2012, 14:39
В даташите на атмегу32 я такого не нашел. Не ну сейчас попробую поиграться с регистром TWBR.
Ну поигрался, как только не менял TWBR все равно получаю 0х20 вместо 0х18 и 0х30 вместо 0х28 при передаче номера регистра.
Я думаю линия SCL работает нормально по крайней мере на 1МГц, однако вот с компасом чето надо думать. Ведь я получаю на линии код, что данные переданы, а подтверждения нету. Ну и от компаса ниче не получаю в регистр данных TWDR вроде(в нем лишь то что я посылал последнее это 0х3D). Может питание побольше подать на компас(не на линии, а именно на компас)?Сейчас я подаю на него минимальное 3.3 Вольта(Vdd).
Цитата(Kruftin @ May 14 2012, 17:39)

Сейчас я подаю на него минимальное 3.3 Вольта(Vdd).
Судя по приложенному Вами DS, 3.3V это не минимальное а
МАКСИМАЛЬНО необходимое значение АVDD.
А на DVDD вообще максимальное 2.0V.
Или я чегото не понимаю?
ILYAUL
May 14 2012, 17:49
Нет я ошибся
Цитата
Судя по приложенному Вами DS, 3.3V это не минимальное а МАКСИМАЛЬНО необходимое значение АVDD.
А на DVDD вообще максимальное 2.0V.
Или я чего то не понимаю?
Там стабилизатор на его плате на 2.5 В и допускается схема включения как я привёл выше
Цитата
"Прим.: TWBR должен быть равен не менее 10, если TWI работает в ведущем режиме. Если TWBR меньше 10, то ведущий может генерировать некорректное состояние на линиях SDA и SCL. Проблема возникает при работе в ведущем режиме при передаче условий СТАРТ+ПОДЧИН_АДР+ ЧТЕНИЕ/ЗАПИСЬ подчиненному."
Совершенно верно. Поэтому ему надо оставить TWBR=1 и
Цитата
поиграться
прескалером. Хотя это тоже не вариант.
Код 08 после старта возвращается?
Kruftin
May 14 2012, 18:11
Ну питание на платку я могу подать до 5 Вольт. Так вот TWBR, то почему я должен в единичку поставить, если у меня контроллер то в ведущем режиме работает(master)? Ну я не думаю что у меня калькулятор меня обманывает, вроде частоту верно рассчитал.
http://www.seeedstudio.com/wiki/index.php?...s_Compass_v1.0b - тут написано про платку на которой компас
После старта код 0х08 возвращается при работе на 1МГц. А при работе на 8МГц 0xF8 возвращается, что и после старта, ну это косяк скорости.
Дак вот настроить бы хоть на 1МГц. Может питание поднять у компаса, хотя ведь он вроде как посылает not ack или это в линии по умолчанию?
ILYAUL
May 14 2012, 18:46
Цитата(Kruftin @ May 14 2012, 22:11)

Ну питание на платку я могу подать до 5 Вольт. Так вот TWBR, то почему я должен в единичку поставить, если у меня контроллер то в ведущем режиме работает(master)? Ну я не думаю что у меня калькулятор меня обманывает, вроде частоту верно рассчитал.
Верно. Давайте остановимся на 8 мгц TWBR=0x03 частота = 200000гц
Блин , забыл в своей формуле 4
TWBR=(SYSCLK/(2*SCL_Freq)-8) /4
Kruftin
May 14 2012, 18:50
Ну сейчас попробую. Он даже старт не может выставить 08. На 1МГц все также 0х30. И еще кстати есть подвижки в лучшую сторону: если я ставлю TWBR больше 10, то у меня старт проходит на 8МГц, но 0х30 в ответе на посылку адреса. Т.е. может быть скорость то та?Кстати попробовал поставить делитель 4 вместо 1, так вот старт не проходит, хм странно, а может быть такое, что компас только на одну скорость настроен?
Скажу сразу, что на 8МГц все значения TWBR ниже 10 не катят, а вот на 1МГц катят все значения.
ILYAUL
May 14 2012, 19:14
Цитата(Kruftin @ May 14 2012, 22:50)

Ну сейчас попробую. Он даже старт не может выставить 08. На 1МГц все также 0х30. И еще кстати есть подвижки в лучшую сторону: если я ставлю TWBR больше 10, то у меня старт проходит на 8МГц, но 0х30 в ответе на посылку адреса. Т.е. может быть скорость то та?Кстати попробовал поставить делитель 4 вместо 1, так вот старт не проходит, хм странно, а может быть такое, что компас только на одну скорость настроен?
А адрес то какой 0x3D или 0x1E
Kruftin
May 14 2012, 19:15
Код
i2cSendStart();
i2cWaitForComplete();
i2cWrite_Address(0x3C); //write to HMC
i2cWaitForComplete();
0х3С разумеется идет на запись в регистр
Адрес по идее устройства 0х1Е, но ты добавляй бит на запись или чтение и будет 0х3С на запись и 0х3D на чтение.
_Артём_
May 14 2012, 19:31
Цитата(Kruftin @ May 14 2012, 21:50)

а может быть такое, что компас только на одну скорость настроен?
Не может. Задана только максимальная скорость.
Либо - это новое слово в науке и технике.
Нашёл такой пунктик в DS на м88. Может ваш случай?
Цитата
TWBR should be 10 or higher if the TWI operates in Master mode. If TWBR is lower than 10, the
Master may produce an incorrect output on SDA and SCL for the reminder of the byte. The prob-
lem occurs when operating the TWI in Master mode, sending Start + SLA + R/W to a Slave (a
Slave does not need to be connected to the bus for the condition to happen).
Kruftin
May 14 2012, 19:35
Не ну если я получаю код в статусном регистре, то значит компас мне отвечает? Артем, писали уже про этот пунктик, он влияет лишь на работу на частоте выше 1МГц, однако коды приходят те же самые, что и при TWBR меньшем 10.
ILYAUL
May 14 2012, 19:36
Цитата(Kruftin @ May 14 2012, 23:15)

Адрес по идее устройства 0х1Е, но ты добавляй бит на запись или чтение и будет 0х3С на запись и 0х3D на чтение.
Так стоп. Если к 1E добвить в конце адресной посылке 1 будет 1F т.к по условию I2C LSB является битом определяющим действие.
Ну да он же 9 всё разобрался. Знаешь , попробуй дать ему родные 5V там согласователь уровней есть и они определяют в схеме тоже 5 . Может на 3-х фронты заваливает , хотя и не должен. И измени ему посылку , дай ему STOP дождсь ответ -Start - ответ - адрес или передерни питание .
Kruftin
May 14 2012, 19:45
Ладно завтра перепаяю, и дам ему чизбургеров на 5Вольт. Хотя щас попробую. От 5 Вольт лучше не стало.
ILYAUL
May 14 2012, 20:00
Цитата(Kruftin @ May 14 2012, 23:45)

Ладно завтра перепаяю, и дам ему чизбургеров на 5Вольт. Хотя щас попробую. От 5 Вольт лучше не стало.
5V и на mege?
Цитата
TWBR should be 10 or higher if the TWI operates in Master mode. If TWBR is lower than 10, the
Master may produce an incorrect output on SDA and SCL for the reminder of the byte. The prob-
lem occurs when operating the TWI in Master mode, sending Start + SLA + R/W to a Slave (a
Slave does not need to be connected to the bus for the condition to happen).
Артём , это есть выше , но в 32 мы этого не нашли . Если в TWBR будет хотя бы 10 то при 8 мгц SCL=83333
Kruftin
May 14 2012, 20:02
Да на меге у меня от 3 батареек на 1,5 вольт (4,5 вольт правда). Кстати пробовал сначала дать стоп(дождался когда он пройдет), потом старт, тоже самое.
ILYAUL
May 14 2012, 20:11
Страно это
Цитата
если я ставлю TWBR больше 10, то у меня старт проходит на 8МГц, но 0х30...
- это ответ на данные а не на адрес. Почему он адрес воспринимает как данные , только в том случае если адрес он уже принял и всё остальное считает данными.
Kruftin
May 14 2012, 20:15
Дак да на адрес у него ответ то 0х20, а на данные 0х30(адрес он воспринимает как адрес). Все равно это типа негативные ответы. Я просто и после адреса смотрел статус и после посылки данных. Ответы то логичные, но содержат not ack. Может надо где-нибудь расставить задержки? Надо бубен прикупить походу.
ILYAUL
May 14 2012, 21:14
Цитата(Kruftin @ May 15 2012, 00:15)

Может надо где-нибудь расставить задержки?
Нет у Вас прямая проверка бита TWINT в ожидании ответа.
Kruftin
May 15 2012, 03:17
Ну как то же люди работают с такими компасами? Или все на ардуино перешли и берут готовый код. Компас такими ответами просто посылает... Да еще и предделитель когда меняешь он отказывается нормальные данные посылать, хотя тут говорят, что частота любая может быть на i2c, главное меньше заданной в даташите компаса. Листаю сижу англиканские сайты, пока ниче не нашел про проблемы похожие.
ILYAUL
May 15 2012, 05:00
А почему так запитаны по разному mega и компас. Чем вызвана такая разница?
Kruftin
May 15 2012, 05:10
Я сейчас питаю мегу и компас от 4,5 вольт. Ну а на линиях SDA и SCL 3.3 вольта через подтягивающие резисторы, вроде все как надо. До этого я питал компас от 3.3 вольт.
ILYAUL
May 15 2012, 05:16
Цитата
Всё как надо
-это работает , как положено? Растояние между двумя платами какое?
Kruftin
May 15 2012, 06:21
Между компасом и моей отладочной? Расстояние сантиметров 7-8.

Никто случаем не знает какой-нибудь нормальный зарубежный форум, где могут подсказать по атмеге, avrfreaks регистрацию приостановил?
Похоже единственный энтузиаст
ILYAUL исчерпал фантазии, печально похоже придется использовать обычный компас, а не цифровой).
ILYAUL
May 15 2012, 18:01
Цитата(Kruftin @ May 15 2012, 10:21)

Похоже единственный энтузиаст ILYAUL исчерпал фантазии, печально похоже придется использовать обычный компас, а не цифровой).
А Вас похоже даже на "фантазии" не хватает . Вы даже и не пытаеттесь разобраться в том коде который Вы скачали.
Берите осцил в руки и проверяйте сигналы SCL и SDA они должны ббыть прямоугольными и до преобразователя уровней и после него
Kruftin
May 15 2012, 18:41
У меня фантазии хватает, тока вот применить я ее не в силах, сейчас вот думаю ножками подрыгать(как пример
http://avrlab.com/node/127). Может дело в TWI модуле атмеги. Кстати вот что интересного про ошибку почерпнул отсюда
http://easyelectronics.ru/avr-uchebnyj-kur...oj-iic-i2c.html 0×20 SLA+W+NACK Мы отправили адрес с битом записи, а нас послали NACK. Обидно, сгенерим ошибку или повторим еще раз.
0×30 Byte+NACK Мы послали байт, но подтверждение не получили. Видимо ведомый уже сыт по горло нашими подачками или он захлебнулся в данных. Либо его ВНЕЗАПНО посреди передачи данных украли инопланетяне.
Просто когда я с уартом разбирался, там больше было возможностей для маневра, а тут только осциллограф в руки. Не я все равно добью этот компас

P.S. Как это я в коде не разобрался?!Он простейший, я все что делаю понимаю, мне регистры уже снятся.
А вот осциллографом я должен быстро получается отлавливать передачу от компаса?Он же когда я к нему не стучусь не кидает ничего на линию? Поясни если можно поподробнее как осциллографом данные от компаса словить и что должно быть в идеале.
ILYAUL
May 15 2012, 19:20
На сеглдняшний момент мы имеем :
1 Связь между mega и компасом есть ( правда я не знаю на какой частоте в данный момент это происходит) т.е они видят друг друга и обмениваются информацией причём правильной
2. Обработка ошибок связи - это отдельная подпрограмма проще перед любым экспериментом выкл и вкл питание. Ксати по какому коду из имеющихся Вы работаете.
3. Зацикли любую отсылку данных только не start и не адрес типа 0x55 или 0xAA, помотри форму импульсов - это снимет ещё один из вариантов такого поведения связи , хотя я в кое в чём себе и противоречу , но хотелось бы снять этот вопрос
Kruftin
May 15 2012, 19:26
По коду в котором явно задается регистр TWBR:
Код
TWBR=0x11; // Bit rate
TWSR=(0<<TWPS1)|(0<<TWPS0); // Setting prescalar bits
// SCL freq= F_CPU/(16+2(TWBR).4^TWPS)
Завтра пойду смотреть что осциллограф кажет. Так питание я включил, контроллер прошил, затем мне опять питание отключить и включить как я понимаю. Ладно зациклю посылку адреса или посылку значения в регистр(0х5А тоже тогда нельзя).
Kruftin
May 16 2012, 12:47
Спасибо ILYAUL, осциллограф помог. Оказалось я перепутал SDA и SCL на атмеге.

Получил я заветные 0х18, правда еще не все проверки проходят, но уже кое-что. Думаю напишу сюда же, что не проходит.
Kruftin
May 17 2012, 18:34
На данный момент все проверки проходят по даташиту как часы, однако от компаса получаю старший байт 0xFF, младший байт 0x00 и так для всех координат (x,y,z). Похоже надо поразбираться с даташитом компаса или компас нерабочий в плане расчетов координат.
Даташит на компас прилагаю.
ILYAUL
May 18 2012, 15:07
Цитата(Kruftin @ May 17 2012, 22:34)

На данный момент все проверки проходят по даташиту как часы, однако от компаса получаю старший байт 0xFF, младший байт 0x00 и так для всех координат (x,y,z). Похоже надо поразбираться с даташитом компаса или компас нерабочий в плане расчетов координат.
Может для начала откалибровать. У меня например в машине , надо задать своё положение (начальную точку- занести начальные координаты в регистр) и сделать круг на машине . Вот тогда показывает все стороны света. У него появляется от чего плясать , а в Вашем они есть.
Помоему на их сайте есть applicattion по калибровке компасов.
Kruftin
May 19 2012, 16:08
Попытаюсь, но если его крутить каждый раз надо для того, чтобы он заработал, то это немного портит мои планы.
ILYAUL
May 19 2012, 19:29
Цитата(Kruftin @ May 19 2012, 20:08)

Попытаюсь, но если его крутить каждый раз надо для того, чтобы он заработал, то это немного портит мои планы.
Достаточно один раз
_Артём_
May 19 2012, 20:05
Цитата(ILYAUL @ May 19 2012, 22:29)

Достаточно один раз
При выключении калибровка не теряется?
Почему же их тогда на заводе настроить нельзя?
Kruftin
May 20 2012, 12:05
Не ну какие-то данные он должен сразу скинуть, даже если он на месте стоит. А он кидает FF и 00, значит компас глючит. А калибровка делается по данным от него.
ILYAUL
May 20 2012, 13:09
Цитата(_Артём_ @ May 20 2012, 00:05)

При выключении калибровка не теряется?
Почему же их тогда на заводе настроить нельзя?
Не знаю . Но вот так написано в инструкции по калибровке компаса. Не теряется , если только аккум не снять , повидимому в EEPROM не пишут
Код
Не ну какие-то данные он должен сразу скинуть, даже если он на месте стоит. А он кидает FF и 00, значит компас глючит
Для какого полушария данные он должен скинуть , для южного или северного?
Kruftin
May 20 2012, 13:42
А как из даташита то понять что сделать, чтобы компас заработал. Я только режим самотестирования нашел. Как я понимаю он сам все должен определить, а калибровка нужна лишь для точности и все. Для северного полушария он все скинуть должен.
http://electronix.ru/forum/index.php?act=a...st&id=68538 (тут датшит)
ILYAUL
May 20 2012, 19:06
Он хоть в каком режиме у Вас работает? И выкладывайте тот код который Вы используете.
Kruftin
May 21 2012, 05:14
Я использую режим continious mode (получается записью 0х00 в регистр 0х02). Код который использую сейчас прилагаю. Пробовал посмотреть статусный регистр компаса - результат 0xff.
Подтяжка из резисторов на линиях sda и scl на результаты от компаса же никак не может повлиять? Все проверки проходят компас подтверждает прием и запись с чтением из его регистров. Раньше я дополнительно делал подтяжку на линиях, а сейчас убрал ее и все вроде также работает, т.е. подтяжка есть на плате с компасом как я понимаю. Пробовал single mode результат все равно ff - MSB, 00 - LSB. Надо может прочитать все регистры конфигурационные или какой план действий?
Вот прочитал регистр configuration A получил 0xf0, что судя по даташиту не совсем гуд, а вот в регистре configuration B получил 0х20, что вроде как по дефолту.
ILYAUL
May 21 2012, 20:56
Почему Вы говорите о 2 данных , если их по идее должно быть шесть. И я Бы попробывал читать в Single mode - default
Kruftin
May 22 2012, 03:11
Дак их итак шесть. Вы же код вроде читали? Там я скидываю старший и младший байты по иксу например и о них говорю( в остальных просто тоже самое). Ну в single mode тоже самое. В датащите рекомендуется continious mode. Я думаю записать значение в первый конфигурационный регистр A, поскольку там биты с 5 по 7 единички, хотя в даташите написано, что для корректной работы там должны быть нули. Хотя непонятно: если они не задействовали эти биты, то зачем их в нули выставлять, написали бы просто что они зарезервированы.
Для просмотра полной версии этой страницы, пожалуйста,
пройдите по ссылке.