OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [ecos-3.0/] [packages/] [hal/] [i386/] [arch/] [current/] [include/] [hal_arch.h] - Blame information for rev 838

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 786 skrzyp
#ifndef CYGONCE_HAL_HAL_ARCH_H
2
#define CYGONCE_HAL_HAL_ARCH_H
3
 
4
//=============================================================================
5
//
6
//      hal_arch.h
7
//
8
//      Architecture specific abstractions
9
//
10
//=============================================================================
11
// ####ECOSGPLCOPYRIGHTBEGIN####                                            
12
// -------------------------------------------                              
13
// This file is part of eCos, the Embedded Configurable Operating System.   
14
// Copyright (C) 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
15
//
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      
19
// version.                                                                 
20
//
21
// eCos is distributed in the hope that it will be useful, but WITHOUT      
22
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or    
23
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License    
24
// for more details.                                                        
25
//
26
// You should have received a copy of the GNU General Public License        
27
// along with eCos; if not, write to the Free Software Foundation, Inc.,    
28
// 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.            
29
//
30
// As a special exception, if other files instantiate templates or use      
31
// macros or inline functions from this file, or you compile this file      
32
// and link it with other works to produce a work based on this file,       
33
// this file does not by itself cause the resulting work to be covered by   
34
// the GNU General Public License. However the source code for this file    
35
// must still be made available in accordance with section (3) of the GNU   
36
// General Public License v2.                                               
37
//
38
// This exception does not invalidate any other reasons why a work based    
39
// on this file might be covered by the GNU General Public License.         
40
// -------------------------------------------                              
41
// ####ECOSGPLCOPYRIGHTEND####                                              
42
//=============================================================================
43
//#####DESCRIPTIONBEGIN####
44
//
45
// Author(s):   proven
46
// Contributors:proven, pjo, nickg
47
// Date:        1998-10-05
48
// Purpose:     Define architecture abstractions
49
// Usage:       #include <cyg/hal/hal_arch.h>
50
//
51
//####DESCRIPTIONEND####
52
//
53
//=============================================================================
54
 
55
#include <pkgconf/hal.h>
56
#include <cyg/infra/cyg_type.h>
57
 
58
#include <cyg/hal/var_arch.h>
59
 
60
//-----------------------------------------------------------------------------
61
// Processor saved states. This structure is also defined in i386.inc for
62
// assembly code. Do not change this without changing that (or vice versa).
63
 
64
#ifdef CYGHWR_HAL_I386_FPU
65
 
66
typedef struct
67
{
68
    cyg_uint32  fpstate_valid;
69
    cyg_uint32  fpstate[108/sizeof(cyg_uint32)];
70
#ifdef CYGHWR_HAL_I386_PENTIUM_SSE
71
    cyg_uint32  xmm0[4];
72
    cyg_uint32  xmm1[4];
73
    cyg_uint32  xmm2[4];
74
    cyg_uint32  xmm3[4];
75
    cyg_uint32  xmm4[4];
76
    cyg_uint32  xmm5[4];
77
    cyg_uint32  xmm6[4];
78
    cyg_uint32  xmm7[4];
79
    cyg_uint32  mxcsr;
80
#endif
81
} HAL_FPU_Context;
82
 
83
#endif
84
 
85
typedef struct
86
{
87
#ifdef CYGHWR_HAL_I386_FPU
88
#ifdef CYGHWR_HAL_I386_FPU_SWITCH_LAZY
89
    HAL_FPU_Context     *fpucontext;
90
#else
91
    HAL_FPU_Context     fpucontext;
92
#endif    
93
#endif    
94
    cyg_uint32  edi;
95
    cyg_uint32  esi;
96
    cyg_uint32  ebp;
97
    cyg_uint32  esp;
98
    cyg_uint32  ebx;
99
    cyg_uint32  edx;
100
    cyg_uint32  ecx;
101
    cyg_uint32  eax;
102
    cyg_uint32  vector; // if saved on interrupt contains intr vector
103
    cyg_uint32  pc;
104
    cyg_uint32  cs;
105
    cyg_uint32  eflags;
106
} HAL_SavedRegisters;
107
 
108
 
109
//-----------------------------------------------------------------------------
110
// Exception handling function.
111
// This function is defined by the kernel according to this prototype. It is
112
// invoked from the HAL to deal with any CPU exceptions that the HAL does
113
// not want to deal with itself. It usually invokes the kernel's exception
114
// delivery mechanism.
115
externC void cyg_hal_deliver_exception( CYG_WORD code, CYG_ADDRWORD data );
116
 
117
//-----------------------------------------------------------------------------
118
// Bit manipulation routines
119
 
120
#define HAL_LSBIT_INDEX(index, mask)            \
121
CYG_MACRO_START                                 \
122
    asm volatile( "bsfl %1,%0\n"                \
123
                  : "=r" (index)                \
124
                  : "r" (mask)                  \
125
                );                              \
126
CYG_MACRO_END
127
 
128
#define HAL_MSBIT_INDEX(index, mask)            \
129
CYG_MACRO_START                                 \
130
    asm volatile( "bsrl %1,%0\n"                \
131
                  : "=r" (index)                \
132
                  : "r" (mask)                  \
133
                );                              \
134
CYG_MACRO_END
135
 
136
//-----------------------------------------------------------------------------
137
// Context Initialization
138
// Initialize the context of a thread.
139
// Arguments:
140
// _sp_ name of variable containing current sp, will be written with new sp
141
// _thread_ thread object address, passed as argument to entry point
142
// _entry_ entry point address.
143
// _id_ bit pattern used in initializing registers, for debugging.
144
 
145
#ifndef CYG_HAL_DEFAULT_CS
146
#define CYG_HAL_DEFAULT_CS 0x0008
147
#endif
148
 
149
#ifdef CYGHWR_HAL_I386_FPU
150
# ifdef CYGHWR_HAL_I386_FPU_SWITCH_LAZY
151
# define HAL_THREAD_INIT_FPU_CONTEXT_SPACE( __sp, __fpspace )   \
152
         __sp -= sizeof(HAL_FPU_Context);                       \
153
         __fpspace = __sp;
154
# define HAL_THREAD_INIT_FPU_CONTEXT( __regs, __fpspace )                               \
155
CYG_MACRO_START                                                                         \
156
    cyg_ucount8 __i;                                                                    \
157
    HAL_FPU_Context *__fpspace_ = (HAL_FPU_Context *)(__fpspace);                       \
158
    (__regs)->fpucontext = __fpspace_;                                                  \
159
    __fpspace_->fpstate_valid = 0;                                                      \
160
    for( __i = 0; __i < (sizeof(__fpspace_->fpstate)/sizeof(cyg_uint32)); __i++ )       \
161
        __fpspace_->fpstate[__i] = 0;                                                   \
162
CYG_MACRO_END
163
# else
164
# define HAL_THREAD_INIT_FPU_CONTEXT_SPACE( __sp, __fpspace )                   \
165
         (__fpspace) = (__fpspace);
166
# define HAL_THREAD_INIT_FPU_CONTEXT( __regs, __fpspace )                               \
167
CYG_MACRO_START                                                                         \
168
    cyg_ucount8 __i;                                                                    \
169
    HAL_FPU_Context *__fpspace_ = &((__regs)->fpucontext);                              \
170
    __fpspace_->fpstate_valid = 0;                                                      \
171
    for( __i = 0; __i < (sizeof(__fpspace_->fpstate)/sizeof(cyg_uint32)); __i++ )       \
172
        __fpspace_->fpstate[__i] = 0;                                                   \
173
CYG_MACRO_END
174
# endif
175
#else
176
# define HAL_THREAD_INIT_FPU_CONTEXT_SPACE( __sp, __fpspace )                   \
177
         (__fpspace) = (__fpspace);
178
# define HAL_THREAD_INIT_FPU_CONTEXT( __regs, __fpspace )
179
#endif
180
 
181
 
182
#define HAL_THREAD_INIT_CONTEXT( _sparg_, _thread_, _entry_, _id_ )     \
183
CYG_MACRO_START                                                         \
184
    register CYG_WORD* _sp_ = ((CYG_WORD*)((_sparg_) &~15));            \
185
    register CYG_WORD *_fpspace_ = NULL;                                \
186
    register HAL_SavedRegisters *_regs_;                                \
187
                                                                        \
188
    HAL_THREAD_INIT_FPU_CONTEXT_SPACE( _sp_, _fpspace_ );               \
189
    *(--_sp_) = (CYG_WORD)(0);                                          \
190
    *(--_sp_) = (CYG_WORD)(0);                                          \
191
    *(--_sp_) = (CYG_WORD)(_thread_);                                   \
192
    *(--_sp_) = (CYG_WORD)(0);                                          \
193
                                                                        \
194
    _regs_ = (HAL_SavedRegisters *)                                     \
195
               ((unsigned long)_sp_ - sizeof(HAL_SavedRegisters));      \
196
    HAL_THREAD_INIT_FPU_CONTEXT( _regs_, _fpspace_ );                   \
197
    _regs_->eflags = (CYG_WORD)(0x00000200);                            \
198
    _regs_->cs     = (CYG_WORD)(CYG_HAL_DEFAULT_CS);                    \
199
    _regs_->pc     = (CYG_WORD)(_entry_);                               \
200
    _regs_->vector = (CYG_WORD)(_id_);                                  \
201
    _regs_->esp    = (CYG_WORD) _sp_-4;                                 \
202
    _regs_->ebp    = (CYG_WORD)(_id_);                                  \
203
    _regs_->esi    = (CYG_WORD)(_id_);                                  \
204
    _regs_->edi    = (CYG_WORD)(_id_);                                  \
205
    _regs_->eax    = (CYG_WORD)(_id_);                                  \
206
    _regs_->ebx    = (CYG_WORD)(_id_);                                  \
207
    _regs_->ecx    = (CYG_WORD)(_id_);                                  \
208
    _regs_->edx    = (CYG_WORD)(_id_);                                  \
209
    (_sparg_)      = (CYG_ADDRESS) _regs_;                              \
210
CYG_MACRO_END
211
 
212
//-----------------------------------------------------------------------------
213
// Context switch macros.
214
// The arguments are pointers to locations where the stack pointer
215
// of the current thread is to be stored, and from where the sp of the
216
// next thread is to be fetched.
217
 
218
externC void hal_thread_switch_context( CYG_ADDRESS to, CYG_ADDRESS from );
219
externC void hal_thread_load_context( CYG_ADDRESS to )
220
    __attribute__ ((noreturn));
221
 
222
#define HAL_THREAD_SWITCH_CONTEXT(_fspptr_,_tspptr_)                    \
223
        hal_thread_switch_context((CYG_ADDRESS)_tspptr_,(CYG_ADDRESS)_fspptr_);
224
 
225
#define HAL_THREAD_LOAD_CONTEXT(_tspptr_)                               \
226
        hal_thread_load_context( (CYG_ADDRESS)_tspptr_ );
227
 
228
//-----------------------------------------------------------------------------
229
// Execution reorder barrier.
230
// When optimizing the compiler can reorder code. In multithreaded systems
231
// where the order of actions is vital, this can sometimes cause problems.
232
// This macro may be inserted into places where reordering should not happen.
233
 
234
#define HAL_REORDER_BARRIER() asm volatile ( "" : : : "memory" )
235
 
