Reply by Charles Manning January 10, 20102010-01-10
You cannot change the address of the vectors, but you can **remap** the
address so that the address points to a different area in memory.

For example, it is common to do this (as is done with the SAM7s):
At boot, 0x0 maps to the start of flash. This allows the boot vectors to be in
flash.
Some time after boot you remap the area to RAM. This allows you to write new
values into the vectors.

On Saturday 09 January 2010 03:56:52 ADNAN wrote:
> Hi,
>
> Actually I want to write a bootloader that will download and execute
> another placed in some area of ROM.How it can be possible.?
>
> My idea is to have vector table of bootloader to be at the start of
> the ROM at 0x0 and of my application to be at the start of rom at 0x5000.
> What do you think? I have tried this way bootloader try starting
> application but application dont works.
>
> Regards
> Dani
>
> --- In A..., "Icli, Bekir" wrote:
> > You cannot change the irq and excp vec. addresses.. I told you they are
> > fixed.. 0x0 thru 0x20 What you can do is, let the code run from 0x5000
> > and relocate (simply copy) your vector handlers
> >
> > > __vector:
> > >
> > > LDR PC,Reset_Addr ; Reset
> > > LDR PC,Undefined_Addr ; Undefined instructions
> > > LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> > > LDR PC,Prefetch_Addr ; Prefetch abort
> > > LDR PC,Abort_Addr ; Data abort
> > > __vector_0x14:
> > > DCD 0 ; RESERVED
> > > LDR PC,IRQ_Addr ; IRQ
> > > LDR PC,FIQ_Addr ; FIQ
> >
> > to 0x0.. that should solve the problem..
> >
> > Best,
> > Bekir
> >
> > ________________________________
> > From: A... [mailto:A...] On Behalf
> > Of ADNAN Sent: Friday, January 08, 2010 2:47 PM
> > To: A...
> > Subject: [AT91SAM] Re: How to move interrupt vector from 0x0 to some
> > offset
> >
> >
> >
> >
> > Hi,
> >
> > You are right. Now tell me what should i do to change the interrupt
> > vector and exception vector address from 0x0 to 0x5000 or 0x105000 so
> > that my application alos works from there.
> >
> > Regards
> > Dani
> >
> > --- In A..., "Icli,
Bekir" wrote:
> > > Hi Dani,
> > >
> > > It makes perfect sense, that it works when you load it to 0x0 or
> > > 0x100000.. Apparently these two memory locations are mirrored.. (means
> > > they are pointing to the same physical memory).. As I stated in my
> > > former mail, you HAVE TO load your exception vectors (with that I mean
> > > irq and the other exception vectors) to 0x0.. In your case:
> > > __vector:
> > >
> > > LDR PC,Reset_Addr ; Reset
> > > LDR PC,Undefined_Addr ; Undefined instructions
> > > LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> > > LDR PC,Prefetch_Addr ; Prefetch abort
> > > LDR PC,Abort_Addr ; Data abort
> > > __vector_0x14:
> > > DCD 0 ; RESERVED
> > > LDR PC,IRQ_Addr ; IRQ
> > > LDR PC,FIQ_Addr ; FIQ
> > > should be placed to 0x0..
> > > Because processor does not know where your handler is, he just jumps to
> > > 0x18 and continues with execution.. If you have a debugger, set a break
> > > point at 0x18 and you'll see what I mean.. and check after that, if
> > > your LDR PC, IRQ_Addr is there.. ;)
> > >
> > > Best,
> > > Bekir
> > >
> > > ________________________________
> > > From: A...
> > > [mailto:A...] On
> > > Behalf Of ADNAN Sent: Friday, January 08, 2010 12:09 PM
> > > To: A...
> > > Subject: [AT91SAM] Re: How to move interrupt vector from 0x0 to some
> > > offset
> > >
> > >
> > >
> > > Hi Bakir,
> > >
> > > Thanks for your reply.
> > >
> > > I am using CMX Rtos for both of my codes, 1, bootloader and other is
> > > the actualy application. The cmx handler for IRQ is as follows, SECTION
> > > .text:CODE:NOROOT:REORDER(2)
> > > ARM
> > > IRQ_Wrapper:
> > > SUB LR,LR,#4 ; adj for proper CMX return
> > > STMFD SP!,{R0-R12,LR} ; save the registers
> > >
> > > ldr r14, =AT91C_BASE_AIC
> > > ldr r0, [r14, #AIC_IVR] ; get vector address
> > > str r14, [r14, #AIC_IVR]
> > >
> > > MRS R9,SPSR ; save the SPSR
> > > STMFD SP!,{R9}
> > > LDR R2,=int_count ; get int_count
> > > MRS R3,CPSR
> > > MOV R4,R3
> > > ORR R4,R4,#Int_Bits ; disable interrupts
> > > MSR CPSR_c,R4
> > > LDRB R1,[R2] ; incr the count
> > > ADD R1,R1,#1
> > > STRB R1,[R2]
> > > MSR CPSR_c,R3 ; restore interrupts
> > >
> > > cmp r0, #0 ; handler available?
> > > beq irq_ack ; no, ack interrupt and exit
> > >
> > > MSR CPSR_c, #SYS_MODE ; SYS mode, interrupts enabled
> > > STMFD sp!,{R0-R12,lr} ; Save registers.
> > > mov lr,pc
> > > BX R0 ; call specified handler
> > > LDMFD SP!,{R0-R12,lr} ; restore registers.
> > > MSR CPSR_c, #IRQ_MODE|I_Bit|F_Bit ; Switch to IRQ mode, no interrupts
> > >
> > > irq_ack
> > > ldr r1, =AT91C_BASE_AIC ; Ack End of Interrupt
> > > str r1, [r1, #AIC_EOICR]
> > >
> > > B K_OS_Intrp_Exit
> > >
> > > This handler works nice when i place intvec at 0x0 or 0x100000, but
> > > stops working when i change address of intvec to 0x5000 or 0x105000 i
> > > dont know why,
> > >
> > > The cStartup is as follows,
> > >
> > > MODULE ?cstartup
> > >
> > > SECTION IRQ_STACK:DATA:NOROOT(3)
> > > SECTION FIQ_STACK:DATA:NOROOT(3)
> > > SECTION UND_STACK:DATA:NOROOT(3)
> > > SECTION ABT_STACK:DATA:NOROOT(3)
> > > SECTION SVC_STACK:DATA:NOROOT(3)
> > > SECTION CSTACK:DATA:NOROOT(3)
> > >
> > > SECTION .intvec:CODE:NOROOT(2)
> > >
> > > PUBLIC __vector
> > > PUBLIC __vector_0x14
> > > PUBLIC __iar_program_start
> > > EXTERN Undef_Wrapper
> > > EXTERN SWI_Wrapper
> > > EXTERN Prefetch_Wrapper
> > > EXTERN Abort_Wrapper
> > > EXTERN IRQ_Wrapper
> > > EXTERN FIQ_Wrapper
> > >
> > > ARM
> > >
> > > ;;====================================================================> > >========= ;; EXECPTION HANDLERS
> > > ; All default exception handlers (except reset) are
> > > ; defined as weak symbol definitions.
> > > ; If a handler is defined by the application it will take precedence.
> > > ;;====================================================================> > >========> > >
> > > __vector:
> > >
> > > LDR PC,Reset_Addr ; Reset
> > > LDR PC,Undefined_Addr ; Undefined instructions
> > > LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> > > LDR PC,Prefetch_Addr ; Prefetch abort
> > > LDR PC,Abort_Addr ; Data abort
> > > __vector_0x14:
> > > DCD 0 ; RESERVED
> > > LDR PC,IRQ_Addr ; IRQ
> > > LDR PC,FIQ_Addr ; FIQ
> > >
> > > Reset_Addr: DCD __iar_program_start
> > > Undefined_Addr: DCD Undef_Wrapper
> > > SWI_Addr: DCD SWI_Wrapper
> > > Prefetch_Addr: DCD Prefetch_Wrapper
> > > Abort_Addr: DCD Abort_Wrapper
> > > IRQ_Addr: DCD IRQ_Wrapper
> > > FIQ_Addr: DCD FIQ_Wrapper
> > >
> > > ;;====================================================================> > >========= ;; LOW LEVEL SYSTEM INITIALIZATION
> > > ; After a reset execution starts here, the mode is ARM, supervisor
> > > ; with interrupts disabled.
> > > ;;====================================================================> > >========> > >
> > > SECTION .text:CODE:NOROOT(2)
> > > EXTERN ?main
> > > REQUIRE __vector
> > > EXTERN AT91LowLevelInit
> > > EXTERN at91_spurious_handler
> > >
> > > ARM
> > >
> > > __iar_program_start:
> > > ?cstartup:
> > >
> > > ; Minumum C initialization
> > >
> > > ldr r13,=SFE(SVC_STACK)
> > > ; Call Low level init function
> > > ldr r0,=AT91LowLevelInit
> > > mov lr, pc
> > > bx r0
> > >
> > > ;
> > > ; Add initialization needed before setup of stackpointers here.
> > > ;
> > >
> > > ;
> > > ; Initialize the stack pointers.
> > > ; The pattern below can be used for any of the exception stacks:
> > > ; FIQ, IRQ, SVC, ABT, UND, SYS.
> > > ; The USR mode uses the same stack as SYS.
> > > ; The stack segments must be defined in the linker command file,
> > > ; and be declared above.
> > > ;
> > >
> > > ; --------------------
> > > ; Mode, corresponds to bits 0-5 in CPSR
> > >
> > > MODE_MSK DEFINE 0x1F ; Bit mask for mode bits in CPSR
> > >
> > > USR_MODE DEFINE 0x10 ; User mode
> > > FIQ_MODE DEFINE 0x11 ; Fast Interrupt Request mode
> > > IRQ_MODE DEFINE 0x12 ; Interrupt Request mode
> > > SVC_MODE DEFINE 0x13 ; Supervisor mode
> > > ABT_MODE DEFINE 0x17 ; Abort mode
> > > UND_MODE DEFINE 0x1B ; Undefined Instruction mode
> > > SYS_MODE DEFINE 0x1F ; System mode
> > >
> > > MRS r0, cpsr ; Original PSR value
> > > ;;====================================================================> > >========= ;; STACK POINTERS SETUP
> > > ;;====================================================================> > >========> > >
> > > ;; Setup the interrupt stack pointer.
> > >
> > > BIC r0, r0, #MODE_MSK ; Clear the mode bits
> > > ORR r0, r0, #IRQ_MODE ; Set IRQ mode bits
> > > MSR cpsr_c, r0 ; Change the mode
> > > LDR sp, =SFE(IRQ_STACK) ; End of IRQ_STACK
> > >
> > > ;; Set up the fast interrupt stack pointer.
> > >
> > > BIC r0, r0, #MODE_MSK ; Clear the mode bits
> > > ORR r0, r0, #FIQ_MODE ; Set FIR mode bits
> > > MSR cpsr_c, r0 ; Change the mode
> > > LDR sp, =SFE(FIQ_STACK) ; End of FIQ_STACK
> > >
> > > bic r0,r0,#MODE_MSK ; Clear the mode bits
> > > orr r0,r0,#UND_MODE ; Set UND mode bits
> > > msr cpsr_c,r0 ; Change the mode
> > > ldr sp,=SFE(UND_STACK) ; End of UND_STACK
> > >
> > > bic r0,r0,#MODE_MSK ; Clear the mode bits
> > > orr r0,r0,#ABT_MODE ; Set ABT mode bits
> > > msr cpsr_c,r0 ; Change the mode
> > > ldr sp,=SFE(ABT_STACK) ; End of ABT_STACK
> > >
> > > bic r0,r0,#MODE_MSK ; Clear the mode bits
> > > orr r0,r0,#SYS_MODE ; Set SYS mode bits
> > > msr cpsr_c,r0 ; Change the mode
> > > ldr sp,=SFE(CSTACK) ; End of CSTACK
> > >
> > > ;; Set up the normal stack pointer.
> > >
> > > BIC r0 ,r0, #MODE_MSK ; Clear the mode bits
> > > ORR r0 ,r0, #SVC_MODE ; Set SVC mode bits
> > > MSR cpsr_c, r0 ; Change the mode
> > > LDR sp, =SFE(SVC_STACK) ; End of SVC_STACK
> > > ; setup spurious interrupt handler
> > > ldr r0,=at91_spurious_handler
> > > ldr r1,=AT91C_BASE_AIC
> > > str r0,[r1, #AIC_SPU]
> > >
> > > #ifdef __ARMVFP__
> > > ;; Enable the VFP coprocessor.
> > >
> > > MOV r0, #0x40000000 ; Set EN bit in VFP
> > > FMXR fpexc, r0 ; FPEXC, clear others.
> > >
> > > ;
> > > ; Disable underflow exceptions by setting flush to zero mode.
> > > ; For full IEEE 754 underflow compliance this code should be removed
> > > ; and the appropriate exception handler installed.
> > > ;
> > >
> > > MOV r0, #0x01000000 ; Set FZ bit in VFP
> > > FMXR fpscr, r0 ; FPSCR, clear others.
> > > #endif
> > >
> > > ;
> > > ; Add more initialization here
> > > ;
> > >
> > > ; Continue to ?main for C-level initialization.
> > >
> > > B ?main
> > >
> > > END
> > > //////////////
> > >
> > > What is wrong. Any views on this.
> > >
> > > Regards
> > > Dani
> > >
> > > --- In
A..., "Icli,
Bekir" wrote:
> > > > Hi Dani,
> > > >
> > > > You should first understand how the interrupts in ARM are handled.
> > > > Wenn the Interrupt Controller asserts the signal, processor loads the
> > > > program counter with the address 0x18. There, you must have a branch
> > > > to your actual IRQ handler.
> > > > It looks pretty much like this:
> > > >
> > > > .section .vectors,"a",%progbits
> > > >
> > > > resetVector:
> > > > b resetHandler /* Reset */
> > > > undefVector:
> > > > b UndefinedException /* Undefined instruction */
> > > > swiVector:
> > > > b SwiException /* Software interrupt !! should not fire!! */
> > > > prefetchAbortVector:
> > > > b PrefetchAbortException /* Prefetch abort */
> > > > dataAbortVector:
> > > > b DataAbortException /* Data abort */
> > > > reservedVector:
> > > > b reservedVector /* Reserved for future use */
> > > > irqVector:
> > > > b irqHandler /* Interrupt */
> > > > fiqVector:
> > > > b fiqVector /* FIQ */
> > > > From there on, it's all up to you, how you deal with the rest in
> > > > "irqHandler".
> > > >
> > > > Good luck,
> > > > Bekir
> > > >
> > > > ________________________________
> > > > From:
> > > > A... > > > >SAM%40yahoogroups.com>
> > > > [mailto:A... > > > >lto:AT91SAM%40yahoogroups.com>] On Behalf Of ADNAN Sent: Thursday,
> > > > January 07, 2010 10:56 PM
> > > > To:
> > > > A... > > > >SAM%40yahoogroups.com> Subject: [AT91SAM] How to move interrupt vector
> > > > from 0x0 to some offset
> > > >
> > > >
> > > >
> > > > Hello all,
> > > >
> > > > I am newbie to Arm and IAR. I have develope an application using
> > > > IAR5.30 and AT91SAM7S128 which has interuupt vector starting from 0x0
> > > > and rom starting from 0x5000 and when i load this application using
> > > > jflash utitlity it is working fine.
> > > >
> > > > On the same configuration(address) i have devloped a bootloader
> > > > application. Now i want to download first application using this
> > > > bootloader application. As the both bootloader application and the
> > > > first application has the same interrupt vector address 0x0 so when i
> > > > download it donot work.
> > > >
> > > > Do i need to move the interrupt vector to some where else, ?
> > > >
> > > > When i moved the interrupt vector of my application to 0x5000 , i.e.
> > > > just in the start of the application, the interrupt are not working.
> > > >
> > > > Kindly send your valuable advise and observation to help solving my
> > > > problem.
> > > >
> > > > Your kind guidence will be highly appricated.
> > > >
> > > > Regards
> > > > Dani

Reply by Greg Nelson January 9, 20102010-01-09
> I am newbie to Arm and IAR. I have develope an application using
> IAR5.30 and AT91SAM7S128 which has interuupt vector starting from
> 0x0 and rom starting from 0x5000 and when i load this application
> using jflash utitlity it is working fine.

Dani,

This is from the AT91SAM7S manual:

-----

18.3.2.2 Internal Memory Area 0

The first 32 bytes of Internal Memory Area 0 contain the ARM processor
exception vectors, in particular, the Reset Vector at address 0x0.

Before execution of the remap command, the on-chip Flash is mapped
into Internal Memory Area 0, so that the ARM7TDMI reaches an
executable instruction contained in Flash. After the remap command,
the internal SRAM at address 0x0020 0000 is mapped into Internal
Memory Area 0. The memory mapped into Internal Memory Area 0 is
accessible in both its original location and at address 0x0.

-----

In short, the address of 0x0 is hard-coded into the ARM architecture.
If you want to change the vectors that are there, you can do that, as
long as you have SRAM memory in that location (see the following
section, 18.3.3 for details), but you can't change the address from
0x0 to 0x5000. The only reason that 0x00100000 works is because that
is the default address where the internal Flash is replicated. If you
had used 0x00200000 instead, you'd be accessing the default address
for the SRAM and it wouldn't work -- or at least, it wouldn't change
the behavior.

*If* the vectors at 0x0 use the AIC, then you should be able to
reprogram where things go for certain exceptions like the IRQ and
FIQ. Or, if the code at the addresses listed in your listing
(__iar_program_start, IRQ_Wrapper, etc) happens to be in RAM, you
could overwrite these routines with your own routines.

Other than that, you will have to change the 32 bytes of data at
address 0x0, and you can only do that if you've remapped the SRAM.

Greg

Reply by stipplethunk January 8, 20102010-01-08
--- In A..., "ADNAN" wrote:
>
> Hello all,
>
> I am newbie to Arm and IAR. I have develope an application using IAR5.30 and AT91SAM7S128 which has interuupt vector starting from 0x0 and rom starting from 0x5000 and when i load this application using jflash utitlity it is working fine.
>
> On the same configuration(address) i have devloped a bootloader application. Now i want to download first application using this bootloader application. As the both bootloader application and the first application has the same interrupt vector address 0x0 so when i download it donot work.
>
> Do i need to move the interrupt vector to some where else, ?
>
> When i moved the interrupt vector of my application to 0x5000 , i.e. just in the start of the application, the interrupt are not working.
>
> Kindly send your valuable advise and observation to help solving my problem.
>
> Your kind guidence will be highly appricated.
>
> Regards
> Dani
>
Although I am not familiar with this device, I believe that there is a 'remap' command, which maps the internal ram to address 0x0000. After reset the internal flash is mapped to address 0x0000. The flash is also always mapped to address 0x100000 & the ram is always mapped to address 0x200000.

Chris.

Reply by ADNAN January 8, 20102010-01-08
Hi,

Actually I want to write a bootloader that will download and execute another placed in some area of ROM.How it can be possible.?

My idea is to have vector table of bootloader to be at the start of
the ROM at 0x0 and of my application to be at the start of rom at 0x5000.
What do you think? I have tried this way bootloader try starting application but application dont works.

Regards
Dani

--- In A..., "Icli, Bekir" wrote:
>
> You cannot change the irq and excp vec. addresses.. I told you they are fixed.. 0x0 thru 0x20
> What you can do is, let the code run from 0x5000 and relocate (simply copy) your vector handlers
> > __vector:
> >
> > LDR PC,Reset_Addr ; Reset
> > LDR PC,Undefined_Addr ; Undefined instructions
> > LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> > LDR PC,Prefetch_Addr ; Prefetch abort
> > LDR PC,Abort_Addr ; Data abort
> > __vector_0x14:
> > DCD 0 ; RESERVED
> > LDR PC,IRQ_Addr ; IRQ
> > LDR PC,FIQ_Addr ; FIQ
> to 0x0.. that should solve the problem..
>
> Best,
> Bekir
>
> ________________________________
> From: A... [mailto:A...] On Behalf Of ADNAN
> Sent: Friday, January 08, 2010 2:47 PM
> To: A...
> Subject: [AT91SAM] Re: How to move interrupt vector from 0x0 to some offset
> Hi,
>
> You are right. Now tell me what should i do to change the interrupt vector and exception vector address from 0x0 to 0x5000 or 0x105000 so that my application alos works from there.
>
> Regards
> Dani
>
> --- In A..., "Icli, Bekir" wrote:
> >
> > Hi Dani,
> >
> > It makes perfect sense, that it works when you load it to 0x0 or 0x100000.. Apparently these two memory locations are mirrored.. (means they are pointing to the same physical memory)..
> > As I stated in my former mail, you HAVE TO load your exception vectors (with that I mean irq and the other exception vectors) to 0x0..
> > In your case:
> > __vector:
> >
> > LDR PC,Reset_Addr ; Reset
> > LDR PC,Undefined_Addr ; Undefined instructions
> > LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> > LDR PC,Prefetch_Addr ; Prefetch abort
> > LDR PC,Abort_Addr ; Data abort
> > __vector_0x14:
> > DCD 0 ; RESERVED
> > LDR PC,IRQ_Addr ; IRQ
> > LDR PC,FIQ_Addr ; FIQ
> > should be placed to 0x0..
> > Because processor does not know where your handler is, he just jumps to 0x18 and continues with execution..
> > If you have a debugger, set a break point at 0x18 and you'll see what I mean.. and check after that, if your LDR PC, IRQ_Addr is there.. ;)
> >
> > Best,
> > Bekir
> >
> > ________________________________
> > From: A... [mailto:A...] On Behalf Of ADNAN
> > Sent: Friday, January 08, 2010 12:09 PM
> > To: A...
> > Subject: [AT91SAM] Re: How to move interrupt vector from 0x0 to some offset
> >
> >
> >
> > Hi Bakir,
> >
> > Thanks for your reply.
> >
> > I am using CMX Rtos for both of my codes, 1, bootloader and other is the actualy application. The cmx handler for IRQ is as follows,
> > SECTION .text:CODE:NOROOT:REORDER(2)
> > ARM
> > IRQ_Wrapper:
> > SUB LR,LR,#4 ; adj for proper CMX return
> > STMFD SP!,{R0-R12,LR} ; save the registers
> >
> > ldr r14, =AT91C_BASE_AIC
> > ldr r0, [r14, #AIC_IVR] ; get vector address
> > str r14, [r14, #AIC_IVR]
> >
> > MRS R9,SPSR ; save the SPSR
> > STMFD SP!,{R9}
> > LDR R2,=int_count ; get int_count
> > MRS R3,CPSR
> > MOV R4,R3
> > ORR R4,R4,#Int_Bits ; disable interrupts
> > MSR CPSR_c,R4
> > LDRB R1,[R2] ; incr the count
> > ADD R1,R1,#1
> > STRB R1,[R2]
> > MSR CPSR_c,R3 ; restore interrupts
> >
> > cmp r0, #0 ; handler available?
> > beq irq_ack ; no, ack interrupt and exit
> >
> > MSR CPSR_c, #SYS_MODE ; SYS mode, interrupts enabled
> > STMFD sp!,{R0-R12,lr} ; Save registers.
> > mov lr,pc
> > BX R0 ; call specified handler
> > LDMFD SP!,{R0-R12,lr} ; restore registers.
> > MSR CPSR_c, #IRQ_MODE|I_Bit|F_Bit ; Switch to IRQ mode, no interrupts
> >
> > irq_ack
> > ldr r1, =AT91C_BASE_AIC ; Ack End of Interrupt
> > str r1, [r1, #AIC_EOICR]
> >
> > B K_OS_Intrp_Exit
> >
> > This handler works nice when i place intvec at 0x0 or 0x100000, but stops working when i change address of intvec to 0x5000 or 0x105000 i dont know why,
> >
> > The cStartup is as follows,
> >
> > MODULE ?cstartup
> >
> > SECTION IRQ_STACK:DATA:NOROOT(3)
> > SECTION FIQ_STACK:DATA:NOROOT(3)
> > SECTION UND_STACK:DATA:NOROOT(3)
> > SECTION ABT_STACK:DATA:NOROOT(3)
> > SECTION SVC_STACK:DATA:NOROOT(3)
> > SECTION CSTACK:DATA:NOROOT(3)
> >
> > SECTION .intvec:CODE:NOROOT(2)
> >
> > PUBLIC __vector
> > PUBLIC __vector_0x14
> > PUBLIC __iar_program_start
> > EXTERN Undef_Wrapper
> > EXTERN SWI_Wrapper
> > EXTERN Prefetch_Wrapper
> > EXTERN Abort_Wrapper
> > EXTERN IRQ_Wrapper
> > EXTERN FIQ_Wrapper
> >
> > ARM
> >
> > ;;
Reply by ADNAN January 8, 20102010-01-08
Hi,

You are right. Now tell me what should i do to change the interrupt vector and exception vector address from 0x0 to 0x5000 or 0x105000 so that my application alos works from there.

Regards
Dani
--- In A..., "Icli, Bekir" wrote:
>
> Hi Dani,
>
> It makes perfect sense, that it works when you load it to 0x0 or 0x100000.. Apparently these two memory locations are mirrored.. (means they are pointing to the same physical memory)..
> As I stated in my former mail, you HAVE TO load your exception vectors (with that I mean irq and the other exception vectors) to 0x0..
> In your case:
> __vector:
>
> LDR PC,Reset_Addr ; Reset
> LDR PC,Undefined_Addr ; Undefined instructions
> LDR PC,SWI_Addr ; Software interrupt (SWI/SVC)
> LDR PC,Prefetch_Addr ; Prefetch abort
> LDR PC,Abort_Addr ; Data abort
> __vector_0x14:
> DCD 0 ; RESERVED
> LDR PC,IRQ_Addr ; IRQ
> LDR PC,FIQ_Addr ; FIQ
> should be placed to 0x0..
> Because processor does not know where your handler is, he just jumps to 0x18 and continues with execution..
> If you have a debugger, set a break point at 0x18 and you'll see what I mean.. and check after that, if your LDR PC, IRQ_Addr is there.. ;)
>
> Best,
> Bekir
>
> ________________________________
> From: A... [mailto:A...] On Behalf Of ADNAN
> Sent: Friday, January 08, 2010 12:09 PM
> To: A...
> Subject: [AT91SAM] Re: How to move interrupt vector from 0x0 to some offset
>
> Hi Bakir,
>
> Thanks for your reply.
>
> I am using CMX Rtos for both of my codes, 1, bootloader and other is the actualy application. The cmx handler for IRQ is as follows,
> SECTION .text:CODE:NOROOT:REORDER(2)
> ARM
> IRQ_Wrapper:
> SUB LR,LR,#4 ; adj for proper CMX return
> STMFD SP!,{R0-R12,LR} ; save the registers
>
> ldr r14, =AT91C_BASE_AIC
> ldr r0, [r14, #AIC_IVR] ; get vector address
> str r14, [r14, #AIC_IVR]
>
> MRS R9,SPSR ; save the SPSR
> STMFD SP!,{R9}
> LDR R2,=int_count ; get int_count
> MRS R3,CPSR
> MOV R4,R3
> ORR R4,R4,#Int_Bits ; disable interrupts
> MSR CPSR_c,R4
> LDRB R1,[R2] ; incr the count
> ADD R1,R1,#1
> STRB R1,[R2]
> MSR CPSR_c,R3 ; restore interrupts
>
> cmp r0, #0 ; handler available?
> beq irq_ack ; no, ack interrupt and exit
>
> MSR CPSR_c, #SYS_MODE ; SYS mode, interrupts enabled
> STMFD sp!,{R0-R12,lr} ; Save registers.
> mov lr,pc
> BX R0 ; call specified handler
> LDMFD SP!,{R0-R12,lr} ; restore registers.
> MSR CPSR_c, #IRQ_MODE|I_Bit|F_Bit ; Switch to IRQ mode, no interrupts
>
> irq_ack
> ldr r1, =AT91C_BASE_AIC ; Ack End of Interrupt
> str r1, [r1, #AIC_EOICR]
>
> B K_OS_Intrp_Exit
>
> This handler works nice when i place intvec at 0x0 or 0x100000, but stops working when i change address of intvec to 0x5000 or 0x105000 i dont know why,
>
> The cStartup is as follows,
>
> MODULE ?cstartup
>
> SECTION IRQ_STACK:DATA:NOROOT(3)
> SECTION FIQ_STACK:DATA:NOROOT(3)
> SECTION UND_STACK:DATA:NOROOT(3)
> SECTION ABT_STACK:DATA:NOROOT(3)
> SECTION SVC_STACK:DATA:NOROOT(3)
> SECTION CSTACK:DATA:NOROOT(3)
>
> SECTION .intvec:CODE:NOROOT(2)
>
> PUBLIC __vector
> PUBLIC __vector_0x14
> PUBLIC __iar_program_start
> EXTERN Undef_Wrapper
> EXTERN SWI_Wrapper
> EXTERN Prefetch_Wrapper
> EXTERN Abort_Wrapper
> EXTERN IRQ_Wrapper
> EXTERN FIQ_Wrapper
>
> ARM
>
> ;;
Reply by "Icli, Bekir" January 8, 20102010-01-08
Reply by ADNAN January 8, 20102010-01-08
Hi Bakir,

Thanks for your reply.

I am using CMX Rtos for both of my codes, 1, bootloader and other is the actualy application. The cmx handler for IRQ is as follows,
SECTION .text:CODE:NOROOT:REORDER(2)
ARM
IRQ_Wrapper:
SUB LR,LR,#4 ; adj for proper CMX return
STMFD SP!,{R0-R12,LR} ; save the registers

ldr r14, =AT91C_BASE_AIC
ldr r0, [r14, #AIC_IVR] ; get vector address
str r14, [r14, #AIC_IVR]

MRS R9,SPSR ; save the SPSR
STMFD SP!,{R9}
LDR R2,=int_count ; get int_count
MRS R3,CPSR
MOV R4,R3
ORR R4,R4,#Int_Bits ; disable interrupts
MSR CPSR_c,R4
LDRB R1,[R2] ; incr the count
ADD R1,R1,#1
STRB R1,[R2]
MSR CPSR_c,R3 ; restore interrupts

cmp r0, #0 ; handler available?
beq irq_ack ; no, ack interrupt and exit

MSR CPSR_c, #SYS_MODE ; SYS mode, interrupts enabled
STMFD sp!,{R0-R12,lr} ; Save registers.
mov lr,pc
BX R0 ; call specified handler
LDMFD SP!,{R0-R12,lr} ; restore registers.
MSR CPSR_c, #IRQ_MODE|I_Bit|F_Bit ; Switch to IRQ mode, no interrupts

irq_ack
ldr r1, =AT91C_BASE_AIC ; Ack End of Interrupt
str r1, [r1, #AIC_EOICR]

B K_OS_Intrp_Exit
This handler works nice when i place intvec at 0x0 or 0x100000, but stops working when i change address of intvec to 0x5000 or 0x105000 i dont know why,

The cStartup is as follows,

MODULE ?cstartup

SECTION IRQ_STACK:DATA:NOROOT(3)
SECTION FIQ_STACK:DATA:NOROOT(3)
SECTION UND_STACK:DATA:NOROOT(3)
SECTION ABT_STACK:DATA:NOROOT(3)
SECTION SVC_STACK:DATA:NOROOT(3)
SECTION CSTACK:DATA:NOROOT(3)

SECTION .intvec:CODE:NOROOT(2)

PUBLIC __vector
PUBLIC __vector_0x14
PUBLIC __iar_program_start
EXTERN Undef_Wrapper
EXTERN SWI_Wrapper
EXTERN Prefetch_Wrapper
EXTERN Abort_Wrapper
EXTERN IRQ_Wrapper
EXTERN FIQ_Wrapper

ARM

;;
Reply by nutleycottage January 8, 20102010-01-08
--- In A..., "ADNAN" wrote:
>
> Hello all,
>
> I am newbie to Arm and IAR. I have develope an application using IAR5.30 and AT91SAM7S128 which has interuupt vector starting from 0x0 and rom starting from 0x5000 and when i load this application using jflash utitlity it is working fine.
>
> On the same configuration(address) i have devloped a bootloader application. Now i want to download first application using this bootloader application. As the both bootloader application and the first application has the same interrupt vector address 0x0 so when i download it donot work.
>
> Do i need to move the interrupt vector to some where else, ?
>
> When i moved the interrupt vector of my application to 0x5000 , i.e. just in the start of the application, the interrupt are not working.
>
> Kindly send your valuable advise and observation to help solving my problem.
>
> Your kind guidence will be highly appricated.
>
> Regards
> Dani
>

Hi Dani,

The SAM7/SAM9 devices have a module called the AIC. You only need to provide an irq_handler that jumps to the AIC_IVR register. The exception vectors can be fixed.

If you really have to have a different set of exception vectors (the only reason I can think of is you are using fiq_handler) then you will have to remap SRAM to address zero and copy the exception vectors from Flash to SRAM.

Regards
Michael

Reply by "Icli, Bekir" January 8, 20102010-01-08
Hi Dani,

You should first understand how the interrupts in ARM are handled.
Wenn the Interrupt Controller asserts the signal, processor loads the program counter with the address 0x18.
There, you must have a branch to your actual IRQ handler.
It looks pretty much like this:

.section .vectors,"a",%progbits

resetVector:
b resetHandler /* Reset */
undefVector:
b UndefinedException /* Undefined instruction */
swiVector:
b SwiException /* Software interrupt !! should not fire!! */
prefetchAbortVector:
b PrefetchAbortException /* Prefetch abort */
dataAbortVector:
b DataAbortException /* Data abort */
reservedVector:
b reservedVector /* Reserved for future use */
irqVector:
b irqHandler /* Interrupt */
fiqVector:
b fiqVector /* FIQ */
From there on, it's all up to you, how you deal with the rest in "irqHandler".

Good luck,
Bekir

________________________________
From: A... [mailto:A...] On Behalf Of ADNAN
Sent: Thursday, January 07, 2010 10:56 PM
To: A...
Subject: [AT91SAM] How to move interrupt vector from 0x0 to some offset

Hello all,

I am newbie to Arm and IAR. I have develope an application using IAR5.30 and AT91SAM7S128 which has interuupt vector starting from 0x0 and rom starting from 0x5000 and when i load this application using jflash utitlity it is working fine.

On the same configuration(address) i have devloped a bootloader application. Now i want to download first application using this bootloader application. As the both bootloader application and the first application has the same interrupt vector address 0x0 so when i download it donot work.

Do i need to move the interrupt vector to some where else, ?

When i moved the interrupt vector of my application to 0x5000 , i.e. just in the start of the application, the interrupt are not working.

Kindly send your valuable advise and observation to help solving my problem.

Your kind guidence will be highly appricated.

Regards
Dani
Reply by arif...@yahoo.com January 8, 20102010-01-08
hjh
Sent on my BlackBerry from Vodafone

-----Original Message-----
From: "ADNAN"
Date: Thu, 07 Jan 2010 21:56:23
To:
Subject: [AT91SAM] How to move interrupt vector from 0x0 to some offset

Hello all,

I am newbie to Arm and IAR. I have develope an application using IAR5.30 and AT91SAM7S128 which has interuupt vector starting from 0x0 and rom starting from 0x5000 and when i load this application using jflash utitlity it is working fine.

On the same configuration(address) i have devloped a bootloader application. Now i want to download first application using this bootloader application. As the both bootloader application and the first application has the same interrupt vector address 0x0 so when i download it donot work.

Do i need to move the interrupt vector to some where else, ?

When i moved the interrupt vector of my application to 0x5000 , i.e. just in the start of the application, the interrupt are not working.

Kindly send your valuable advise and observation to help solving my problem.

Your kind guidence will be highly appricated.

Regards
Dani