roboforum.ru

Технический форум по робототехнике.

dccharacter - Излить посильно

Блоги посетителей.
Правила форума
В данном разделе каждый может иметь не более одной темы. Тема должна начинаться с логина (ника) робофорума.

Re: dccharacter - Излить посильно

Сообщение dccharacter » 06 авг 2014, 21:09

Как же меня достали i2c и любые приборы, которые не толерантны к пяти вольтам. Ну пипец просто.
Скажите, есть люди, у которых не было затяжных проблем с i2C?
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение dccharacter » 07 авг 2014, 09:03

Вот залипает и все бит BF на каждом втором чтении. То ли не проталкивается принятый бит в буфер, то ли бит вообще не принимается, ти ли флаг липнет. Анализатор пиковский не помогает (вшивая все-таки штукенция)

[Ad]D0[RX]15[RX]07[Ad]D0[RX]16[RX]1B

Write event triggered. <- Что он вот тут имеет ввиду вообще не ясно. Почему-то только на каждом втором цикле записи пишет это.

[Ad]D0[RX]3E[RX]01[P_]
[Ad]D0[RX]17[RX]00[P_]


Write event triggered.

[Ad]D0[RX]00[Ad]D1[DR][TX]C4[P_]
[Ad]D0[RX]00[Ad]D1[DR]

Read event triggered.

Добавлено спустя 3 минуты 55 секунд:
Кстати залипает еще и бит ADON. Вроде бы на нескольких МК. чип pic16f1827, ревизия пятая, эррата не признается ни в чем.

Добавлено спустя 1 час 50 минут 1 секунду:
Вот удалось частично поймать мастер на передаче. Странное поведение линии SDA между пересылкой байтов, она, почему-то, отпускается. А судя по даташиту - не должна. Завтра попробую поймать что там на приеме творится. OSL - тоже лажовый анализатор, хотя на порядки лучше PLA.
i2c.jpg


Добавлено спустя 11 минут 39 секунд:
Да вроде нормально ITG3200 отвечает адресом своим.... Хрень какая-то
i2c_receive.jpg
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение dccharacter » 08 авг 2014, 09:33

Отличный учебник по i2c.
http://www.eti.pg.gda.pl/katedry/ksg/dy ... ow/i2c.pdf
Но не помог. То ли МК битый то ли гира.

