EXeGLuMATOR 0 3 мая, 2012 Опубликовано 3 мая, 2012 · Жалоба Имеется следующий проектик, как водится, состоящий из двух частей. Бутлоадер и основная программа. Причем в основной программе также есть блок перепрошивки "самой себя". Используется RL-ARM. Вопрос в следующем - как после перпрошивки перезапустить проц? Собсно как перезапустить более или менее понятно. Проблема в том, что после перезапуска все уходит в HardFault при вызове os_sys_init(). Т.е. перешиваемся, рестартуем, код запускается, но как только доходит до инита операционки - вылет. Кто знает, как это победить? Компилятор ессно Keil. :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 236 3 мая, 2012 Опубликовано 3 мая, 2012 · Жалоба как делаете рестарт? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
EXeGLuMATOR 0 3 мая, 2012 Опубликовано 3 мая, 2012 · Жалоба как делаете рестарт? А по всякому пробовал. Благо вариантов в ветке представлено. :) И так: static const uint16_t code[] = { 0xF850, 0xDB04, // LDR.W SP, [R0], #4 0x6800, // LDR.W R0, [R0] 0x4700, // BX R0 }; ((void (*)(uint32_t))(1 + (int)code))(PAYLOAD_START_ADDR); И так: typedef void (*pFunction)(void); pFunction Jump_To_Application; uint32_t JumpAddress; void (*user_code_entry)(void); user_code_entry = ((void (*)(void))(PAYLOAD_START_ADDR+4)); user_code_entry(); И так, что в общем идентично предыдущему, но без смещения: void execute_user_code(void) { void (*user_code_entry)(void); user_code_entry = (void (*)(void))USER_START_SECTOR_ADDRESS; user_code_entry(); } Результат один. Перезапуск удается, код запускается, инитится вся периферия, но как только дело доходит до запуска непосредственно оси функцией os_sys_init(TaskInit); - все вылетает в HARD Fault Handler. Причем изначально все запускается и работает без нареканий. Программа скомпилирована, заружена и запущена без лоадера, с адреса 0. В качестве эксперимента просто пытаюсь рестартовать проц из самой проги. Потом уже все остальное. На 23хх процах была подобная фигня при перезагрузке лоадером - вылечилось дефайнами RAM_INTVEC RAM_MODE REMAP. Сейчас не проходит. Где-то что-то упускаю. :( Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Артём__ 0 3 мая, 2012 Опубликовано 3 мая, 2012 · Жалоба Результат один. Перезапуск удается, код запускается, инитится вся периферия, но как только дело доходит до запуска непосредственно оси функцией os_sys_init(TaskInit); - все вылетает в HARD Fault Handler. Причем изначально все запускается и работает без нареканий. Программа скомпилирована, заружена и запущена без лоадера, с адреса 0. В качестве эксперимента просто пытаюсь рестартовать проц из самой проги. Потом уже все остальное. На 23хх процах была подобная фигня при перезагрузке лоадером - вылечилось дефайнами RAM_INTVEC RAM_MODE REMAP. Сейчас не проходит. Где-то что-то упускаю. :( У вас в boot-е используется Systick? Может bootloader создаёт дополнительную задержку и происходит прерывание таймера SysTick раньше чем ОСь проинициализировалась? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
AlexandrY 3 3 мая, 2012 Опубликовано 3 мая, 2012 · Жалоба Т.е. перешиваемся, рестартуем, код запускается, но как только доходит до инита операционки - вылет. Кто знает, как это победить? Компилятор ессно Keil. :) Вот такой код работает в моих приложениях под RL-ARM /*------------------------------------------------------------------------------ ------------------------------------------------------------------------------*/ __asm void Select_msp (void) { MOVNE R0,#0x00 MSR CONTROL,R0 BX LR ALIGN } /*------------------------------------------------------------------------------ ------------------------------------------------------------------------------*/ static void Goto_app(void) { // Запрещаем все источники прерываний SysTick->CTRL = 0; NVICx->ICER[0] = 0xFFFFFFFF; NVICx->ICER[1] = 0xFFFFFFFF; Select_msp(); __MSR_MSP(*(vu32*) PROGRAMM_AREA_BEG_ADDR); APP_entry = (fnc)(*(vu32*) (PROGRAMM_AREA_BEG_ADDR + 4)); APP_entry(); } Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 236 4 мая, 2012 Опубликовано 4 мая, 2012 · Жалоба А по всякому пробовал. Благо вариантов в ветке представлено. :) И ни одного правильного Вы не использовали ;) Результат один. Перезапуск удается, код запускается, инитится вся периферия, но как только дело доходит до запуска непосредственно оси функцией os_sys_init(TaskInit); - все вылетает в HARD Fault Handler. Причем изначально все запускается и работает без нареканий. Программа скомпилирована, заружена и запущена без лоадера, с адреса 0. В качестве эксперимента просто пытаюсь рестартовать проц из самой проги. Потом уже все остальное. На 23хх процах была подобная фигня при перезагрузке лоадером - вылечилось дефайнами RAM_INTVEC RAM_MODE REMAP. Сейчас не проходит. Где-то что-то упускаю. :( Вы разницу понимаете между аппаратным ресетом, после которого у вас всё работает и тем, что вы делаете в приведённых примерах? Разница в том, что в первом случае вся периферия процессора изначально находится в дефолтном состоянии, а во втором - нет. У вас инициализирующий код где-то завязан на это дефолтное состояние после сброса. Я уже приводил правильный способ сброса - аппаратный сброс через внутренний сторожевик. Либо через внешний (который у должен быть в любом нормальном устройстве) блокированием импульсов WDI. После него все узлы контроллера будут находиться в дефолтном состоянии, почти как после включения питания (отличие только, что внешние устройства на плате не будут в дефолтном состоянии). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Sanya_kv 0 4 мая, 2012 Опубликовано 4 мая, 2012 · Жалоба EXeGLuMATOR А какое ядро Вы используете ARM 7 или Cortex XX Предполагаю, что функцию перехода на начало основной программы, Вы вызываете из ”User mode”, и как следствие не правильная инициализация стеков в основной программе (Из User mode не все регистры доступны.). Я, после обновления основной программы из загрузчика, вызываю программное прерывание (Supervisor mode), и от туда запускаю основную программу. При использовании RL-ARM (в Keil), необходимо использовать SWI(8) или более . Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
EXeGLuMATOR 0 21 мая, 2012 Опубликовано 21 мая, 2012 · Жалоба Отвлекся на другие дела... Не совсем может понятно написал. В лоадере RL-ARM не используется. Там все просто. Камушек LPC1343. Используется встроенный HID - драйвер. По HID происходит обносвление основной прошивки. Потом соотв переход на неё. Из встроенной периферии используется помимо USB еще UART - для вывода сообщений. Ну GPIO еще. И собственно все. Так вот, если заливать и стартовать основной код с адреса 0 - то он сам себя прекрасно перезапускает. Тестовый код тоже простой - ничего не инитится, только ЮАРТ - вывод строчки на терминал и далее - перезагрузка. Следующий этап - через лоадер. Заливаем софтинку лоадером. Если простая тестовая софтинка - та-же что и впредыдущем этапе - все нормально. Все обновляется, запускается и выполняется переход на основной код. Там тоже все нормально. Но как только появляется RL-ARM в пользовательском софте - все. Никаких движений после перехода на пользовательский софт. Стартапы одинаковые - тестовый проект сделан на базе основного, только урезан по максимуму. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
net 0 23 мая, 2012 Опубликовано 23 мая, 2012 · Жалоба странно - у нас из под загрузчика с rtx запускается задача с rtx и никаких проблем нет так обсуждать тяжеловато все но проблем быть не должно - может просто явный ляп не видите Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
EXeGLuMATOR 0 23 мая, 2012 Опубликовано 23 мая, 2012 · Жалоба Да может и явный ляп. Понять-бы где. На LPC2368 - нужно было стартап править и таблицу SWI. Здесь не пойму, что не так. Может кто-нибудь startup_LPC13xx.s и SVC_Table.s от рабочих проектов с RL-ARM в качестве загружаемой софтины выложить? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 236 24 мая, 2012 Опубликовано 24 мая, 2012 · Жалоба Не очень понятно - зачем упорно пытаться сделать сброс коряво - переходом на стартовый адрес, вместо корректного ресета через сторожевик??? Наверно я чего-то не понимай :) Если по каким-то религиозным соображениям не нравится сторожевик, то часто в контроллерах есть другие документированные способы сброса. Например в Cortex-M3: регистр AIRCR (0xE000ED0C). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
EXeGLuMATOR 0 24 мая, 2012 Опубликовано 24 мая, 2012 · Жалоба Не очень понятно - зачем упорно пытаться сделать сброс коряво - переходом на стартовый адрес, вместо корректного ресета через сторожевик??? Наверно я чего-то не понимай :) Если по каким-то религиозным соображениям не нравится сторожевик, то часто в контроллерах есть другие документированные способы сброса. Например в Cortex-M3: регистр AIRCR (0xE000ED0C). Ну сбросили камень. Дальше что - опять заходим в лоадер. Мне не сброс нужен а переход из лоадера на основную программу, которая находится далеко не на 0 адресе. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 136 24 мая, 2012 Опубликовано 24 мая, 2012 · Жалоба Ну сбросили камень. Дальше что - опять заходим в лоадер. А из него "с чистого листа" BX R0. При этом уверены, что ни прерывания не разрешены, ни запросы на них необслуженные не висят, ну и т.д. Мне не сброс нужен а переход из лоадера на основную программу, которая находится далеко не на 0 адресе.Программа-то ладно, где у вас вектора от этой программы расположены? Куда попадет инструкция SWI - в загрузчик? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
EXeGLuMATOR 0 24 мая, 2012 Опубликовано 24 мая, 2012 · Жалоба А из него "с чистого листа" BX R0. При этом уверены, что ни прерывания не разрешены, ни запросы на них необслуженные не висят, ну и т.д. Программа-то ладно, где у вас вектора от этой программы расположены? Куда попадет инструкция SWI - в загрузчик? Ну так в лоадер-то все равно заходить нужно. Смысл - ведь все работало и так раньше. Ппросто потребовалось перенести проект на другой проц. Не могу понять в чем дело. Вот с тем, где все вектора будут лежать и как их положить куда нужно и хочу разобраться. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 236 24 мая, 2012 Опубликовано 24 мая, 2012 · Жалоба Ну так в лоадер-то все равно заходить нужно. Смысл - ведь все работало и так раньше. Ппросто потребовалось перенести проект на другой проц. Не могу понять в чем дело. Вот с тем, где все вектора будут лежать и как их положить куда нужно и хочу разобраться. Значит у вас не работает запуск рабочего ПО и при включении питания, а не только при ресете из него. Значит - надо вначале добиться этого, а потом сброс через сторожевик сделает его подобным PowerOn. "Как положить куда нужно" описано в командном файле компоновщика (в IAR это - *.icf) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться