source: rtems/cpukit/score/cpu/i386/cpu_asm.S @ 30f7ff9

4.104.114.84.95
Last change on this file since 30f7ff9 was 30f7ff9, checked in by Joel Sherrill <joel.sherrill@…>, on 10/05/99 at 19:11:57

Removed targets and configurations that are no longer functional
and not likely to become so. Comments on each configuration
are below.

+ Force CPU386 - This BSP was developed as part of the initial

port of RTEMS to the i386. This board has been unavailable
for a long time now.

+ GO32 - This BSP and some CPU code supported djgpp v1.x. This

version is now quite old. No one has stepped forward to
update the code to v2.x which may be technically impossible
anyway. More importantly, go32 has been superceded by the pc386 BSP.

  • Property mode set to 100644
File size: 7.7 KB
Line 
1/*  cpu_asm.s
2 *
3 *  This file contains all assembly code for the Intel i386 implementation
4 *  of RTEMS.
5 *
6 *  COPYRIGHT (c) 1989-1998.
7 *  On-Line Applications Research Corporation (OAR).
8 *  Copyright assigned to U.S. Government, 1994.
9 *
10 *  The license and distribution terms for this file may be
11 *  found in the file LICENSE in this distribution or at
12 *  http://www.OARcorp.com/rtems/license.html.
13 *
14 *  $Id$
15 */
16
17#include <asm.h>
18
19/*
20 * Format of i386 Register structure
21 */
22
23.set REG_EFLAGS,  0
24.set REG_ESP,     REG_EFLAGS + 4
25.set REG_EBP,     REG_ESP + 4
26.set REG_EBX,     REG_EBP + 4
27.set REG_ESI,     REG_EBX + 4
28.set REG_EDI,     REG_ESI + 4
29.set SIZE_REGS,   REG_EDI + 4
30
31        BEGIN_CODE
32
33/*
34 *  void _CPU_Context_switch( run_context, heir_context )
35 *
36 *  This routine performs a normal non-FP context.
37 */
38
39        .p2align  1
40        PUBLIC (_CPU_Context_switch)
41
42.set RUNCONTEXT_ARG,   4                   # save context argument
43.set HEIRCONTEXT_ARG,  8                   # restore context argument
44
45SYM (_CPU_Context_switch):
46        movl      RUNCONTEXT_ARG(esp),eax  # eax = running threads context
47        pushf                              # push eflags
48        popl      REG_EFLAGS(eax)          # save eflags
49        movl      esp,REG_ESP(eax)         # save stack pointer
50        movl      ebp,REG_EBP(eax)         # save base pointer
51        movl      ebx,REG_EBX(eax)         # save ebx
52        movl      esi,REG_ESI(eax)         # save source register
53        movl      edi,REG_EDI(eax)         # save destination register
54
55        movl      HEIRCONTEXT_ARG(esp),eax # eax = heir threads context
56
57restore:
58        pushl     REG_EFLAGS(eax)          # push eflags
59        popf                               # restore eflags
60        movl      REG_ESP(eax),esp         # restore stack pointer
61        movl      REG_EBP(eax),ebp         # restore base pointer
62        movl      REG_EBX(eax),ebx         # restore ebx
63        movl      REG_ESI(eax),esi         # restore source register
64        movl      REG_EDI(eax),edi         # restore destination register
65        ret
66
67/*
68 *  NOTE: May be unnecessary to reload some registers.
69 */
70
71/*
72 *  void _CPU_Context_restore( new_context )
73 *
74 *  This routine performs a normal non-FP context.
75 */
76
77        PUBLIC (_CPU_Context_restore)
78
79.set NEWCONTEXT_ARG,   4                   # context to restore argument
80
81SYM (_CPU_Context_restore):
82
83        movl      NEWCONTEXT_ARG(esp),eax  # eax = running threads context
84        jmp       restore
85
86/*PAGE
87 *  void _CPU_Context_save_fp_context( &fp_context_ptr )
88 *  void _CPU_Context_restore_fp_context( &fp_context_ptr )
89 *
90 *  This section is used to context switch an i80287, i80387,
91 *  the built-in coprocessor or the i80486 or compatible.
92 */
93
94.set FPCONTEXT_ARG,   4                    # FP context argument
95
96        .p2align  1
97        PUBLIC (_CPU_Context_save_fp)
98SYM (_CPU_Context_save_fp):
99        movl      FPCONTEXT_ARG(esp),eax   # eax = &ptr to FP context area
100        movl      (eax),eax                # eax = FP context area
101        fsave     (eax)                    # save FP context
102        ret
103
104        .p2align  1
105        PUBLIC (_CPU_Context_restore_fp)
106SYM (_CPU_Context_restore_fp):
107        movl      FPCONTEXT_ARG(esp),eax   # eax = &ptr to FP context area
108        movl      (eax),eax                # eax = FP context area
109        frstor    (eax)                    # restore FP context
110        ret
111
112        PUBLIC (_Exception_Handler)
113SYM (_Exception_Handler):
114        pusha                              # Push general purpose registers
115        pushl   esp                        # Push exception frame address
116        movl    _currentExcHandler, eax    # Call function storead in _currentExcHandler
117        call    * eax
118        addl    $4, esp
119        popa                               # restore general purpose registers
120        addl    $8, esp                    # skill vector number and faultCode
121        iret
122               
123#define DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY(_vector) \
124        .p2align 4                         ; \
125        PUBLIC (rtems_exception_prologue_ ## _vector ) ; \
126SYM (rtems_exception_prologue_ ## _vector ):             \
127        pushl   $ _vector       ; \
128        jmp   SYM (_Exception_Handler) ;
129
130#define DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY(_vector) \
131        .p2align 4                         ; \
132        PUBLIC (rtems_exception_prologue_ ## _vector ) ; \
133SYM (rtems_exception_prologue_ ## _vector ):             \
134        pushl   $ 0             ; \
135        pushl   $ _vector       ; \
136        jmp   SYM (_Exception_Handler) ;
137
138/*
139 * Divide Error
140 */     
141DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (0)
142/*
143 * Debug Exception
144 */     
145DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (1)
146/*
147 * NMI
148 */     
149DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (2)
150/*
151 * Breakpoint
152 */     
153DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (3)
154/*
155 * Overflow
156 */     
157DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (4)
158/*
159 * Bound Range Exceeded
160 */     
161DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (5)
162/*
163 * Invalid Opcode
164 */     
165DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (6)
166/*
167 * No Math Coproc
168 */     
169DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (7)
170/*
171 * Double Fault
172 */     
173DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (8)
174/*
175 * Coprocessor segment overrun
176 */     
177DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (9)
178/*
179 * Invalid TSS
180 */     
181DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (10)
182/*
183 * Segment Not Present
184 */     
185DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (11)
186/*
187 * Stack segment Fault
188 */     
189DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (12)
190/*
191 * General Protection Fault
192 */     
193DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (13)
194/*
195 * Page Fault
196 */     
197DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (14)
198/*
199 * Floating point error (NB 15 is reserved it is therefor skipped)
200 */     
201DISTINCT_EXCEPTION_WITHOUT_FAULTCODE_ENTRY (16)
202/*
203 * Aligment Check
204 */     
205DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (17)
206/*
207 * Machine Check
208 */     
209DISTINCT_EXCEPTION_WITH_FAULTCODE_ENTRY (18)
210       
211
212/*
213 *  void *i386_Logical_to_physical(
214 *     rtems_unsigned16  segment,
215 *     void             *address
216 *  );
217 *
218 *  Returns thirty-two bit physical address for segment:address.
219 */
220
221.set SEGMENT_ARG, 4
222.set ADDRESS_ARG, 8
223
224             PUBLIC (i386_Logical_to_physical)
225
226SYM (i386_Logical_to_physical):
227
228        xorl    eax,eax                # clear eax
229        movzwl  SEGMENT_ARG(esp),ecx   # ecx = segment value
230        movl    $ SYM (_Global_descriptor_table),edx
231                                       # edx = address of our GDT
232        addl    ecx,edx                # edx = address of desired entry
233        movb    7(edx),ah              # ah = base 31:24
234        movb    4(edx),al              # al = base 23:16
235        shll    $16,eax                # move ax into correct bits
236        movw    2(edx),ax              # ax = base 0:15
237        movl    ADDRESS_ARG(esp),ecx   # ecx = address to convert
238        addl    eax,ecx                # ecx = physical address equivalent
239        movl    ecx,eax                # eax = ecx
240        ret
241
242/*
243 *  void *i386_Physical_to_logical(
244 *     rtems_unsigned16  segment,
245 *     void             *address
246 *  );
247 *
248 *  Returns thirty-two bit physical address for segment:address.
249 */
250
251/*
252 *.set SEGMENT_ARG, 4
253 *.set ADDRESS_ARG, 8   -- use sets from above
254 */
255
256       PUBLIC (i386_Physical_to_logical)
257
258SYM (i386_Physical_to_logical):
259        xorl    eax,eax                # clear eax
260        movzwl  SEGMENT_ARG(esp),ecx   # ecx = segment value
261        movl    $ SYM (_Global_descriptor_table),edx
262                                       # edx = address of our GDT
263        addl    ecx,edx                # edx = address of desired entry
264        movb    7(edx),ah              # ah = base 31:24
265        movb    4(edx),al              # al = base 23:16
266        shll    $16,eax                # move ax into correct bits
267        movw    2(edx),ax              # ax = base 0:15
268        movl    ADDRESS_ARG(esp),ecx   # ecx = address to convert
269        subl    eax,ecx                # ecx = logical address equivalent
270        movl    ecx,eax                # eax = ecx
271        ret
272
273END_CODE
274
275END
Note: See TracBrowser for help on using the repository browser.