Misha537 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба Здравствуйте! Пишу код для MSP430F449. Есть два разных проекта: основная программа и загрузчик для обновления программы по uart. В xcl файле описал расположение кодов независимо друг от друга. xcl-файл основной программы: -Z(CONST)DATA16_C,DATA16_ID,TLS16_ID,DIFUNCT,CHECKSUM=1200-EFFF -Z(CODE)ISR_CODE,CODE_ID=1200-EFFF -Z(CODE)CSTART=2000-20FF -P(CODE)CODE=1200-EFFF -Z(CODE)INTVEC=FFE0-FFFF -Z(CODE)RESET=FFFE-FFFF xcl-файл загрузчика: -Z(CONST)DATA16_C,DATA16_ID,TLS16_ID,DIFUNCT,CHECKSUM=F000-FDFF -Z(CODE)ISR_CODE,CODE_ID=F000-FDFF -Z(CODE)CSTART=F800-F8FF -P(CODE)CODE=F000-FDFF -Z(CODE)RESET=FFFE-FFFF В загрузчике прерывания не использую. Выполняю следующие действия в загрузчике: 1. Очищаю все сектора флеш-памяти по адресам основной программы и сектор векторов прерываний. 2. Постранично (по 256 слов) прописываю код основной программы во флеш-память. 3. Когда записываю адрес перехода при сбросе по адресу 0xFFFE-0xFFFF, контроллер зависает. 4. Помогает аппаратный сброс программатором. 5. После этого нормально работает загрузчик и основная программа. Что я делаю не так, подскажите пожалуйста. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
rezident 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба Что я делаю не так, подскажите пожалуйста.У вас ошибка в алгоритме/идеологии программы. Вектор RESET не может использоваться обеими программами. RESET должен использовать только загрузчик. После сброса всегда должен запускаться загрузчик, который в соответствии с какими-то критериями определяет: оставаться в загрузчике для апдейта основной программы или передать ей управление. Соответственно тело загрузчика и вектор сброса переписываться апдейтом программы не должны. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
d7d1cd 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба Я видел подобное сочетание программ. В основную программу можно было через UART отправить команду, по которой: 1. Управление передавалось на загрузчик; 2. Загрузчик менял вектор сброса на адрес своего начала. То есть, даже после выключения\включения начинал работать загрузчик. Работал он до тех пор, пока ему не отправлялась другая команда - на выход из загрузчика. Он переписывал вектор сброса на начало основной программы и передавал ей управление. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Misha537 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба У вас ошибка в алгоритме/идеологии программы. Вектор RESET не может использоваться обеими программами. RESET должен использовать только загрузчик. После сброса всегда должен запускаться загрузчик, который в соответствии с какими-то критериями определяет: оставаться в загрузчике для апдейта основной программы или передать ей управление. Соответственно тело загрузчика и вектор сброса переписываться апдейтом программы не должны. А как же быть с векторами прерываний основной программы? Они же в одном сегменте с вектором сброса загрузчика. Если их перепишу, то и вектор сброса тоже придется переписать. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Артём__ 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба А как же быть с векторами прерываний основной программы? Они же в одном сегменте с вектором сброса загрузчика. Можно не переписывать вектор сброса: если модифицируется страница на которой он расположен, то сначала прочитать что записано на месте вектора сброса, потом эти же байты туда и записать. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
rezident 0 14 ноября, 2012 Опубликовано 14 ноября, 2012 · Жалоба А как же быть с векторами прерываний основной программы? Они же в одном сегменте с вектором сброса загрузчика. Если их перепишу, то и вектор сброса тоже придется переписать.Для таких случаев вектора программно эмулируют перемещение векторов в другой сектор Flash или в ОЗУ. Хотя, например, в серии MSP430F5xxx даже аппаратный ремап векторов в ОЗУ реализовали. То бишь на место штатных векторов записывают адреса ячеек памяти в которых лежат команды JMP непосредственно на функции обработчиков прерываний. И обновляются не сами вектора, а та область Flash на которую они ссылаются. Для корректного функционирования бутлоадер должен работать по опросу флагов UART, не используя прерываний UART, особенно в случае, если этот же UART используется в основном программном модуле. Кроме того, бутлоадер должен контролировать целостность прошивки основного (загружаемого) программного модуля (например по CRC) и валидность перемещенных векторов прерываний. При нарушении целостности прошивки бутлоадер не передает управление основному программному модулю, а "крутится" внутри себя. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
KARLSON 1 15 ноября, 2012 Опубликовано 15 ноября, 2012 (изменено) · Жалоба Я делал такую вещь. 2 программы, загрущик и основная. В загрущике в секторе векторов только адрес начала программы (то же не использую прерывания) @FFFE 00 F6 В прошивке основной программы меняю адрес начала программы по тому же адресу на начало загрущика. Заливаю основную программу через свой загрущик. В конце загрущик считает контрольную суммму всей флеш памяти и сохраняет её в информационной памяти. Затем считываю через программатор всю флеш память и этот текстовый файл передаю в производство, что бы не заливали основную программу сами, т.к. это долго. Кстати, загрущик у меня стирает память по сегментно, не всё сразу. При старте загрущик считает контрольную сумму всей памяти и сверяет с сохранённым значением. Если правильно, переходим на адрес основной прошивки. Вот и всё. Изменено 15 ноября, 2012 пользователем KARLSON Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Misha537 0 15 ноября, 2012 Опубликовано 15 ноября, 2012 · Жалоба Я делал такую вещь. 2 программы, загрущик и основная. В загрущике в секторе векторов только адрес начала программы (то же не использую прерывания) @FFFE 00 F6 В прошивке основной программы меняю адрес начала программы по тому же адресу на начало загрущика. Заливаю основную программу через свой загрущик. В конце загрущик считает контрольную суммму всей флеш памяти и сохраняет её в информационной памяти. Затем считываю через программатор всю флеш память и этот текстовый файл передаю в производство, что бы не заливали основную программу сами, т.к. это долго. Кстати, загрущик у меня стирает память по сегментно, не всё сразу. При старте загрущик считает контрольную сумму всей памяти и сверяет с сохранённым значением. Если правильно, переходим на адрес основной прошивки. Вот и всё. Я делаю точно также. Наконец нашел причину перезагрузки контроллера после записи векторов прерываний. Я писал с адреса 0xFFE0 256 слов вместо 16 и перетирал флеш с адреса 0x0000. Невнимательность. Всем спасибо за помощь! Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться