Полная версия этой страницы:
MSP430F5510
usercod
Jan 17 2012, 11:55
Добрый день!
Для хранения номера прибора и установочных коэффициентов использую сегмент памяти INFOD. Всего получается 10 байт.
Проблема в том, что иногда приходят команды по I2C, (одна за другой через 5мс) по которым нужно эти коэффициенты переписывать. Если приходит одна команда, после которой I2C молчит более 30мС -все нормально. Но если команды записи идут через 5мС - возникают проблемы. Как я понял время стирание сегмента может быть от 23 до 32 мС. Сейчас во время записи во флеш прерывания запрещены, поэтому если команда приходит именно в этот момент запись следующего коэф. пропускается.
Как лучше оптимизировать запись во флеш, чтобы избежать таких огромных задержек на стирание сегмента?
Можно в принципе, переписывать массив данных со смещением в 10 байт, но когда сегмент закончится, его нужно будет стереть и теоретически в этот момент может прийти последовательность команд записи.
rezident
Jan 17 2012, 19:42
Для реализации желаемого во-первых, ваша функция приема данных через I2C во время записи во Flash должна выполнятся из SRAM, а не из Flash. Во-вторых, если вы хотите использовать прием именно по прерываниям, то функцию обработчика прерывания и главное сами вектора прерываний также нужно разместить в SRAM. Для этого в серии MSP430F5xxx имеется функция маппирования векторов прерываний. См. описание 1.3.6.1 Alternate Interrupt Vectors в MSP430x5xx/MSP430x6xx Family User's Guide.
usercod
Jan 18 2012, 06:32
rezident, спасибо за ответ.
Буду делать согласно вашему совету. Есть несколько вопросов.
Самый главный тупой вопрос: Как после реализации это будет работать, если честно пока не представляю весь механизм процесса.
По первому пункту более-менее понятно, мне нужно разместить обработчик прерывания I2C в SRAM.
Второй пункт вызывает затруднения в реализации, если можно по-подробнее как это нужно сделать. И последнее, не пострадают ли остальные прерывания, которые также есть в проекте?
rezident
Jan 18 2012, 22:04
К сожалению я к серией MSP430F5xxx не работал, поэтому большего, чем написано в документации, я вам рассказать не смогу.
Перед ремапом нужно скопировать все вектора прерываний. Потому, что установка SYSRIVECT в регистре SYSCTL оказывает влияние на все вектора сразу. Надеюсь, вы понимаете, как работает система прерываний и в чем разница между вектором прерывания и функцией обработки прерывания? Если нет, то см. раздел 1.3 Interrupts в User'Guide. Могу пояснить лишь "на пальцах".
Вектор прерывания это адрес, который загружается из определенной ячейки памяти в счетчик команд (PC) при возникновении прерывании. Предшествует загрузке сохранение на стеке регистра состояний (SR), текущего содержимого PC и очистка некоторых битов в регистре SR, которые отвечают за тактирование ядра МК. Соотвественно, после загрузки адреса из вектора прерывания в PC программа будет дальше выполнятся именно с этого адреса по которому в свою очередь должна находится функция обработки прерывания. В конце функции обработчки прерывания выполняется специальная команда (reti), возвращаюшая из стека значения PC и SR, которые были до возникновения прерывания.
Таблица векторов прерываний, содержащая адреса функций обработки прерываний, находится на границе 64кБ раздела Flash-памяти. При записи/стирании Flash доступ к ней (к Flash, а не только таблице векторов) недопустим. Поэтому на время записи/стирания Flash прерывания запрещают. Чтобы можно было использовать прерывания во время записи/стирания нужно, чтобы таблица векторов прерываний находилась в SRAM, ограничений на использование которой в этот момент нет. Для этого предусмотрен альтерантивное место для размещения таблицы в конце SRAM (Alternate Interrupt Vectors) и механизм, который позволяет переадресовать извлечение векторов из этого альтернативного места.
Так вот перед использованием вам требуется скопировать из Flash в SRAM а) всю таблицу векторов прерываний на место размещения Alternate Interrupt Vectors и как минимум б) функцию обработчика прерываний I2C и в) функцию записи во Flash. Функции эти в свою очередь должны быть "автономными" и не использовать другие функции, размещенные и вызываемые из Flash. При компиляции вы должны выделить сегмент в SRAM под размщение ваший функций и векторов прерываний, указав компилятору, чтобы он не использовал эту часть SRAM под размещение данных, стека или "кучи".
usercod
Jan 20 2012, 04:57
Спасибо. Очень хороший ответ. Буду реализовывать.
Для просмотра полной версии этой страницы, пожалуйста,
пройдите по ссылке.