Добавлено спустя 1 час 24 минуты 54 секунды:
МК :-(
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение dccharacter » 09 авг 2014, 02:27

Ну вот и че мне делать с этим идиотским МК, который не может прочитать байт из гиры? Переделывать все на дискавери сил уж нет...
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение Dmitry__ » 09 авг 2014, 04:41

В pic16f1827 2 модуля i2c. Соедини их и протестируй на каком-нибудь примере, а потом переходи на внешние железки.
dccharacter писал(а):Вот удалось частично поймать мастер на передаче. Странное поведение линии SDA между пересылкой байтов, она, почему-то, отпускается. А судя по даташиту - не должна.

В i2c, при передаче последнего байта, может не устанавливаться ACK (noACK). Используется для пакетной передачи данных. Может оно? Резисторы стоят на + питания? Еще могу посоветовать тестировать на низкой частоте (100кгц)...

Добавлено спустя 6 минут 20 секунд:
Удержание scl в нуле в активном состоянии - нормально, данные на sda могут меняться только при нуле на scl, иначе будет пойман start или stop.

Добавлено спустя 32 минуты 13 секунд:
пффффффф, весь инет кишит засадой: dccharacter + i2c + pic16f1827, аж с 2011 года, ужос, надо помогать бедному зверю :crazy:
Аватара пользователя
Dmitry__
 
Сообщения: 8033
Зарегистрирован: 13 янв 2011, 15:25
Откуда: Санкт-Петербург

Re: dccharacter - Излить посильно

Сообщение dccharacter » 09 авг 2014, 05:03

Уж помоги, что ли, пожалуйста
Вот репа: https://github.com/dccharacter/RC_RX.X
Цапани к ней что-нить i2c-шное и проверь плз - работает ли. Поскольку я там уже неделю как слон в посудной лавке, код уже превратился черти во что.
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение Dmitry__ » 09 авг 2014, 07:13

Нуууу, штука сложная, буду глазеть по мере появления своб. времени...
Чем компилишь проект? Линуховый mplab x ide ругается на:
Код: Выделить всёРазвернуть
__CONFIG(FOSC_INTOSC & CLKOUTEN_OFF & WDTE_OFF & PWRTE_ON & PLLEN_OFF);
и:
__delay_ms(ххх);


Замеченные косяки:
Зачем в прерывании проверять флаги "ie"? Оверхеды жОсткие.
Код: Выделить всёРазвернуть
if (ADIE && ADIF)
...
if (TMR0IF && TMR0IE)

Если периф. узел выключен, то не будет генериться флаг "IF" и соотв. isr, а если узел вкл. то незачем проверять "IE".
Далее, ты настроил ADC на чтение в isr. Сразу после чтения запускаешь новое преобразование:
Код: Выделить всёРазвернуть
    if (ADIE && ADIF) {
        ADIF = 0;
        v_bat_sample = (ADRESH << 8) + ADRESL;
        GO_nDONE = 1;
    }

АЦП - штука быстрая, за n тактов - происходит новое прерывание от ацп. А нужно тебе это для жутко медленного v_bat_sample. Если ты запустишь дебаггер (можно чисто софтовый), то увидишь что твоя прога все время крутится в isr adc. При выходе из прерывания, выполняется всего несколько команд основной программы и происходит очередное прерывание от adc.
Аватара пользователя
Dmitry__
 
Сообщения: 8033
Зарегистрирован: 13 янв 2011, 15:25
Откуда: Санкт-Петербург

Re: dccharacter - Излить посильно

Сообщение dccharacter » 09 авг 2014, 07:18

Dmitry__ писал(а):Нуууу, штука сложная, буду глазеть по мере появления своб. времени...
Чем компилишь проект? Линуховый mplab x ide ругается на:
Код: Выделить всёРазвернуть
__CONFIG(FOSC_INTOSC & CLKOUTEN_OFF & WDTE_OFF & PWRTE_ON & PLLEN_OFF);
и:
__delay_ms(ххх);


xc8
Dmitry__ писал(а):Замеченные косяки:
Зачем в прерывании проверять флаги "ie"? Оверхеды жОсткие.
Код: Выделить всёРазвернуть
if (ADIE && ADIF)
...
if (TMR0IF && TMR0IE)

Если периф. узел выключен, то не будет генериться флаг "IF" и соотв. isr, а если узел вкл. то незачем проверять "IE".

Ты это! Чего говоришь-то! Флаги один хрен взводятся. Надо пруфов?
The ADIF bit is set at the completion of
every conversion, regardless of whether
or not the ADC interrupt is enabled.

Dmitry__ писал(а):Далее, ты настроил ADC на чтение в isr. Сразу после чтения запускаешь новое преобразование:
Код: Выделить всёРазвернуть
    if (ADIE && ADIF) {
        ADIF = 0;
        v_bat_sample = (ADRESH << 8) + ADRESL;
        GO_nDONE = 1;
    }

АЦП - штука быстрая, за n тактов - происходит новое прерывание от ацп. А нужно тебе это для жутко медленного v_bat_sample. Если ты запустишь дебаггер (можно чисто софтовый), то увидишь что твоя прога все время крутится в isr adc. При выходе из прерывания, выполняется всего несколько команд основной программы и происходит очередное прерывание от adc.

А вот это я ща проверю!
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение Dmitry__ » 09 авг 2014, 07:26

dccharacter писал(а):xc8

Я тож xc8, линуховый, ладно, потом гляну инклуды...

dccharacter писал(а):Ты это! Чего говоришь-то! Флаги один хрен взводятся. Надо пруфов?
The ADIF bit is set at the completion of
every conversion, regardless of whether
or not the ADC interrupt is enabled.

Ну, дык, если отключить adc или таймер (не прерывание!), то не будет ADIF или TMR0IF взводиться, ибо модуль отключен. А если у тебя эти модули вкл. то зачем проверять IF???
Даже если не откл. adc, но больше не взводить GO_nDONE, то сброшенный ADIF больше не установится, будет однократное преобразование...

Добавлено спустя 29 секунд:
я спать.
Аватара пользователя
Dmitry__
 
Сообщения: 8033
Зарегистрирован: 13 янв 2011, 15:25
Откуда: Санкт-Петербург

Re: dccharacter - Излить посильно

Сообщение dccharacter » 09 авг 2014, 07:37

Там вообще история вывода АДЦ в прерывания такая - флаг ГОДАН виснет. В эррате пишут, что исправили, а на самом деле нет. Но что так часто делаю - да, моя совсем плохой.
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение dccharacter » 09 авг 2014, 19:57

Дим, кажись заработало! Виню провода и сидение в прерываниях
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение Dmitry__ » 09 авг 2014, 20:33

Ну, круто, меня испугалось :)
А ты ведь сделал 100кгц:
Код: Выделить всёРазвернуть
    SSP1ADD = _XTAL_FREQ / (4 * 100000l) - 1; //400kHz

