Цитата(Jevys @ Sep 23 2009, 20:40)

Встала задача по созданию программного обеспечения для обновления ПО 8051. Особенностью создаваемого устройства является то, что в процессе эксплуатации может потребоваться неоднократное обновление программного обеспечение. В связи с этим хочу спросить две вещи:
1. Можно ли вообще написать модуль ПО перепрошивки на Си? В проекте стоит опция максимальной оптимизации по размеру кода, при которой Кеil по идее может сам находить похожие куски кода и выделять их в подпрограммы. И тогда код, расположенный в ПО перепрошивки, будет вызывать код, который лежит за пределами области памяти программ перепрошивщика, что недопустимо. Остается только ассемблер?
2. Если все же писать на Си, то как жестко разместить программу перепрошивки с заданного адреса? Например 0xF800. И как это сделать в варианте на ассемблере.
1. Можно, какая разница на чем писать.
2. В кейле project->options for target->bl51 locate. В asm это делается с помощью например ORG или смотрите далее. Найдите ее описание.
Но в общем Вы ничего не написали о том как хотите обновлять прошивку. Если предположить, что Вы хотите по UART присылать новую прошиву и полностью переписывать содержимое внутренней flash-памяти программ, относящейся к основной программе. Следует прочитать "AN-112 UART IN-APPLICATION CODE LOADING EXAMPLES" у silabs. Я делал следующим образом. Создал 2 проекта - основной и bootloader. Основная прога ложится в память начиная, например, с адреса 0x100 (задается установками линкера). Естественно, вектора прерывания находятся по своим местам ниже этой точки. В проекте бутлоадера делаем установки линкера размещать код с выбранного Вами адреса 0xf800. Далее, в оба проекта явно добавляем копии стандартного startup.a51. Далее немного модифицируем эти копии. Для основного проекта:
Код
PUBLIC ?C_STARTUP
CSEG AT 100h <-измененный адрес!
?C_STARTUP: LJMP STARTUP1
RSEG ?C_C51STARTUP
для бутлоадера:
Код
CSEG AT 0;делаем переход на нужный адрес 0xf800
LJMP 0f800h
CSEG AT 0f800h; теперь прога начинается с этой позиции
?C_STARTUP: LJMP STARTUP1
Теперь при старте начинает выполняться бутлоадер. Если для него работы нет, то он передает управление основной программе вызовом application(); имеющей только прототип void (*application)(void)=(void code *)0x0100;
Основная программа при выполнении получает новую прошиву, размещает ее во внешней памяти, выставляет какой нибудь флаг. После этого сбрасывает контроллер или переходит на выполнение строки по 0-му адресу, бутлоадер видит флаг и начинается ...
Можно и самим бутлоадером получать прошиву. Зависит от Ваших требований. Описывайте подробнее желаемое. Можно и основную прогу начинать по 0-му адресу, а из нее вызывать бутлоадер. Но в моем варианте критическим является переписывание только 0-го сектора. Даже если в процессе перезаписи произошел сбой, пропадание питания или еще что-нибудь, бутлоадер начнет сначала.
Для обоих проектов создаем HEX-файлы и объеденяем их в один, не забывая удалить в одном из них строку окончания файла. Получившийся файл загружаем в камень при первой прошивке.
Ну и еще можно добавить в бутлоадер функции по расшифровке полученного перед записью во флэш и тогда можно прошивки передавать через третьих лиц