Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: AT91SAM7X256 запретить прерывания временно
Форум разработчиков электроники ELECTRONIX.ru > Сайт и форум > В помощь начинающему > ARM, 32bit
TU-104
Нужно на время запретить прерывания при записи внутренней флешки.
Делаю так:

Код
ISR_MASK = AT91C_BASE_AIC->AIC_IMR;
AT91C_BASE_AIC->AIC_IDCR = 0xFFFFFFFF;  // запрет
... FalshDWrite(...);
AT91C_BASE_AIC->AIC_IECR = ISR_MASK; // восстановить


В какой-то момент виснет на записи в IDCR=FFFFFFFF

Проверял так, без записи во внутреннюю флеш:
Код
printf(".");
ISR_MASK = AT91C_BASE_AIC->AIC_IMR;  /*printf("m");*/
printf(",");
AT91C_BASE_AIC->AIC_IDCR = 0xFFFFFFFF;
j++;
printf("|");
AT91C_BASE_AIC->AIC_IECR = ISR_MASK;
j++;


Соответственно, в консоли:
Код
,|.,|.,|.,|.,|.,|.,
и зависает.

Правильно ли так запрещать прерывания? Что еще попробовать? Заранее благодарю любые за любые советы

Включен PIT, TC0, UART, прерывания от ног.
И еще, вроде бы только с PIT -ом виснет, попробую его отдельно отключить...
Fedor
Вот пример из FreeRTOS
CODE

#define portDISABLE_INTERRUPTS() \
__asm volatile ( \
"STMDB SP!, {R0} \n\t" /* Push R0. */ \
"MRS R0, CPSR \n\t" /* Get CPSR. */ \
"ORR R0, R0, #0xC0 \n\t" /* Disable IRQ, FIQ. */ \
"MSR CPSR, R0 \n\t" /* Write back modified value. */ \
"LDMIA SP!, {R0} " ) /* Pop R0. */

#define portENABLE_INTERRUPTS() \
__asm volatile ( \
"STMDB SP!, {R0} \n\t" /* Push R0. */ \
"MRS R0, CPSR \n\t" /* Get CPSR. */ \
"BIC R0, R0, #0xC0 \n\t" /* Enable IRQ, FIQ. */ \
"MSR CPSR, R0 \n\t" /* Write back modified value. */ \
"LDMIA SP!, {R0} " ) /* Pop R0. */
TU-104
Спасибо! Ночь проработало без зависаний. Только сама FreeRTOS не стартует, если перед прыжком таким способом запрещать прерывания.
Сергей Борщ
Цитата(TU-104 @ May 28 2014, 07:08) *
Спасибо! Ночь проработало без зависаний. Только сама FreeRTOS не стартует, если перед прыжком таким способом запрещать прерывания.
Перед прыжком куда? По таким симптомам поставить диагноз невозможно (разве что телепатически, но это на другой форум надо). Описывайте задачу, показывайте исходники.
TU-104
Есть подобие бутлоадера, который распологается с начала флеш, 0х100000.
Есть Freertos, которая лежит дальше с дреса 0х110000.
Из бутлоадера делаю запуск freertos так:
Код
  //запрет всех прерываний
  //ISR_DISABLE();
  ISR_DISABLE_IDCR();
  JUMP_ADDR = (void(*)(void))(0х110000);
  JUMP_ADDR();

Или так тоже неправильно делать?

Во freertos, как подсказали в соседней ветке, я сначала копирую первые 0х80 байт в оперативную память.
"FreeRTOS не стартует" - уточняю: доходит до запуска шедуллера и виснет.
Если же этим макросом не запрещать прерывания, то шедуллер стартует и работает
Fedor
Разрешите прерывания указанным способом перед первым вызовом xTaskCreate, но если работает в thumb режиме то вот таким способом (оттуда же из FreeRTOS)
Код
void vPortEnableInterruptsFromThumb( void )
{
    asm volatile (
        "STMDB    SP!, {R0}        \n\t"    /* Push R0.                                    */
        "MRS    R0, CPSR        \n\t"    /* Get CPSR.                                */
        "BIC    R0, R0, #0xC0    \n\t"    /* Enable IRQ, FIQ.                            */
        "MSR    CPSR, R0        \n\t"    /* Write back modified value.                */
        "LDMIA    SP!, {R0}        \n\t"    /* Pop R0.                                    */
        "BX        R14" );                    /* Return back to thumb.                    */
}
andrewlekar
Лучше запретите прерывания глобально, а то у вас в стеке какая-то чушь останется после прыжка. В FreeRTOS после инициализации явно разрешите прерывания.
Сергей Борщ
Цитата(TU-104 @ May 28 2014, 09:34) *
Или так тоже неправильно делать?
Хм. Трудно сказать, не зная точно, что вы поместили внутрь ISR_DISABLE() и ISR_DISABLE_IDCR().
Цитата(TU-104 @ May 28 2014, 09:34) *
Если же этим макросом не запрещать прерывания, то шедуллер стартует и работает
В вашем коде два макроса, при этом один закомментирован. Так в каком случае работает, а в каком - нет?
Цитата(TU-104 @ May 28 2014, 09:34) *
Во freertos, как подсказали в соседней ветке, я сначала копирую первые 0х80 байт в оперативную память.
Дайте, пожалуйста, ссылочку, почитаю. Надеюсь, память в ОЗУ под эти 0x80 байт вы резервируете?

