Bootloader Web Page

Vegipete's no-host serial bootloader for PIC18 devices.

Bootloader Web Page

Postby vegipete » Fri May 04, 2012 10:21 pm

I've put up a new web page describing my bootloader for PIC18 microcontrollers. Let me know if you find it useful, see any issues, have questions or whatever.
/vp
vegipete
 
Posts: 37
Joined: Sat Jul 09, 2011 7:38 pm

Bootloader Web Page

Sponsor

Sponsor
 

Re: Bootloader Web Page

Postby pas80 » Mon Feb 11, 2013 8:57 am

Hi guy,
I need a bootloader that assumes control when the mcu comes out of reset and remain in this state for 10 second.
I need this because I have to program remotely 40 MCU simultaneously via the 2-wire RS485, so I do not know how to tell the MCU to start with the bootloader. If the MCU does not receive the HEX file within 10 seconds, then starts the user application. Can you do?
thanks in advance
pas80
 
Posts: 1
Joined: Mon Feb 11, 2013 8:42 am

Re: Bootloader Web Page

Postby vegipete » Sat Feb 16, 2013 10:07 am

pas80 wrote:I need this because I have to program remotely 40 MCU simultaneously via the 2-wire RS485
40 at once! Wow!

While my code could certainly be modified to work, this starts to get out of the realm of what works easily with ordinary communications software. This really would be better served with custom software on the PC. Since the serial link is RS485, I presume that each MCU is addressable so the control software should be able to communicate with each MCU to ensure all are behaving correctly.
/vp
vegipete
 
Posts: 37
Joined: Sat Jul 09, 2011 7:38 pm

Re: Bootloader Web Page

Postby neverlog » Sun Nov 02, 2014 4:05 am

Hi Vegipete,

I want to confirm if the hex file need to send line by line? or it can be send out as a whole file?

I tried both but I keep receiving NG...

Hope to hear from you soon. thks!

Regards,
Neverlog
neverlog
 
Posts: 4
Joined: Sun Nov 02, 2014 4:02 am

Re: Bootloader Web Page

Postby vegipete » Wed Nov 19, 2014 11:43 am

Oops, sorry for the delay in responding, I wasn't paying attention.

neverlog wrote:I want to confirm if the hex file need to send line by line? or it can be send out as a whole file?

Yes, the hex file must be sent line by line. A PIC18 doesn't have enough RAM to buffer very much program, so I wrote my bootloader to do one flash page write at a time. As soon as enough data has been received to fill the write buffers, the serial reception is requested to stop and the flash write is started. The cpu stalls during the write so serial reception can't work for that (brief) period of time.

I tried both but I keep receiving NG...

If you are getting lots of NG, it is likely because your handshaking is not working. Version 5 uses hardware handshaking (!CTS), version 6 uses software flow control (XON/XOFF.)
/vp
vegipete
 
Posts: 37
Joined: Sat Jul 09, 2011 7:38 pm

Re: Bootloader Web Page

Postby neverlog » Sat Dec 06, 2014 8:12 am

Hi Vegipete,

I really appreciate your help again.

Now I am able to write my Hex file into the 18F46K22 ( I modified a bit from 18F26K22, because they are same family) with your bootloader

But the program is unable to run, it is just a simple LED blink program.

I am using c programming, you mention that application firmware must start with :

ORG 0x0000 ;reset vector
GOTO UserProgramStart
GOTO UserProgramStart
ORG 0x0008 ;(high priority) interrupt vector
GOTO HighPriorityInterruptHandler
ORG 0x0018 ;low priority interrupt vector
GOTO LowPriortiyInterruptHandler

I try to insert the asm code into my c program, before main() and within main(), but the program just doesn't run after successfully written.

I don't know what when wrong. I need you advise on this, thank you.

Hope to hear from you soon.

Neverlog.
neverlog
 
Posts: 4
Joined: Sun Nov 02, 2014 4:02 am

Re: Bootloader Web Page

Postby vegipete » Sat Dec 20, 2014 9:52 pm

neverlog wrote:I try to insert the asm code into my c program, before main() and within main(), but the program just doesn't run after successfully written.

