[prev in list] [next in list] [prev in thread] [next in thread] 

List:       qemu-discuss
Subject:    Re: [Qemu-discuss] How to trigger software interrupt on Versatile Express ?
From:       Mirela_Simonoviæ <mirelasimonovic () gmail ! com>
Date:       2012-04-17 18:47:08
Message-ID: CAAmXuEkpbR87z2ntPhEHigH6Nq27j_ULipd9pUrG1aT7x=iR-w () mail ! gmail ! com
[Download RAW message or body]

2012/4/12 Mirela Simonović <mirelasimonovic@gmail.com>

> Hi,
>
> I'm having troubles with triggering a software interrupt on Versatile
> Express board (Cortex-A9).
> I managed to set an interrupt pending, but jump to Vector Table does not
> execute.
> Here is simple program that I'm running:
>
> *//
> ======================================================================================
> *
> *// File: test.c*
> *//
> ======================================================================================
> *
> *
> *
> *
> #define HAL_READ_UINT32(register, value)  (( value ) = *((volatile
> unsigned int *)( register )))
> *
> #define HAL_WRITE_UINT32(register, value) (*((volatile unsigned int *)(
> register )) = ( value ))
>
> #define PERIPHBASE 0x1e000000
> #define CPUBASE ( PERIPHBASE + 0x100 ) // CPU Interface Base Address
> #define DISTBASE   ( PERIPHBASE + 0x1000 )        // Distributor Base
> Address
>
> #define ICCICR     0x00       // CPU Interface Control Register (RW)
> #define ICCPMR   0x04       //*
>  CPU Interface
> **
>  Priority Mask Register (RW)
> *
> *
> #define ICDDCR   0x000 // Distributor Control Register (RW)
> *
> #define ICDISER  0x100 // *
> Distributor
> **
> Interrupt Set Enable Registers (RW)
> *
> #define ICDISPR  0x200 // *
> Distributor
> **
> Set Pending Register (RW)
> *
> #define ICDIPR    0x400 // *
> Distributor
> **
> Interrupt Priority Register (RW)
> *
> #define ICDSGIR  0xF00 // *
> Distributor
> **
> Software Generated Interrupt Register (WO)
> *
>
> int main ()
> {
> unsigned int tmp;
>
>  *HAL_WRITE_UINT32( CPUBASE  + ICCICR, 0 );         * // Disable CPU
> Interface (it is already disabled, but nevermind)
>  *HAL_WRITE_UINT32( DISTBASE + ICDDCR, 0 ); * // Disable Distributor (it
> is already disabled, but nevermind)
>  *HAL_WRITE_UINT32( DISTBASE + ICDISER, 0x0000ffff );* // Set enable
> (enable all SGIs)
>  *HAL_WRITE_UINT32( CPUBASE  + ICCPMR, 0xff );* // All interrupts whose
> priority is > 0xff are unmasked
>  *HAL_WRITE_UINT32( DISTBASE + ICDIPR, 0 );* // Set the highest priority
>  *HAL_WRITE_UINT32( DISTBASE + ICDDCR, 1 );*  // Enable Distributor
>  *HAL_WRITE_UINT32( CPUBASE  + ICCICR, 1 ); * // Enable CPU Interface
>
> HAL_READ_UINT32 ( DISTBASE + ICDISPR, tmp); // Is the interrupt pending?
> => No, it's not
>  *HAL_WRITE_UINT32( DISTBASE + ICDSGIR, 0x02000000); * // Generate
> software interrupt ID=0 to CPU0 (to this, running CPU)
>  HAL_READ_UINT32 ( DISTBASE + ICDISPR, tmp); // Is the interrupt pending?
> => Yes, it is
>
> return 0;
> }
>
> *//
> ======================================================================================
> *
> *// File: startup.s*
> *//
> ======================================================================================
> *
> *
> *
> .section INTERRUPT_VECTOR, "x"
> .global _Reset
> _Reset:
>   B Reset_Handler /* Reset */
>   B . /* Undefined */
>   B . /* SWI */
>   B . /* Prefetch Abort */
>   B . /* Data Abort */
>   B . /* reserved */
>   B . /* IRQ */
>   B . /* FIQ */
>
> Reset_Handler:
>   LDR sp, =stack_top
>   BL main
>   B .
>
> *//
> ======================================================================================
> *
> *// File: test.ld*
> *//
> ======================================================================================
> *
> ENTRY(_Reset)
> SECTIONS
> {
> . = 0x0;
>  .text : { startup.o(INTERRUPT_VECTOR)
>   *(.text) }
> .data : { *(.data) }
>  .bss : { *(.bss) }
>  . = . + 0x10000; /* 4 kB for stack */
> stack_top = .;
> }
>
> *//
> ======================================================================================
> *
> *
> *
> Files are compiled and linked with the following:
>
> $* arm-none-eabi-gcc -c -mcpu=cortex-a9 -g test.c -o test.o*
> $* arm-none-eabi-as -mcpu=cortex-a9 -g startup.s -o startup.o*
> $* arm-none-eabi-ld -T test.ld test.o startup.o -o test*
>
> And I run Qemu with:
>
> $ *qemu-system-arm -M vexpress-a9 -m 1024 -kernel test -serial stdio -s -S
> *
> *
> *
> In another terminal I attach GDB with:
>
> $ *arm-none-eabi-gdb test*
> (gdb) *target remote : 1234*
> *
> *
> From GDB I can see that all the time CPU is in SVC mode (default after
> reset) and in CSPR register I flag is 0 (interrupt enabled).
>

