2014-02-08 4 views
1

У меня проблема в приложении, написанном для ST Microelectronics STM32F103 (ARM Cortex-M3 r1p1). RTOS - это uC/OS-III; dev - IAR EWARM v. 6.44; он также использует стандартную периферийную библиотеку ST v. 1.0.1.Как отклонить ошибку неисправности шины после конфигурации распределения приоритетных бит, Cortex M3 STM32F10x w uC/OS-III

Приложение не новое; он находится в разработке и на местах не менее года. Он использует два UART, I2C и один или два таймера. Недавно я решил рассмотреть приоритеты приоритетов прерывания, и я перераспределял приоритеты в рамках обзора (все, казалось, работало нормально).

Я обнаружил, что явное распределение битов группы и подприоритета в коде инициализации, включая RTOS, и поэтому, чтобы приложение соответствовало другому приложению (одному и тому же продукту, другому процессору) и новому приоритету схема, я добавил вызов NVIC_PriorityGroupConfig(), передав в NVIC_PriorityGroup_2. Это устанавливает значение PRIGROUP в Регистре управления прерыванием приложения и сброса (AIRCR) до 5, выделяя 2 бита для приоритета группы (приоритет) и 2 бита для подвыражения.

После этого я получаю неточное исключение ошибки шины при выполнении, а не сразу, но очень быстро после этого. (Больше о том, где я подозреваю, что это происходит через мгновение.) Поскольку это неточно (утверждается BFSR.IMPRECISERR), в BFAR нет ничего полезного (BFSR.BFARVALID clear).

Группа семейств STM32F реализует 4 бита приоритета. Хотя я не нашел здесь упомянутого явно в любом месте, это, по-видимому, самый значительный оттенок приоритета. Это предположение, по-видимому, подтверждается таблицей PRIGROUP, приведенной в документации (стр. 134, STM32F10xxx/20xxx/21xxx/L1xxx Руководство по программированию Cortex-M3 (Doc 15491, Rev 5), п. 4.4.5, Регистр прерывания приложения и управления (см. SCB_AIRCR), Таблица 45, Группа приоритетов, стр. 134).

В схеме ARM значения приоритета содержат некоторое количество битов приоритета группы или приоритета и некоторое количество битов приоритета. Биты группового приоритета - это верхние биты; нижеприведенность ниже. Значение 3-битного значения AIRCR.PRIGROUP определяет, как определяется распределение бит для каждого из них. PRIGROUP = 0 настраивает 7 бит группового приоритета и 1 бит субприорности; PRIGROUP = 7 конфигурирует 0 бит группового приоритета и 8 бит субприорности (таким образом, приоритеты - все сущностные приоритеты, и для исключений с устанавливаемыми приоритетами не возникает преференций).

Значение сброса AIRCR.PRIGROUP определяется как 0.

Для STM32F10x, так как только верхние 4 бита реализованы, по-видимому, следует, что PRIGROUP = 0, 1, 2, 3 должны все эквивалентны, поскольку все они соответствуют> = 4 бит группового приоритета.

Учитывая это предположение, я также попытался вызвать NVIC_PriorityGroupConfig() со значением NVIC_PriorityGroup_4, что соответствует значению PRIGROUP, равному 3 (4-битный групповой приоритет, без subpriority).

Это изменение также приводит к исключению ошибки шины.

К сожалению, STM32F103 является, я считаю, r1p1, и поэтому не реализует регистр вспомогательного управления (ACTLR; введен в r2p0), поэтому я не могу опробовать бит DISDEFWBUF (отключает использование буфера записи во время доступ к карте памяти по умолчанию, делая все ошибки шины точными за счет снижения производительности).

Я почти уверен, что ошибка шины происходит в ISR и, скорее всего, в UART ISR.Я установил точку останова в определенном месте в коде, запустил приложение и имел ошибку шины до того, как выполнение достигло точки останова; однако, если я прохожу через код в отладчике, я могу добраться до и после этого местоположения точки останова, и если я разрешу ему выполнить оттуда, я увижу ошибку шины через некоторое время после того, как я продолжу.

Следующим шагом будет попытка определить, какой ISR генерирует ошибку шины, чтобы я мог измерить ее и/или попытаться поймать ее вызов и пройти через нее.

