source: trunk/packages/xen-3.1/xen-3.1/xen/arch/ia64/vmx/vmx_minstate.h @ 34

Last change on this file since 34 was 34, checked in by hartmans, 18 years ago

Add xen and xen-common

File size: 11.8 KB
Line 
1/* -*-  Mode:C; c-basic-offset:4; tab-width:4; indent-tabs-mode:nil -*- */
2/*
3 * vmx_minstate.h:
4 * Copyright (c) 2005, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
13 * more details.
14 *
15 * You should have received a copy of the GNU General Public License along with
16 * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
17 * Place - Suite 330, Boston, MA 02111-1307 USA.
18 *
19 *  Xuefei Xu (Anthony Xu) (Anthony.xu@intel.com)
20 */
21
22#include <linux/config.h>
23
24#include <asm/asmmacro.h>
25#include <asm/fpu.h>
26#include <asm/mmu_context.h>
27#include <asm/offsets.h>
28#include <asm/pal.h>
29#include <asm/pgtable.h>
30#include <asm/processor.h>
31#include <asm/ptrace.h>
32#include <asm/system.h>
33#include <asm/vmx_pal_vsa.h>
34#include <asm/vmx_vpd.h>
35#include <asm/cache.h>
36#include "entry.h"
37
38#define VMX_MINSTATE_START_SAVE_MIN         \
39    mov ar.rsc=0;       /* set enforced lazy mode, pl 0, little-endian, loadrs=0 */ \
40    ;;                                          \
41    mov.m r28=ar.rnat;                                  \
42    addl r22=IA64_RBS_OFFSET,r1;            /* compute base of RBS */       \
43    ;;                                          \
44    lfetch.fault.excl.nt1 [r22];                                \
45    addl r1=IA64_STK_OFFSET-IA64_PT_REGS_SIZE,r1;   /* compute base of memory stack */  \
46    mov r23=ar.bspstore;                /* save ar.bspstore */          \
47    ;;                                          \
48    mov ar.bspstore=r22;                /* switch to kernel RBS */      \
49    ;;                                          \
50    mov r18=ar.bsp;                                     \
51    mov ar.rsc=0x3;     /* set eager mode, pl 0, little-endian, loadrs=0 */     \
52
53
54
55#define VMX_MINSTATE_END_SAVE_MIN           \
56    bsw.1;          /* switch back to bank 1 (must be last in insn group) */    \
57    ;;
58
59
60#define PAL_VSA_SYNC_READ           \
61    /* begin to call pal vps sync_read */     \
62    add r25=IA64_VPD_BASE_OFFSET, r21;       \
63    movl r20=__vsa_base;     \
64    ;;          \
65    ld8 r25=[r25];      /* read vpd base */     \
66    ld8 r20=[r20];      /* read entry point */  \
67    ;;      \
68    add r20=PAL_VPS_SYNC_READ,r20;  \
69    ;;  \
70{ .mii;  \
71    nop 0x0;   \
72    mov r24=ip;        \
73    mov b0=r20;     \
74    ;;      \
75};           \
76{ .mmb;      \
77    add r24 = 0x20, r24;    \
78    nop 0x0;     \
79    br.cond.sptk b0;        /*  call the service */ \
80    ;;              \
81};           \
82
83
84
85#define IA64_CURRENT_REG    IA64_KR(CURRENT)  /* r21 is reserved for current pointer */
86//#define VMX_MINSTATE_GET_CURRENT(reg)   mov reg=IA64_CURRENT_REG
87#define VMX_MINSTATE_GET_CURRENT(reg)   mov reg=r21
88
89/*
90 * VMX_DO_SAVE_MIN switches to the kernel stacks (if necessary) and saves
91 * the minimum state necessary that allows us to turn psr.ic back
92 * on.
93 *
94 * Assumed state upon entry:
95 *  psr.ic: off
96 *  r31:    contains saved predicates (pr)
97 *
98 * Upon exit, the state is as follows:
99 *  psr.ic: off
100 *   r2 = points to &pt_regs.r16
101 *   r8 = contents of ar.ccv
102 *   r9 = contents of ar.csd
103 *  r10 = contents of ar.ssd
104 *  r11 = FPSR_DEFAULT
105 *  r12 = kernel sp (kernel virtual address)
106 *  r13 = points to current task_struct (kernel virtual address)
107 *  p15 = TRUE if psr.i is set in cr.ipsr
108 *  predicate registers (other than p2, p3, and p15), b6, r3, r14, r15:
109 *      preserved
110 *
111 * Note that psr.ic is NOT turned on by this macro.  This is so that
112 * we can pass interruption state as arguments to a handler.
113 */
114
115#define VMX_DO_SAVE_MIN(COVER,SAVE_IFS,EXTRA)                           \
116    VMX_MINSTATE_GET_CURRENT(r16);  /* M (or M;;I) */                   \
117    mov r27=ar.rsc;         /* M */                         \
118    mov r20=r1;         /* A */                         \
119    mov r25=ar.unat;        /* M */                         \
120    mov r29=cr.ipsr;        /* M */                         \
121    mov r26=ar.pfs;         /* I */                     \
122    mov r18=cr.isr;         \
123    COVER;              /* B;; (or nothing) */                  \
124    ;;                                          \
125    tbit.z p6,p0=r29,IA64_PSR_VM_BIT;       \
126    ;;      \
127    tbit.nz.or p6,p0 = r18,39; \
128    ;;        \
129(p6) br.sptk.few vmx_panic;        \
130    tbit.z p0,p15=r29,IA64_PSR_I_BIT;   \
131    mov r1=r16;                     \
132/*    mov r21=r16;      */              \
133    /* switch from user to kernel RBS: */                           \
134    ;;                                          \
135    invala;             /* M */                         \
136    SAVE_IFS;                                       \
137    ;;                                          \
138    VMX_MINSTATE_START_SAVE_MIN                                 \
139    adds r17=2*L1_CACHE_BYTES,r1;       /* really: biggest cache-line size */       \
140    adds r16=PT(CR_IPSR),r1;                                \
141    ;;                                          \
142    lfetch.fault.excl.nt1 [r17],L1_CACHE_BYTES;                     \
143    st8 [r16]=r29;      /* save cr.ipsr */                      \
144    ;;                                          \
145    lfetch.fault.excl.nt1 [r17];                                \
146    tbit.nz p15,p0=r29,IA64_PSR_I_BIT;                          \
147    mov r29=b0                                      \
148    ;;                                          \
149    adds r16=PT(R8),r1; /* initialize first base pointer */             \
150    adds r17=PT(R9),r1; /* initialize second base pointer */                \
151    ;;                                          \
152.mem.offset 0,0; st8.spill [r16]=r8,16;                             \
153.mem.offset 8,0; st8.spill [r17]=r9,16;                             \
154        ;;                                          \
155.mem.offset 0,0; st8.spill [r16]=r10,24;                            \
156.mem.offset 8,0; st8.spill [r17]=r11,24;                            \
157        ;;                                          \
158    mov r9=cr.iip;         /* M */                         \
159    mov r10=ar.fpsr;        /* M */                         \
160        ;;                      \
161    st8 [r16]=r9,16;    /* save cr.iip */                       \
162    st8 [r17]=r30,16;   /* save cr.ifs */                       \
163    sub r18=r18,r22;    /* r18=RSE.ndirty*8 */                      \
164    ;;          \
165    st8 [r16]=r25,16;   /* save ar.unat */                      \
166    st8 [r17]=r26,16;    /* save ar.pfs */                       \
167    shl r18=r18,16;     /* compute ar.rsc to be used for "loadrs" */            \
168    ;;                                          \
169    st8 [r16]=r27,16;   /* save ar.rsc */                       \
170    st8 [r17]=r28,16;   /* save ar.rnat */                      \
171    ;;          /* avoid RAW on r16 & r17 */                    \
172    st8 [r16]=r23,16;   /* save ar.bspstore */                      \
173    st8 [r17]=r31,16;   /* save predicates */                       \
174    ;;                                          \
175    st8 [r16]=r29,16;   /* save b0 */                           \
176    st8 [r17]=r18,16;   /* save ar.rsc value for "loadrs" */                \
177    cmp.eq pNonSys,pSys=r0,r0   /* initialize pSys=0, pNonSys=1 */          \
178    ;;                                          \
179.mem.offset 0,0; st8.spill [r16]=r20,16;    /* save original r1 */              \
180.mem.offset 8,0; st8.spill [r17]=r12,16;                            \
181    adds r12=-16,r1;    /* switch to kernel memory stack (with 16 bytes of scratch) */  \
182    ;;                                          \
183.mem.offset 0,0; st8.spill [r16]=r13,16;                            \
184.mem.offset 8,0; st8.spill [r17]=r10,16;    /* save ar.fpsr */              \
185    mov r13=r21;   /* establish `current' */               \
186    ;;                                          \
187.mem.offset 0,0; st8.spill [r16]=r15,16;                            \
188.mem.offset 8,0; st8.spill [r17]=r14,16;                            \
189    ;;                                          \
190.mem.offset 0,0; st8.spill [r16]=r2,16;                             \
191.mem.offset 8,0; st8.spill [r17]=r3,16;                             \
192    adds r2=IA64_PT_REGS_R16_OFFSET,r1;                         \
193     ;;  \
194    adds r16=IA64_VCPU_IIPA_OFFSET,r13;                       \
195    adds r17=IA64_VCPU_ISR_OFFSET,r13;                       \
196    mov r26=cr.iipa;  \
197    mov r27=cr.isr;   \
198    ;;      \
199    st8 [r16]=r26;      \
200    st8 [r17]=r27;      \
201    ;;  \
202    EXTRA;                                          \
203    mov r8=ar.ccv;          \
204    mov r9=ar.csd;                                      \
205    mov r10=ar.ssd;                                     \
206    movl r11=FPSR_DEFAULT;   /* L-unit */                           \
207    movl r1=__gp;       /* establish kernel global pointer */               \
208    ;;                                          \
209    PAL_VSA_SYNC_READ           \
210    VMX_MINSTATE_END_SAVE_MIN
211
212/*
213 * SAVE_REST saves the remainder of pt_regs (with psr.ic on).
214 *
215 * Assumed state upon entry:
216 *  psr.ic: on
217 *  r2: points to &pt_regs.f6
218 *  r3: points to &pt_regs.f7
219 *  r8: contents of ar.ccv
220 *  r9: contents of ar.csd
221 *  r10:    contents of ar.ssd
222 *  r11:    FPSR_DEFAULT
223 *
224 * Registers r14 and r15 are guaranteed not to be touched by SAVE_REST.
225 */
226#define VMX_SAVE_REST               \
227.mem.offset 0,0; st8.spill [r2]=r16,16;     \
228.mem.offset 8,0; st8.spill [r3]=r17,16;     \
229    ;;                  \
230.mem.offset 0,0; st8.spill [r2]=r18,16;     \
231.mem.offset 8,0; st8.spill [r3]=r19,16;     \
232    ;;                  \
233.mem.offset 0,0; st8.spill [r2]=r20,16;     \
234.mem.offset 8,0; st8.spill [r3]=r21,16;     \
235    mov r18=b6;         \
236    ;;                  \
237.mem.offset 0,0; st8.spill [r2]=r22,16;     \
238.mem.offset 8,0; st8.spill [r3]=r23,16;     \
239    mov r19=b7;     \
240    ;;                  \
241.mem.offset 0,0; st8.spill [r2]=r24,16;     \
242.mem.offset 8,0; st8.spill [r3]=r25,16;     \
243    ;;                  \
244.mem.offset 0,0; st8.spill [r2]=r26,16;     \
245.mem.offset 8,0; st8.spill [r3]=r27,16;     \
246    ;;                  \
247.mem.offset 0,0; st8.spill [r2]=r28,16;     \
248.mem.offset 8,0; st8.spill [r3]=r29,16;     \
249    ;;                  \
250.mem.offset 0,0; st8.spill [r2]=r30,16;     \
251.mem.offset 8,0; st8.spill [r3]=r31,32;     \
252    ;;                  \
253    mov ar.fpsr=r11;     \
254    st8 [r2]=r8,8;       \
255    adds r24=PT(B6)-PT(F7),r3;      \
256    ;;                  \
257    stf.spill [r2]=f6,32;           \
258    stf.spill [r3]=f7,32;           \
259    ;;                  \
260    stf.spill [r2]=f8,32;           \
261    stf.spill [r3]=f9,32;           \
262    ;;                  \
263    stf.spill [r2]=f10,32;         \
264    stf.spill [r3]=f11;         \
265    adds r25=PT(B7)-PT(F11),r3;     \
266    ;;                  \
267    st8 [r24]=r18,16;       /* b6 */    \
268    st8 [r25]=r19,16;       /* b7 */    \
269    adds r3=PT(R5)-PT(F11),r3;     \
270    ;;                  \
271    st8 [r24]=r9;           /* ar.csd */    \
272    st8 [r25]=r10;          /* ar.ssd */    \
273    ;;          \
274    mov r18=ar.unat;    \
275    adds r19=PT(EML_UNAT)-PT(R4),r2;    \
276    ;;                  \
277    st8 [r19]=r18;       /* eml_unat */ \
278
279
280#define VMX_SAVE_EXTRA               \
281.mem.offset 0,0; st8.spill [r2]=r4,16;     \
282.mem.offset 8,0; st8.spill [r3]=r5,16;     \
283    ;;                  \
284.mem.offset 0,0; st8.spill [r2]=r6,16;      \
285.mem.offset 8,0; st8.spill [r3]=r7;      \
286    ;;                  \
287    mov r26=ar.unat;    \
288    ;;                  \
289    st8 [r2]=r26;       /* eml_unat */ \
290
291#define VMX_SAVE_MIN_WITH_COVER   VMX_DO_SAVE_MIN(cover, mov r30=cr.ifs,)
292#define VMX_SAVE_MIN_WITH_COVER_R19 VMX_DO_SAVE_MIN(cover, mov r30=cr.ifs, mov r15=r19)
293#define VMX_SAVE_MIN      VMX_DO_SAVE_MIN(     , mov r30=r0, )
Note: See TracBrowser for help on using the repository browser.