I'm working through a SH7058 32bit ROM, and trying to figure out how the interrupts work. I've been looking at this for hours, but something doesn't seem to make sense. So, I'm hoping someone can help out.
The interrupts trigger the subroutines in the VBR near the end of the ROM. These subroutines JSR/BSR/JMP/BRA to other subroutines. The address of one subroutine is loaded into r0 and from there it is loaded into the PR. For this subroutine to be accessed, I was expecting an RTS would follow which would transfer execution to the address stored in the PR. However, a JSR follows soon after. This overwrites the PR meaning there was no point in storing it in the first place.
If the subroutine doesn't get accessed, the whole interrupt routine has no real effect, so something I'm doing must be wrong.
Here's the detail...
Subroutine called by the VBR...
Code:
*************************************************************
* FUNCTION
*************************************************************
undefined Func_Incr_0xFF12B8_set_0xFF2064+0xFF208Dx8_to_
undefined r0:1 <RETURN>
undefined4 Stack[-0x4]:4 local_4 XREF[1]: 00002978 (*)
undefined4 Stack[-0x8]:4 local_8 XREF[1]: 0000297c (*)
undefined4 Stack[-0xc]:4 local_c XREF[1]: 00002980 (*)
Func_Incr_0xFF12B8_set_0xFF2064+0xFF208Dx8_to_ XREF[1]: 000ffd64 (*)
00002978 2f 06 mov.l r0,@- r15 =>local_4
0000297a d0 04 mov.l @(->Func_0xFF12C0_to_SR_0xFF12B8++_Save_Regs_t = 00003428
0000297c 4f 22 sts.l pr,@- r15 =>local_8
0000297e 40 0b jsr @r0=>Func_0xFF12C0_to_SR_0xFF12B8++_Save_Regs_ void Func_0xFF12C0_to_SR_0xFF12B
00002980 2f 16 _mov.l r1,@- r15 =>local_c
00002982 d1 01 mov.l @(->Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and = 00005596
00002984 41 2b jmp @r1=>Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_an undefined Func_Set_0xFF2064+0xFF
00002986 40 2a _lds r0,pr
-- Flow Override: CALL_RETURN (COMPUTED_CALL_TERMINATOR)
The first JSR in the above subroutine goes to the subroutine below. At the end of this subroutine, the address of another subroutine (0x3470) is loaded into r0 (the r0 destination is cut off in this view). The RTS then returns to the above subroutine. The above subroutine then branches using a JMP, but first the value in r0 (subroutine address 0x3470) is loaded into the PR.
Code:
*************************************************************
* FUNCTION
*************************************************************
void Func_0xFF12C0_to_SR_0xFF12B8++_Save_Regs_to_Stack_P
void <VOID> <RETURN>
undefined4 Stack[-0x4]:4 local_4 XREF[1]: 00003428 (*)
undefined4 Stack[-0x8]:4 local_8 XREF[1]: 0000343a (*)
undefined4 Stack[-0xc]:4 local_c XREF[1]: 0000343c (*)
undefined4 Stack[-0x10]:4 local_10 XREF[1]: 0000343e (*)
undefined4 Stack[-0x18]:4 local_18 XREF[2]: 00003442 (*) ,
00003444 (*)
undefined4 Stack[-0x20]:4 local_20 XREF[1]: 00003448 (*)
undefined4 Stack[-0x28]:4 local_28 XREF[1]: 0000344c (*)
undefined4 Stack[-0x30]:4 local_30 XREF[1]: 00003450 (*)
undefined4 Stack[-0x38]:4 local_38 XREF[1]: 00003454 (*)
undefined4 Stack[-0x40]:4 local_40 XREF[1]: 00003458 (*)
undefined4 Stack[-0x48]:4 local_48 XREF[2]: 0000345a (*) ,
0000345c (*)
undefined4 Stack[-0x50]:4 local_50 XREF[1]: 0000345e (*)
Func_0xFF12C0_to_SR_0xFF12B8++_Save_Regs_to_St XREF[238]:
00003428 2f 26 mov.l r2,@- r15 =>local_4
0000342a d1 0f mov.l @(->RAM_0xFF12B0 ,pc),r1 = ffff12b0
0000342c 02 02 stc sr,r2
0000342e 50 14 mov.l @(offset DAT_ffff12c0 ,r1),r0 = ??
00003430 40 0e ldc r0,sr
00003432 50 12 mov.l @(offset RAM_0xFF12B8 ,r1),r0 = ??
00003434 70 01 add 0x1 ,r0
00003436 11 02 mov.l r0,@( offset RAM_0xFF12B8 ,r1) = ??
00003438 42 0e ldc r2,sr
0000343a 2f 36 mov.l r3,@- r15 =>local_8
0000343c 2f 46 mov.l r4,@- r15 =>local_c
0000343e 2f 56 mov.l r5,@- r15 =>local_10
00003440 2f 66 mov.l r6,@- r15 =>Stack [-0x14 ]
00003442 2f 76 mov.l r7,@- r15 =>local_18
00003444 ff 0b fmov.s fr0 ,@- r15 =>local_18
00003446 ff 1b fmov.s fr1 ,@- r15 =>Stack [-0x1c ]
00003448 ff 2b fmov.s fr2 ,@- r15 =>local_20
0000344a ff 3b fmov.s fr3 ,@- r15 =>Stack [-0x24 ]
0000344c ff 4b fmov.s fr4 ,@- r15 =>local_28
0000344e ff 5b fmov.s fr5 ,@- r15 =>Stack [-0x2c ]
00003450 ff 6b fmov.s fr6 ,@- r15 =>local_30
00003452 ff 7b fmov.s fr7 ,@- r15 =>Stack [-0x34 ]
00003454 ff 8b fmov.s fr8 ,@- r15 =>local_38
00003456 ff 9b fmov.s fr9 ,@- r15 =>Stack [-0x3c ]
00003458 ff ab fmov.s fr10 ,@- r15 =>local_40
0000345a 4f 62 sts.l fpscr ,@- r15 =>local_48
0000345c ff bb fmov.s fr11 ,@- r15 =>local_48
0000345e 4f 52 sts.l fpul ,@- r15 =>local_50
00003460 d0 02 mov.l @(->Func_Check_Stack_Full_or_Empty_Check_Prior = 00003470
00003462 00 0b rts
00003464 00 09 _nop
00003466 00 09 nop
The JMP from above leads to the subroutine below...
Code:
*************************************************************
* FUNCTION
*************************************************************
undefined Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and_+4_
undefined r0:1 <RETURN>
Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and_+4_ XREF[2]:
00005596 94 23 mov.w @(Constant_0xED1A ,pc),r4 = ED1Ah
00005598 63 41 mov.w @r4=>DAT_ffffed1a ,r3 = ??
0000559a 92 26 mov.w @(Constant_0x00FB ,pc),r2 = FBh
0000559c 24 21 mov.w r2,@r4=>DAT_ffffed1a = ??
0000559e af 9d bra Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and_+4_ undefined Func_Set_0xFF2064+0xFF
000055a0 e4 45 _mov #0x45 ,r4
-- Flow Override: CALL_RETURN (CALL_TERMINATOR)
And the BRA from above leads to the subroutine below... At 0x54e4, the subroutine executes a JSR which would overwrite the PR with 0x54e8 (I think?). So, the subroutine at 0x3470 is never used. Which can't be right because the subroutine at 0x3470 is critical for handling the interrupt (it checks interrupt level, restores the stack and calls the subroutine to execute as a result of the interruption). Without this running, the interruption achieves nothing.
Code:
*************************************************************
* FUNCTION
*************************************************************
undefined Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and_+4_
undefined r0:1 <RETURN>
undefined4 Stack[-0x4]:4 local_4 XREF[2]: 000054e2 (*) ,
000054ec (*)
Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and_+4_ XREF[106]:
000054dc 95 7b mov.w @(Constant_0x00E0 ,pc),r5 = E0h
000054de 7f f8 add -0x8 ,r15
000054e0 d3 44 mov.l @(->Func_Set_Value_at_A_to_I3-I0_and_update_SR = 00002088
000054e2 1f 41 mov.l r4,@( 0x4 =>local_4 ,r15 )
000054e4 43 0b jsr @r3=>Func_Set_Value_at_A_to_I3-I0_and_update_S void Func_Set_Value_at_A_to_I3-I
000054e6 64 f3 _mov r15 ,r4
000054e8 d3 43 mov.l @(->Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_and = 0000e5d0
000054ea 43 0b jsr @r3=>Func_Set_0xFF2064+0xFF208Dx8_to_0x00C8_an void Func_Set_0xFF2064+0xFF208Dx
000054ec 54 f1 _mov.l @(0x4 =>local_4 ,r15 ),r4
LAB_000054ee XREF[1]:
000054ee af fe bra LAB_000054ee
000054f0 00 09 _nop
So, something doesn't make sense. Any help greatly appreciated.