]> git.saurik.com Git - apple/xnu.git/blame - osfmk/ppc/savearea.h
xnu-792.12.6.tar.gz
[apple/xnu.git] / osfmk / ppc / savearea.h
CommitLineData
1c79356b 1/*
91447636 2 * Copyright (c) 2000-2004 Apple Computer, Inc. All rights reserved.
1c79356b 3 *
8ad349bb 4 * @APPLE_LICENSE_OSREFERENCE_HEADER_START@
1c79356b 5 *
8ad349bb
A
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. The rights granted to you under the
10 * License may not be used to create, or enable the creation or
11 * redistribution of, unlawful or unlicensed copies of an Apple operating
12 * system, or to circumvent, violate, or enable the circumvention or
13 * violation of, any terms of an Apple operating system software license
14 * agreement.
15 *
16 * Please obtain a copy of the License at
17 * http://www.opensource.apple.com/apsl/ and read it before using this
18 * file.
19 *
20 * The Original Code and all software distributed under the License are
21 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
22 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
23 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
24 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
25 * Please see the License for the specific language governing rights and
26 * limitations under the License.
27 *
28 * @APPLE_LICENSE_OSREFERENCE_HEADER_END@
1c79356b 29 */
91447636
A
30#ifdef XNU_KERNEL_PRIVATE
31
1c79356b
A
32#ifndef _PPC_SAVEAREA_H_
33#define _PPC_SAVEAREA_H_
34
9bccf70c
A
35#ifndef ASSEMBLER
36
37#include <sys/appleapiopts.h>
38
39#ifdef __APPLE_API_PRIVATE
40
41#ifdef MACH_KERNEL_PRIVATE
55e303ae
A
42#include <stdint.h>
43#include <mach/vm_types.h>
44
45#pragma pack(4) /* Make sure the structure stays as we defined it */
9bccf70c
A
46typedef struct savearea_comm {
47
48/*
49 * The following fields are common to all saveareas and are used to manage individual
50 * contexts.
51 *
52 * Fields that start with "save" are part of the individual saveareas. Those that
53 * start with "sac" pertain to the free pool stuff and are valid only on the first slot
54 * in the page.
55 */
56
57
55e303ae 58/* Keep the save_prev, sac_next, and sac_prev in these positions, some assembler code depends upon it to
9bccf70c
A
59 * match up with fields in saveanchor.
60 */
55e303ae
A
61 /* offset 0x000 */
62 addr64_t save_prev; /* The address of the previous (or next) savearea */
63 addr64_t sac_next; /* Points to next savearea page that has a free slot - real */
64 addr64_t sac_prev; /* Points to previous savearea page that has a free slot - real */
9bccf70c 65 unsigned int save_level; /* Context ID */
55e303ae
A
66 unsigned int save_01C;
67
68 /* 0x20 */
9bccf70c 69 unsigned int save_time[2]; /* Context save time - for debugging or performance */
91447636 70 struct thread *save_act; /* Associated thread */
55e303ae
A
71 unsigned int save_02c;
72 uint64_t sac_vrswap; /* XOR mask to swap V to R or vice versa */
73 unsigned int save_flags; /* Various flags */
de355530 74 unsigned int sac_flags; /* Various flags */
55e303ae
A
75
76 /* offset 0x040 */
77 uint64_t save_misc0; /* Various stuff */
3a60a9f5 78 uint64_t save_misc1; /* Various stuff - snapshot chain during hibernation */
55e303ae
A
79 unsigned int sac_alloc; /* Bitmap of allocated slots */
80 unsigned int save_054;
81 unsigned int save_misc2;
82 unsigned int save_misc3;
9bccf70c
A
83
84 /* offset 0x0060 */
85} savearea_comm;
55e303ae 86#pragma pack()
9bccf70c
A
87#endif
88
89#ifdef BSD_KERNEL_PRIVATE
90typedef struct savearea_comm {
91 unsigned int save_000[24];
92} savearea_comm;
93#endif
94
95#if defined(MACH_KERNEL_PRIVATE) || defined(BSD_KERNEL_PRIVATE)
96/*
97 * This type of savearea contains all of the general context.
98 */
99
55e303ae 100#pragma pack(4) /* Make sure the structure stays as we defined it */
9bccf70c
A
101typedef struct savearea {
102
103 savearea_comm save_hdr; /* Stuff common to all saveareas */
104
e5568f75
A
105 uint64_t save_xdat0; /* Exception data 0 */
106 uint64_t save_xdat1; /* Exception data 1 */
107 uint64_t save_xdat2; /* Exception data 2 */
108 uint64_t save_xdat3; /* Exception data 3 */
55e303ae
A
109 /* offset 0x0080 */
110 uint64_t save_r0;
111 uint64_t save_r1;
112 uint64_t save_r2;
113 uint64_t save_r3;
114 /* offset 0x0A0 */
115 uint64_t save_r4;
116 uint64_t save_r5;
117 uint64_t save_r6;
118 uint64_t save_r7;
119 /* offset 0x0C0 */
120 uint64_t save_r8;
121 uint64_t save_r9;
122 uint64_t save_r10;
123 uint64_t save_r11;
124 /* offset 0x0E0 */
125 uint64_t save_r12;
126 uint64_t save_r13;
127 uint64_t save_r14;
128 uint64_t save_r15;
129 /* offset 0x100 */
130 uint64_t save_r16;
131 uint64_t save_r17;
132 uint64_t save_r18;
133 uint64_t save_r19;
134 /* offset 0x120 */
135 uint64_t save_r20;
136 uint64_t save_r21;
137 uint64_t save_r22;
138 uint64_t save_r23;
139 /* offset 0x140 */
140 uint64_t save_r24;
141 uint64_t save_r25;
142 uint64_t save_r26;
143 uint64_t save_r27;
144 /* offset 0x160 */
145 uint64_t save_r28;
146 uint64_t save_r29;
147 uint64_t save_r30;
148 uint64_t save_r31;
149 /* offset 0x180 */
150 uint64_t save_srr0;
151 uint64_t save_srr1;
152 uint64_t save_xer;
153 uint64_t save_lr;
154 /* offset 0x1A0 */
155 uint64_t save_ctr;
156 uint64_t save_dar;
9bccf70c 157 unsigned int save_cr;
9bccf70c 158 unsigned int save_dsisr;
55e303ae
A
159 unsigned int save_exception;
160 unsigned int save_vrsave;
161 /* offset 0x1C0 */
162 unsigned int save_vscr[4];
9bccf70c
A
163 unsigned int save_fpscrpad;
164 unsigned int save_fpscr;
55e303ae
A
165 unsigned int save_1d8[2];
166 /* offset 0x1E0 */
9bccf70c 167 unsigned int save_1E0[8];
55e303ae
A
168 /* offset 0x200 - keep on 128 byte bndry */
169 uint32_t save_pmc[8];
170 uint64_t save_mmcr0; /* offset 0x220 */
171 uint64_t save_mmcr1;
172 uint64_t save_mmcr2;
173
174 unsigned int save_238[2];
175 /* offset 0x240 */
176 unsigned int save_instr[16]; /* Instrumentation */
9bccf70c
A
177 /* offset 0x280 */
178} savearea;
55e303ae 179#pragma pack()
9bccf70c
A
180
181
182/*
183 * This type of savearea contains all of the floating point context.
184 */
185
55e303ae 186#pragma pack(4) /* Make sure the structure stays as we defined it */
9bccf70c 187typedef struct savearea_fpu {
1c79356b 188
9bccf70c
A
189 savearea_comm save_hdr; /* Stuff common to all saveareas */
190
191 unsigned int save_060[8]; /* Fill 32 bytes */
192 /* offset 0x0080 */
193 double save_fp0;
194 double save_fp1;
195 double save_fp2;
196 double save_fp3;
197
198 double save_fp4;
199 double save_fp5;
200 double save_fp6;
201 double save_fp7;
202
203 double save_fp8;
204 double save_fp9;
205 double save_fp10;
206 double save_fp11;
207
208 double save_fp12;
209 double save_fp13;
210 double save_fp14;
211 double save_fp15;
212
213 double save_fp16;
214 double save_fp17;
215 double save_fp18;
216 double save_fp19;
217
218 double save_fp20;
219 double save_fp21;
220 double save_fp22;
221 double save_fp23;
222
223 double save_fp24;
224 double save_fp25;
225 double save_fp26;
226 double save_fp27;
227
228 double save_fp28;
229 double save_fp29;
230 double save_fp30;
231 double save_fp31;
232 /* offset 0x180 */
233 unsigned int save_180[8];
234 unsigned int save_1A0[8];
235 unsigned int save_1C0[8];
236 unsigned int save_1E0[8];
237 unsigned int save_200[8];
238 unsigned int save_220[8];
239 unsigned int save_240[8];
240 unsigned int save_260[8];
241
242 /* offset 0x280 */
243} savearea_fpu;
55e303ae 244#pragma pack()
9bccf70c
A
245
246
247
248/*
249 * This type of savearea contains all of the vector context.
250 */
251
55e303ae 252#pragma pack(4) /* Make sure the structure stays as we defined it */
9bccf70c
A
253typedef struct savearea_vec {
254
255 savearea_comm save_hdr; /* Stuff common to all saveareas */
256
257 unsigned int save_060[7]; /* Fill 32 bytes */
258 unsigned int save_vrvalid; /* Valid registers in saved context */
259
260 /* offset 0x0080 */
261 unsigned int save_vr0[4];
262 unsigned int save_vr1[4];
263 unsigned int save_vr2[4];
264 unsigned int save_vr3[4];
265 unsigned int save_vr4[4];
266 unsigned int save_vr5[4];
267 unsigned int save_vr6[4];
268 unsigned int save_vr7[4];
269 unsigned int save_vr8[4];
270 unsigned int save_vr9[4];
271 unsigned int save_vr10[4];
272 unsigned int save_vr11[4];
273 unsigned int save_vr12[4];
274 unsigned int save_vr13[4];
275 unsigned int save_vr14[4];
276 unsigned int save_vr15[4];
277 unsigned int save_vr16[4];
278 unsigned int save_vr17[4];
279 unsigned int save_vr18[4];
280 unsigned int save_vr19[4];
281 unsigned int save_vr20[4];
282 unsigned int save_vr21[4];
283 unsigned int save_vr22[4];
284 unsigned int save_vr23[4];
285 unsigned int save_vr24[4];
286 unsigned int save_vr25[4];
287 unsigned int save_vr26[4];
288 unsigned int save_vr27[4];
289 unsigned int save_vr28[4];
290 unsigned int save_vr29[4];
291 unsigned int save_vr30[4];
292 unsigned int save_vr31[4];
293
294 /* offset 0x280 */
295} savearea_vec;
55e303ae 296#pragma pack()
9bccf70c
A
297#endif /* MACH_KERNEL_PRIVATE || BSD_KERNEL_PRIVATE */
298
299#ifdef MACH_KERNEL_PRIVATE
300
55e303ae 301#pragma pack(4) /* Make sure the structure stays as we defined it */
9bccf70c
A
302struct Saveanchor {
303
304/*
305 * Note that this force aligned in aligned_data.s and must be in V=R storage.
306 * Also, all addresses in chains are physical. This structure can only be
307 * updated with translation and interrupts disabled. This is because it is
308 * locked during exception processing and if we were to take a PTE miss while the
309 * lock were held, well, that would be very bad now wouldn't it?
55e303ae 310 * Note that the first 24 bytes must be the same format as a savearea header.
9bccf70c
A
311 */
312
55e303ae
A
313 unsigned int savelock; /* 000 Lock word for savearea free list manipulation */
314 int saveRSVD4; /* 004 reserved */
315 addr64_t savepoolfwd; /* 008 Forward anchor for the free pool */
316 addr64_t savepoolbwd; /* 010 Backward anchor for the free pool */
317 volatile addr64_t savefree; /* 018 Anchor for the global free list */
318 volatile unsigned int savefreecnt; /* 020 Number of saveareas on global free list */
319 volatile int saveadjust; /* 024 If 0 number of saveareas is ok, otherwise # to change (pos means grow, neg means shrink */
320 volatile int saveinuse; /* 028 Number of areas in use counting those on the local free list */
91447636 321 unsigned int savetarget; /* 02C Number of saveareas needed */
55e303ae 322 int savemaxcount; /* 030 Maximum saveareas ever allocated */
91447636
A
323 unsigned int saveinusesnapshot; /* 034 snapshot inuse count */
324 volatile addr64_t savefreesnapshot; /* 038 snapshot global free list header */
55e303ae 325/* 040 */
9bccf70c 326};
55e303ae 327#pragma pack()
9bccf70c 328
91447636 329extern struct Saveanchor saveanchor; /* Aliged savearea anchor */
9bccf70c
A
330
331#define sac_cnt (4096 / sizeof(savearea)) /* Number of saveareas per page */
332#define sac_empty (0xFFFFFFFF << (32 - sac_cnt)) /* Mask with all entries empty */
333#define sac_perm 0x40000000 /* Page permanently assigned */
334#define sac_permb 1 /* Page permanently assigned - bit position */
335
336#define LocalSaveTarget (((8 + sac_cnt - 1) / sac_cnt) * sac_cnt) /* Target for size of local savearea free list */
337#define LocalSaveMin (LocalSaveTarget / 2) /* Min size of local savearea free list before we grow */
338#define LocalSaveMax (LocalSaveTarget * 2) /* Max size of local savearea free list before we trim */
339
91447636
A
340#define FreeListMin (2 * LocalSaveTarget) /* Always make sure there are enough to fill local list twice per processor */
341#define SaveLowHysteresis LocalSaveTarget /* The number off from target before we adjust upwards */
342#define SaveHighHysteresis (2 * FreeListMin) /* The number off from target before we adjust downwards */
9bccf70c 343#define InitialSaveAreas (2 * FreeListMin) /* The number of saveareas to make at boot time */
91447636 344#define InitialSaveTarget FreeListMin /* The number of saveareas for an initial target. This should be the minimum ever needed. */
9bccf70c 345#define InitialSaveBloks (InitialSaveAreas + sac_cnt - 1) / sac_cnt /* The number of savearea blocks to allocate at boot */
55e303ae
A
346#define BackPocketSaveBloks 8 /* Number of pages of back pocket saveareas */
347
348void save_queue(ppnum_t); /* Add a new savearea block to the free list */
349addr64_t save_get_init(void); /* special savearea-get for cpu initialization (returns physical address) */
350struct savearea *save_get(void); /* Obtains a savearea from the free list (returns virtual address) */
351reg64_t save_get_phys_32(void); /* Obtains a savearea from the free list (returns phys addr in r3) */
352reg64_t save_get_phys_64(void); /* Obtains a savearea from the free list (returns phys addr in r3) */
353struct savearea *save_alloc(void); /* Obtains a savearea and allocates blocks if needed */
354struct savearea *save_cpv(addr64_t); /* Converts a physical savearea address to virtual */
355void save_ret(struct savearea *); /* Returns a savearea to the free list by virtual address */
356void save_ret_wMSR(struct savearea *, reg64_t); /* returns a savearea and restores an MSR */
357void save_ret_phys(reg64_t); /* Returns a savearea to the free list by physical address */
358void save_adjust(void); /* Adjust size of the global free list */
359struct savearea_comm *save_trim_free(void); /* Remove free pages from savearea pool */
360int save_recover(void); /* returns nonzero if we can recover enough from the free pool */
361void savearea_init(vm_offset_t addr); /* Boot-time savearea initialization */
9bccf70c 362
91447636
A
363void save_fake_zone_info( /* report savearea usage statistics as fake zone info */
364 int *count,
365 vm_size_t *cur_size,
366 vm_size_t *max_size,
367 vm_size_t *elem_size,
368 vm_size_t *alloc_size,
369 int *collectable,
370 int *exhaustable);
371
372void save_snapshot(void);
373void save_snapshot_restore(void);
9bccf70c 374
9bccf70c
A
375#endif /* MACH_KERNEL_PRIVATE */
376#endif /* __APPLE_API_PRIVATE */
377
378#endif /* ndef ASSEMBLER */
1c79356b 379
9bccf70c
A
380#define SAVattach 0x80000000 /* Savearea has valid context */
381#define SAVrststk 0x00010000 /* Indicates that the current stack should be reset to empty */
382#define SAVsyscall 0x00020000 /* Indicates that the savearea is associated with a syscall */
383#define SAVredrive 0x00040000 /* Indicates that the low-level fault handler associated */
55e303ae
A
384#define SAVredriveb 13 /* Indicates that the low-level fault handler associated */
385#define SAVinstrument 0x00080000 /* Indicates that we should return instrumentation data */
386#define SAVinstrumentb 12 /* Indicates that we should return instrumentation data */
a3d08fcd
A
387#define SAVeat 0x00100000 /* Indicates that interruption should be ignored */
388#define SAVeatb 11 /* Indicates that interruption should be ignored */
9bccf70c
A
389#define SAVtype 0x0000FF00 /* Shows type of savearea */
390#define SAVtypeshft 8 /* Shift to position type */
391#define SAVempty 0x86 /* Savearea is on free list */
392#define SAVgeneral 0x01 /* Savearea contains general context */
393#define SAVfloat 0x02 /* Savearea contains floating point context */
394#define SAVvector 0x03 /* Savearea contains vector context */
1c79356b 395
55e303ae
A
396
397
9bccf70c 398#endif /* _PPC_SAVEAREA_H_ */
91447636
A
399
400#endif /* XNU_KERNEL_PRIVATE */