CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

[pic18F2520] problem bootloader with interrupt vector

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
moulefrite13



Joined: 22 Jul 2013
Posts: 3

View user's profile Send private message

[pic18F2520] problem bootloader with interrupt vector
PostPosted: Mon Jul 22, 2013 8:36 am     Reply with quote

Hi everybody,

I'm new in embedded development, and I try to create a simple project with bootloader + classic program with really basic interrupt ( timer and usart ) on PIC18F2520.

My dev environment :
CCS PCH C Compiler, Version 4.140, xxxxx ( extract from my main.lst file ) and MPLAB IDE v1.70, debugger ICD3.


I used sample provided in PIC directory ( loader.c, ex_bootload, ex_bootloader ).
I also found a thread about these same problem :

http://www.ccsinfo.com/forum/viewtopic.php?t=49819&highlight=remap+interrupt+vector

and a little help on this link
http://www.picprojects.net/serialbootloader/

Now my code :
############ bootloader.h ###############

Code:

 #ifndef BOOT_H
#define   BOOT_H

#NOLIST
#use delay(clock=20000000)
#DEFINE LOADER_END 0x7FF
#BUILD (reset=LOADER_END+1,interrupt=LOADER_END+9)
#ORG 0x000,LOADER_END{}
 #endif   /* BOOT_H */



############ appMain.c ###################

Code:


#include "18F2520.h"
#DEVICE *=16

#fuses HS
#fuses NOMCLR
#fuses DEBUG
#fuses NOWDT

#include "bootloader.h"

#use rs232(UART1,bits=8,stop=1)


int16 count = 0;

#INT_TIMER1
void timer1_isr()
{
   if(count){count--;}
}


#INT_RDA
void rxInterrupt(void)
{
    byteReceive = getc();
}


#define COUNTER_VAL 500

void main()
{

   setup_timer_1(T1_INTERNAL);
   set_timer1(0);

   enable_interrupts(INT_TIMER1);
   enable_interrupts(INT_RDA);
   

   enable_interrupts(GLOBAL);

   count = COUNTER_VAL;

   while(TRUE)
   {
      if(!count)
      {
         printf("Timer Finished...Restarting\r\n");
         count = COUNTER_VAL;
      }
   }
}




Now my question is why no interrupt occurs.
I read threads with search module, but some explain I need to remap IVT.
And in my first link ( picprojects ), it explain just to use one line for move reset vector and interrupt vector.
Code:

/* ------------------------------------------------------------------------- */
/* map reset vector and interrupt vector                                     */
/* 0x000-0x3FF is used by the bootloader. The bootloader maps the original   */
/* reset vector (0x000) to 0x400 and the interrupt vector (0x008) to 0x408.  */
/* ------------------------------------------------------------------------- */
#build (reset=0x400, interrupt=0x408)
/* ------------------------------------------------------------------------- */
/* reserve boot block area                                                   */
/* This memory range is used by the bootloader, so the application must not  */
/* use this area.                                                            */
/* ------------------------------------------------------------------------- */
#org 0, 0x3FF {}


My code build successfully but no interrupt occur, if I comment the line
Code:
#BUILD (reset=LOADER_END+1,interrupt=LOADER_END+9)
my interrupt work fine.

I continued to look for another solution, I analyzed file built ( .LST, .STA, .SYM ) and some people ask to look GOTO instruction, and mine seems to be good

############# main.LST ##################


Code:


*
0800:  GOTO   091E
*
0808:  MOVWF  04
080A:  MOVFF  FD8,05
080E:  MOVFF  FE0,06
0812:  MOVLB  0
0814:  MOVFF  FE9,0C
0818:  MOVFF  FEA,07
081C:  MOVFF  FE1,08
0820:  MOVFF  FE2,09
0824:  MOVFF  FD9,0A
0828:  MOVFF  FDA,0B
082C:  MOVFF  FF3,12
0830:  MOVFF  FF4,13
0834:  MOVFF  FFA,14
0838:  MOVFF  FF5,15
083C:  MOVFF  FF6,16
0840:  MOVFF  FF7,17
0844:  MOVFF  00,0E
0848:  MOVFF  01,0F
084C:  MOVFF  02,10
0850:  MOVFF  03,11
0854:  BTFSS  F9D.0
0856:  GOTO   0860
085A:  BTFSC  F9E.0
085C:  GOTO   08BA
0860:  BTFSS  F9D.5
0862:  GOTO   086C
0866:  BTFSC  F9E.5
0868:  GOTO   08CE
086C:  MOVFF  0E,00
0870:  MOVFF  0F,01
0874:  MOVFF  10,02
0878:  MOVFF  11,03
087C:  MOVFF  0C,FE9
0880:  MOVFF  07,FEA
0884:  BSF    07.7
0886:  MOVFF  08,FE1
088A:  MOVFF  09,FE2
088E:  MOVFF  0A,FD9
0892:  MOVFF  0B,FDA
0896:  MOVFF  12,FF3
089A:  MOVFF  13,FF4
089E:  MOVFF  14,FFA
08A2:  MOVFF  15,FF5
08A6:  MOVFF  16,FF6
08AA:  MOVFF  17,FF7
08AE:  MOVF   04,W
08B0:  MOVFF  06,FE0
08B4:  MOVFF  05,FD8
08B8:  RETFIE 0
............................
............................
............................
0982:  BRA    0982

