interrupt(i, 0);
}
- /* mask all IRQs by default */
- for(i=0; i<16; i++) {
- mask_irq(i);
- }
-
/* by including intrtab.h here the series of INTR_ENTRY_* macros will be
* expanded to a series of function prototypes for all interrupt entry
* points and the corresponding calls to set_intr_entry to set up the IDT
/* initialize the programmable interrupt controller
* setting up the maping of IRQs [0, 15] to interrupts [32, 47]
*/
- init_pic();
+ prog_pic(IRQ_OFFSET);
eoi_pending = 0;
}
+void cleanup_intr(void)
+{
+ disable_intr();
+ /* reprogram the PIC to the default BIOS offset (8) */
+ prog_pic(8);
+}
+
/* retrieve the current interrupt frame.
* returns 0 when called during init.
*/
panic("unhandled exception %u, error code: %u, at cs:eip=%x:%x\n",
frm.inum, frm.err, frm.cs, frm.eip);
}
- printf("unhandled interrupt %d\n", frm.inum);
+ /*printf("unhandled interrupt %d\n", frm.inum);*/
}
disable_intr();
}
}
-void init_pic(void)
-{
- prog_pic(IRQ_OFFSET);
-}
-
void prog_pic(int offs)
{
/* send ICW1 saying we'll follow with ICW4 later on */
*/
int dpl = (num == SYSCALL_INT) ? 3 : 0;
- gate_desc(idt + num, selector(SEGM_KCODE, 0), (uint32_t)handler, dpl, type);
+ gate_desc(idt + num, selector(SEGM_CODE, 0), (uint32_t)handler, dpl, type);
}
void set_pic_mask(int pic, unsigned char mask)
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
+#include <stdio.h>
#include <string.h>
#include "segm.h"
#include "desc.h"
static void segm_desc(desc_t *desc, uint32_t base, uint32_t limit, int dpl, int type);
static void segm_desc16(desc_t *desc, uint32_t base, uint32_t limit, int dpl, int type);
-static void task_desc(desc_t *desc, uint32_t base, uint32_t limit, int dpl);
+/*static void task_desc(desc_t *desc, uint32_t base, uint32_t limit, int dpl);*/
/* these functions are implemented in segm-asm.S */
void setup_selectors(uint16_t code, uint16_t data);
void set_gdt(uint32_t addr, uint16_t limit);
void set_task_reg(uint16_t tss_selector);
+static void dbg_print_gdt(void);
+static void print_desc(desc_t *desc);
/* our global descriptor table */
static desc_t gdt[NUM_SEGMENTS] __attribute__((aligned(8)));
-
+uint16_t orig_seg;
void init_segm(void)
{
+ asm volatile (
+ "mov %%fs, %0\n\t"
+ : "=a"(orig_seg));
+
memset(gdt, 0, sizeof gdt);
- segm_desc(gdt + SEGM_KCODE, 0, 0xffffffff, 0, TYPE_CODE);
- segm_desc(gdt + SEGM_KDATA, 0, 0xffffffff, 0, TYPE_DATA);
- segm_desc(gdt + SEGM_UCODE, 0, 0xffffffff, 3, TYPE_CODE);
- segm_desc(gdt + SEGM_UDATA, 0, 0xffffffff, 3, TYPE_DATA);
- segm_desc16(gdt + SEGM_CODE16, 0, 0xffff, 0, TYPE_CODE);
+ segm_desc(gdt + SEGM_CODE, 0, 0xffffffff, 0, TYPE_CODE);
+ segm_desc(gdt + SEGM_DATA, 0, 0xffffffff, 0, TYPE_DATA);
+ segm_desc(gdt + SEGM_XCODE, orig_seg << 4, 0xffffffff, 0, TYPE_CODE);
+ segm_desc(gdt + SEGM_XDATA, orig_seg << 4, 0xffffffff, 0, TYPE_DATA);
+ segm_desc16(gdt + SEGM_CODE16, orig_seg << 4, 0xffff, 0, TYPE_CODE);
set_gdt((uint32_t)gdt, sizeof gdt - 1);
- setup_selectors(selector(SEGM_KCODE, 0), selector(SEGM_KDATA, 0));
+ setup_selectors(selector(SEGM_CODE, 0), selector(SEGM_DATA, 0));
+
+ dbg_print_gdt();
}
/* constructs a GDT selector based on index and priviledge level */
return (idx << 3) | (rpl & 3);
}
+/*
void set_tss(uint32_t addr)
{
task_desc(gdt + SEGM_TASK, addr, sizeof(struct task_state) - 1, 3);
set_task_reg(selector(SEGM_TASK, 0));
}
+*/
static void segm_desc(desc_t *desc, uint32_t base, uint32_t limit, int dpl, int type)
{
desc->d[3] = 0;
}
+#if 0
static void task_desc(desc_t *desc, uint32_t base, uint32_t limit, int dpl)
{
desc->d[0] = limit & 0xffff;
TSS_TYPE_BITS; /* XXX busy ? */
desc->d[3] = ((limit >> 16) & 0xf) | ((base >> 16) & 0xff00) | BIT_GRAN;
}
-/*
+#endif
+
static void dbg_print_gdt(void)
{
int i;
printf("Global Descriptor Table\n");
printf("-----------------------\n");
- for(i=0; i<6; i++) {
+ for(i=0; i<NUM_SEGMENTS; i++) {
+ printf("%d: ", i);
print_desc(gdt + i);
}
}
static void print_desc(desc_t *desc)
{
uint32_t base, limit;
- int dpl, g, db, l, avl, p, s, type;
- char *type_str;
+ int dpl, g;
+
+ if((desc->d[0] | desc->d[1] | desc->d[2] | desc->d[3]) == 0) {
+ printf("null\n");
+ }
base = (uint32_t)desc->d[1] | ((uint32_t)(desc->d[2] & 0xff) << 16) | ((uint32_t)(desc->d[3] >> 8) << 24);
limit = (uint32_t)desc->d[0] | ((uint32_t)(desc->d[3] & 0xf) << 16);
dpl = (desc->d[2] >> 13) & 3;
- type = (desc->d[2] >> 8) & 0xf;
- g = (desc->d[3] >> 23) & 1;
- db = (desc->d[3] >> 22) & 1;
- l = (desc->d[3] >> 21) & 1;
- avl = (desc->d[3] >> 20) & 1;
-
- p = (desc->d[2] >> 15) & 1;
- s = (desc->d[2] >> 12) & 1;
+ g = (desc->d[3] >> 7) & 1;
+
+ if(g) limit = ((limit + 1) << 12) - 1;
+
+ printf("base:%x lim:%x dpl:%d type:%s %dbit\n", base, limit, dpl,
+ desc->d[2] & BIT_CODE ? "code" : "data", desc->d[3] & BIT_BIG ? 32 : 16);
}
-*/