Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Bootloader, но не совсем, на Atmega64
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > Cредства разработки для МК > IAR
statim
Доброго времени суток.
Существует задача перешивать базу данных, находящуюся во FLASH контроллера, из собственной EEPROM
Загрузчик базы я написал, работает, а вот с оновным кодом проблеммы...
Как сделать перезагрузку контроллера желательно не через WD?
По идее я сначала заливаю основную программу, затем шью в конец FLASH бутлоадер.
Как можно узнать что проц стартует правильно т.е. с бутлоадера (его работу проверял через Jtag), и при перезагрузке, вызванной основной прграммой.
Может есть какой-то другой способ перешивать флешь, и загрузчик отдельный делать не обязательно, а надо просто функцию в бут области разместить? (я не знаю как).

Fuses
OSCCAL = C7, C7, BF, BF
BLEV = 0
BODEN = 0
SUT = 2
CKSEL = F
BLB1 = 3
BLB0 = 3
OCDEN = 1
JTAGEN = 0
CKOPT = 0
EESV = 1
BSIZ = 2
BRST = 0
M103C = 1
WDTON = 1

Собственно код загрузчика (слизан у Атмел)

Код
/**************** Библиотеки общего назначения ******************/
#include <board.h>

/**************** Подключаемые внешние модули всякие******************/
#include "main.h"
#define BLOCKSIZE   256 // байт

#define SCMDCOUNT   70
#define SCMDLEN     (1/*блока*/ * BLOCKSIZE /**/) // 256
#define SCMDADDR    10240

#define LCMDCOUNT   15
#define LCMDLEN     (2/*блока*/ * BLOCKSIZE /**/) //512
#define LCMDADDR    (SCMDADDR+(SCMDCOUNT*SCMDLEN))



typedef struct database{
  unsigned short s_addr;
  unsigned short e_addr;
  unsigned short data[384];
}pdatabase;

#define _ENABLE_RWW_SECTION() __DataToR0ByteToSPMCR_SPM( 0x00, 0x11 )
#define _WAIT_FOR_SPM() while( SPMCR & (1<<SPMEN) );
#define _LOAD_PROGRAM_MEMORY(addr) __load_program_memory( (const unsigned char __flash *) (addr) )
#define _FILL_TEMP_WORD(addr,data) __AddrToZWordToR1R0ByteToSPMCR_SPM( (void __flash *) (addr), data, 0x01 )
#define _PAGE_ERASE(addr) __AddrToZByteToSPMCR_SPM( (void __flash *) (addr), 0x03 )
#define _PAGE_WRITE(addr) __AddrToZByteToSPMCR_SPM( (void __flash *) (addr), 0x05 )


__no_init __eeprom database db@15;

void BlockLoad(unsigned int size, unsigned long *address, unsigned short *cnt)
{

    unsigned int data;
    long tempaddress;
        tempaddress = (*address);  // Store address in page.
        do
    {
          
            data = db.data[(*cnt++)];
            #pragma diag_suppress=Pe1053 // Suppress warning for conversion from long-type address to flash ptr.
            _FILL_TEMP_WORD(*address,data);
            #pragma diag_default=Pe1053 // Back to default.
            (*address)+=2; // Select next word in memory.
            size -= 2; // Reduce number of bytes to write by two.
        } while(size); // Loop until all bytes written.

    #pragma diag_suppress=Pe1053 // Suppress warning for conversion from long-type address to flash ptr.
    _PAGE_WRITE(tempaddress);
    #pragma diag_default=Pe1053 // Back to default.
    _WAIT_FOR_SPM();
    _ENABLE_RWW_SECTION();
//        (*address) >>= 1; // Convert address back to Flash words again.

}


__C_task main(void)
{
unsigned long addr;
unsigned long s_addr;
unsigned long e_addr;
unsigned short i;
unsigned char block_count;
unsigned short ee_cnt;
void (*funcptr)( void ) = 0x0000; // Set up function pointer to RESET vector.
__disable_interrupt();

_ENABLE_RWW_SECTION();
//for(i=0;i<384;i++)db.data[i]=i;
//db.s_addr = 10240;
//db.e_addr = 11008;
s_addr = db.s_addr;
e_addr = db.e_addr;
if(s_addr>=64000)s_addr = 0x00;
while(1){
  if(s_addr)
    {// есть задание записать пару блоков
    addr = s_addr;
    block_count = ((e_addr-s_addr)/BLOCKSIZE); // расчитываю количество
    ee_cnt = 0x00;
    for(i=0;i<block_count;i++)BlockLoad(BLOCKSIZE, &addr, &ee_cnt);
    }  
  
   s_addr = 0x00;
   e_addr = 0x00;
   db.s_addr = 0x00;
   db.e_addr = 0x00;
   funcptr(); // Перехожу к основной программе
  }



}
Палыч
Цитата(statim @ May 29 2009, 12:27) *
Может есть какой-то другой способ перешивать флешь, и загрузчик отдельный делать не обязательно, а надо просто функцию в бут области разместить? (я не знаю как).
Вам нужно записать некий массив данных в память программ? Если - да, то, помнится, это - уже обсуждалось... Действительно, нужно иметь в области загрузчика процедуру записи данных в память программ. Вызов из основной программы (приложения) - по адресу процедуры через указатель.
statim
Спасибо, что-то нашёл, попробую разместить в буте функцию, так намного локаничнее должно получится.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.