Configuration Fuses:
   Word  1: C200   HS FCMEN IESO
   Word  2: 1E19   NOPUT NOBROWNOUT BORV21 NOWDT WDT32768
   Word  3: 0700   CCP2C1 PBADEN LPT1OSC NOMCLR
   Word  4: 0000   NOSTVREN NOLVP NOXINST DEBUG
   Word  5: C00F   NOPROTECT NOCPB NOCPD
   Word  6: E00F   NOWRT NOWRTC NOWRTB NOWRTD
   Word  7: 400F   NOEBTR NOEBTRB

   Some fuses have been forced to be compatible with the ICD debugger.



this first line :
Code:

0800:  GOTO   091E


Confirm that my reset vector "jump" to its new address ( 0x091E )

########## main.SYM ##############
Code:

..........................
..........................
ROM Allocation:
0008BA  timer1_isr
0008CE  rxInterrupt
00091E  main
0008DC  @const80
0008FA  @PSTRINGC_9600_31766_31767
00091E  @cinit1
000950  @cinit2
..........................
..........................


############# main.STA ###########
Code:

 Segment     Used  Free
-----------  ----  ----
00000-007FE     0  2048 
00800-00806     4  4 
00808-008B8   178  0 
008BA-07CBE   202  29500 


I ( suppose I ) see a good mapping Confused

My real first step is to create a really simple program with dedicated memory space for my (future) boot program and continue to use interrupt.

Is that someone could give me some advice for understand where is my mistake.

Other question, it is necessary to load first the boot program to address 0x0 to 0x7FF before "load" with my ICD 3 the main program and debug it ?

It's possible to run the main program (debug with ICD3 ) with nothing written into the dedicated zone for boot ?

Thanks in advance for your help,

ps : sorry for my bad english Embarassed

Regards,

Moulefrite
moulefrite13



Joined: 22 Jul 2013
Posts: 3

View user's profile Send private message

PostPosted: Fri Aug 02, 2013 2:55 am     Reply with quote

Please UP Sad
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Fri Aug 02, 2013 8:33 am     Reply with quote

As it stands, your bootloader is intercepting the interrupt vectors.

Do you really need interrupts in the bootloader?. Much simpler not to use these.
If you look at the usb_bootloader.h, you will see that this uses interrupt polling, to avoid having to do this....

If you do, you will need a quite complex interrupt re-locator.
Basically you'd have to have an int_global handler, which then tests a flag set in the bootloader, and if this is set (to say you are in bootloader mode), calls the corresponding interrupt routines for the bootloader. If not, it jumps to the interrupt address for the main code. A lot of work, and slows the interrupt response.

Even if you don't use interrupts, your bootloader needs to include the interrupt relocation code. This is the #int_global code in ex_bootloader.c

and, yes, the bootloader needs to be present. If your main code is located at 0x7ff, it is the bootloader that jumps to this location, and that relocates the interrupt vectors.

Best Wishes
moulefrite13



Joined: 22 Jul 2013
Posts: 3

View user's profile Send private message

PostPosted: Mon Aug 05, 2013 3:51 am     Reply with quote

Ttelmah wrote:
As it stands, your bootloader is intercepting the interrupt vectors.

Do you really need interrupts in the bootloader?. Much simpler not to use these.
If you look at the usb_bootloader.h, you will see that this uses interrupt polling, to avoid having to do this....

If you do, you will need a quite complex interrupt re-locator.
Basically you'd have to have an int_global handler, which then tests a flag set in the bootloader, and if this is set (to say you are in bootloader mode), calls the corresponding interrupt routines for the bootloader. If not, it jumps to the interrupt address for the main code. A lot of work, and slows the interrupt response.

Even if you don't use interrupts, your bootloader needs to include the interrupt relocation code. This is the #int_global code in ex_bootloader.c

and, yes, the bootloader needs to be present. If your main code is located at 0x7ff, it is the bootloader that jumps to this location, and that relocates the interrupt vectors.

Best Wishes


Thanks a lot Ttelmah for your reply,

I confirm my bootloader don't need to use interruption.
My bootloader is used only for flash FW by classic UART.

So if I understand you :

bootloader.hex :
_ use space 0 to 0x7FF
_ DON'T remap interruptVector to 0x808 ( with #build ?? )
_ RELOCATE only interruptVector ( "#int_global" with "jump_to_isr" )

MainFW.hex :
_ Allow memory 0 to 0x7FF like unusable ( reserved )
_ relocate resetVector to 0x800 ( with #build ?? )
_ Do I need to remap interruptVector ???


So I just need to modify this line ( remove interrupt ) in the bootloader.h :
Code:

#BUILD (reset=0x800,interrupt=0x808)

by
Code:

#BUILD (reset=0x800) // don't use interrupt



and add in bootloader.c the code :
Code:

#int_global
void isr(void) // relocate interrupt vector
{
   jump_to_isr(0x808*(getenv("BITS_PER_INSTRUCTION")/8));
}



And modify this line in appMain.c :
Code:

#BUILD (reset=0x800,interrupt=0x808)

by
Code:

#BUILD (interrupt=0x808) // just relocate interruptVector adress ?



Please someone could confirm if it's ok,
I will try it soon,

Thanks Ttelmah and any help, link, explanation is welcome,

Best regards,

Moulefrite Very Happy
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group