236
//-----------------------------------------------------------------------------
237
// Breakpoint support
238
// HAL_BREAKPOINT() is a code sequence that will cause a breakpoint to happen 
239
// if executed.
240
// HAL_BREAKINST is the value of the breakpoint instruction and 
241
// HAL_BREAKINST_SIZE is its size in bytes.
242
 
243
#define HAL_BREAKPOINT(_label_)                 \
244
CYG_MACRO_START                                 \
245
    asm volatile (" .globl  " #_label_ ";"      \
246
                  #_label_":"                   \
247
                  "int $3"                      \
248
        );                                      \
249
CYG_MACRO_END
250
 
251
#define HAL_BREAKINST                    0xCC
252
#define HAL_BREAKINST_SIZE               1
253
 
254
//-----------------------------------------------------------------------------
255
// Thread register state manipulation for GDB support.
256
 
257
// Translate a stack pointer as saved by the thread context macros above into
258
// a pointer to a HAL_SavedRegisters structure.
259
#define HAL_THREAD_GET_SAVED_REGISTERS( _sp_, _regs_ )  \
260
        (_regs_) = (HAL_SavedRegisters *)(_sp_)
261
 
262
// Copy a set of registers from a HAL_SavedRegisters structure into a
263
// GDB ordered array.    
264
 
265
externC void hal_get_gdb_registers(CYG_ADDRWORD *, HAL_SavedRegisters *);
266
externC void hal_set_gdb_registers(HAL_SavedRegisters *, CYG_ADDRWORD *);
267
 
268
#define HAL_GET_GDB_REGISTERS( _aregval_, _regs_ ) \
269
                hal_get_gdb_registers((CYG_ADDRWORD *)(_aregval_), (_regs_))
270
 
271
// Copy a GDB ordered array into a HAL_SavedRegisters structure.
272
#define HAL_SET_GDB_REGISTERS( _regs_ , _aregval_ ) \
273
                hal_set_gdb_registers((_regs_), (CYG_ADDRWORD *)(_aregval_))
274
 
275
//-----------------------------------------------------------------------------
276
// HAL setjmp
277
 
278
#define CYGARC_JMP_BUF_SP        0
279
#define CYGARC_JMP_BUF_EBP       1
280
#define CYGARC_JMP_BUF_EBX       2
281
#define CYGARC_JMP_BUF_ESI       3
282
#define CYGARC_JMP_BUF_EDI       4
283
#define CYGARC_JMP_BUF_PC        5
284
 
285
#define CYGARC_JMP_BUF_SIZE      6
286
 
287
typedef cyg_uint32 hal_jmp_buf[CYGARC_JMP_BUF_SIZE];
288
 
289
externC int hal_setjmp(hal_jmp_buf env);
290
externC void hal_longjmp(hal_jmp_buf env, int val);
291
 
292
//-----------------------------------------------------------------------------
293
// Idle thread code.
294
// This macro is called in the idle thread loop, and gives the HAL the
295
// chance to insert code. Typical idle thread behaviour might be to halt the
296
// processor.
297
 
298
externC void hal_idle_thread_action(cyg_uint32 loop_count);
299
 
300
#define HAL_IDLE_THREAD_ACTION(_count_) hal_idle_thread_action(_count_)
301
 
302
//-----------------------------------------------------------------------------
303
// Minimal and sensible stack sizes: the intention is that applications
304
// will use these to provide a stack size in the first instance prior to
305
// proper analysis.  Idle thread stack should be this big.
306
 
307
//    THESE ARE NOT INTENDED TO BE MICROMETRICALLY ACCURATE FIGURES.
308
//           THEY ARE HOWEVER ENOUGH TO START PROGRAMMING.
309
// YOU MUST MAKE YOUR STACKS LARGER IF YOU HAVE LARGE "AUTO" VARIABLES!
310
 
311
// This is not a config option because it should not be adjusted except
312
// under "enough rope" sort of disclaimers.
313
 
