1 #ifndef CYGONCE_HAL_INTR_H
2 #define CYGONCE_HAL_INTR_H
4 //==========================================================================
8 // HAL Interrupt and clock support
10 //==========================================================================
11 //####ECOSGPLCOPYRIGHTBEGIN####
12 // -------------------------------------------
13 // This file is part of eCos, the Embedded Configurable Operating System.
14 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
16 // eCos is free software; you can redistribute it and/or modify it under
17 // the terms of the GNU General Public License as published by the Free
18 // Software Foundation; either version 2 or (at your option) any later version.
20 // eCos is distributed in the hope that it will be useful, but WITHOUT ANY
21 // WARRANTY; without even the implied warranty of MERCHANTABILITY or
22 // FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
25 // You should have received a copy of the GNU General Public License along
26 // with eCos; if not, write to the Free Software Foundation, Inc.,
27 // 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
29 // As a special exception, if other files instantiate templates or use macros
30 // or inline functions from this file, or you compile this file and link it
31 // with other works to produce a work based on this file, this file does not
32 // by itself cause the resulting work to be covered by the GNU General Public
33 // License. However the source code for this file must still be made available
34 // in accordance with section (3) of the GNU General Public License.
36 // This exception does not invalidate any other reasons why a work based on
37 // this file might be covered by the GNU General Public License.
39 // Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
40 // at http://sources.redhat.com/ecos/ecos-license/
41 // -------------------------------------------
42 //####ECOSGPLCOPYRIGHTEND####
43 //==========================================================================
44 //#####DESCRIPTIONBEGIN####
46 // Author(s): nickg, gthomas
47 // Contributors: nickg, gthomas,
50 // Purpose: Define Interrupt support
51 // Description: The macros defined here provide the HAL APIs for handling
52 // interrupts and the clock.
54 // Usage: #include <cyg/hal/hal_intr.h>
58 //####DESCRIPTIONEND####
60 //==========================================================================
62 #include <pkgconf/hal.h>
64 #include <cyg/infra/cyg_type.h>
66 // This is to allow a variant to decide that there is no platform-specific
67 // interrupts file; and that in turn can be overridden by a platform that
68 // refines the variant's ideas.
69 #ifdef CYGBLD_HAL_PLF_INTS_H
70 # include CYGBLD_HAL_PLF_INTS_H // should include variant data as required
72 # ifdef CYGBLD_HAL_VAR_INTS_H
73 # include CYGBLD_HAL_VAR_INTS_H
75 # include <cyg/hal/hal_platform_ints.h> // default less-complex platforms
79 // Spurious interrupt (no interrupt source could be found)
80 #define CYGNUM_HAL_INTERRUPT_NONE -1
82 //--------------------------------------------------------------------------
83 // ARM exception vectors.
85 // These vectors correspond to VSRs. These values are the ones to use for
88 #define CYGNUM_HAL_VECTOR_RESET 0
89 #define CYGNUM_HAL_VECTOR_UNDEF_INSTRUCTION 1
90 #define CYGNUM_HAL_VECTOR_SOFTWARE_INTERRUPT 2
91 #define CYGNUM_HAL_VECTOR_ABORT_PREFETCH 3
92 #define CYGNUM_HAL_VECTOR_ABORT_DATA 4
93 #define CYGNUM_HAL_VECTOR_reserved 5
94 #define CYGNUM_HAL_VECTOR_IRQ 6
95 #define CYGNUM_HAL_VECTOR_FIQ 7
97 #define CYGNUM_HAL_VSR_MIN 0
98 #define CYGNUM_HAL_VSR_MAX 7
99 #define CYGNUM_HAL_VSR_COUNT 8
101 // Exception vectors. These are the values used when passed out to an
102 // external exception handler using cyg_hal_deliver_exception()
104 #define CYGNUM_HAL_EXCEPTION_ILLEGAL_INSTRUCTION \
105 CYGNUM_HAL_VECTOR_UNDEF_INSTRUCTION
106 #define CYGNUM_HAL_EXCEPTION_INTERRUPT \
107 CYGNUM_HAL_VECTOR_SOFTWARE_INTERRUPT
108 #define CYGNUM_HAL_EXCEPTION_CODE_ACCESS CYGNUM_HAL_VECTOR_ABORT_PREFETCH
109 #define CYGNUM_HAL_EXCEPTION_DATA_ACCESS CYGNUM_HAL_VECTOR_ABORT_DATA
111 #define CYGNUM_HAL_EXCEPTION_MIN CYGNUM_HAL_EXCEPTION_ILLEGAL_INSTRUCTION
112 #define CYGNUM_HAL_EXCEPTION_MAX CYGNUM_HAL_EXCEPTION_DATA_ACCESS
113 #define CYGNUM_HAL_EXCEPTION_COUNT (CYGNUM_HAL_EXCEPTION_MAX - \
114 CYGNUM_HAL_EXCEPTION_MIN + 1)
116 //--------------------------------------------------------------------------
117 // Static data used by HAL
120 externC CYG_ADDRESS hal_interrupt_handlers[CYGNUM_HAL_ISR_COUNT];
121 externC CYG_ADDRWORD hal_interrupt_data[CYGNUM_HAL_ISR_COUNT];
122 externC CYG_ADDRESS hal_interrupt_objects[CYGNUM_HAL_ISR_COUNT];
125 externC CYG_ADDRESS hal_vsr_table[CYGNUM_HAL_VSR_COUNT];
127 // Platform setup memory size (0 if unknown by hardware)
128 externC CYG_ADDRWORD hal_dram_size;
129 // what, if anything, this means, is platform dependent:
130 externC CYG_ADDRWORD hal_dram_type;
132 #if CYGINT_HAL_ARM_MEM_REAL_REGION_TOP
134 externC cyg_uint8 *hal_arm_mem_real_region_top( cyg_uint8 *_regionend_ );
136 # define HAL_MEM_REAL_REGION_TOP( _regionend_ ) \
137 hal_arm_mem_real_region_top( _regionend_ )
140 //--------------------------------------------------------------------------
142 // The #define is used to test whether this routine exists, and to allow
143 // code outside the HAL to call it.
145 externC cyg_uint32 hal_default_isr(CYG_ADDRWORD vector, CYG_ADDRWORD data);
147 #define HAL_DEFAULT_ISR hal_default_isr
149 //--------------------------------------------------------------------------
150 // Interrupt state storage
152 typedef cyg_uint32 CYG_INTERRUPT_STATE;
154 //--------------------------------------------------------------------------
155 // Interrupt control macros
158 // Note: This disables both FIQ and IRQ interrupts!
159 #define HAL_DISABLE_INTERRUPTS(_old_) \
170 #define HAL_ENABLE_INTERRUPTS() \
180 #define HAL_RESTORE_INTERRUPTS(_old_) \
192 #define HAL_QUERY_INTERRUPTS(_old_) \
203 // Thumb mode does not have access to the PSR registers;
205 #if 0 // These don't seem to always work
206 #define HAL_DISABLE_INTERRUPTS(_old_) \
225 #define HAL_ENABLE_INTERRUPTS() \
243 #define HAL_RESTORE_INTERRUPTS(_old_) \
263 #define HAL_QUERY_INTERRUPTS(_old_) \
282 externC cyg_uint32 hal_disable_interrupts(void);
283 externC void hal_enable_interrupts(void);
284 externC void hal_restore_interrupts(cyg_uint32);
285 externC cyg_uint32 hal_query_interrupts(void);
287 #define HAL_DISABLE_INTERRUPTS(_old_) \
288 _old_ = hal_disable_interrupts();
290 #define HAL_ENABLE_INTERRUPTS() \
291 hal_enable_interrupts();
293 #define HAL_RESTORE_INTERRUPTS(_old_) \
294 hal_restore_interrupts(_old_);
296 #define HAL_QUERY_INTERRUPTS(_old_) \
297 _old_ = hal_query_interrupts();
302 //--------------------------------------------------------------------------
303 // Routine to execute DSRs using separate interrupt stack
305 #ifdef CYGIMP_HAL_COMMON_INTERRUPTS_USE_INTERRUPT_STACK
306 externC void hal_interrupt_stack_call_pending_DSRs(void);
307 #define HAL_INTERRUPT_STACK_CALL_PENDING_DSRS() \
308 hal_interrupt_stack_call_pending_DSRs()
310 // these are offered solely for stack usage testing
311 // if they are not defined, then there is no interrupt stack.
312 #define HAL_INTERRUPT_STACK_BASE cyg_interrupt_stack_base
313 #define HAL_INTERRUPT_STACK_TOP cyg_interrupt_stack
314 // use them to declare these extern however you want:
315 // extern char HAL_INTERRUPT_STACK_BASE[];
316 // extern char HAL_INTERRUPT_STACK_TOP[];
320 //--------------------------------------------------------------------------
321 // Vector translation.
323 #ifndef HAL_TRANSLATE_VECTOR
324 #define HAL_TRANSLATE_VECTOR(_vector_,_index_) \
325 (_index_) = (_vector_)
328 //--------------------------------------------------------------------------
329 // Interrupt and VSR attachment macros
331 #define HAL_INTERRUPT_IN_USE( _vector_, _state_) \
333 cyg_uint32 _index_; \
334 HAL_TRANSLATE_VECTOR ((_vector_), _index_); \
336 if( hal_interrupt_handlers[_index_] == (CYG_ADDRESS)hal_default_isr ) \
342 #define HAL_INTERRUPT_ATTACH( _vector_, _isr_, _data_, _object_ ) \
344 if( hal_interrupt_handlers[_vector_] == (CYG_ADDRESS)hal_default_isr ) \
346 hal_interrupt_handlers[_vector_] = (CYG_ADDRESS)_isr_; \
347 hal_interrupt_data[_vector_] = (CYG_ADDRWORD) _data_; \
348 hal_interrupt_objects[_vector_] = (CYG_ADDRESS)_object_; \
352 #define HAL_INTERRUPT_DETACH( _vector_, _isr_ ) \
354 if( hal_interrupt_handlers[_vector_] == (CYG_ADDRESS)_isr_ ) \
356 hal_interrupt_handlers[_vector_] = (CYG_ADDRESS)hal_default_isr; \
357 hal_interrupt_data[_vector_] = 0; \
358 hal_interrupt_objects[_vector_] = 0; \
362 #define HAL_VSR_GET( _vector_, _pvsr_ ) \
363 *(CYG_ADDRESS *)(_pvsr_) = hal_vsr_table[_vector_];
366 #define HAL_VSR_SET( _vector_, _vsr_, _poldvsr_ ) \
368 if( _poldvsr_ != NULL ) \
369 *(CYG_ADDRESS *)_poldvsr_ = hal_vsr_table[_vector_]; \
370 hal_vsr_table[_vector_] = (CYG_ADDRESS)_vsr_; \
373 //--------------------------------------------------------------------------
374 // Interrupt controller access
376 externC void hal_interrupt_mask(int);
377 externC void hal_interrupt_unmask(int);
378 externC void hal_interrupt_acknowledge(int);
379 externC void hal_interrupt_configure(int, int, int);
380 externC void hal_interrupt_set_level(int, int);
382 #define HAL_INTERRUPT_MASK( _vector_ ) \
383 hal_interrupt_mask( _vector_ )
384 #define HAL_INTERRUPT_UNMASK( _vector_ ) \
385 hal_interrupt_unmask( _vector_ )
386 #define HAL_INTERRUPT_ACKNOWLEDGE( _vector_ ) \
387 hal_interrupt_acknowledge( _vector_ )
388 #define HAL_INTERRUPT_CONFIGURE( _vector_, _level_, _up_ ) \
389 hal_interrupt_configure( _vector_, _level_, _up_ )
390 #define HAL_INTERRUPT_SET_LEVEL( _vector_, _level_ ) \
391 hal_interrupt_set_level( _vector_, _level_ )
393 //--------------------------------------------------------------------------
396 externC void hal_clock_initialize(cyg_uint32);
397 externC void hal_clock_read(cyg_uint32 *);
398 externC void hal_clock_reset(cyg_uint32, cyg_uint32);
400 #define HAL_CLOCK_INITIALIZE( _period_ ) hal_clock_initialize( _period_ )
401 #define HAL_CLOCK_RESET( _vec_, _period_ ) hal_clock_reset( _vec_, _period_ )
402 #define HAL_CLOCK_READ( _pvalue_ ) hal_clock_read( _pvalue_ )
403 #ifdef CYGVAR_KERNEL_COUNTERS_CLOCK_LATENCY
404 # ifndef HAL_CLOCK_LATENCY
405 # define HAL_CLOCK_LATENCY( _pvalue_ ) HAL_CLOCK_READ( (cyg_uint32 *)_pvalue_ )
409 //--------------------------------------------------------------------------
410 #endif // ifndef CYGONCE_HAL_INTR_H