I don't know what when wrong. I need you advise on this, thank you.
Ah, yes. This is a tricky one. Microchip's C18 uses a bit of 'special' start-up code to get the processor running. This gets placed at memory location 0 and following. C18 also had a strangeness that required an extra byte or two after a 'function', so trying to jam your own code in at 0 wouldn't fit. (I haven't experimented with XC8.)

The solution I found was to re-write the start-up code to include everything in one piece, instead of a couple of separate pieces. I'll try dig out my code in the next few days and post it here.
/vp
vegipete
 
Posts: 37
Joined: Sat Jul 09, 2011 7:38 pm

Re: Bootloader Web Page

Postby neverlog » Wed Dec 24, 2014 8:35 pm

Hi Vegipete,

Thanks for prompt action.

Looking forward for favourable reply.

Merry Christmas and Happy New Year!! :D


Neverlog
neverlog
 
Posts: 4
Joined: Sun Nov 02, 2014 4:02 am

Re: Bootloader Web Page

Postby vegipete » Sun Feb 01, 2015 11:37 pm

neverlog wrote:Thanks for prompt action.
Oh my, not so prompt at all. Sorry about that.

I was looking into my code that allows a C program to coexist with my bootloader. What I've got works, but it is not a good example. It implements the complete ISR in assembly language with none of the ease of set-up that C allows. It is also very tailored to that particular program.
Code: Select all
File: ISR stub in assembly language
;-----------------------------------------------
; Declare a code segment.
; Some trickery is required here to generate a .HEX file
; that will work correctly with my BootLoader.
; The BootLoader will change the first two locations to
; "goto BootLoaderStart" so they must not contain real code.
; The standard C18 startup code won't allow this (or rather,
; I don't know how to force it) so "c018i.c" is copied into
; the project and modified to skip the reset vector code.
; The required reset code appears here.
; The linker script is also changed to not use the standard
; "c018i.c" so that the local one is used instead.
INTERRUPTCODE CODE 0x00

ResetVect:
   nop         ;these NOP's are for the
   nop         ;  BootLoader to change
   goto   _startup   ;8 bytes of code so HighInt starts at 0x0008
HighInt:
   movlb   0
   btfss   PIR1,TMR2IF   ;test for T2 match interrupt
;******************************************************************************
;unexpected interrupt - what to do, what to do...
unknown_int:
   reset
;   bra   unknown_int   ;Oh Dear! Unexpected interrupt
;******************************************************************************
; Interrupt Routine
;******************************************************************************
[SNIP]
;=====================================
;1) Housekeeping
T2_int:
   bcf   PIR1,TMR2IF   ;clear T2 interrupt
[SNIP]
   retfie   FAST

   END



As the comments indicate, I changed the file "c018i.c", which is located somewhere in the C18 compiler folder structure. I put the modified version in the same folder as the C project, and added it to the list of source files.

Note in the function void _entry(void) I tried to add two 'nop's in front of the 'goto startup' The compiler didn't like that idea at all so I commented that part right out and made it part of the assembly ISR partially shown above.

Code: Select all
File Name: c018i.c
/* $Id: c018i.c,v 1.7 2006/11/15 22:53:12 moshtaa Exp $ */
/* Copyright (c)1999 Microchip Technology */
/* MPLAB-C18 startup code, including initialized data */

/* external reference to __init() function */
extern void __init (void);

/* external reference to the user's main routine */
extern void main (void);

/* prototype for the startup function */
//void _entry (void);
void _startup (void);

/* prototype for the initialized data setup */
void _do_cinit (void);

extern volatile near unsigned long short TBLPTR;
extern near unsigned FSR0;
extern near char __FPFLAGS;
#define RND 6

#pragma code _entry_scn=0x000000

//void
//_entry (void)
//{
//_asm
//   //nop
//   //nop
//   goto _startup
//_endasm
//}

#pragma code _startup_scn
void
_startup (void)
{
  _asm
    // Initialize the stack pointer
    lfsr 1, _stack
    lfsr 2, _stack

    clrf TBLPTRU, 0 // 1st silicon doesn't do this on POR

    bcf __FPFLAGS,RND,0 // Initialize rounding flag for floating point libs
   
    _endasm
    _do_cinit ();

loop:

  // If user defined __init is not found, the one in clib.lib will be used
  __init ();

  // Call the user's main routine
  main ();

  goto loop;
}                               /* end _startup() */

/* MPLAB-C18 initialized data memory support */
/* The linker will populate the _cinit table */
extern far rom struct
{
  unsigned short num_init;
  struct _init_entry
  {
    unsigned long from;
    unsigned long to;
    unsigned long size;
  }
  entries[];
}
_cinit;