Если вернуть 400кгц., будет работать?
Покурил этот xc8 - ужасная штука, по крайней мере в бесплатной версии. Но кое чего нарыл. Вот это:
Код: Выделить всёРазвернуть
    v_bat_sample = (ADRESH << 8) + ADRESL;

Можно смело менять на это:
Код: Выделить всёРазвернуть
    v_bat_sample = ADRES;

Генерируемый код одинаковый.

А вот писать в xc8 по ассемблерному - бяка:
Код: Выделить всёРазвернуть
uint16_t v_bat_sample;
  union
  {
      uint16_t v_bat_sample;
      unsigned char byte_v_bat_sample[sizeof(v_bat_sample)];
  }mU;

а вместо:
    v_bat_sample = (ADRESH << 8) + ADRESL;

так:
    mU.byte_v_bat_sample[0] = ADRESL;
    mU.byte_v_bat_sample[1] = ADRESH;


Но компилятор генерит лишнюю дрянь:
Код: Выделить всёРазвернуть
  7814                           ;main.c: 160: mU.byte_v_bat_sample[0] = ADRESL;
  7815  00DC  0021                  movlb   1   ; select bank1
  7816  00DD  081B                  movf   27,w   ;volatile
  7817  00DE  0020                  movlb   0   ; select bank0
  7818  00DF  00AE                  movwf   ??_isr
  7819  00E0  082E                  movf   ??_isr,w
  7820  00E1  00D3                  movwf   _mU
  7821                           
  7822                           ;main.c: 161: mU.byte_v_bat_sample[1] = ADRESH;
  7823  00E2  0021                  movlb   1   ; select bank1
  7824  00E3  081C                  movf   28,w   ;volatile
  7825  00E4  0020                  movlb   0   ; select bank0
  7826  00E5  00AE                  movwf   ??_isr
  7827  00E6  082E                  movf   ??_isr,w
  7828  00E7  00D4                  movwf   _mU+1


а должно было быть так:
Код: Выделить всёРазвернуть
  7814                           ;main.c: 160: mU.byte_v_bat_sample[0] = ADRESL;
  7815  00DC  0021                  movlb   1   ; select bank1
  7816  00DD  081B                  movf   27,w   ;volatile
  7817  00DE  0020                  movlb   0   ; select bank0
  7820  00E1  00D3                  movwf   _mU
  7821                           
  7822                           ;main.c: 161: mU.byte_v_bat_sample[1] = ADRESH;
  7823  00E2  0021                  movlb   1   ; select bank1
  7824  00E3  081C                  movf   28,w   ;volatile
  7825  00E4  0020                  movlb   0   ; select bank0
  7828  00E7  00D4                  movwf   _mU+1

Сравни с вариантом: "v_bat_sample = (ADRESH << 8) + ADRESL;"
Код: Выделить всёРазвернуть
  7809                           ;main.c: 160: v_bat_sample = (ADRESH << 8) + ADRESL;
  7810  00DC  0021                  movlb   1   ; select bank1
  7811  00DD  081C                  movf   28,w   ;volatile
  7812  00DE  0020                  movlb   0   ; select bank0
  7813  00DF  01D1                  clrf   _v_bat_sample+1
  7814  00E0  07D1                  addwf   _v_bat_sample+1,f
  7815  00E1  0021                  movlb   1   ; select bank1
  7816  00E2  081B                  movf   27,w   ;volatile
  7817  00E3  0020                  movlb   0   ; select bank0
  7818  00E4  01D0                  clrf   _v_bat_sample
  7819  00E5  07D0                  addwf   _v_bat_sample,f