CSPR register I flag is not 0. Before interrupt is generated *CPSIE
i*should be added.

Cheers,
Mirela


> By reading *Set Pending Register* at the end of the main function I can
> see that interrupt is pending, but it not caused jump.
> Vector table is placed at the address 0x0, but even if that is not correct
> I expected a jump.
> Please, can anyone take a look what am I missing in the configuration of
> the GIC?
> Or is problem somewhere else?
>
> Thanks,
> Mirela
>
> *
> *
>

[Attachment #3 (text/html)]

<br><div class="gmail_quote">2012/4/12 Mirela Simonović <span dir="ltr">&lt;<a \
href="mailto:mirelasimonovic@gmail.com">mirelasimonovic@gmail.com</a>&gt;</span><br><blockquote \
class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc \
solid;padding-left:1ex"> Hi,<div><br></div><div>I&#39;m having troubles with \
triggering a software interrupt on Versatile Express board (Cortex-A9).</div><div>I \
managed to set an interrupt pending, but jump to Vector Table does not execute.</div> \
<div> Here is simple program that I&#39;m running:</div><div><br></div><div><i>// \
======================================================================================</i></div><div><i>// \
File: test.c</i></div><div><i>// \
======================================================================================</i></div>


<div><i><br></i></div><div><div style="font-style:italic"><i><div \
style="display:inline!important">#define HAL_READ_UINT32(register, value)  <span \
style="white-space:pre-wrap">	</span>(( value ) = *((volatile unsigned int *)( \
register )))</div>

</i></div><div style="font-style:italic">#define HAL_WRITE_UINT32(register, \
value)<span style="white-space:pre-wrap">	</span>(*((volatile unsigned int *)( \
register )) = ( value ))</div><div style="font-style:italic"> <br></div><div \
style="font-style:italic">#define PERIPHBASE<span \
style="white-space:pre-wrap">	</span>0x1e000000<span \
style="white-space:pre-wrap">				</span></div><div style="font-style:italic"> #define \
CPUBASE<span style="white-space:pre-wrap">		</span>( PERIPHBASE + 0x100 )<span \
style="white-space:pre-wrap">		</span>// CPU Interface Base Address</div><div \
style="font-style:italic"> #define DISTBASE    <span \
style="white-space:pre-wrap">		</span>( PERIPHBASE + 0x1000 )            // \
Distributor Base Address</div><div style="font-style:italic"><br></div><div \
style="font-style:italic">#define ICCICR        0x00         <span \
style="white-space:pre-wrap">	</span>// CPU Interface Control Register (RW)</div>

<div style="font-style:italic">#define ICCPMR     0x04         <span \
style="white-space:pre-wrap">		</span>//<i><div style="display:inline!important"><i>  \
CPU Interface</i></div></i><i><div style="display:inline!important">  Priority Mask \
Register (RW)</div></i></div><div style="font-style:italic"><i><div \
style="display:inline!important">#define ICDDCR    0x000<span \
style="white-space:pre-wrap">		</span>// Distributor Control Register (RW)</div>

</i></div><div style="font-style:italic">#define ICDISER   0x100<span \
style="white-space:pre-wrap">		</span>//  <i><div \
style="display:inline!important"><i>Distributor  </i></div></i><i><div \
style="display:inline!important">

