]> git.kernelconcepts.de Git - karo-tx-redboot.git/blob - packages/hal/coldfire/mcf5272/v2_0/src/var_misc.c
Initial revision
[karo-tx-redboot.git] / packages / hal / coldfire / mcf5272 / v2_0 / src / var_misc.c
1 //==========================================================================
2 //
3 //      var_misc.c
4 //
5 //      Miscellaneous functions specific to the processor variant
6 //
7 //==========================================================================
8 //####ECOSGPLCOPYRIGHTBEGIN####
9 // -------------------------------------------
10 // This file is part of eCos, the Embedded Configurable Operating System.
11 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
12 // Copyright (C) 2006 eCosCentric Ltd.
13 //
14 // eCos is free software; you can redistribute it and/or modify it under
15 // the terms of the GNU General Public License as published by the Free
16 // Software Foundation; either version 2 or (at your option) any later version.
17 //
18 // eCos is distributed in the hope that it will be useful, but WITHOUT ANY
19 // WARRANTY; without even the implied warranty of MERCHANTABILITY or
20 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
21 // for more details.
22 //
23 // You should have received a copy of the GNU General Public License along
24 // with eCos; if not, write to the Free Software Foundation, Inc.,
25 // 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
26 //
27 // As a special exception, if other files instantiate templates or use macros
28 // or inline functions from this file, or you compile this file and link it
29 // with other works to produce a work based on this file, this file does not
30 // by itself cause the resulting work to be covered by the GNU General Public
31 // License. However the source code for this file must still be made available
32 // in accordance with section (3) of the GNU General Public License.
33 //
34 // This exception does not invalidate any other reasons why a work based on
35 // this file might be covered by the GNU General Public License.
36 // -------------------------------------------
37 //####ECOSGPLCOPYRIGHTEND####
38 //==========================================================================
39 //#####DESCRIPTIONBEGIN####
40 //
41 // Author(s):     Enrico Piria
42 // Contributors:
43 // Date:          2005-25-06
44 // Purpose:       Miscellaneous functions specific to the MCF5272 processor.
45 //
46 //####DESCRIPTIONEND####
47 //========================================================================
48
49 #include <pkgconf/hal.h>
50
51 #include <cyg/infra/cyg_type.h>
52
53 #include <cyg/hal/hal_intr.h>
54 #include <cyg/hal/hal_arch.h>
55 #include <cyg/hal/hal_io.h>
56
57 #include CYGHWR_MEMORY_LAYOUT_H
58
59 // -------------------------------------------------------------------------
60 // VSR table
61
62 // For the MCF5272, we can point the VBR directly to the VSR table.
63 // However, the table must be on a 1 MB boundary. Locate the VSR table where
64 // the linker tells us to.
65
66 volatile CYG_ADDRESS cyg_hal_vsr_table[CYGNUM_HAL_VSR_COUNT]
67                     __attribute__ ((section (".ramvec")));
68
69 // -------------------------------------------------------------------------
70 // Function prototypes
71
72 static void hal_update_interrupt_controller(int vector);
73
74 // -------------------------------------------------------------------------
75 // Interrupt controller management
76 //
77 // With the MCF5272 interrupt controller, it is not possible to mask an
78 // interrupt while retaining its associated priority. Moreover, if we enabled
79 // the use of interrupts with different priorities, we don't have a means to
80 // retrieve the priority of the current interrupt, after having raised the
81 // IPL to the maximum, in the first instruction of the HAL ISR handler.
82 // So, we use an auxiliary table (cyg_hal_ILVL_table) that records all the
83 // priorities set for the various interrupts.
84 // The purpose of the cyg_hal_IMASK_table table is to record wether an
85 // interrupt is currently masked (0) or not (1).
86
87 volatile cyg_uint8 cyg_hal_ILVL_table[CYGNUM_HAL_ISR_COUNT];
88 volatile cyg_uint8 cyg_hal_IMASK_table[CYGNUM_HAL_ISR_COUNT];
89
90
91 // Update priority table and interrupt controller
92 void hal_interrupt_set_level(int vector, int level)
93 {
94     cyg_uint32 index;
95     
96     CYG_ASSERT((0 <= (level) && 7 >= (level)), "Illegal level");
97     CYG_ASSERT((CYGNUM_HAL_ISR_MIN <= (vector)
98                 && CYGNUM_HAL_ISR_MAX >= (vector)), "Illegal vector");
99
100     HAL_TRANSLATE_VECTOR(vector, index);
101     cyg_hal_ILVL_table[index] = (cyg_uint8) level;
102
103     hal_update_interrupt_controller(vector);
104 }
105
106 // Update mask table and interrupt controller
107 void hal_interrupt_mask(int vector)
108 {
109     cyg_uint32 index;
110     
111     CYG_ASSERT((CYGNUM_HAL_ISR_MIN <= (vector)
112         && CYGNUM_HAL_ISR_MAX >= (vector)), "Illegal vector");
113     
114     HAL_TRANSLATE_VECTOR(vector, index);
115     cyg_hal_IMASK_table[index] = 0;
116     
117     hal_update_interrupt_controller(vector);
118 }
119
120 // Update mask table and interrupt controller
121 void hal_interrupt_unmask(int vector)
122 {
123     cyg_uint32 index;
124
125     CYG_ASSERT((CYGNUM_HAL_ISR_MIN <= (vector)
126     && CYGNUM_HAL_ISR_MAX >= (vector)), "Illegal vector");
127     
128     HAL_TRANSLATE_VECTOR(vector, index);
129     cyg_hal_IMASK_table[index] = 1;
130          
131     hal_update_interrupt_controller(vector);
132 }
133
134
135 // Set the priority in the interrupt control register.
136 // Disable all interrupts while we access the hardware registers.
137 static void hal_update_interrupt_controller(int vector)
138 {
139     cyg_uint32 index;
140     cyg_uint8 level;
141     cyg_uint32 vec_offset;
142     cyg_uint32 icr, icr_msk_offset, icr_msk, icr_val, icr_oldval;
143     CYG_INTERRUPT_STATE intr_state;
144     
145     HAL_TRANSLATE_VECTOR(vector, index); 
146     level = cyg_hal_IMASK_table[index] ? cyg_hal_ILVL_table[index] : 0;
147
148     vec_offset = (vector) - HAL_PROG_INT_VEC_BASE - 1;
149     icr = vec_offset / 8;
150     icr_msk_offset = ((8-1)*4) - (vec_offset % 8) * 4;
151     icr_msk = 0x0F << (icr_msk_offset);
152     icr_val = (0x08 | (level & 0x07)) << icr_msk_offset;
153     
154     HAL_DISABLE_INTERRUPTS(intr_state);
155     HAL_READ_UINT32(&MCF5272_DEVS->intc.icr[icr], icr_oldval);
156     icr_val |= icr_oldval & 0x77777777 & ~icr_msk;
157     HAL_WRITE_UINT32(&MCF5272_DEVS->intc.icr[icr], icr_val);
158     HAL_RESTORE_INTERRUPTS(intr_state);
159 }
160 // -------------------------------------------------------------------------
161 // End of var_misc.c