Hi all,
here I'm with my first PBP bootloader that unfortunately doesn't work properly....
The main program jumps to bootloader, flash the new code, come back to main, do something expected at beginning
then starts to behave "funny", resets chips, etc.
I describe everything as if it were a tutorial so some expert maybe can see where is the weak area.
The bootloader is intended for a PIC18F67k22 that has a blocksize of 128 bytes and Int_Vector at 08h and 18h.
I leave free the first block 0-127 to remap Reset_Vector and Int_Vectors.
The bootloader code starts at 80h after the first block and has available all memory to 2FFFh, it's about 12k.
The main program starts at 3000h and have avaliable the remaining about 120k.
The bootloader has a complex UART communication with a GSM module and I need interrupt to manage properly
a 1k serial buffer. It works fine in other applications of mine, no problem at all that side.
Please note, I have found in this forum some other interesting solutions, like keeping the bootloader in the
high memory, retrieve code from I2C EEprom etc. But for several reasons they doesn't fit my needings.
I just would like to discover why my code fails and let it works properly, hope to find help :-)
This is the bootloader code:
Code:DEFINE RESET_ORG 80h BlockSize CON 128 UpperLimit CON $1FFFF-BlockSize @ nop STKPTR=0 CLEAR ' initialize your stuff, declare VAR, etc Goto BootLoaderStart INCLUDE "DT_INTS-18.bas" ; Base Interrupt System INCLUDE "ReEnterPBP-18.bas" ; Include if using PBP interrupts ASM INT_LIST macro ; IntSource, Label, Type, ResetFlag? INT_Handler RX1_INT, _Rx1INT, PBP, yes endm INT_CREATE ; Creates the interrupt processor ENDASM INCLUDE "interrupt.inc" ; here I manage the serial buffer, it works perfect BootLoaderStart: ' remap Reset_Vector and INT_Vectors for bootloader EraseCode 0 ' erase first block WriteCode $00,$EF40 ' --> put a GoTo $80 at address $00 WriteCode $02,$F000 WriteCode $08,$EF44 ' --> put a GoTo $88 at address $08 WriteCode $0A,$F000 WriteCode $18,$EF4C ' --> put a GoTo $98 at address $18 WriteCode $1A,$F000 WriteCode $7F,$FF ' write the last byte of the block to allow WriteCode Pause 500 ' erase memory from $3000 to end FOR Adr=$3000 to UpperLimit STEP BlockSize ERASECODE Adr NEXT Adr ' enable UART RCSTA1.4=0 ' Reset Overrun flag RCSTA1.4=1 @ INT_ENABLE RX1_INT ; enable RS232 interrupts INTCON.7=1 ; enable global int INTCON.6=1 ' here i scan the new HEX file that has been already downloaded via FTP and stored in the GSM module memory ScanLoop: ' read a line, example :1000A0000BE0060604C0E9FF05C0EAFFEE50E9CF09 ' decode address, check crc, etc ' be careful to skip addresses from 0 to 2FFFh, not to overwrite the bootloader we are executing ' WRITECODE Adr, FlashByte ' when fnished, exit loop goto ScanLoop ExitBootLoader: ' remap Reset_Vector and INT_Vectors before jumping back to main program @ INT_DISABLE RX1_INT ; disable RS232 interrupts INTCON=0 ; disable INT EraseCode 0 ; erase first block 0-127 WriteCode $00,$EF00 ; --> put a GoTo $3000 at address 0h WriteCode $02,$F018 WriteCode $08,$EF04 ; --> put a GoTo $3008 at address 8h WriteCode $0A,$F018 WriteCode $18,$EF0C ; --> put a GoTo $3018 aat address 18h WriteCode $1A,$F018 WriteCode $7F,$FF ; write the last byte of the block to allow WriteCode Pause 500 @ RESET @ ORG 0h @ GOTO 80h ' Reset Vector @ ORG 8h @ GOTO 88h ' High priority Int_Vector @ ORG 18h @ GOTO 98h ' Low priority Int_Vector PIC18F67K22 @ ORG 3000h BootLoaderEnd:
Now build the program. I'm using PBP Long option here to be able to WriteCode at address > 64k
I'm in MPLAB IDE 8.92, open "Program memory" view, then in the "Opcode HEX" tab right click "Export Table"
Put 0x80 as start Address and 0x2FFF as End Address, check "Single column output" and save.
Now you need to write a tool (I have used B4J) to read this file and obtain this format
Code:ASM dw 0x0EFA1, 0x0F002, 0x0FFFF, 0x0FFFF, 0x0EF4D, 0x0F004, 0x0FFFF dw 0x0E00B, 0x00606, 0x0C004, 0x0FFE9, 0x0C005, 0x0FFEA, 0x050EE ..... ..... ENDASM
Let's jump now to our main program. This (and all updates) needs to work starting at 3000h so it will have
the structure as below. When you want to trigger an update you can simpy call @ GOTO 80h
Code:DEFINE RESET_ORG 3000h @ nop STKPTR=0 CLEAR ' initialize your stuff, declare VAR, etc goto Start INCLUDE "DT_INTS-18.bas" ; Base Interrupt System INCLUDE "ReEnterPBP-18.bas" ; Include if using PBP interrupts ASM INT_LIST macro ; IntSource, Label, Type, ResetFlag? INT_Handler TMR1_INT, _Timer1_250mS_INT, PBP, yes INT_Handler RX1_INT, _Rx1INT, PBP, yes INT_Handler RX2_INT, _Rx2INT, PBP, yes INT_Handler TMR0_INT, _Timer0_8000mS_INT, PBP, yes endm INT_CREATE ; Creates the interrupt processor ENDASM INCLUDE "interrupt.inc" ; here I manage all the interrupt, it works perfect (before an update) Start: ; do your main program stuff ; When you want to trigger an update you can simpy call @ GOTO 80h if Update_Needed = true then ; download the new HEX file via FTP and store in the GSM module memory ; so that it will be available for the BootLoader code, then @ INT_DISABLE TMR1_INT @ INT_DISABLE TMR0_INT @ INT_DISABLE RX1_INT @ INT_DISABLE RX2_INT INTCON.7=0 @ goto 80h endif goto start @ ORG 0h @ GOTO 3000h @ ORG 8h @ GOTO 3008h @ ORG 18h @ GOTO 3018h ' here you have to copy the file generated before @ ORG 80h BootLoader: ASM dw 0x0EFA1, 0x0F002, 0x0FFFF, 0x0FFFF, 0x0EF4D, 0x0F004, 0x0FFFF dw 0x0E00B, 0x00606, 0x0C004, 0x0FFE9, 0x0C005, 0x0FFEA, 0x050EE ..... ..... ENDASM
The main program above works normally as expected. When I want to publish an update, I send the new HEX file
to the FTP server then send a message to the main program to inform that a new update is available.
As I told at beginning, everything works, but when the BootLoader jump back to the new main program, it starts
to do something correctly then behave funny and reset the chip.
Can you see some concept errors ? Besides disabling interrupt before enetering bootloader and remapping the vectors
is there any other register to take care ?
Thanks in advance. Hope that (once fixed) this stuff can be useful to other in the forum.
Cheers





Bookmarks