Subversion Repositories shark

Rev

Rev 3 | Go to most recent revision | Details | 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
/*      Routines that implements threads (creation, end, dump, and AS
23
        assignment      */
24
 
25
#include <ll/i386/stdio.h>
26
#include <ll/i386/mem.h>
27
#include <ll/i386/cons.h>
28
#include <ll/i386/error.h>
29
 
30
#include <ll/i386/tss-ctx.h>
31
#include <ll/sys/ll/ll-instr.h> /* Only for HW instr... */
32
#include <ll/sys/ll/ll-func.h>
33
 
34
FILE(KL - Context - Switch);
35
 
36
extern TSS TSS_table[TSSMax];
37
extern WORD TSS_control[TSSMax];
38
extern BYTE ll_FPU_stdctx[FPU_CONTEXT_SIZE];
39
 
40
#ifdef __VIRCSW__
41
extern unsigned short int currCtx;
42
extern int activeInt;
43
#endif
44
 
45
extern DWORD entrypoint;
46
 
47
/* Just a debugging function; it dumps the status of the TSS */
48
void dump_TSS(WORD sel)
49
{
50
    BYTE acc, gran;
51
    DWORD base, lim;
52
    message("TR %x\n", sel);
53
    sel = TSSsel2index(sel);
54
    message("SS:SP %x:%lx\n", TSS_table[sel].ss, TSS_table[sel].esp);
55
    message("Stack0 : %x:%lx\n", TSS_table[sel].ss0, TSS_table[sel].esp0);
56
    message("Stack1 : %x:%lx\n", TSS_table[sel].ss1, TSS_table[sel].esp1);
57
    message("Stack2 : %x:%lx\n", TSS_table[sel].ss2, TSS_table[sel].esp2);
58
    message("CS : %x DS : %x\n", TSS_table[sel].cs, TSS_table[sel].ds);
59
    sel = TSSindex2sel(sel);
60
    message("Descriptor [%x] Info", sel);
61
    base = GDT_read(sel, &lim, &acc, &gran);
62
    message("Base : %lx Lim : %lx Acc : %x Gran %x\n", base, lim,
63
            (unsigned) (acc), (unsigned) (gran));
64
}
65
 
66
 
67
void ll_context_setspace(CONTEXT c, WORD as)
68
{
69
    int index = TSSsel2index(c);
70
 
71
    TSS_table[index].ss0 = as;
72
    TSS_table[index].cs = as + 8;
73
    TSS_table[index].es = as;
74
    TSS_table[index].ds = as;
75
    TSS_table[index].ss = as;
76
}
77
 
78
/* Initialize context -> TSS in 32 bit */
79
CONTEXT ll_context_create(void (*task) (void *p), BYTE * stack,
80
                          void *parm, void (*killer) (void), WORD control)
81
{
82
    CONTEXT index = 0;
83
    DWORD *stack_ptr = (DWORD *) stack;
84
 
85
    /* Push onto stack the input parameter              */
86
    /* And the entry point to the task killer procedure */
87
    stack_ptr--;
88
    *stack_ptr = (DWORD) (parm);
89
    stack_ptr--;
90
    *stack_ptr = (DWORD) (killer);
91
    /* Find a free TSS */
92
    while ((TSS_control[index] & TSS_USED) && (index < TSSMain))
93
        index++;
94
    /* This exception would signal an error */
95
    if (index >= TSSMain) {
96
        message("No more Descriptors...\n");
97
        return 0;
98
    }
99
    TSS_control[index] |= (TSS_USED | control);
100
    /* Fill the TSS structure */
101
    /* No explicit protection; use only one stack */
102
    TSS_table[index].esp0 = (DWORD) (stack_ptr);
103
    TSS_table[index].esp1 = 0;
104
    TSS_table[index].esp2 = 0;
105
    TSS_table[index].ss0 = get_DS();
106
    TSS_table[index].ss1 = 0;
107
    TSS_table[index].ss2 = 0;
108
    /* No paging activated */
109
    TSS_table[index].cr3 = 0;
110
    /* Task entry point */
111
    TSS_table[index].eip = (DWORD) (task);
112
    /* Need only to unmask interrupts */
113
    TSS_table[index].eflags = 0x00000200;
114
    TSS_table[index].eax = 0;
115
    TSS_table[index].ebx = 0;
116
    TSS_table[index].ecx = 0;
117
    TSS_table[index].edx = 0;
118
    TSS_table[index].esi = 0;
119
    TSS_table[index].edi = 0;
120
    TSS_table[index].esp = (DWORD) (stack_ptr);
121
    TSS_table[index].ebp = (DWORD) (stack_ptr);
122
    TSS_table[index].cs = get_CS();
123
    TSS_table[index].es = get_DS();
124
    TSS_table[index].ds = get_DS();
125
    TSS_table[index].ss = get_DS();
126
    TSS_table[index].gs = X_FLATDATA_SEL;
127
    TSS_table[index].fs = X_FLATDATA_SEL;
128
    /* Use only the GDT */
129
    TSS_table[index].ldt = 0;
130
    TSS_table[index].trap = 0;
131
    TSS_table[index].io_base = 0;
132
    /* Fill in the coprocessor status */
133
    memcpy(TSS_table[index].ctx_FPU, ll_FPU_stdctx, FPU_CONTEXT_SIZE);
134
    /* Convert the index into a valid selector  */
135
    /* Which really represent CONTEXT           */
136
    return (TSSindex2sel(index));
137
}
138
 
139
 
140
/* Release the used TSS */
141
 
142
void ll_context_delete(CONTEXT c)
143
{
144
    int index = TSSsel2index(c);
145
    TSS_control[index] = 0;
146
}
147
 
148
#if 0                           /* It does not work... Fix it!!! */
149
DWORD ll_push_func(void (*func) (void))
150
{
151
    DWORD *p;
152
    DWORD old;
153
 
154
    p = (DWORD *) entrypoint;
155
    old = *p;
156
 
157
    *p = (DWORD) func;
158
 
159
    return old;
160
}
161
#endif
162
 
163
/* Well this is used for debug purposes mainly; as the context is an       */
164
/* abstract type, we must provide some function to convert in into a       */
165
/* printable form; anyway this depend from the architecture as the context */
166
 
167
char *ll_context_sprintf(char *str, CONTEXT c)
168
{
169
    ksprintf(str, "%x (Hex)", c);
170
    return (str);
171
}