Interrupt Set Enable Registers (RW)  </div></i></div><div \
style="font-style:italic">#define ICDISPR   0x200<span \
style="white-space:pre-wrap">		</span>//  <i><div \
style="display:inline!important"><i>Distributor  </i></div> </i><i><div \
style="display:inline!important">Set Pending Register (RW)</div></i></div><div \
style="font-style:italic">#define ICDIPR<span style="white-space:pre-wrap">	</span>   \
0x400<span style="white-space:pre-wrap">		</span>//  <i><div \
style="display:inline!important">

<i>Distributor  </i></div></i><i><div style="display:inline!important">Interrupt \
Priority Register (RW)</div></i></div><div style="font-style:italic">#define ICDSGIR  \
0xF00<span style="white-space:pre-wrap">		</span>//  <i><div \
style="display:inline!important">

<i>Distributor  </i></div></i><i><div style="display:inline!important">Software \
Generated Interrupt Register (WO)</div></i></div><div \
style="font-style:italic"><br></div><div style="font-style:italic">int main \
()</div><div style="font-style:italic">

{<span style="white-space:pre-wrap">	</span></div><div \
style="font-style:italic"><span style="white-space:pre-wrap">	</span>unsigned int \
tmp;</div><div style="font-style:italic"><br></div> <div \
style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( CPUBASE   \
+ ICCICR, 0 );              </b><span \
style="font-weight:bold;white-space:pre-wrap">		</span>// Disable CPU Interface (it \
is already disabled, but nevermind)</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( DISTBASE + \
ICDDCR, 0 ); </b><span style="font-weight:bold;white-space:pre-wrap">			</span>// \
Disable Distributor (it is already disabled, but nevermind)</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( DISTBASE + \
ICDISER, 0x0000ffff );</b><span \
style="font-weight:bold;white-space:pre-wrap">		</span>// Set enable (enable all \
SGIs)  </div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( CPUBASE   \
+ ICCPMR, 0xff );</b><span style="font-weight:bold;white-space:pre-wrap">			</span>// \
All interrupts whose priority is &gt; 0xff are unmasked</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( DISTBASE + \
ICDIPR, 0 );</b><span style="font-weight:bold;white-space:pre-wrap">				</span>// Set \
the highest priority</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( DISTBASE + \
ICDDCR, 1 );</b><span style="font-weight:bold;white-space:pre-wrap">	</span> <span \
style="font-weight:bold;white-space:pre-wrap">		</span>// Enable Distributor</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( CPUBASE   \
+ ICCICR, 1 ); </b><span style="font-weight:bold;white-space:pre-wrap">			</span>// \
Enable CPU Interface</div>

<div style="font-style:italic"><br></div><div style="font-style:italic"><span \
style="white-space:pre-wrap">	</span>HAL_READ_UINT32 ( DISTBASE + ICDISPR, tmp);<span \
style="white-space:pre-wrap">			</span>// Is the interrupt pending? =&gt; No, \
it&#39;s not</div>

<div style="font-style:italic"><span \
style="font-weight:bold;white-space:pre-wrap">	</span><b>HAL_WRITE_UINT32( DISTBASE + \
ICDSGIR, 0x02000000); </b><span style="white-space:pre-wrap">	</span>// Generate \
software interrupt ID=0 to CPU0 (to this, running CPU)</div>

<div style="font-style:italic"><span \
style="white-space:pre-wrap">	</span>HAL_READ_UINT32 ( DISTBASE + ICDISPR, tmp);<span \
style="white-space:pre-wrap">			</span>// Is the interrupt pending? =&gt; Yes, it \
is</div> <div style="font-style:italic"><br></div><div \
style="font-style:italic"><span style="white-space:pre-wrap">	</span>return \
0;</div><div style="font-style:italic">}</div><div style="font-style:italic"><br> \
</div><div style="font-style:italic"><div style="font-style:normal"><i>// \
======================================================================================</i></div><div \
style="font-style:normal"><i>// File: startup.s</i></div>

<div style="font-style:normal"><i>// \
======================================================================================</i></div></div><div \
style="font-style:normal"><i><br></i></div><div><div style="font-style:italic">

.section INTERRUPT_VECTOR, &quot;x&quot;</div><div style="font-style:italic">.global \
_Reset</div><div style="font-style:italic">_Reset:</div><div \
style="font-style:italic">   B Reset_Handler /* Reset */</div><div \
style="font-style:italic">

   B . /* Undefined */</div><div style="font-style:italic">   B . /* SWI */</div><div \