Так что мои вопросы:

1) Кто-нибудь есть какие-либо предложения о том, как идти об определении происхождения исключения аварийного неточной шины более разумно?

2) Почему настройка PRIGROUP = 3 изменяет поведение системы, когда PRIGROUP = 0 является сбросом по умолчанию? (PRIGROUP = 0 означает 7-битную группу, 1-битный дополнительный приоритет, PRIGROUP = 3 означает 4-битную группу, 4-битный приоритет, STM32F10x реализует только верхние 4 бита приоритета.)

Многие, спасибо всем заранее для любых проницательных или не-NULL-указателей!

(И, конечно, если я понять это заранее, я буду обновлять этот пост с любой информацией, которая может оказаться полезной для других встречая такой же сценарий.)

ответ

1

Даже если BFAR не действует, вы все еще можете прочитать другие соответствующие регистры в вашей ISR шины замыкания:

void HardFault_Handler_C(unsigned int* hardfault_args) 
{ 
    printf("R0 = 0x%.8X\r\n",hardfault_args[0]);   
    printf("R1 = 0x%.8X\r\n",hardfault_args[1]);   
    printf("R2 = 0x%.8X\r\n",hardfault_args[2]);   
    printf("R3 = 0x%.8X\r\n",hardfault_args[3]);   
    printf("R12 = 0x%.8X\r\n",hardfault_args[4]);   
    printf("LR = 0x%.8X\r\n",hardfault_args[5]);   
    printf("PC = 0x%.8X\r\n",hardfault_args[6]);   
    printf("PSR = 0x%.8X\r\n",hardfault_args[7]);   
    printf("BFAR = 0x%.8X\r\n",*(unsigned int*)0xE000ED38); 
    printf("CFSR = 0x%.8X\r\n",*(unsigned int*)0xE000ED28); 
    printf("HFSR = 0x%.8X\r\n",*(unsigned int*)0xE000ED2C); 
    printf("DFSR = 0x%.8X\r\n",*(unsigned int*)0xE000ED30); 
    printf("AFSR = 0x%.8X\r\n",*(unsigned int*)0xE000ED3C); 
    printf("SHCSR = 0x%.8X\r\n",SCB->SHCSR);     
    while (1); 
} 

Если вы не можете использовать printf в момент выполнения, когда происходит эта специфическая Hard-Fault прерывания, а затем сохранить все вышеуказанные данные вместо этого в глобальном буфере, поэтому вы можете просмотреть его после достижения while (1).

Вот полное описание того, как подключить этот ISR к вектору прерывания (хотя, как я понял из вашего вопроса, то у вас уже есть это реализовано):

Jumping from one firmware to another in MCU internal FLASH

Вы могли бы быть в состоянии найти дополнительную информацию на вершине, что вы уже знаете, по адресу:

http://www.keil.com/appnotes/files/apnt209.pdf

+0

Я сделал беглый осмотр уложенных данных, но казалось, что я видел, не имеет смысла в то время. Я буду повторно исследовать (я надеялся, что был более простой подход, который я бы забыл). – Cygnus

+0

Пытался отредактировать мой последний комментарий, закончилось время: Кстати, у меня уже есть заметка приложения Keil (209). Для всех, кто мог бы посмотреть на это: обратите внимание, что волшебное значение на стр. 4, который переходит в SCB-> SHCSR, чтобы включить ошибки использования, памяти и шины ** неправильно ** - это должно быть 0x00070000, _not_ 0x00007000. (Хотя в зависимости от вашего компилятора и/или ОС есть, вероятно, макросы или функции, которые предпочтительнее использовать для ясности.) – Cygnus

+0

Из личного опыта найдите любую операцию над структурой, которая содержит 4-байтную переменную ('int 'или' float') или 8-байтная переменная ('double'). Эти нестандартные операции загрузки/хранения могут вызывать много косвенного ущерба (они могут не создавать прямого исключения, но они, несомненно, генерируют неправильное значение, которое, например, если впоследствии используется как индекс для массива, скорее всего, нарушение доступа). –

 Смежные вопросы

  • Нет связанных вопросов^_^