source: rtems/c/src/lib/libcpu/sh/sh7045/score/cpu_asm.c @ a5fb3d1b

4.104.115
Last change on this file since a5fb3d1b was be7ca34, checked in by Joel Sherrill <joel.sherrill@…>, on 09/25/08 at 19:32:15

2008-09-25 Joel Sherrill <joel.sherrill@…>

  • Makefile.am, configure.ac, sh7032/score/cpu_asm.c, sh7045/score/cpu_asm.c, sh7750/score/cpu_asm.c: Move duplicated context switch code to score/cpu and provide an interrupt handling stub for the GDB SuperH simulator since it does not support interrupts or devices. This has been used to run tests on the simulator BSP as SH1, SH2, and SH4.
  • shgdb/score/cpu_asm.c, shgdb/score/ispshgdb.c: New files.
  • Property mode set to 100644
File size: 4.0 KB
Line 
1/*
2 *  This file contains the basic algorithms for all assembly code used
3 *  in an specific CPU port of RTEMS.  These algorithms must be implemented
4 *  in assembly language
5 *
6 *  NOTE:  This port uses a C file with inline assembler instructions
7 *
8 *  Authors: Ralf Corsepius (corsepiu@faw.uni-ulm.de) and
9 *           Bernd Becker (becker@faw.uni-ulm.de)
10 *
11 *  COPYRIGHT (c) 1997-1998, FAW Ulm, Germany
12 *
13 *  This program is distributed in the hope that it will be useful,
14 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
16 *
17 *
18 *  COPYRIGHT (c) 1998.
19 *  On-Line Applications Research Corporation (OAR).
20 *
21 *  The license and distribution terms for this file may be
22 *  found in the file LICENSE in this distribution or at
23 *  http://www.rtems.com/license/LICENSE.
24 *
25 *  $Id$
26 */
27
28/*
29 *  This is supposed to be an assembly file.  This means that system.h
30 *  and cpu.h should not be included in a "real" cpu_asm file.  An
31 *  implementation in assembly should include "cpu_asm.h"
32 */
33
34#include <rtems/system.h>
35#include <rtems/score/cpu.h>
36#include <rtems/score/isr.h>
37#include <rtems/score/thread.h>
38#include <rtems/score/sh.h>
39
40#include <rtems/score/ispsh7045.h>
41#include <rtems/score/iosh7045.h>
42#include <rtems/score/sh_io.h>
43
44/* from cpu_isps.c */
45extern proc_ptr         _Hardware_isr_Table[];
46
47#if( CPU_HAS_SOFTWARE_INTERRUPT_STACK == TRUE)
48  unsigned long    *_old_stack_ptr;
49#endif
50
51register unsigned long  *stack_ptr asm("r15");
52
53/*
54 * sh_set_irq_priority
55 *
56 * this function sets the interrupt level of the specified interrupt
57 *
58 * parameters:
59 *             - irq : interrupt number
60 *             - prio: priority to set for this interrupt number
61 *
62 * returns:    0 if ok
63 *             -1 on error
64 */
65
66unsigned int sh_set_irq_priority(
67  unsigned int irq,
68  unsigned int prio )
69{
70  uint32_t   shiftcount;
71  uint32_t   prioreg;
72  uint16_t   temp16;
73  ISR_Level  level;
74
75  /*
76   * first check for valid interrupt
77   */
78  if(( irq > 156) || (irq < 64) || (_Hardware_isr_Table[irq] == _dummy_isp))
79    return -1;
80  /*
81   * check for valid irq priority
82   */
83  if( prio > 15 )
84    return -1;
85
86  /*
87   * look up appropriate interrupt priority register
88   */
89  if( irq > 71)
90    {
91      irq = irq - 72;
92      shiftcount = 12 - ((irq & ~0x03) % 16);
93
94      switch( irq / 16)
95        {
96        case 0: { prioreg = INTC_IPRC; break;}
97        case 1: { prioreg = INTC_IPRD; break;}
98        case 2: { prioreg = INTC_IPRE; break;}
99        case 3: { prioreg = INTC_IPRF; break;}
100        case 4: { prioreg = INTC_IPRG; break;}
101        case 5: { prioreg = INTC_IPRH; break;}
102        default: return -1;
103        }
104    }
105  else
106    {
107      shiftcount = 12 - 4 * ( irq % 4);
108      if( irq > 67)
109        prioreg = INTC_IPRB;
110      else
111        prioreg = INTC_IPRA;
112    }
113
114  /*
115   * Set the interrupt priority register
116   */
117  _ISR_Disable( level );
118
119    temp16 = read16( prioreg);
120    temp16 &= ~( 15 << shiftcount);
121    temp16 |= prio << shiftcount;
122    write16( temp16, prioreg);
123
124  _ISR_Enable( level );
125
126  return 0;
127}
128
129/*
130 *  This routine provides the RTEMS interrupt management.
131 */
132
133void __ISR_Handler( uint32_t   vector)
134{
135  ISR_Level level;
136
137  _ISR_Disable( level );
138
139  _Thread_Dispatch_disable_level++;
140
141#if( CPU_HAS_SOFTWARE_INTERRUPT_STACK == TRUE)
142  if( _ISR_Nest_level == 0 )
143    {
144      /* Install irq stack */
145      _old_stack_ptr = stack_ptr;
146      stack_ptr = _CPU_Interrupt_stack_high;
147    }
148
149#endif
150
151  _ISR_Nest_level++;
152
153  _ISR_Enable( level );
154
155  /* call isp */
156  if( _ISR_Vector_table[ vector])
157    (*_ISR_Vector_table[ vector ])( vector );
158
159  _ISR_Disable( level );
160
161  _Thread_Dispatch_disable_level--;
162
163  _ISR_Nest_level--;
164
165#if( CPU_HAS_SOFTWARE_INTERRUPT_STACK == TRUE)
166
167  if( _ISR_Nest_level == 0 )
168    /* restore old stack pointer */
169    stack_ptr = _old_stack_ptr;
170#endif
171
172  _ISR_Enable( level );
173
174  if ( _ISR_Nest_level )
175    return;
176
177  if ( _Thread_Dispatch_disable_level ) {
178    _ISR_Signals_to_thread_executing = FALSE;
179    return;
180  }
181
182  if ( _Context_Switch_necessary || _ISR_Signals_to_thread_executing ) {
183    _ISR_Signals_to_thread_executing = FALSE;
184    _Thread_Dispatch();
185  }
186}
Note: See TracBrowser for help on using the repository browser.