#pragma code _cinit_scn
void
_do_cinit (void)
{
  /* we'll make the assumption in the following code that these statics
   * will be allocated into the same bank.
   */
  static short long prom;
  static unsigned short curr_byte;
  static unsigned short curr_entry;
  static short long data_ptr;

  // Initialized data...
  TBLPTR = (short long)&_cinit;
  _asm
    movlb data_ptr
    tblrdpostinc
    movf TABLAT, 0, 0
    movwf curr_entry, 1
    tblrdpostinc
    movf TABLAT, 0, 0
    movwf curr_entry+1, 1
  _endasm
    //while (curr_entry)
    //{
    test:
    _asm
     bnz 3
    tstfsz curr_entry, 1
    bra 1
    _endasm
    goto done;
      /* Count down so we only have to look up the data in _cinit
       * once.
       *
       * At this point we know that TBLPTR points to the top of the current
       * entry in _cinit, so we can just start reading the from, to, and
       * size values.
       */
      _asm
   /* read the source address */
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf prom, 1
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf prom+1, 1
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf prom+2, 1
   /* skip a byte since it's stored as a 32bit int */
   tblrdpostinc
   /* read the destination address directly into FSR0 */
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf FSR0L, 0
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf FSR0H, 0
   /* skip two bytes since it's stored as a 32bit int */
   tblrdpostinc
   tblrdpostinc
   /* read the destination address directly into FSR0 */
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf curr_byte, 1
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf curr_byte+1, 1
   /* skip two bytes since it's stored as a 32bit int */
   tblrdpostinc
   tblrdpostinc
      _endasm 
      //prom = data_ptr->from;
      //FSR0 = data_ptr->to;
      //curr_byte = (unsigned short) data_ptr->size;
      /* the table pointer now points to the next entry. Save it
       * off since we'll be using the table pointer to do the copying
       * for the entry.
       */
      data_ptr = TBLPTR;
     
      /* now assign the source address to the table pointer */
      TBLPTR = prom;

      /* do the copy loop */
      _asm
        // determine if we have any more bytes to copy
   movlb curr_byte
   movf curr_byte, 1, 1
copy_loop:
   bnz 2 // copy_one_byte
   movf curr_byte + 1, 1, 1
   bz 7 // done_copying

copy_one_byte:
   tblrdpostinc
   movf TABLAT, 0, 0
   movwf POSTINC0, 0

   // decrement byte counter
   decf curr_byte, 1, 1
   bc -8 // copy_loop
        decf curr_byte + 1, 1, 1
   bra -7 // copy_one_byte

done_copying:

      _endasm
      /* restore the table pointer for the next entry */
      TBLPTR = data_ptr;
      /* next entry... */
      curr_entry--;
      goto test;
done:
;
}

Here is a section of the linker file, showing that 'c018i.o' is commented out and that the end of available flash memory has been reduced to protect the bootloader.
Code: Select all
File: 18f14k22_g.lkr (portion of)
#IFDEF _CRUNTIME
  #IFDEF _EXTENDEDMODE
    FILES c018i_e.o
    FILES clib_e.lib
    FILES p18f14k22_e.lib

  #ELSE
//    FILES c018i.o
    FILES clib.lib
    FILES p18f14k22.lib
  #FI

#FI

#IFDEF _DEBUGCODESTART
  CODEPAGE   NAME=page       START=0x0               END=_CODEEND
  CODEPAGE   NAME=debug      START=_DEBUGCODESTART   END=_CEND        PROTECTED
#ELSE
  CODEPAGE   NAME=page       START=0x0               END=0x39FF
  // END reduced from 0x3FFF to protect bootloader
#FI


Now that any readers are hideously confused by all this, I see that I should create a complete project template that contains all of these details in a working example, complete with both high and low priority interrupts.

Hopefully this won't take too long...
/vp
vegipete
 
Posts: 37
Joined: Sat Jul 09, 2011 7:38 pm

Re: Bootloader Web Page

Postby neverlog » Fri Sep 11, 2015 5:40 pm

Hi Vegipete,

Is there any progress? Ha....hope it won't cause you too much problem...

Thanks in advance.

I am willing to pay for the job, if it won't cost too much, and if it is okay for you.

Hope to hear from you soon. TQ.


Neverlog.
neverlog
 
Posts: 4
Joined: Sun Nov 02, 2014 4:02 am

Next

Return to PIC18 BootLoader

Who is online

Users browsing this forum: No registered users and 1 guest