style="font-style:italic">   B . /* Prefetch Abort */</div><div \
style="font-style:italic">   B . /* Data Abort */</div><div \
style="font-style:italic">

   B . /* reserved */</div><div style="font-style:italic">   B . /* IRQ */</div><div \
style="font-style:italic">   B . /* FIQ */</div><div \
style="font-style:italic"><br></div><div \
style="font-style:italic">Reset_Handler:</div>

<div style="font-style:italic">   LDR sp, =stack_top</div><div \
style="font-style:italic">   BL main</div><div style="font-style:italic">   B \
.</div><div style="font-style:normal"><br></div><div style="font-style:normal"><i>// \
======================================================================================</i></div>


<div style="font-style:normal"><i>// File: test.ld</i></div><div \
style="font-style:normal"><i>// \
======================================================================================</i><br>
 </div><div style="font-style:italic"><div>ENTRY(_Reset)</div><div>SECTIONS</div><div>{</div><div><span \
style="white-space:pre-wrap">	</span>. = 0x0;<span \
style="white-space:pre-wrap">	</span></div> <div><span \
style="white-space:pre-wrap">	</span>.text <span \
style="white-space:pre-wrap">		</span>:<span style="white-space:pre-wrap">	</span>{ \
startup.o(INTERRUPT_VECTOR)</div> <div><span \
style="white-space:pre-wrap">					</span>   *(.text) <span \
style="white-space:pre-wrap">					</span>}</div><div><span \
style="white-space:pre-wrap">	</span>.data<span \
style="white-space:pre-wrap">		</span>:<span style="white-space:pre-wrap">	</span>{ \
*(.data) <span style="white-space:pre-wrap">						</span>}</div>

<div><span style="white-space:pre-wrap">	</span>.bss<span \
style="white-space:pre-wrap">		</span>: <span style="white-space:pre-wrap">	</span>{ \
*(.bss) <span style="white-space:pre-wrap">						</span>}</div> <div><span \
style="white-space:pre-wrap">	</span>. = . + 0x10000; <span \
style="white-space:pre-wrap">									</span>/* 4 kB for stack */</div><div><span \
style="white-space:pre-wrap">	</span>stack_top = .;<span \
style="white-space:pre-wrap">										</span></div>

<div>}</div></div><div style="font-style:italic"><br></div><div \
style="font-style:italic"><i>// \
======================================================================================</i></div><div \
style="font-style:italic">

<i><br></i></div><div>Files are compiled and linked with the \
following:</div></div></div><div><br></div><div>$<i> arm-none-eabi-gcc -c \
-mcpu=cortex-a9 -g test.c -o test.o</i></div><div><div>$<i>  arm-none-eabi-as \
-mcpu=cortex-a9 -g startup.s -o startup.o</i></div>

<div>$<i>  arm-none-eabi-ld -T test.ld test.o startup.o -o \
test</i></div></div><div><br></div><div>And I run Qemu \
with:</div><div><br></div><div>$ <i>qemu-system-arm -M vexpress-a9 -m 1024 -kernel \
test -serial stdio -s -S</i></div>

<div><i><br></i></div><div>In another terminal I attach GDB \
with:</div><div><br></div><div>$ <i>arm-none-eabi-gdb test</i></div><div>(gdb) \
<i>target remote : 1234</i></div><div><i><br></i></div><div>From GDB I can see that \
all the time CPU is in SVC mode (default after reset) and in CSPR register I flag is \
0 (interrupt enabled).</div> </blockquote><div><br></div><div>CSPR register I flag is \
not 0. Before interrupt is generated <i>CPSIE i</i> should be \
added.</div><div><br></div><div>Cheers,</div><div>Mirela</div><div>  \
</div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc \
solid;padding-left:1ex">

<div>By reading  <i>Set Pending Register</i>  at the end of the main function  I can \
see that interrupt is pending, but it not caused jump.</div><div>Vector table is \
placed at the address 0x0, but even if that is not correct I expected a jump.</div>

<div>Please, can anyone take a look what am I missing in the configuration of the \
GIC?</div><div>Or is problem somewhere \
else?</div><div><br></div><div>Thanks,</div><div>Mirela</div><div><br></div><div><i><br></i></div>
 </blockquote></div><br>



[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic