Перейти к содержанию
    

RFM50 (Si1000) + SmaRTClock + ISR

Здравствуйте

 

Решил обратиться сюда, т.к. сам уже все перепробовал и особого результата не добился.

Проблема такая:

 

Есть радиомодуль от HopeRF, который построен на базе Si1000. В этом Si1000 есть так называемый SmaRTClock для реализации часов реального времени.

Необходимо в заданный интервал (пускай будет раз в секунду) отправлять пакет с данными. Настраиваю обработчик прерывания INTERRUPT_RTC0ALARM и в нем делаю инкремент переменной и моргание светодиодом

 

...
U8 __xdata Pktcnt;
...
INTERRUPT (RTC0ALARM_ISR, INTERRUPT_RTC0ALARM)
{
    LEDTX = !LEDTX;
    Pktcnt = (Pktcnt == 255 ) ? 0 : Pktcnt + 1;
    RTC_Alarm = 1;
}

 

в основном теле программы я по событию отправляю некий пакет в котором передаю значение переменной Pktcnt

 

...
U8 __xdata RxBuffer[64];
U8 __xdata TxBuffer[64];
...

void main (void)
{

    while (1) {
        PCON |= 0x01;                    // Enter Idle mode 
        PCON = PCON;                   // Safety dummy instruction 
      
        if(RTC_Alarm) {
            RTC_Alarm = 0;                
            TxBuffer[0] = Pktcnt; 
            TxBuffer[1] = 0; 
            TxBuffer[2] = 0; 
            TxBuffer[3] = 0; 
            TxBuffer[4] = 0; 
            rtPhyTx( 5, TxBuffer );
        }
   }
}

 

по идее я должен на приемной стороне каждую секунду получать пакеты где значение Pktcnt каждый раз увеличивается на 1. Но ну тут то было. Светодиод моргает как положено раз в секунду. Пакеты тоже приходят раз в секунду, но значение поля меняется нифига не на 1. Изменяться оно может на 6 на 7. По разному бывает. Т.е. получаю в пакете 1, потом 7, потом 13 и т.д.

Мой мозг отказывается это понимать :smile3046:

 

Помогите пожалуйста разобраться в этих "чудесах" . :help:

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Есть радиомодуль от HopeRF, который построен на базе Si1000. В этом Si1000 есть так называемый SmaRTClock для реализации часов реального времени.

Изменяться оно может на 6 на 7. По разному бывает. Т.е. получаю в пакете 1, потом 7, потом 13 и т.д.

Мой мозг отказывается это понимать :smile3046:

 

Помогите пожалуйста разобраться в этих "чудесах" . :help:

 

Предупреждаю, ни с HopeRF ни с si1000 не работал. И не пойму каким компилятором Вы пользовались и все остальное. Но, как мне видится, Вы в обработчике прерываний дожны убрать какой-то аппаратный флаг. А раз Вы этого не делаете, то несколько раз подряд это прерывание вызывается до того как заснуть. Не угадал? Либо нужно переводить будильник на секунду вперед. Но у Вас я вообще не вижу никаких переводов и манипуляций с модулем SmaRTCclock в прерывании. Видимо эти действия выполняет какая-то ОС?

 

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Предупреждаю, ни с HopeRF ни с si1000 не работал. И не пойму каким компилятором Вы пользовались и все остальное. Но, как мне видится, Вы в обработчике прерываний дожны убрать какой-то аппаратный флаг. А раз Вы этого не делаете, то несколько раз подряд это прерывание вызывается до того как заснуть. Не угадал? Либо нужно переводить будильник на секунду вперед. Но у Вас я вообще не вижу никаких переводов и манипуляций с модулем SmaRTCclock в прерывании. Видимо эти действия выполняет какая-то ОС?

 

Компилятор я использую SDCC, хотя пробовал на Keil и "чудес" там было не меньше.

По идее Вы правы в начале обработчика надо бы выключать это прерывание с помощью

EIE1 &= ~0x02;

в на выходе включать

EIE1 |= 0x02;

 

но я так делал, и проблемы это не решало.

Выяснил тут, что действительно как то обработчик похоже несколько раз вызывается. Щас добавил флаг, чтобы значение устанавливалось только один раз и больше не менялось пока не считаю его. Помогло, но это тоже не выход. Почему возникает такой "дребезг" в ISR не понимаю. Обработчик делал по примеру от Silabs.

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

EIE1 &= ~0x02;

в на выходе включать

EIE1 |= 0x02;

нет, я имел ввиду другое. Нужно не сбрасывать флаг разрешения прерывания, а хардверный флаг, тот что выставляет железо. Как флаги TI и RI для UART. Например, у меня в f410 для сброса прерывания от RTC был такой код:

 

void RTCinter(void)interrupt 8 using 1
    {
    unsigned char contr;
    while(RTC0ADR & 0x80);
    RTC0ADR=RTC0CN;
    RTC0ADR|=0x80;
    while(RTC0ADR & 0x80);
    contr=RTC0DAT;
if(contr&0x20)            //OSCFAIL=1,сбой генератора часов
        {
    //!!! перезапускаем. 
        contr&=~0x20;
        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0CN;
        RTC0DAT=contr;

        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0CN;
        RTC0DAT=0;

        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0XCN;
        RTC0DAT=0x60;

        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0CN;
        RTC0DAT=0x90;
    }
if(contr&0x04)            //ALRM=1,сработал будильник, переставляем на секунду
    {// 
    contr&=~0x0c;        //сбрасываем ALRM и RTC0AEN-разрешение аларма 
        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0CN;
        RTC0DAT=contr;
        sec_tick=1;
        }
    }

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