314
// Stack frame overhead per call. Four arguments, 3 local registers
315
// (edi, esi, ebx), four local variables and return address.
316
#define CYGNUM_HAL_STACK_FRAME_SIZE (12 * 4)
317
 
318
// Stack needed for a context switch ( sizeof(HAL_SavedRegisters) ).
319
#ifdef CYGHWR_HAL_I386_FPU
320
# define CYGNUM_HAL_STACK_CONTEXT_SIZE ((4 * 12) + 108)
321
#else
322
# define CYGNUM_HAL_STACK_CONTEXT_SIZE (4 * 12)
323
#endif
324
 
325
// Interrupt + call to ISR, interrupt_end() and the DSR
326
#define CYGNUM_HAL_STACK_INTERRUPT_SIZE \
327
    ((4*CYGNUM_HAL_STACK_CONTEXT_SIZE) + 4 * CYGNUM_HAL_STACK_FRAME_SIZE)
328
 
329
// We define a minimum stack size as the minimum any thread could ever
330
// legitimately get away with. We can throw asserts if users ask for less
331
// than this. Allow enough for three interrupt sources - clock, serial and
332
// one other
333
 
334
#if defined(CYGIMP_HAL_COMMON_INTERRUPTS_USE_INTERRUPT_STACK)
335
 
336
// An interrupt stack which is large enough for all possible interrupt
337
// conditions (and only used for that purpose) exists.  "User" stacks
338
// can therefore be much smaller
339
 
340
# define CYGNUM_HAL_STACK_SIZE_MINIMUM \
341
         (2*CYGNUM_HAL_STACK_FRAME_SIZE + 2*CYGNUM_HAL_STACK_INTERRUPT_SIZE)
342
 
343
#else
344
 
345
// No separate interrupt stack exists.  Make sure all threads contain
346
// a stack sufficiently large
347
 
348
# define CYGNUM_HAL_STACK_SIZE_MINIMUM                  \
349
        (((2+3+10)*CYGNUM_HAL_STACK_INTERRUPT_SIZE) +   \
350
         (2*CYGNUM_HAL_STACK_FRAME_SIZE))
351
 
352
#endif
353
 
354
// Now make a reasonable choice for a typical thread size. Pluck figures
355
// from thin air and say 15 call frames with an average of 16 words of
356
// automatic variables per call frame
357
 
358
#define CYGNUM_HAL_STACK_SIZE_TYPICAL                \
359
        (CYGNUM_HAL_STACK_SIZE_MINIMUM +             \
360
         15 * (CYGNUM_HAL_STACK_FRAME_SIZE+(16*4)))
361
 
362
//--------------------------------------------------------------------------
363
// Memory access macros
364
 
365
#define CYGARC_CACHED_ADDRESS(x)                       (x)
366
#define CYGARC_UNCACHED_ADDRESS(x)                     (x)
367
#define CYGARC_PHYSICAL_ADDRESS(x)                     (x)
368
#define CYGARC_VIRTUAL_ADDRESS(x)                      (x)
369
 
370
//--------------------------------------------------------------------------
371
// Region size finder
372
 
373
#if CYGINT_HAL_I386_MEM_REAL_REGION_TOP
374
 
375
externC cyg_uint8 *hal_i386_mem_real_region_top( cyg_uint8 *_regionend_ );
376
 
377
# define HAL_MEM_REAL_REGION_TOP( _regionend_ ) \
378
    hal_i386_mem_real_region_top( _regionend_ )
379
#endif
380
 
381
//--------------------------------------------------------------------------
382
// Macros for switching context between two eCos instances (jump from
383
// code in ROM to code in RAM or vice versa).
384
 
385
#define CYGARC_HAL_SAVE_GP()
386
#define CYGARC_HAL_RESTORE_GP()
387
 
388
//--------------------------------------------------------------------------
389
#endif // CYGONCE_HAL_HAL_ARCH_H
390
// End of hal_arch.h

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.