Subversion Repositories shark

Rev

Rev 3 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 pj 1
/* Project:     OSLib
2
 * Description: The OS Construction Kit
3
 * Date:                1.6.2000
4
 * Idea by:             Luca Abeni & Gerardo Lamastra
5
 *
6
 * OSLib is an SO project aimed at developing a common, easy-to-use
7
 * low-level infrastructure for developing OS kernels and Embedded
8
 * Applications; it partially derives from the HARTIK project but it
9
 * currently is independently developed.
10
 *
11
 * OSLib is distributed under GPL License, and some of its code has
12
 * been derived from the Linux kernel source; also some important
13
 * ideas come from studying the DJGPP go32 extender.
14
 *
15
 * We acknowledge the Linux Community, Free Software Foundation,
16
 * D.J. Delorie and all the other developers who believe in the
17
 * freedom of software and ideas.
18
 *
19
 * For legalese, check out the included GPL license.
20
 */
21
 
22
/* These function provide access to hardware structutes GDT/IDT */
23
 
24
#include <ll/i386/cons.h>
25
#include <ll/i386/mem.h>
26
 
40 pj 27
FILE(X-SysTab);
2 pj 28
 
29
extern GATE IDT[256];
30
 
31
/* We usually need to set-up an interrupt handler; to do this we have */
32
/* to fill a GATE structure & copy it into the Interrupt Descriptor   */
33
/* Table or IDT; its phisical address is given by IDT_base            */
34
 
40 pj 35
void IDT_place(BYTE num,void (*handler)(void))
2 pj 36
{
40 pj 37
    DWORD offset = (DWORD)(handler);
2 pj 38
    IDT[num].sel = X_FLATCODE_SEL;
39
    /* Set DPL = 3, to allow execution of the gate from any ring */
40
    IDT[num].access = INT_GATE386 | 0x60;
41
    IDT[num].dword_cnt = 0;
42
    IDT[num].offset_lo = offset & 0xFFFF;
43
    offset >>= 16;
44
    IDT[num].offset_hi = offset & 0xFFFF;
45
}
46
 
47
/* Ok; the GDT is managed in the same way as the IDT                */
48
/* When a descriptor is cleared using it will cause a SEGMENT FAULT */
49
/* to refer such descriptor                                         */
50
 
40 pj 51
void GDT_place(WORD sel,DWORD base,DWORD lim,BYTE acc,BYTE gran)
2 pj 52
{
53
    union gdt_entry x;
54
    /* This is declared in [wc32/gnu]\x0.[asm/s] */
55
    extern LIN_ADDR GDT_base;
56
/*    DWORD offset = appl2linear(&x); */
57
    x.d.base_lo = (base & 0x0000FFFF);
58
    x.d.base_med = ((base & 0x00FF0000) >> 16);
59
    x.d.base_hi = ((base & 0xFF000000) >> 24);
60
    x.d.access = acc;
61
    x.d.lim_lo = (lim & 0xFFFF);
40 pj 62
    x.d.gran = (gran | ((lim >> 16) & 0x0F) | 0x40);    
63
    memcpy(GDT_base+(sel & ~3),&x,sizeof(union gdt_entry));
2 pj 64
}
65
 
66
/* This function is used to read & format the descriptor data */
67
/* Anyway is better to use the hw 386 instruction to modify   */
68
/* a descriptor rather than reading,modifying & updating with */
69
/* this high level functions!                                 */
70
 
40 pj 71
DWORD GDT_read(WORD sel,DWORD *lim,BYTE *acc,BYTE *gran)
2 pj 72
{
73
    union gdt_entry x;
74
    /* This is declared in [wc32/gnu]\x0.[asm/s] */
75
    extern LIN_ADDR GDT_base;
40 pj 76
    /*DWORD offset = appl2linear(&x);*/
2 pj 77
    DWORD base;
40 pj 78
    memcpy(&x,GDT_base+sel,sizeof(union gdt_entry));
2 pj 79
    base = x.d.base_hi;
80
    base <<= 8;
81
    base |= x.d.base_med;
82
    base <<= 16;
83
    base |= x.d.base_lo;
84
    if (lim != NULL) {
85
        *lim = (x.d.gran & 0x0F);
86
        *lim <<= 16;
87
        *lim |= x.d.lim_lo;
88
    }
40 pj 89
    if (acc != NULL) *acc = x.d.access;
90
    if (gran != NULL) *gran = x.d.gran & 0xF0;
91
    return(base);
2 pj 92
}