нет, я имел ввиду другое. Нужно не сбрасывать флаг разрешения прерывания, а хардверный флаг, тот что выставляет железо. Как флаги TI и RI для UART. Например, у меня в f410 для сброса прерывания от RTC был такой код:

 

void RTCinter(void)interrupt 8 using 1
    {
    unsigned char contr;

if(contr&0x04)            //ALRM=1,сработал будильник, переставляем на секунду
    {// 
    contr&=~0x0c;        //сбрасываем ALRM и RTC0AEN-разрешение аларма 
        while(RTC0ADR & 0x80);
        RTC0ADR=RTC0CN;
        RTC0DAT=contr;
        sec_tick=1;
        }
    }

 

Блин, похоже так и есть. Вечером попробую и отпишусь. В примерах от Silabs они только флаг разрешения прерывания сбрасывали, вот я и сделал так же.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

нет, я имел ввиду другое. Нужно не сбрасывать флаг разрешения прерывания, а хардверный флаг, тот что выставляет железо. Как флаги TI и RI для UART. Например, у меня в f410 для сброса прерывания от RTC был такой код:

 

Ваш совет действительно помог. Спасибо! :beer:

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Ваш совет действительно помог. Спасибо! :beer:

 

 

Добрый день!

 

Столкнулся с подобной проблемой при разработке цепи (передатчик-приемник) на базе si1000.

 

Суть проблемы вкратце такова: передача срабатывает 1 раз, дальше приемник "наглухо" висит, ожидая пакет.

 

Пробовал добавить цикл инициализации параметров приемника после получения данных - результат тот же: висим.

 

Подскажите, кого нужно сбросить/обнулить/установить после приема данных.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Добрый день!

 

Столкнулся с подобной проблемой при разработке цепи (передатчик-приемник) на базе si1000.

 

Суть проблемы вкратце такова: передача срабатывает 1 раз, дальше приемник "наглухо" висит, ожидая пакет.

 

Пробовал добавить цикл инициализации параметров приемника после получения данных - результат тот же: висим.

 

Подскажите, кого нужно сбросить/обнулить/установить после приема данных.

 

А код для отправки и приема пакетов откуда брал? У Silabs или HopeRF? Код у них отличается. HopeRF взял код у Silabs, наговнякал по китайски туда всяких флагов и выдает этот код со своими модулями RFM50.

 

Еще если сам делал модуль, то подключил ли вывод NIRQ к P0.7 (к примеру), через подтяжку? Причем в доке пишут что надо через 100 кОм, но мне пришлось в параллель еще 100 кОм поставить чтобы заработало иначе тоже вело себя по разному.

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А код для отправки и приема пакетов откуда брал? У Silabs или HopeRF? Код у них отличается. HopeRF взял код у Silabs, наговнякал по китайски туда всяких флагов и выдает этот код со своими модулями RFM50.

 

Еще если сам делал модуль, то подключил ли вывод NIRQ к P0.7 (к примеру), через подтяжку? Причем в доке пишут что надо через 100 кОм, но мне пришлось в параллель еще 100 кОм поставить чтобы заработало иначе тоже вело себя по разному.

Код брал у Silabs. NIRQ Подключил к P0.1 (конт.35. (SBIT(IRQ, SFR_P0, 1); // SI100x Daughter Card Connection) как в исходнике), правда без подтяжки (внешней).

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Код брал у Silabs. NIRQ Подключил к P0.1 (конт.35. (SBIT(IRQ, SFR_P0, 1); // SI100x Daughter Card Connection) как в исходнике), правда без подтяжки (внешней).

 

Подтянул NIRQ через 33к, результат тот же. Один раз срабатывает, больше не хочет, висит наглухо. После разрыва питания или Reset при отладке в IDE Silabs также срабатывает один раз.

Где искать не знаю. Есть ли какие предложения?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Подтянул NIRQ через 33к, результат тот же. Один раз срабатывает, больше не хочет, висит наглухо. После разрыва питания или Reset при отладке в IDE Silabs также срабатывает один раз.

Где искать не знаю. Есть ли какие предложения?

 

А в сон не загоняете его? Может отправляет и засыпает с концами?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А в сон не загоняете его? Может отправляет и засыпает с концами?

В сон конечно вначале уходил, но убрал и ничего не помогло. Обратился в Silabs. Посоветовали убрать исполняемые коды (мои) и оставить только передачу, сменив несущую ( я работаю на частоте 434MHz). Таким образом удалось локализовать ошибку. При выполнении исполняемого кода нарушалась начальная установка порта Р2 (SDN). После принудительной установки SDN все заработало. Хотя я изначально выходил на начальную установку портов, но это почему-то не помогло. Дальше разбираться не стал, хотя наверное надо бы. Еще раз всем спасибо.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...