На самом деле таблица векторов ARM7TDMI занимает 8 слов, плюс еще 7 слов могут занимать адреса векторов для перехода командами LDR PC, адрес. Итого достаточно копировать 60 байтов. И делать это в загрузчике (хотя это больше вопрос вкуса). Расположение вашей программы и загрузчика с адресов 01xxxxxx (а не с 0) - правильное.

Цитата(TU-104 @ May 28 2014, 09:34) *
"FreeRTOS не стартует" - уточняю: доходит до запуска шедуллера и виснет.
Отладчика нет?
TU-104
Цитата(Fedor @ May 28 2014, 13:13) *
Разрешите прерывания указанным способом перед первым вызовом xTaskCreate, но если работает в thumb режиме то вот таким способом (оттуда же из FreeRTOS)
Код
void vPortEnableInterruptsFromThumb( void )

Попробую.

Цитата(Сергей Борщ @ May 28 2014, 13:26) *
Так в каком случае работает, а в каком - нет?
Дайте, пожалуйста, ссылочку, почитаю. Надеюсь, память в ОЗУ под эти 0x80 байт вы резервируете?

На самом деле таблица векторов ARM7TDMI занимает 8 слов, плюс еще 7 слов могут занимать адреса векторов для перехода командами LDR PC, адрес. Итого достаточно копировать 60 байтов. И делать это в загрузчике (хотя это больше вопрос вкуса). Расположение вашей программы и загрузчика с адресов 01xxxxxx (а не с 0) - правильное.

Отладчика нет?

ISR_DISABLE_IDCR() обозвал способ из своего первого сообщения:
AT91C_BASE_AIC->AIC_IDCR = 0xFFFFFFFF;
ISR_DISABLE - макрос из фриртоса, предложенный Федором во втором сообщении.
Если пользуюсь вторым макросом, то виснет на старте шедуллера.

Тема про бутлоадер вот
http://electronix.ru/forum/index.php?showt...p;#entry1254289
Да, просто скопировал с запасом круглое число rolleyes.gif . В ИАРе указал, что ОЗУ начинается с 0х2000080.

Отладчика нет.. Точнее, достать можно JLINK, но jtag не разведен, припаиваться буду целый день
Сергей Борщ
Цитата(TU-104 @ May 28 2014, 12:52) *
Если пользуюсь вторым макросом, то виснет на старте шедуллера.

Отладчика нет.. Точнее, достать можно JLINK, но jtag не разведен, припаиваться буду целый день
Посмотрел описание процессора и описание самого ядра от ARM и ни там ни там не нашел указания, в каком состоянии находятся биты запрета прерывания в ядре при старте. Учитывая, что они называются "Interrupt disable bits" можно предположить, что прерывания ядра по умолчанию включены и FreeRTOS может полагаясь на это не трогать их и не разрешать прерывания дополнительно. Увы, у меня нет под рукой устройства на ARM7TDMI чтобы проверить это предположение. Но если я прав, вам действительно надо перед передачей управления запрещать все прерывания в AIC записью в IDCR не трогая CPSR.

А вот для первой вашей задачи - "временно запретить все прерывания на время записи во флешь" надо использовать манипуляцию с CPSR.

Кстати, а чем обусловлен ваш выбор этого морально устаревшего контроллера?
TU-104
Цитата(Сергей Борщ @ May 28 2014, 16:42) *
надо перед передачей управления запрещать все прерывания в AIC записью в IDCR не трогая CPSR.
А вот для первой вашей задачи - "временно запретить все прерывания на время записи во флешь" надо использовать манипуляцию с CPSR.

Кстати, а чем обусловлен ваш выбор этого морально устаревшего контроллера?

Ясно, спасибо.
По выбору: платы лежали года 3, в один момент понадобилось срочно запустить )) А выбирать, переразводить - это время
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.