Но на вооружение такой способ взять стоит...
По анализу твоего кода, советую переписать блокировки типа:
Код: Выделить всёРазвернуть
    while ((SSP1CON2 & 0x1F) || (SSP1STATbits.R_nW));


В ожидания определенное время, если за опред. время биты не сбросились (например за 20мс.) то переходить на сброс i2c модуля. Т.к. вылавливать ошибки модуля в бесконечном цикле ожидания - засада для коммерческих программ.
Аватара пользователя
Dmitry__
 
Сообщения: 8033
Зарегистрирован: 13 янв 2011, 15:25
Откуда: Санкт-Петербург

Re: dccharacter - Излить посильно

Сообщение dccharacter » 10 авг 2014, 04:25

Я ж в ассемблере ни бум бум!
Что бесконечные циклы - зло, я в курсе, да...

Но оно летает. Уже летает. Пока только одно управляющее воздействие - ручка газа. Даже без элеровнов. Дергается немножко, но, я думаю, можно настройками ПИД-а сделать так, что вообще будет сидеть как родная...
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Re: dccharacter - Излить посильно

Сообщение Dmitry__ » 10 авг 2014, 06:37

Я так понял, основное зло было из-за большого времени обработки прерываний. Лучше доводи isr до идеала, а в основной программе можно быдлокодить. Про проверку флагов IE уже говорил, еще совет по isr:
У тебя обработка isr делается кучей if идущих друг за другом. Это плохо, т.к. одно частое прерывание (например от ADC) будет запускать всю цепочку проверок IF. Лучше после каждого типа прерывания делать return. И самые частые прерывания делать первыми. Если установятся 2 и более прерываний одновременно, то после обработки одного прер. управление передается основной прогр. и тут же происходит след. прерывание (т.к. флаг if не был очищен). T.e. было так:
Код: Выделить всёРазвернуть
void interrupt isr(void) {
    if (IOCIE && IOCIF) {}
    if (IOCBF3) {}
    if (IOCBF7) {}
    if (ADIE && ADIF) {}
    if (TMR0IF && TMR0IE) {}
}

Делать так:
Код: Выделить всёРазвернуть
void interrupt isr(void) {
    if (ADIF) {} return; //самый шустрый вверх, ADIE - удалить.
    if (IOCIF) {} return;
    if (IOCBF3) {} return;
    if (IOCBF7) {} return;

    if (TMR0IF && TMR0IE) {}
}


С прерываниями от IO уточнить как там сбрасывается флаг if...
Аватара пользователя
Dmitry__
 
Сообщения: 8033
Зарегистрирован: 13 янв 2011, 15:25
Откуда: Санкт-Петербург

Re: dccharacter - Излить посильно

Сообщение dccharacter » 10 авг 2014, 09:23

Вот запилил видео:

Вертолет стал примерно в полтора раза тяжелее оригинала. На старте видно, как он начинает вращаться - это еще не выросла интегральная состовляющая ПИД-а. Вертолет дергается - это связано с регулярным провалом замера напряжения батареи и привязки ШИМ-а к нему (выпендрился зачем-то). После отвязки рывки пропали. Компенсирующую работу ПИД-а видно очень хорошо на 1:36, когда вертолет уходит от оператора - хвост мелко дергается туда сюда. Не задействован хвостовой винт, поэтому вертолет перемещается в горизонтальной плоскости из-за передней центровки (и частично боковой) и потоков воздуха, созданных своим же винтом. Потоки достаточно сильные, так как вертолет тяжелый, и его сносит элементарно. Ему вообще ничего кроме легкого дуновения ничего не нужно.

Из бонусов - несоклько раз смог пролететь через дверь. На оригинале не получалось (как сейчас понимаю - из-за сильно передней центровки и высокой скорости). Вообще убедился, что на оригинальной плате где-то прячется гира. Ну никак нельзя без нее.

Добавлено спустя 2 часа 16 секунд:
Дим, ну че скажешь-то???
Мой волшебник это я сам. Всю архитектуру программы придумал лично, а ребята помогли воплотить её. Я бы и сам мог написать, но лень учить язык и его конструкции.
Аватара пользователя
dccharacter
 
Сообщения: 4995
Зарегистрирован: 10 дек 2010, 13:16
Откуда: Красногорск МО
прог. языки: C, Python, wiring/processing
ФИО: Андрей

Пред.След.

Вернуться в Блоги

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 0

cron