Ejemplo n.º 1
0
static bool hex_load(const char *file, long firmsize, uint8_t *image)
{
	FILE *f;
	char s[0x80];
	f = fopen(file, "r");
	if(f == NULL){
		return false;
	}
	fseek(f, 0, SEEK_SET);
	
	struct record *t = ihex_new();
	bool ret = true;
	while(fgets(s, 0x80, f) != NULL){
		if(ihex_load(s, t) == false){
			ret = false;
			break;
		}
		ihex_write(t, firmsize, image);
	}
	ihex_destory(t);
	return ret;
}
Ejemplo n.º 2
0
/*--- MAIN -------------------------------------------------------------------*/
int main(void)
{
    char temp_char;
    uint16_t loop  = 1;
	uint8_t bootFlag = TRUE;
    
    cli();
	
    /* the following code moves the interrupt vector pointer to the bootloader
       section. The problem is the compiler doesn't understand where to put
       the IV table. */
    GICR = _BV(IVCE);       
    GICR |= _BV(IVSEL); //move interruptvectors to the Boot sector       
 
    /* The slow baud rate is required because of the intel hex parsing overhead.
       If I could figure out how to enable interrupts in the BLS (compiler issue)
       then a higher speed could be used by switching to an interrupt based
       UART ISR. The code could also be optimized. */

    SerCom0Init(BAUD_2400); // NOTE, the baud rates are constants defined in
                            // sercom.h. You need to adjust those constants
                            // to fit your MCU speed
							
	   // poll USART receive complete flag 64k times to catch the 'i' reliably
 
 
	
// test if flash is empty (i.e. flash content is 0xff)
	if(pgm_read_byte_near(0x0000) != 0xFF) {
		bootFlag = FALSE; 
	}

    do {
	if(bit_is_set( UCSRA, RXC))
	    if( UDR == 'i')
		{ 	bootFlag = TRUE;
			PutString0("Boot V ");
			PutChar0(VER_HIGH_BYTE);
			PutChar0(VER_LOW_BYTE);
			PutString0("\r\n");
		}		
		
    } while(loop++);
 
    
    /* this main loop is the user 'menu'. */
    while(bootFlag)                             
    {
			   
	if( Hit0() ) // more necessary for UART code running interrupts
	{
	    temp_char=GetChar0();

 	    switch(temp_char)
	    {
		case 'u': // download new program
		{
		    /* erase the main flash excepting BLS */
		    buf_address = 0; 
		    while ( APP_END > buf_address )
		    {
			boot_page_erase(buf_address);	// Perform page erase
			boot_spm_busy_wait();		// Wait until the memory is erased.
			buf_address += SPM_PAGESIZE;
		    }
		    buf_address = 0;

		    /* load new program */
		    PutString0("READY");
		    if(( temp_char = ihex_load()))
		    {
			PutString0("ERR ");
			PutInt0(temp_char);
		    }
		    else
			{( PutString0("OK") );
				bootFlag = FALSE ;  // Exit to run
			}
		}
		break;
		
		case 'x':                   //Exit upgrade
		{
			GICR = _BV(IVCE); 
			GICR &= ~_BV(IVSEL); //move interruptvectors to the Application sector
			jump_to_app(); // Jump to application sector
//		    wdt_enable(WDTO_15MS); // Enable Watchdog Timer to give reset
		}
		break;
		default:
		{
		    PutString0("u - Upload or x - Execute\r\n");
		}
	    } // end switch
	} // end if( Hit0() )
    }	// end while(1)
// Start to application

	 GICR = _BV(IVCE); 
	 GICR &= ~_BV(IVSEL); //move interruptvectors to the Application sector
	 jump_to_app(); // Jump to application sector

    return 0;
}
Ejemplo n.º 3
0
/*--- MAIN -------------------------------------------------------------------*/
int main(void)
{
    uint8_t temp_char,tmp;
 	uint8_t bootFlag = TRUE;
    
    cli();
	
    /* the following code moves the interrupt vector pointer to the bootloader
       section. The problem is the compiler doesn't understand where to put
       the IV table. */
    GICR = _BV(IVCE);       
    GICR = _BV(IVSEL); //move interruptvectors to the Boot sector  ** WRITE 0 TO IVCE use = not |
   

// Initial 7 Segments on E_io
// Set direction of two switch to Input	
    DDRB =  0xFF;   // Output	
    DDRC  = 0x18;  // P3, P4 for  Control 7 segments Digits 

// Enable pull up resistor 
 	PORTC |= 0x24;

	
    /* The slow baud rate is required because of the intel hex parsing overhead.
       If I could figure out how to enable interrupts in the BLS (compiler issue)
       then a higher speed could be used by switching to an interrupt based
       UART ISR. The code could also be optimized. */
    
	uart_init( UART_INTERRUPT,UART_8_N_1,UART_38400);   
 
// poll USART receive complete flag 64k times to catch the 'i' reliably
 
// test if flash is empty (i.e. flash content is 0xff)
	if(pgm_read_byte_near(0x0000) != 0xFF) {
		bootFlag = FALSE; 
	}
	
//  Enter boot mode by press b 	
//	while (!(tmp  = uart_read()));
//	if (tmp == 'b')
//	     bootFlag = TRUE;
		 
// Check SW for enter boot mode either press both SW at the same time	
	tmp = PINC & (0x24);   // PB0, PB3 port
    if (!tmp)    // Press SW tmp = 0
        bootFlag = TRUE;	 
		 

	uart_write_str (VERSION);
// Display b characters 
	E_OUT_PORTA  =  0x7C;  // b
 	E_OUT_PB1(0);
 	E_OUT_PB2(1);
 
    
    /* this main loop is the user 'menu'. */
    while(bootFlag)                             
    {
			   
	if( (tmp = uart_read()) ) 
	{
 	   switch(tmp)
	   {
		case 'u': // download new program
		{
		    /* erase the main flash excepting BLS */
		    buf_address = 0; 
		    while ( APP_END > buf_address )
		    {
			boot_page_erase(buf_address);	// Perform page erase
			boot_spm_busy_wait();		// Wait until the memory is erased.
			buf_address += SPM_PAGESIZE;
		    }
		    buf_address = 0;

		    /* load new program */
			uart_write_str("READY \n");
		    if(( temp_char = ihex_load()))
		    {
				uart_write_str("ERR ");
				uart_write_char(temp_char + '0' );
				uart_write_char('\n');
		    }
		    else
			{
				bootFlag = FALSE ;  // Exit to run
			}
		}
		break;
		
		case 'x':                   //Exit upgrade
		{
			GICR = _BV(IVCE); 
			GICR &= ~(_BV(IVSEL) | _BV(IVCE)); //move interruptvectors to the Application sector  Write 0 to IVCE
		    jump_to_app(); // Jump to application sector
//		    wdt_enable(WDTO_15MS); // Enable Watchdog Timer to give reset
		}
		break;    
		default:
		{
		   uart_write_str(" u - Upload or x - Execute \n");
		}
	   } // end switch
	}  
    }	// end while(1)
// Start to application

	 GICR = _BV(IVCE); 
	 GICR &= ~(_BV(IVSEL) | _BV(IVCE)); //move interruptvectors to the Application sector  Write 0 to IVCE
	 jump_to_app(); // Jump to application sector

    return 0;
}