[BACK]Return to segments.h CVS log [TXT][DIR] Up to [local] / sys / arch / amd64 / include

Annotation of sys/arch/amd64/include/segments.h, Revision 1.1.1.1

1.1       nbrk        1: /*     $OpenBSD: segments.h,v 1.4 2005/12/13 00:18:19 jsg Exp $        */
                      2: /*     $NetBSD: segments.h,v 1.1 2003/04/26 18:39:47 fvdl Exp $        */
                      3:
                      4: /*-
                      5:  * Copyright (c) 1995, 1997
                      6:  *     Charles M. Hannum.  All rights reserved.
                      7:  * Copyright (c) 1989, 1990 William F. Jolitz
                      8:  * Copyright (c) 1990 The Regents of the University of California.
                      9:  * All rights reserved.
                     10:  *
                     11:  * This code is derived from software contributed to Berkeley by
                     12:  * William Jolitz.
                     13:  *
                     14:  * Redistribution and use in source and binary forms, with or without
                     15:  * modification, are permitted provided that the following conditions
                     16:  * are met:
                     17:  * 1. Redistributions of source code must retain the above copyright
                     18:  *    notice, this list of conditions and the following disclaimer.
                     19:  * 2. Redistributions in binary form must reproduce the above copyright
                     20:  *    notice, this list of conditions and the following disclaimer in the
                     21:  *    documentation and/or other materials provided with the distribution.
                     22:  * 3. Neither the name of the University nor the names of its contributors
                     23:  *    may be used to endorse or promote products derived from this software
                     24:  *    without specific prior written permission.
                     25:  *
                     26:  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
                     27:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     28:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     29:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
                     30:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     31:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     32:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     33:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     34:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     35:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     36:  * SUCH DAMAGE.
                     37:  *
                     38:  *     @(#)segments.h  7.1 (Berkeley) 5/9/91
                     39:  */
                     40:
                     41: /*
                     42:  * Adapted for NetBSD/amd64 by fvdl@wasabisystems.com.
                     43:  */
                     44:
                     45: /*
                     46:  * 386 Segmentation Data Structures and definitions
                     47:  *     William F. Jolitz (william@ernie.berkeley.edu) 6/20/1989
                     48:  */
                     49:
                     50: #ifndef _AMD64_SEGMENTS_H_
                     51: #define _AMD64_SEGMENTS_H_
                     52:
                     53: /*
                     54:  * Selectors
                     55:  */
                     56:
                     57: #define        ISPL(s)         ((s) & SEL_RPL) /* what is the priority level of a selector */
                     58: #define        SEL_KPL         0               /* kernel privilege level */
                     59: #define        SEL_UPL         3               /* user privilege level */
                     60: #define        SEL_RPL         3               /* requester's privilege level mask */
                     61: #define        ISLDT(s)        ((s) & SEL_LDT) /* is it local or global */
                     62: #define        SEL_LDT         4               /* local descriptor table */
                     63:
                     64: /* Dynamically allocated TSSs and LDTs start (byte offset) */
                     65: #define SYSSEL_START   (NGDT_MEM << 3)
                     66: #define DYNSEL_START   (SYSSEL_START + (NGDT_SYS << 4))
                     67:
                     68: /*
                     69:  * These define the index not from the start of the GDT, but from
                     70:  * the part of the GDT that they're allocated from.
                     71:  * First NGDT_MEM entries are 8-byte descriptors for CS and DS.
                     72:  * Next NGDT_SYS entries are 16-byte descriptors defining LDTs.
                     73:  *
                     74:  * The rest is 16-byte descriptors for TSS and LDT.
                     75:  */
                     76:
                     77: #define        IDXSEL(s)       (((s) >> 3) & 0x1fff)
                     78: #define IDXDYNSEL(s)   ((((s) & ~SEL_RPL) - DYNSEL_START) >> 4)
                     79:
                     80: #define        GSEL(s,r)       (((s) << 3) | r)
                     81: #define        GSYSSEL(s,r)    ((((s) << 4) + SYSSEL_START) | r)
                     82: #define GDYNSEL(s,r)   ((((s) << 4) + DYNSEL_START) | r | SEL_KPL)
                     83:
                     84: #define LSEL(s,r)      ((s) | r | SEL_LDT)
                     85:
                     86: #define        USERMODE(c, f)          (ISPL(c) == SEL_UPL)
                     87: #define        KERNELMODE(c, f)        (ISPL(c) == SEL_KPL)
                     88:
                     89: #ifndef _LOCORE
                     90:
                     91: /*
                     92:  * Memory and System segment descriptors
                     93:  */
                     94:
                     95: /*
                     96:  * Below is used for TSS and LDT.
                     97:  */
                     98: struct sys_segment_descriptor {
                     99: /*BITFIELDTYPE*/ u_int64_t sd_lolimit:16;/* segment extent (lsb) */
                    100: /*BITFIELDTYPE*/ u_int64_t sd_lobase:24;/* segment base address (lsb) */
                    101: /*BITFIELDTYPE*/ u_int64_t sd_type:5;  /* segment type */
                    102: /*BITFIELDTYPE*/ u_int64_t sd_dpl:2;   /* segment descriptor priority level */
                    103: /*BITFIELDTYPE*/ u_int64_t sd_p:1;     /* segment descriptor present */
                    104: /*BITFIELDTYPE*/ u_int64_t sd_hilimit:4;/* segment extent (msb) */
                    105: /*BITFIELDTYPE*/ u_int64_t sd_xx1:3;   /* avl, long and def32 (not used) */
                    106: /*BITFIELDTYPE*/ u_int64_t sd_gran:1;  /* limit granularity (byte/page) */
                    107: /*BITFIELDTYPE*/ u_int64_t sd_hibase:40;/* segment base address (msb) */
                    108: /*BITFIELDTYPE*/ u_int64_t sd_xx2:8;   /* reserved */
                    109: /*BITFIELDTYPE*/ u_int64_t sd_zero:5;  /* must be zero */
                    110: /*BITFIELDTYPE*/ u_int64_t sd_xx3:19;  /* reserved */
                    111: } __attribute__((packed));
                    112:
                    113: /*
                    114:  * Below is used for cs, ds, etc.
                    115:  */
                    116: struct mem_segment_descriptor {
                    117:        unsigned int sd_lolimit:16;         /* segment extent (lsb) */
                    118:        unsigned int sd_lobase:24;          /* segment base address (lsb) */
                    119:        unsigned int sd_type:5;             /* segment type */
                    120:        unsigned int sd_dpl:2;              /* segment descriptor priority level */
                    121:        unsigned int sd_p:1;                /* segment descriptor present */
                    122:        unsigned int sd_hilimit:4;          /* segment extent (msb) */
                    123:        unsigned int sd_avl:1;          /* available */
                    124:        unsigned int sd_long:1;         /* long mode */
                    125:        unsigned int sd_def32:1;            /* default 32 vs 16 bit size */
                    126:        unsigned int sd_gran:1;             /* limit granularity (byte/page) */
                    127:        unsigned int sd_hibase:8;           /* segment base address (msb) */
                    128: } __attribute__((packed));
                    129:
                    130: /*
                    131:  * Gate descriptors (e.g. indirect descriptors)
                    132:  */
                    133: struct gate_descriptor {
                    134: /*BITFIELDTYPE*/ u_int64_t gd_looffset:16;/* gate offset (lsb) */
                    135: /*BITFIELDTYPE*/ u_int64_t gd_selector:16;/* gate segment selector */
                    136: /*BITFIELDTYPE*/ u_int64_t gd_ist:3;   /* IST select */
                    137: /*BITFIELDTYPE*/ u_int64_t gd_xx1:5;   /* reserved */
                    138: /*BITFIELDTYPE*/ u_int64_t gd_type:5;  /* segment type */
                    139: /*BITFIELDTYPE*/ u_int64_t gd_dpl:2;   /* segment descriptor priority level */
                    140: /*BITFIELDTYPE*/ u_int64_t gd_p:1;     /* segment descriptor present */
                    141: /*BITFIELDTYPE*/ u_int64_t gd_hioffset:48;/* gate offset (msb) */
                    142: /*BITFIELDTYPE*/ u_int64_t gd_xx2:8;   /* reserved */
                    143: /*BITFIELDTYPE*/ u_int64_t gd_zero:5;  /* must be zero */
                    144: /*BITFIELDTYPE*/ u_int64_t gd_xx3:19;  /* reserved */
                    145: } __attribute__((packed));
                    146:
                    147: /*
                    148:  * region descriptors, used to load gdt/idt tables before segments yet exist.
                    149:  */
                    150: struct region_descriptor {
                    151:        u_int16_t rd_limit;             /* segment extent */
                    152:        u_int64_t rd_base;              /* base address  */
                    153: } __attribute__((packed));
                    154:
                    155: #ifdef _KERNEL
                    156: #if 0
                    157: extern struct sys_segment_descriptor *ldt;
                    158: #endif
                    159: extern struct gate_descriptor *idt;
                    160: extern char *gdtstore;
                    161: extern char *ldtstore;
                    162:
                    163: void setgate(struct gate_descriptor *, void *, int, int, int, int);
                    164: void unsetgate(struct gate_descriptor *);
                    165: void setregion(struct region_descriptor *, void *, u_int16_t);
                    166: void set_sys_segment(struct sys_segment_descriptor *, void *, size_t,
                    167:                          int, int, int);
                    168: void set_mem_segment(struct mem_segment_descriptor *, void *, size_t,
                    169:                          int, int, int, int, int);
                    170: int idt_vec_alloc(int, int);
                    171: void idt_vec_set(int, void (*)(void));
                    172: void idt_vec_free(int);
                    173: void cpu_init_idt(void);
                    174:
                    175: #endif /* _KERNEL */
                    176:
                    177: #endif /* !_LOCORE */
                    178:
                    179: /* system segments and gate types */
                    180: #define        SDT_SYSNULL      0      /* system null */
                    181: #define        SDT_SYS286TSS    1      /* system 286 TSS available */
                    182: #define        SDT_SYSLDT       2      /* system local descriptor table */
                    183: #define        SDT_SYS286BSY    3      /* system 286 TSS busy */
                    184: #define        SDT_SYS286CGT    4      /* system 286 call gate */
                    185: #define        SDT_SYSTASKGT    5      /* system task gate */
                    186: #define        SDT_SYS286IGT    6      /* system 286 interrupt gate */
                    187: #define        SDT_SYS286TGT    7      /* system 286 trap gate */
                    188: #define        SDT_SYSNULL2     8      /* system null again */
                    189: #define        SDT_SYS386TSS    9      /* system 386 TSS available */
                    190: #define        SDT_SYSNULL3    10      /* system null again */
                    191: #define        SDT_SYS386BSY   11      /* system 386 TSS busy */
                    192: #define        SDT_SYS386CGT   12      /* system 386 call gate */
                    193: #define        SDT_SYSNULL4    13      /* system null again */
                    194: #define        SDT_SYS386IGT   14      /* system 386 interrupt gate */
                    195: #define        SDT_SYS386TGT   15      /* system 386 trap gate */
                    196:
                    197: /* memory segment types */
                    198: #define        SDT_MEMRO       16      /* memory read only */
                    199: #define        SDT_MEMROA      17      /* memory read only accessed */
                    200: #define        SDT_MEMRW       18      /* memory read write */
                    201: #define        SDT_MEMRWA      19      /* memory read write accessed */
                    202: #define        SDT_MEMROD      20      /* memory read only expand dwn limit */
                    203: #define        SDT_MEMRODA     21      /* memory read only expand dwn limit accessed */
                    204: #define        SDT_MEMRWD      22      /* memory read write expand dwn limit */
                    205: #define        SDT_MEMRWDA     23      /* memory read write expand dwn limit acessed */
                    206: #define        SDT_MEME        24      /* memory execute only */
                    207: #define        SDT_MEMEA       25      /* memory execute only accessed */
                    208: #define        SDT_MEMER       26      /* memory execute read */
                    209: #define        SDT_MEMERA      27      /* memory execute read accessed */
                    210: #define        SDT_MEMEC       28      /* memory execute only conforming */
                    211: #define        SDT_MEMEAC      29      /* memory execute only accessed conforming */
                    212: #define        SDT_MEMERC      30      /* memory execute read conforming */
                    213: #define        SDT_MEMERAC     31      /* memory execute read accessed conforming */
                    214:
                    215: /* is memory segment descriptor pointer ? */
                    216: #define ISMEMSDP(s)    ((s->d_type) >= SDT_MEMRO && \
                    217:                         (s->d_type) <= SDT_MEMERAC)
                    218:
                    219: /* is 286 gate descriptor pointer ? */
                    220: #define IS286GDP(s)    ((s->d_type) >= SDT_SYS286CGT && \
                    221:                         (s->d_type) < SDT_SYS286TGT)
                    222:
                    223: /* is 386 gate descriptor pointer ? */
                    224: #define IS386GDP(s)    ((s->d_type) >= SDT_SYS386CGT && \
                    225:                         (s->d_type) < SDT_SYS386TGT)
                    226:
                    227: /* is gate descriptor pointer ? */
                    228: #define ISGDP(s)       (IS286GDP(s) || IS386GDP(s))
                    229:
                    230: /* is segment descriptor pointer ? */
                    231: #define ISSDP(s)       (ISMEMSDP(s) || !ISGDP(s))
                    232:
                    233: /* is system segment descriptor pointer ? */
                    234: #define ISSYSSDP(s)    (!ISMEMSDP(s) && !ISGDP(s))
                    235:
                    236: /*
                    237:  * Segment Protection Exception code bits
                    238:  */
                    239: #define        SEGEX_EXT       0x01    /* recursive or externally induced */
                    240: #define        SEGEX_IDT       0x02    /* interrupt descriptor table */
                    241: #define        SEGEX_TI        0x04    /* local descriptor table */
                    242:
                    243: /*
                    244:  * Entries in the Interrupt Descriptor Table (IDT)
                    245:  */
                    246: #define        NIDT    256
                    247: #define        NRSVIDT 32              /* reserved entries for cpu exceptions */
                    248:
                    249: /*
                    250:  * Entries in the Global Descriptor Table (GDT)
                    251:  * The code and data descriptors must come first. There
                    252:  * are NGDT_MEM of them.
                    253:  *
                    254:  * Then come the predefined LDT (and possibly TSS) descriptors.
                    255:  * There are NGDT_SYS of them.
                    256:  */
                    257: #define        GNULL_SEL       0       /* Null descriptor */
                    258: #define        GCODE_SEL       1       /* Kernel code descriptor */
                    259: #define        GDATA_SEL       2       /* Kernel data descriptor */
                    260: #define        GUCODE_SEL      3       /* User code descriptor */
                    261: #define        GUDATA_SEL      4       /* User data descriptor */
                    262: #define        GAPM32CODE_SEL  5
                    263: #define        GAPM16CODE_SEL  6
                    264: #define        GAPMDATA_SEL    7
                    265: #define        GBIOSCODE_SEL   8
                    266: #define        GBIOSDATA_SEL   9
                    267: #define GPNPBIOSCODE_SEL 10
                    268: #define GPNPBIOSDATA_SEL 11
                    269: #define GPNPBIOSSCRATCH_SEL 12
                    270: #define GPNPBIOSTRAMP_SEL 13
                    271: #define GUCODE32_SEL   14
                    272: #define GUDATA32_SEL   15
                    273: #define NGDT_MEM 16
                    274:
                    275: #define        GLDT_SEL        0       /* Default LDT descriptor */
                    276: #define NGDT_SYS       1
                    277:
                    278: #define GDT_SYS_OFFSET (NGDT_MEM << 3)
                    279:
                    280: #define GDT_ADDR_MEM(s,i)      \
                    281:     ((struct mem_segment_descriptor *)((s) + ((i) << 3)))
                    282: #define GDT_ADDR_SYS(s,i)      \
                    283:    ((struct sys_segment_descriptor *)((s) + (((i) << 4) + SYSSEL_START)))
                    284:
                    285: /*
                    286:  * Byte offsets in the Local Descriptor Table (LDT)
                    287:  * Strange order because of syscall/sysret insns
                    288:  */
                    289: #define        LSYS5CALLS_SEL  0       /* iBCS system call gate */
                    290: #define LUCODE32_SEL   8       /* 32 bit user code descriptor */
                    291: #define        LUDATA_SEL      16      /* User data descriptor */
                    292: #define        LUCODE_SEL      24      /* User code descriptor */
                    293: #define        LSOL26CALLS_SEL 32      /* Solaris 2.6 system call gate */
                    294: #define LUDATA32_SEL   56      /* 32 bit user data descriptor (needed?)*/
                    295: #define        LBSDICALLS_SEL  128     /* BSDI system call gate */
                    296:
                    297: #define LDT_SIZE       144
                    298:
                    299: #define LSYSRETBASE_SEL        LUCODE32_SEL
                    300:
                    301: /*
                    302:  * Checks for valid user selectors. If USER_LDT ever gets implemented
                    303:  * for amd64, these must check the ldt length and SEL_UPL if a user
                    304:  * ldt is active.
                    305:  */
                    306: #define VALID_USER_DSEL32(s) \
                    307:     ((s) == GSEL(GUDATA32_SEL, SEL_UPL) || (s) == LSEL(LUDATA32_SEL, SEL_UPL))
                    308: #define VALID_USER_CSEL32(s) \
                    309:     ((s) == GSEL(GUCODE32_SEL, SEL_UPL) || (s) == LSEL(LUCODE32_SEL, SEL_UPL))
                    310:
                    311: #define VALID_USER_CSEL(s) \
                    312:     ((s) == GSEL(GUCODE_SEL, SEL_UPL) || (s) == LSEL(LUCODE_SEL, SEL_UPL))
                    313: #define VALID_USER_DSEL(s) \
                    314:     ((s) == GSEL(GUDATA_SEL, SEL_UPL) || (s) == LSEL(LUDATA_SEL, SEL_UPL))
                    315:
                    316: #endif /* _AMD64_SEGMENTS_H_ */

CVSweb