summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFreya Murphy <freya@freyacat.org>2025-04-08 10:49:18 -0400
committerFreya Murphy <freya@freyacat.org>2025-04-08 10:49:18 -0400
commitc8a1e0531d7ccdce5f76aec8a5b6147c686d3403 (patch)
tree2a68ab7da901a96fea975ca2ec02a9c77137686b
parenttty => term (diff)
downloadcomus-c8a1e0531d7ccdce5f76aec8a5b6147c686d3403.tar.gz
comus-c8a1e0531d7ccdce5f76aec8a5b6147c686d3403.tar.bz2
comus-c8a1e0531d7ccdce5f76aec8a5b6147c686d3403.zip
fix old checkout
-rw-r--r--kernel/old/Make.mk76
-rw-r--r--kernel/old/cio.c810
-rw-r--r--kernel/old/clock.c (renamed from kernel/old/drivers/clock.c)67
-rw-r--r--kernel/old/include/.vm.h.swpbin0 -> 24576 bytes
-rw-r--r--kernel/old/include/bindings.h73
-rw-r--r--kernel/old/include/bootstrap.h101
-rw-r--r--kernel/old/include/cio.h40
-rw-r--r--kernel/old/include/clock.h12
-rw-r--r--kernel/old/include/common.h31
-rw-r--r--kernel/old/include/compat.h27
-rw-r--r--kernel/old/include/debug.h243
-rw-r--r--kernel/old/include/defs.h89
-rw-r--r--kernel/old/include/elf.h235
-rw-r--r--kernel/old/include/kdefs.h113
-rw-r--r--kernel/old/include/klib.h8
-rw-r--r--kernel/old/include/kmem.h20
-rw-r--r--kernel/old/include/lib.h314
-rw-r--r--kernel/old/include/list.h6
-rw-r--r--kernel/old/include/offsets.h83
-rw-r--r--kernel/old/include/params.h10
-rw-r--r--kernel/old/include/procs.h145
-rw-r--r--kernel/old/include/serial.h3
-rw-r--r--kernel/old/include/sio.h28
-rw-r--r--kernel/old/include/support.h27
-rw-r--r--kernel/old/include/syscalls.h38
-rw-r--r--kernel/old/include/types.h53
-rw-r--r--kernel/old/include/udefs.h113
-rw-r--r--kernel/old/include/ulib.h315
-rw-r--r--kernel/old/include/user.h25
-rw-r--r--kernel/old/include/userids.h33
-rw-r--r--kernel/old/include/vm.h356
-rw-r--r--kernel/old/include/vmtables.h2
-rw-r--r--kernel/old/include/x86/arch.h350
-rw-r--r--kernel/old/include/x86/bios.h73
-rw-r--r--kernel/old/include/x86/ops.h266
-rw-r--r--kernel/old/include/x86/pic.h125
-rw-r--r--kernel/old/include/x86/pit.h75
-rw-r--r--kernel/old/include/x86/uart.h371
-rw-r--r--kernel/old/isrs.S18
-rw-r--r--kernel/old/kernel.c246
-rw-r--r--kernel/old/kernel.ld71
-rw-r--r--kernel/old/kmem.c272
-rw-r--r--kernel/old/list.c17
-rw-r--r--kernel/old/procs.c524
-rw-r--r--kernel/old/sio.c (renamed from kernel/old/drivers/serial.c)329
-rw-r--r--kernel/old/startup.S153
-rw-r--r--kernel/old/support.c122
-rw-r--r--kernel/old/syscalls.c402
-rw-r--r--kernel/old/user.c808
-rw-r--r--kernel/old/vm.c722
-rw-r--r--kernel/old/vmtables.c573
51 files changed, 4817 insertions, 4196 deletions
diff --git a/kernel/old/Make.mk b/kernel/old/Make.mk
new file mode 100644
index 0000000..ac8928d
--- /dev/null
+++ b/kernel/old/Make.mk
@@ -0,0 +1,76 @@
+#
+# Makefile fragment for the kernel components of the system.
+#
+# Makefile fragment for the kernel component of the system.
+#
+# THIS IS NOT A COMPLETE Makefile - run GNU make in the top-level
+# directory, and this will be pulled in automatically.
+#
+
+SUBDIRS += kernel
+
+###################
+# FILES SECTION #
+###################
+
+BOOT_OBJ := $(patsubst %.c, $(BUILDDIR)/%.o, $(BOOT_SRC))
+
+KERN_SRC := kernel/startup.S kernel/isrs.S \
+ kernel/cio.c kernel/clock.c kernel/kernel.c kernel/kmem.c \
+ kernel/list.c kernel/procs.c kernel/sio.c kernel/support.c \
+ kernel/syscalls.c kernel/user.c kernel/vm.c kernel/vmtables.c
+
+KERN_OBJ := $(patsubst %.c, $(BUILDDIR)/%.o, $(KERN_SRC))
+KERN_OBJ := $(patsubst %.S, $(BUILDDIR)/%.o, $(KERN_OBJ))
+
+KCFLAGS := -ggdb
+KLDFLAGS := -T kernel/kernel.ld
+KLIBS := -lkernel -lcommon
+
+###################
+# RULES SECTION #
+###################
+
+kernel: $(BUILDDIR)/kernel/kernel.b
+
+$(BUILDDIR)/kernel/%.o: kernel/%.c $(BUILDDIR)/.vars.CFLAGS
+ @mkdir -p $(@D)
+ $(CC) $(CFLAGS) $(KCFLAGS) -c -o $@ $<
+
+#$(BUILDDIR)/kernel/%.o: kernel/%.S $(BUILDDIR)/.vars.CFLAGS
+# @mkdir -p $(@D)
+# $(CPP) $(CPPFLAGS) -o $(@D)/$*.s $<
+# $(AS) $(ASFLAGS) $(KCFLAGS) -o $@ $(@D)/$*.s -a=$(@D)/$*.lst
+# $(RM) -f $(@D)/$*.s
+
+$(BUILDDIR)/kernel/%.o: kernel/%.S $(BUILDDIR)/.vars.CFLAGS
+ @mkdir -p $(@D)
+ $(CC) $(CFLAGS) $(KCFLAGS) -c -o $@ $<
+ $(OBJDUMP) -S $@ > $(@D)/$*.asm
+
+$(BUILDDIR)/kernel/kernel: $(KERN_OBJ)
+ @mkdir -p $(@D)
+ $(LD) $(KLDFLAGS) $(LDFLAGS) -o $@ $(KERN_OBJ) $(KLIBS)
+ $(OBJDUMP) -S $@ > $@.asm
+ $(NM) -n $@ > $@.sym
+ $(READELF) -a $@ > $@.info
+
+$(BUILDDIR)/kernel/kernel.b: $(BUILDDIR)/kernel/kernel
+ $(LD) $(LDFLAGS) -o $(BUILDDIR)/kernel/kernel.b -s \
+ --oformat binary -Ttext 0x10000 $(BUILDDIR)/kernel/kernel
+
+# some debugging assist rules
+$(BUILDDIR)/kernel/%.i: kernel/%.c $(BUILDDIR)/.vars.CFLAGS
+ @mkdir -p $(@D)
+ $(CC) $(CFLAGS) $(KCFLAGS) -E -c $< > $(@D)/$*.i
+
+$(BUILDDIR)/kernel/%.dat: $(BUILDDIR)/kernel/%.o
+ @mkdir -p $(@D)
+ $(OBJCOPY) -S -O binary -j .data $< $@
+ hexdump -C $@ > $(@D)/$*.hex
+
+$(BUILDDIR)/kernel/%.rodat: $(BUILDDIR)/kernel/%.o
+ @mkdir -p $(@D)
+ $(OBJCOPY) -S -O binary -j .rodata $< $@
+ hexdump -C $@ > $(@D)/$*.hex
+
diff --git a/kernel/old/cio.c b/kernel/old/cio.c
index deb6b76..cfff543 100644
--- a/kernel/old/cio.c
+++ b/kernel/old/cio.c
@@ -30,18 +30,18 @@
/*
** Bit masks for the lower five and eight bits of a value
*/
-#define BMASK5 0x1f
-#define BMASK8 0xff
+#define BMASK5 0x1f
+#define BMASK8 0xff
/*
** Video parameters
*/
-#define SCREEN_MIN_X 0
-#define SCREEN_MIN_Y 0
-#define SCREEN_X_SIZE 80
-#define SCREEN_Y_SIZE 25
-#define SCREEN_MAX_X (SCREEN_X_SIZE - 1)
-#define SCREEN_MAX_Y (SCREEN_Y_SIZE - 1)
+#define SCREEN_MIN_X 0
+#define SCREEN_MIN_Y 0
+#define SCREEN_X_SIZE 80
+#define SCREEN_Y_SIZE 25
+#define SCREEN_MAX_X ( SCREEN_X_SIZE - 1 )
+#define SCREEN_MAX_Y ( SCREEN_Y_SIZE - 1 )
/*
** Video state
@@ -55,56 +55,56 @@ static unsigned int max_x, max_y;
// pointer to input notification function
static void (*notify)(int);
-#ifdef SA_DEBUG
+#ifdef SA_DEBUG
#include <stdio.h>
-#define cio_putchar putchar
-#define cio_puts(x) fputs(x, stdout)
+#define cio_putchar putchar
+#define cio_puts(x) fputs( x, stdout )
#endif
+
/*
** VGA definitions.
*/
// calculate the memory address of a specific character position
// within VGA memory
-#define VIDEO_ADDR(x, y) \
- (unsigned short *)((VID_BASE_ADDR + 2 * ((y) * SCREEN_X_SIZE + (x))) | \
- 0x80000000)
+#define VIDEO_ADDR(x,y) ( unsigned short * ) \
+ ( VID_BASE_ADDR + 2 * ( (y) * SCREEN_X_SIZE + (x) ) )
// port addresses
-#define VGA_CTRL_IX_ADDR 0x3d4
-#define VGA_CTRL_CUR_HIGH 0x0e // cursor location, high byte
-#define VGA_CTRL_CUR_LOW 0x0f // cursor location, low byte
-#define VGA_CTRL_IX_DATA 0x3d5
+#define VGA_CTRL_IX_ADDR 0x3d4
+# define VGA_CTRL_CUR_HIGH 0x0e // cursor location, high byte
+# define VGA_CTRL_CUR_LOW 0x0f // cursor location, low byte
+#define VGA_CTRL_IX_DATA 0x3d5
// attribute bits
-#define VGA_ATT_BBI 0x80 // blink, or background intensity
-#define VGA_ATT_BGC 0x70 // background color
-#define VGA_ATT_FICS 0x80 // foreground intensity or char font select
-#define VGA_ATT_FGC 0x70 // foreground color
+#define VGA_ATT_BBI 0x80 // blink, or background intensity
+#define VGA_ATT_BGC 0x70 // background color
+#define VGA_ATT_FICS 0x80 // foreground intensity or char font select
+#define VGA_ATT_FGC 0x70 // foreground color
// color selections
-#define VGA_BG_BLACK 0x0000 // background colors
-#define VGA_BG_BLUE 0x1000
-#define VGA_BG_GREEN 0x2000
-#define VGA_BG_CYAN 0x3000
-#define VGA_BG_RED 0x4000
-#define VGA_BG_MAGENTA 0x5000
-#define VGA_BG_BROWN 0x6000
-#define VGA_BG_WHITE 0x7000
+#define VGA_BG_BLACK 0x0000 // background colors
+#define VGA_BG_BLUE 0x1000
+#define VGA_BG_GREEN 0x2000
+#define VGA_BG_CYAN 0x3000
+#define VGA_BG_RED 0x4000
+#define VGA_BG_MAGENTA 0x5000
+#define VGA_BG_BROWN 0x6000
+#define VGA_BG_WHITE 0x7000
-#define VGA_FG_BLACK 0x0000 // foreground colors
-#define VGA_FG_BLUE 0x0100
-#define VGA_FG_GREEN 0x0200
-#define VGA_FG_CYAN 0x0300
-#define VGA_FG_RED 0x0400
-#define VGA_FG_MAGENTA 0x0500
-#define VGA_FG_BROWN 0x0600
-#define VGA_FG_WHITE 0x0700
+#define VGA_FG_BLACK 0x0000 // foreground colors
+#define VGA_FG_BLUE 0x0100
+#define VGA_FG_GREEN 0x0200
+#define VGA_FG_CYAN 0x0300
+#define VGA_FG_RED 0x0400
+#define VGA_FG_MAGENTA 0x0500
+#define VGA_FG_BROWN 0x0600
+#define VGA_FG_WHITE 0x0700
// color combinations
-#define VGA_WHITE_ON_BLACK (VGA_FG_WHITE | VGA_BG_BLACK)
-#define VGA_BLACK_ON_WHITE (VGA_FG_BLACK | VGA_BG_WHITE)
+#define VGA_WHITE_ON_BLACK (VGA_FG_WHITE | VGA_BG_BLACK)
+#define VGA_BLACK_ON_WHITE (VGA_FG_BLACK | VGA_BG_WHITE)
/*
** Internal support routines.
@@ -113,40 +113,38 @@ static void (*notify)(int);
/*
** setcursor: set the cursor location (screen coordinates)
*/
-static void setcursor(void)
-{
+static void setcursor( void ) {
unsigned addr;
unsigned int y = curr_y;
- if (y > scroll_max_y) {
+ if( y > scroll_max_y ) {
y = scroll_max_y;
}
- addr = (unsigned)(y * SCREEN_X_SIZE + curr_x);
+ addr = (unsigned)( y * SCREEN_X_SIZE + curr_x );
- outb(VGA_CTRL_IX_ADDR, VGA_CTRL_CUR_HIGH);
- outb(VGA_CTRL_IX_DATA, (addr >> 8) & BMASK8);
- outb(VGA_CTRL_IX_ADDR, VGA_CTRL_CUR_LOW);
- outb(VGA_CTRL_IX_DATA, addr & BMASK8);
+ outb( VGA_CTRL_IX_ADDR, VGA_CTRL_CUR_HIGH );
+ outb( VGA_CTRL_IX_DATA, ( addr >> 8 ) & BMASK8 );
+ outb( VGA_CTRL_IX_ADDR, VGA_CTRL_CUR_LOW );
+ outb( VGA_CTRL_IX_DATA, addr & BMASK8 );
}
/*
** putchar_at: physical output to the video memory
*/
-static void putchar_at(unsigned int x, unsigned int y, unsigned int c)
-{
+static void putchar_at( unsigned int x, unsigned int y, unsigned int c ) {
/*
** If x or y is too big or small, don't do any output.
*/
- if (x <= max_x && y <= max_y) {
- unsigned short *addr = VIDEO_ADDR(x, y);
+ if( x <= max_x && y <= max_y ) {
+ unsigned short *addr = VIDEO_ADDR( x, y );
/*
** The character may have attributes associated with it; if
** so, use those, otherwise use white on black.
*/
- c &= 0xffff; // keep only the lower bytes
- if (c > BMASK8) {
+ c &= 0xffff; // keep only the lower bytes
+ if( c > BMASK8 ) {
*addr = (unsigned short)c;
} else {
*addr = (unsigned short)c | VGA_WHITE_ON_BLACK;
@@ -161,13 +159,12 @@ static void putchar_at(unsigned int x, unsigned int y, unsigned int c)
/*
** Set the scrolling region
*/
-void cio_setscroll(unsigned int s_min_x, unsigned int s_min_y,
- unsigned int s_max_x, unsigned int s_max_y)
-{
- scroll_min_x = bound(min_x, s_min_x, max_x);
- scroll_min_y = bound(min_y, s_min_y, max_y);
- scroll_max_x = bound(scroll_min_x, s_max_x, max_x);
- scroll_max_y = bound(scroll_min_y, s_max_y, max_y);
+void cio_setscroll( unsigned int s_min_x, unsigned int s_min_y,
+ unsigned int s_max_x, unsigned int s_max_y ) {
+ scroll_min_x = bound( min_x, s_min_x, max_x );
+ scroll_min_y = bound( min_y, s_min_y, max_y );
+ scroll_max_x = bound( scroll_min_x, s_max_x, max_x );
+ scroll_max_y = bound( scroll_min_y, s_max_y, max_y );
curr_x = scroll_min_x;
curr_y = scroll_min_y;
setcursor();
@@ -176,19 +173,17 @@ void cio_setscroll(unsigned int s_min_x, unsigned int s_min_y,
/*
** Cursor movement in the scroll region
*/
-void cio_moveto(unsigned int x, unsigned int y)
-{
- curr_x = bound(scroll_min_x, x + scroll_min_x, scroll_max_x);
- curr_y = bound(scroll_min_y, y + scroll_min_y, scroll_max_y);
+void cio_moveto( unsigned int x, unsigned int y ) {
+ curr_x = bound( scroll_min_x, x + scroll_min_x, scroll_max_x );
+ curr_y = bound( scroll_min_y, y + scroll_min_y, scroll_max_y );
setcursor();
}
/*
** The putchar family
*/
-void cio_putchar_at(unsigned int x, unsigned int y, unsigned int c)
-{
- if ((c & 0x7f) == '\n') {
+void cio_putchar_at( unsigned int x, unsigned int y, unsigned int c ) {
+ if( ( c & 0x7f ) == '\n' ) {
unsigned int limit;
/*
@@ -196,41 +191,43 @@ void cio_putchar_at(unsigned int x, unsigned int y, unsigned int c)
** leave it. If we're not in the scroll region, don't
** let this loop enter it.
*/
- if (x > scroll_max_x) {
+ if( x > scroll_max_x ) {
limit = max_x;
- } else if (x >= scroll_min_x) {
+ }
+ else if( x >= scroll_min_x ) {
limit = scroll_max_x;
- } else {
+ }
+ else {
limit = scroll_min_x - 1;
}
- while (x <= limit) {
- putchar_at(x, y, ' ');
+ while( x <= limit ) {
+ putchar_at( x, y, ' ' );
x += 1;
}
- } else {
- putchar_at(x, y, c);
+ }
+ else {
+ putchar_at( x, y, c );
}
}
#ifndef SA_DEBUG
-void cio_putchar(unsigned int c)
-{
+void cio_putchar( unsigned int c ) {
/*
** If we're off the bottom of the screen, scroll the window.
*/
- if (curr_y > scroll_max_y) {
- cio_scroll(curr_y - scroll_max_y);
+ if( curr_y > scroll_max_y ) {
+ cio_scroll( curr_y - scroll_max_y );
curr_y = scroll_max_y;
}
- switch (c & BMASK8) {
+ switch( c & BMASK8 ) {
case '\n':
/*
** Erase to the end of the line, then move to new line
** (actual scroll is delayed until next output appears).
*/
- while (curr_x <= scroll_max_x) {
- putchar_at(curr_x, curr_y, ' ');
+ while( curr_x <= scroll_max_x ) {
+ putchar_at( curr_x, curr_y, ' ' );
curr_x += 1;
}
curr_x = scroll_min_x;
@@ -242,9 +239,9 @@ void cio_putchar(unsigned int c)
break;
default:
- putchar_at(curr_x, curr_y, c);
+ putchar_at( curr_x, curr_y, c );
curr_x += 1;
- if (curr_x > scroll_max_x) {
+ if( curr_x > scroll_max_x ) {
curr_x = scroll_min_x;
curr_y += 1;
}
@@ -257,23 +254,21 @@ void cio_putchar(unsigned int c)
/*
** The puts family
*/
-void cio_puts_at(unsigned int x, unsigned int y, const char *str)
-{
+void cio_puts_at( unsigned int x, unsigned int y, const char *str ) {
unsigned int ch;
- while ((ch = *str++) != '\0' && x <= max_x) {
- cio_putchar_at(x, y, ch);
+ while( (ch = *str++) != '\0' && x <= max_x ) {
+ cio_putchar_at( x, y, ch );
x += 1;
}
}
#ifndef SA_DEBUG
-void cio_puts(const char *str)
-{
+void cio_puts( const char *str ) {
unsigned int ch;
- while ((ch = *str++) != '\0') {
- cio_putchar(ch);
+ while( (ch = *str++) != '\0' ) {
+ cio_putchar( ch );
}
}
#endif
@@ -281,41 +276,38 @@ void cio_puts(const char *str)
/*
** Write a "sized" buffer (like cio_puts(), but no NUL)
*/
-void cio_write(const char *buf, int length)
-{
- for (int i = 0; i < length; ++i) {
- cio_putchar(buf[i]);
+void cio_write( const char *buf, int length ) {
+ for( int i = 0; i < length; ++i ) {
+ cio_putchar( buf[i] );
}
}
-void cio_clearscroll(void)
-{
+void cio_clearscroll( void ) {
unsigned int nchars = scroll_max_x - scroll_min_x + 1;
unsigned int l;
unsigned int c;
- for (l = scroll_min_y; l <= scroll_max_y; l += 1) {
- unsigned short *to = VIDEO_ADDR(scroll_min_x, l);
+ for( l = scroll_min_y; l <= scroll_max_y; l += 1 ) {
+ unsigned short *to = VIDEO_ADDR( scroll_min_x, l );
- for (c = 0; c < nchars; c += 1) {
+ for( c = 0; c < nchars; c += 1 ) {
*to++ = ' ' | 0x0700;
}
}
}
-void cio_clearscreen(void)
-{
- unsigned short *to = VIDEO_ADDR(min_x, min_y);
- unsigned int nchars = (max_y - min_y + 1) * (max_x - min_x + 1);
+void cio_clearscreen( void ) {
+ unsigned short *to = VIDEO_ADDR( min_x, min_y );
+ unsigned int nchars = ( max_y - min_y + 1 ) * ( max_x - min_x + 1 );
- while (nchars > 0) {
+ while( nchars > 0 ) {
*to++ = ' ' | 0x0700;
nchars -= 1;
}
}
-void cio_scroll(unsigned int lines)
-{
+
+void cio_scroll( unsigned int lines ) {
unsigned short *from;
unsigned short *to;
int nchars = scroll_max_x - scroll_min_x + 1;
@@ -324,7 +316,7 @@ void cio_scroll(unsigned int lines)
/*
** If # of lines is the whole scrolling region or more, just clear.
*/
- if (lines > scroll_max_y - scroll_min_y) {
+ if( lines > scroll_max_y - scroll_min_y ) {
cio_clearscroll();
curr_x = scroll_min_x;
curr_y = scroll_min_y;
@@ -335,84 +327,85 @@ void cio_scroll(unsigned int lines)
/*
** Must copy it line by line.
*/
- for (line = scroll_min_y; line <= scroll_max_y - lines; line += 1) {
- from = VIDEO_ADDR(scroll_min_x, line + lines);
- to = VIDEO_ADDR(scroll_min_x, line);
- for (c = 0; c < nchars; c += 1) {
+ for( line = scroll_min_y; line <= scroll_max_y - lines; line += 1 ) {
+ from = VIDEO_ADDR( scroll_min_x, line + lines );
+ to = VIDEO_ADDR( scroll_min_x, line );
+ for( c = 0; c < nchars; c += 1 ) {
*to++ = *from++;
}
}
- for (; line <= scroll_max_y; line += 1) {
- to = VIDEO_ADDR(scroll_min_x, line);
- for (c = 0; c < nchars; c += 1) {
+ for( ; line <= scroll_max_y; line += 1 ) {
+ to = VIDEO_ADDR( scroll_min_x, line );
+ for( c = 0; c < nchars; c += 1 ) {
*to++ = ' ' | 0x0700;
}
}
}
-static int mypad(int x, int y, int extra, int padchar)
-{
- while (extra > 0) {
- if (x != -1 || y != -1) {
- cio_putchar_at(x, y, padchar);
+static int mypad( int x, int y, int extra, int padchar ) {
+ while( extra > 0 ) {
+ if( x != -1 || y != -1 ) {
+ cio_putchar_at( x, y, padchar );
x += 1;
- } else {
- cio_putchar(padchar);
+ }
+ else {
+ cio_putchar( padchar );
}
extra -= 1;
}
return x;
}
-static int mypadstr(int x, int y, char *str, int len, int width, int leftadjust,
- int padchar)
-{
+static int mypadstr( int x, int y, char *str, int len, int width,
+ int leftadjust, int padchar ) {
int extra;
- if (len < 0) {
- len = strlen(str);
+ if( len < 0 ) {
+ len = strlen( str );
}
extra = width - len;
- if (extra > 0 && !leftadjust) {
- x = mypad(x, y, extra, padchar);
+ if( extra > 0 && !leftadjust ) {
+ x = mypad( x, y, extra, padchar );
}
- if (x != -1 || y != -1) {
- cio_puts_at(x, y, str);
+ if( x != -1 || y != -1 ) {
+ cio_puts_at( x, y, str );
x += len;
- } else {
- cio_puts(str);
}
- if (extra > 0 && leftadjust) {
- x = mypad(x, y, extra, padchar);
+ else {
+ cio_puts( str );
+ }
+ if( extra > 0 && leftadjust ) {
+ x = mypad( x, y, extra, padchar );
}
return x;
}
-static void do_printf(int x, int y, char **f)
-{
+static void do_printf( int x, int y, char **f ) {
char *fmt = *f;
- int *ap;
- char buf[12];
+ int *ap;
+ char buf[ 12 ];
char ch;
char *str;
- int leftadjust;
- int width;
- int len;
- int padchar;
+ int leftadjust;
+ int width;
+ int len;
+ int padchar;
/*
** Get characters from the format string and process them
*/
- ap = (int *)(f + 1);
+ ap = (int *)( f + 1 );
+
+ while( (ch = *fmt++) != '\0' ) {
- while ((ch = *fmt++) != '\0') {
/*
** Is it the start of a format code?
*/
- if (ch == '%') {
+ if( ch == '%' ) {
+
/*
** Yes, get the padding and width options (if there).
** Alignment must come at the beginning, then fill,
@@ -425,17 +418,17 @@ static void do_printf(int x, int y, char **f)
ch = *fmt++;
- if (ch == '-') {
+ if( ch == '-' ) {
leftadjust = 1;
ch = *fmt++;
}
- if (ch == '0') {
+ if( ch == '0' ) {
padchar = '0';
ch = *fmt++;
}
- while (ch >= '0' && ch <= '9') {
+ while( ch >= '0' && ch <= '9' ) {
width *= 10;
width += ch - '0';
ch = *fmt++;
@@ -444,52 +437,55 @@ static void do_printf(int x, int y, char **f)
/*
** What data type do we have?
*/
- switch (ch) {
+ switch( ch ) {
+
case 'c':
// ch = *( (int *)ap )++;
ch = *ap++;
- buf[0] = ch;
- buf[1] = '\0';
- x = mypadstr(x, y, buf, 1, width, leftadjust, padchar);
+ buf[ 0 ] = ch;
+ buf[ 1 ] = '\0';
+ x = mypadstr( x, y, buf, 1, width, leftadjust, padchar );
break;
case 'd':
// len = cvtdec( buf, *( (int *)ap )++ );
- len = cvtdec(buf, *ap++);
- x = mypadstr(x, y, buf, len, width, leftadjust, padchar);
+ len = cvtdec( buf, *ap++ );
+ x = mypadstr( x, y, buf, len, width, leftadjust, padchar );
break;
case 's':
// str = *( (char **)ap )++;
- str = (char *)(*ap++);
- x = mypadstr(x, y, str, -1, width, leftadjust, padchar);
+ str = (char *) (*ap++);
+ x = mypadstr( x, y, str, -1, width, leftadjust, padchar );
break;
case 'x':
// len = cvthex( buf, *( (int *)ap )++ );
- len = cvthex(buf, *ap++);
- x = mypadstr(x, y, buf, len, width, leftadjust, padchar);
+ len = cvthex( buf, *ap++ );
+ x = mypadstr( x, y, buf, len, width, leftadjust, padchar );
break;
case 'o':
// len = cvtoct( buf, *( (int *)ap )++ );
- len = cvtoct(buf, *ap++);
- x = mypadstr(x, y, buf, len, width, leftadjust, padchar);
+ len = cvtoct( buf, *ap++ );
+ x = mypadstr( x, y, buf, len, width, leftadjust, padchar );
break;
case 'u':
- len = cvtuns(buf, *ap++);
- x = mypadstr(x, y, buf, len, width, leftadjust, padchar);
+ len = cvtuns( buf, *ap++ );
+ x = mypadstr( x, y, buf, len, width, leftadjust, padchar );
break;
+
}
} else {
+
/*
** No - just print it normally.
*/
- if (x != -1 || y != -1) {
- cio_putchar_at(x, y, ch);
- switch (ch) {
+ if( x != -1 || y != -1 ) {
+ cio_putchar_at( x, y, ch );
+ switch( ch ) {
case '\n':
y += 1;
/* FALL THRU */
@@ -501,352 +497,129 @@ static void do_printf(int x, int y, char **f)
default:
x += 1;
}
- } else {
- cio_putchar(ch);
+ }
+ else {
+ cio_putchar( ch );
}
}
}
}
-void cio_printf_at(unsigned int x, unsigned int y, char *fmt, ...)
-{
- do_printf(x, y, &fmt);
+void cio_printf_at( unsigned int x, unsigned int y, char *fmt, ... ) {
+ do_printf( x, y, &fmt );
}
-void cio_printf(char *fmt, ...)
-{
- do_printf(-1, -1, &fmt);
+void cio_printf( char *fmt, ... ) {
+ do_printf( -1, -1, &fmt );
}
/*
** These are the "standard" IBM AT "Set 1" keycodes.
*/
-static unsigned char scan_code[2][128] = { { // unshifted characters
- /* 00-07 */ '\377',
- '\033',
- '1',
- '2',
- '3',
- '4',
- '5',
- '6',
- /* 08-0f */ '7',
- '8',
- '9',
- '0',
- '-',
- '=',
- '\b',
- '\t',
- /* 10-17 */ 'q',
- 'w',
- 'e',
- 'r',
- 't',
- 'y',
- 'u',
- 'i',
- /* 18-1f */ 'o',
- 'p',
- '[',
- ']',
- '\n',
- '\377',
- 'a',
- 's',
- /* 20-27 */ 'd',
- 'f',
- 'g',
- 'h',
- 'j',
- 'k',
- 'l',
- ';',
- /* 28-2f */ '\'',
- '`',
- '\377',
- '\\',
- 'z',
- 'x',
- 'c',
- 'v',
- /* 30-37 */ 'b',
- 'n',
- 'm',
- ',',
- '.',
- '/',
- '\377',
- '*',
- /* 38-3f */ '\377',
- ' ',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 40-47 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '7',
- /* 48-4f */ '8',
- '9',
- '-',
- '4',
- '5',
- '6',
- '+',
- '1',
- /* 50-57 */ '2',
- '3',
- '0',
- '.',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 58-5f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 60-67 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 68-6f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 70-77 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 78-7f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377' },
+static unsigned char scan_code[ 2 ][ 128 ] = {
+ { // unshifted characters
+/* 00-07 */ '\377', '\033', '1', '2', '3', '4', '5', '6',
+/* 08-0f */ '7', '8', '9', '0', '-', '=', '\b', '\t',
+/* 10-17 */ 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i',
+/* 18-1f */ 'o', 'p', '[', ']', '\n', '\377', 'a', 's',
+/* 20-27 */ 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';',
+/* 28-2f */ '\'', '`', '\377', '\\', 'z', 'x', 'c', 'v',
+/* 30-37 */ 'b', 'n', 'm', ',', '.', '/', '\377', '*',
+/* 38-3f */ '\377', ' ', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 40-47 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '7',
+/* 48-4f */ '8', '9', '-', '4', '5', '6', '+', '1',
+/* 50-57 */ '2', '3', '0', '.', '\377', '\377', '\377', '\377',
+/* 58-5f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 60-67 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 68-6f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 70-77 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 78-7f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377'
+ },
- { // shifted characters
- /* 00-07 */ '\377',
- '\033',
- '!',
- '@',
- '#',
- '$',
- '%',
- '^',
- /* 08-0f */ '&',
- '*',
- '(',
- ')',
- '_',
- '+',
- '\b',
- '\t',
- /* 10-17 */ 'Q',
- 'W',
- 'E',
- 'R',
- 'T',
- 'Y',
- 'U',
- 'I',
- /* 18-1f */ 'O',
- 'P',
- '{',
- '}',
- '\n',
- '\377',
- 'A',
- 'S',
- /* 20-27 */ 'D',
- 'F',
- 'G',
- 'H',
- 'J',
- 'K',
- 'L',
- ':',
- /* 28-2f */ '"',
- '~',
- '\377',
- '|',
- 'Z',
- 'X',
- 'C',
- 'V',
- /* 30-37 */ 'B',
- 'N',
- 'M',
- '<',
- '>',
- '?',
- '\377',
- '*',
- /* 38-3f */ '\377',
- ' ',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 40-47 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '7',
- /* 48-4f */ '8',
- '9',
- '-',
- '4',
- '5',
- '6',
- '+',
- '1',
- /* 50-57 */ '2',
- '3',
- '0',
- '.',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 58-5f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 60-67 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 68-6f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 70-77 */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- /* 78-7f */ '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377',
- '\377' } };
+ { // shifted characters
+/* 00-07 */ '\377', '\033', '!', '@', '#', '$', '%', '^',
+/* 08-0f */ '&', '*', '(', ')', '_', '+', '\b', '\t',
+/* 10-17 */ 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I',
+/* 18-1f */ 'O', 'P', '{', '}', '\n', '\377', 'A', 'S',
+/* 20-27 */ 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':',
+/* 28-2f */ '"', '~', '\377', '|', 'Z', 'X', 'C', 'V',
+/* 30-37 */ 'B', 'N', 'M', '<', '>', '?', '\377', '*',
+/* 38-3f */ '\377', ' ', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 40-47 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '7',
+/* 48-4f */ '8', '9', '-', '4', '5', '6', '+', '1',
+/* 50-57 */ '2', '3', '0', '.', '\377', '\377', '\377', '\377',
+/* 58-5f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 60-67 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 68-6f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 70-77 */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377',
+/* 78-7f */ '\377', '\377', '\377', '\377', '\377', '\377', '\377', '\377'
+ }
+};
/*
** Scan code masks
*/
// 'release' bit
-#define REL_BIT 0x80
-#define CODE_BITS 0x7f
+#define REL_BIT 0x80
+#define CODE_BITS 0x7f
-#define IS_PRESS(c) (((c) & REL_BIT) == 0)
-#define IS_RELEASE(c) (((c) & REL_BIT) != 0)
+#define IS_PRESS(c) (((c) & REL_BIT) == 0)
+#define IS_RELEASE(c) (((c) & REL_BIT) != 0)
/*
** Scan codes for some special characters
*/
// escape code - followed by another code byte
-#define SCAN_ESC 0xe0
+#define SCAN_ESC 0xe0
// shift keys: press, release
-#define L_SHIFT_DN 0x2a
-#define R_SHIFT_DN 0x36
-#define L_SHIFT_UP 0xaa
-#define R_SHIFT_UP 0xb6
+#define L_SHIFT_DN 0x2a
+#define R_SHIFT_DN 0x36
+#define L_SHIFT_UP 0xaa
+#define R_SHIFT_UP 0xb6
// control keys
-#define L_CTRL_DN 0x1d
-#define L_CTRL_UP 0x9d
+#define L_CTRL_DN 0x1d
+#define L_CTRL_UP 0x9d
/*
** I/O communication constants
*/
-#define KBD_DATA 0x60
-#define KBD_STATUS 0x64
-#define READY 0x1
+#define KBD_DATA 0x60
+#define KBD_STATUS 0x64
+#define READY 0x1
/*
** Circular buffer for input characters. Characters are inserted at
** next_space, and are removed at next_char. Buffer is empty if
** these are equal.
*/
-#define C_BUFSIZE 200
+#define C_BUFSIZE 200
-static char input_buffer[C_BUFSIZE];
+static char input_buffer[ C_BUFSIZE ];
static volatile char *next_char = input_buffer;
static volatile char *next_space = input_buffer;
-static volatile char *increment(volatile char *pointer)
-{
- if (++pointer >= input_buffer + C_BUFSIZE) {
+static volatile char *increment( volatile char *pointer ) {
+ if( ++pointer >= input_buffer + C_BUFSIZE ) {
pointer = input_buffer;
}
return pointer;
}
-static int input_scan_code(int code)
-{
- static int shift = 0;
- static int ctrl_mask = BMASK8;
+static int input_scan_code( int code ) {
+ static int shift = 0;
+ static int ctrl_mask = BMASK8;
int rval = -1;
/*
** Do the shift processing
*/
code &= BMASK8;
- switch (code) {
+ switch( code ) {
case L_SHIFT_DN:
case R_SHIFT_DN:
shift = 1;
@@ -870,76 +643,74 @@ static int input_scan_code(int code)
** Process ordinary characters only on the press (to handle
** autorepeat). Ignore undefined scan codes.
*/
- if (IS_PRESS(code)) {
- code = scan_code[shift][(int)code];
- if (code != '\377') {
- volatile char *next = increment(next_space);
+ if( IS_PRESS(code) ) {
+ code = scan_code[ shift ][ (int)code ];
+ if( code != '\377' ) {
+ volatile char *next = increment( next_space );
/*
** Store character only if there's room
*/
rval = code & ctrl_mask;
- if (next != next_char) {
+ if( next != next_char ) {
*next_space = code & ctrl_mask;
next_space = next;
}
}
}
}
- return (rval);
+ return( rval );
}
-static void keyboard_isr(int vector, int code)
-{
- int data = inb(KBD_DATA);
- int val = input_scan_code(data);
+static void keyboard_isr( int vector, int code ) {
+
+ int data = inb( KBD_DATA );
+ int val = input_scan_code( data );
// if there is a notification function, call it
- if (val != -1 && notify)
- notify(val);
+ if( val != -1 && notify )
+ notify( val );
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
}
-int cio_getchar(void)
-{
- char c;
+int cio_getchar( void ) {
+ char c;
int interrupts_enabled = r_eflags() & EFL_IF;
- while (next_char == next_space) {
- if (!interrupts_enabled) {
+ while( next_char == next_space ) {
+ if( !interrupts_enabled ) {
/*
** Must read the next keystroke ourselves.
*/
- while ((inb(KBD_STATUS) & READY) == 0) {
+ while( ( inb( KBD_STATUS ) & READY ) == 0 ) {
;
}
- (void)input_scan_code(inb(KBD_DATA));
+ (void) input_scan_code( inb( KBD_DATA ) );
}
}
c = *next_char & BMASK8;
- next_char = increment(next_char);
- if (c != EOT) {
- cio_putchar(c);
+ next_char = increment( next_char );
+ if( c != EOT ) {
+ cio_putchar( c );
}
return c;
}
-int cio_gets(char *buffer, unsigned int size)
-{
- char ch;
+int cio_gets( char *buffer, unsigned int size ) {
+ char ch;
int count = 0;
- while (size > 1) {
+ while( size > 1 ) {
ch = cio_getchar();
- if (ch == EOT) {
+ if( ch == EOT ) {
break;
}
*buffer++ = ch;
count += 1;
size -= 1;
- if (ch == '\n') {
+ if( ch == '\n' ) {
break;
}
}
@@ -947,11 +718,10 @@ int cio_gets(char *buffer, unsigned int size)
return count;
}
-int cio_input_queue(void)
-{
+int cio_input_queue( void ) {
int n_chars = next_space - next_char;
- if (n_chars < 0) {
+ if( n_chars < 0 ) {
n_chars += C_BUFSIZE;
}
return n_chars;
@@ -960,15 +730,14 @@ int cio_input_queue(void)
/*
** Initialization routines
*/
-void cio_init(void (*fcn)(int))
-{
+void cio_init( void (*fcn)(int) ) {
/*
** Screen dimensions
*/
- min_x = SCREEN_MIN_X;
- min_y = SCREEN_MIN_Y;
- max_x = SCREEN_MAX_X;
- max_y = SCREEN_MAX_Y;
+ min_x = SCREEN_MIN_X;
+ min_y = SCREEN_MIN_Y;
+ max_x = SCREEN_MAX_X;
+ max_y = SCREEN_MAX_Y;
/*
** Scrolling region
@@ -993,35 +762,34 @@ void cio_init(void (*fcn)(int))
/*
** Set up the interrupt handler for the keyboard
*/
- install_isr(VEC_KBD, keyboard_isr);
+ install_isr( VEC_KBD, keyboard_isr );
}
#ifdef SA_DEBUG
-int main()
-{
- cio_printf("%d\n", 123);
- cio_printf("%d\n", -123);
- cio_printf("%d\n", 0x7fffffff);
- cio_printf("%d\n", 0x80000001);
- cio_printf("%d\n", 0x80000000);
- cio_printf("x%14dy\n", 0x80000000);
- cio_printf("x%-14dy\n", 0x80000000);
- cio_printf("x%014dy\n", 0x80000000);
- cio_printf("x%-014dy\n", 0x80000000);
- cio_printf("%s\n", "xyz");
- cio_printf("|%10s|\n", "xyz");
- cio_printf("|%-10s|\n", "xyz");
- cio_printf("%c\n", 'x');
- cio_printf("|%4c|\n", 'y');
- cio_printf("|%-4c|\n", 'y');
- cio_printf("|%04c|\n", 'y');
- cio_printf("|%-04c|\n", 'y');
- cio_printf("|%3d|\n", 5);
- cio_printf("|%3d|\n", 54321);
- cio_printf("%x\n", 0x123abc);
- cio_printf("|%04x|\n", 20);
- cio_printf("|%012x|\n", 0xfedcba98);
- cio_printf("|%-012x|\n", 0x76543210);
+int main() {
+ cio_printf( "%d\n", 123 );
+ cio_printf( "%d\n", -123 );
+ cio_printf( "%d\n", 0x7fffffff );
+ cio_printf( "%d\n", 0x80000001 );
+ cio_printf( "%d\n", 0x80000000 );
+ cio_printf( "x%14dy\n", 0x80000000 );
+ cio_printf( "x%-14dy\n", 0x80000000 );
+ cio_printf( "x%014dy\n", 0x80000000 );
+ cio_printf( "x%-014dy\n", 0x80000000 );
+ cio_printf( "%s\n", "xyz" );
+ cio_printf( "|%10s|\n", "xyz" );
+ cio_printf( "|%-10s|\n", "xyz" );
+ cio_printf( "%c\n", 'x' );
+ cio_printf( "|%4c|\n", 'y' );
+ cio_printf( "|%-4c|\n", 'y' );
+ cio_printf( "|%04c|\n", 'y' );
+ cio_printf( "|%-04c|\n", 'y' );
+ cio_printf( "|%3d|\n", 5 );
+ cio_printf( "|%3d|\n", 54321 );
+ cio_printf( "%x\n", 0x123abc );
+ cio_printf( "|%04x|\n", 20 );
+ cio_printf( "|%012x|\n", 0xfedcba98 );
+ cio_printf( "|%-012x|\n", 0x76543210 );
}
int curr_x, curr_y, max_x, max_y;
diff --git a/kernel/old/drivers/clock.c b/kernel/old/clock.c
index 9f3d4be..96f71c4 100644
--- a/kernel/old/drivers/clock.c
+++ b/kernel/old/clock.c
@@ -1,3 +1,11 @@
+/**
+** @file clock.c
+**
+** @author CSCI-452 class of 20245
+**
+** @brief Clock module implementation
+*/
+
#define KERNEL_SRC
#include <common.h>
@@ -22,8 +30,8 @@
*/
// pinwheel control variables
-static uint32_t pinwheel; // pinwheel counter
-static uint32_t pindex; // index into pinwheel string
+static uint32_t pinwheel; // pinwheel counter
+static uint32_t pindex; // index into pinwheel string
/*
** PUBLIC GLOBAL VARIABLES
@@ -44,15 +52,15 @@ uint32_t system_time;
** @param vector Vector number for the clock interrupt
** @param code Error code (0 for this interrupt)
*/
-static void clk_isr(int vector, int code)
-{
+static void clk_isr( int vector, int code ) {
+
// spin the pinwheel
++pinwheel;
- if (pinwheel == (CLOCK_FREQ / 10)) {
+ if( pinwheel == (CLOCK_FREQ / 10) ) {
pinwheel = 0;
++pindex;
- cio_putchar_at(0, 0, "|/-\\"[pindex & 3]);
+ cio_putchar_at( 0, 0, "|/-\\"[ pindex & 3 ] );
}
#if defined(SYSTEM_STATUS)
@@ -62,11 +70,14 @@ static void clk_isr(int vector, int code)
// Define the symbol SYSTEM_STATUS with a value equal to the desired
// reporting frequency, in seconds.
- if ((system_time % SEC_TO_TICKS(SYSTEM_STATUS)) == 0) {
- cio_printf_at(1, 0, " queues: R[%u] W[%u] S[%u] Z[%u] I[%u] ",
- pcb_queue_length(ready), pcb_queue_length(waiting),
- pcb_queue_length(sleeping), pcb_queue_length(zombie),
- pcb_queue_length(sioread));
+ if( (system_time % SEC_TO_TICKS(SYSTEM_STATUS)) == 0 ) {
+ cio_printf_at( 1, 0, " queues: R[%u] W[%u] S[%u] Z[%u] I[%u] ",
+ pcb_queue_length(ready),
+ pcb_queue_length(waiting),
+ pcb_queue_length(sleeping),
+ pcb_queue_length(zombie),
+ pcb_queue_length(sioread)
+ );
}
#endif
@@ -80,42 +91,42 @@ static void clk_isr(int vector, int code)
do {
// if there isn't anyone in the sleep queue, we're done
- if (pcb_queue_empty(sleeping)) {
+ if( pcb_queue_empty(sleeping) ) {
break;
}
// peek at the first member of the queue
- pcb_t *tmp = pcb_queue_peek(sleeping);
- assert(tmp != NULL);
+ pcb_t *tmp = pcb_queue_peek( sleeping );
+ assert( tmp != NULL );
// the sleep queue is sorted in ascending order by wakeup
// time, so we know that the retrieved PCB's wakeup time is
// the earliest of any process on the sleep queue; if that
// time hasn't arrived yet, there's nobody left to awaken
- if (tmp->wakeup > system_time) {
+ if( tmp->wakeup > system_time ) {
break;
}
// OK, we need to wake this process up
- assert(pcb_queue_remove(sleeping, &tmp) == SUCCESS);
- schedule(tmp);
- } while (1);
+ assert( pcb_queue_remove(sleeping,&tmp) == SUCCESS );
+ schedule( tmp );
+ } while( 1 );
// next, we decrement the current process' remaining time
current->ticks -= 1;
// has it expired?
- if (current->ticks < 1) {
+ if( current->ticks < 1 ) {
// yes! reschedule it
- schedule(current);
+ schedule( current );
current = NULL;
// and pick a new process
dispatch();
}
// tell the PIC we're done
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
}
/*
@@ -128,10 +139,10 @@ static void clk_isr(int vector, int code)
** Initializes the clock module
**
*/
-void clk_init(void)
-{
+void clk_init( void ) {
+
#if TRACING_INIT
- cio_puts(" Clock");
+ cio_puts( " Clock" );
#endif
// start the pinwheel
@@ -143,10 +154,10 @@ void clk_init(void)
// configure the clock
uint32_t divisor = PIT_FREQ / CLOCK_FREQ;
- outb(PIT_CONTROL_PORT, PIT_0_LOAD | PIT_0_SQUARE);
- outb(PIT_0_PORT, divisor & 0xff); // LSB of divisor
- outb(PIT_0_PORT, (divisor >> 8) & 0xff); // MSB of divisor
+ outb( PIT_CONTROL_PORT, PIT_0_LOAD | PIT_0_SQUARE );
+ outb( PIT_0_PORT, divisor & 0xff ); // LSB of divisor
+ outb( PIT_0_PORT, (divisor >> 8) & 0xff ); // MSB of divisor
// register the second-stage ISR
- install_isr(VEC_TIMER, clk_isr);
+ install_isr( VEC_TIMER, clk_isr );
}
diff --git a/kernel/old/include/.vm.h.swp b/kernel/old/include/.vm.h.swp
new file mode 100644
index 0000000..eb334b9
--- /dev/null
+++ b/kernel/old/include/.vm.h.swp
Binary files differ
diff --git a/kernel/old/include/bindings.h b/kernel/old/include/bindings.h
deleted file mode 100644
index 365abc9..0000000
--- a/kernel/old/include/bindings.h
+++ /dev/null
@@ -1,73 +0,0 @@
-/**
- * @file bindings.h
- * @author Freya Murphy <freya@freyacat.org>
- *
- * C-style function definitions binded to their named assembly instruction.
- */
-
-#ifndef _BINDINGS_H
-#define _BINDINGS_H
-#include <types.h>
-
-static inline uint8_t inb(uint16_t port)
-{
- uint8_t ret;
- __asm__ volatile("inb %1, %0" : "=a"(ret) : "Nd"(port));
- return ret;
-}
-
-static inline void outb(uint16_t port, uint8_t val)
-{
- __asm__ volatile("outb %0, %1" : : "a"(val), "Nd"(port));
-}
-
-static inline uint16_t inw(uint16_t port)
-{
- uint16_t ret;
- __asm__ volatile("inw %1, %0" : "=a"(ret) : "Nd"(port));
- return ret;
-}
-
-static inline void outw(uint16_t port, uint16_t val)
-{
- __asm__ volatile("outw %0, %1" : : "a"(val), "Nd"(port));
-}
-
-static inline uint32_t inl(uint16_t port)
-{
- uint32_t ret;
- __asm__ volatile("inl %1, %0" : "=a"(ret) : "Nd"(port));
- return ret;
-}
-
-static inline void outl(uint16_t port, uint32_t val)
-{
- __asm__ volatile("outl %0, %1" : : "a"(val), "Nd"(port));
-}
-
-static inline void io_wait(void)
-{
- outb(0x80, 0);
-}
-
-static inline void sti(void)
-{
- __asm__ volatile("sti");
-}
-
-static inline void cli(void)
-{
- __asm__ volatile("cli");
-}
-
-static inline void int_wait(void)
-{
- __asm__ volatile("sti; hlt");
-}
-
-static inline void halt(void)
-{
- __asm__ volatile("cli; hlt");
-}
-
-#endif /* bindings.h */
diff --git a/kernel/old/include/bootstrap.h b/kernel/old/include/bootstrap.h
index 6c6dfcc..ade778a 100644
--- a/kernel/old/include/bootstrap.h
+++ b/kernel/old/include/bootstrap.h
@@ -9,89 +9,89 @@
** Addresses where various stuff goes in memory.
*/
-#ifndef BOOTSTRAP_H_
-#define BOOTSTRAP_H_
+#ifndef BOOTSTRAP_H_
+#define BOOTSTRAP_H_
/*
** The boot device
*/
-#define BDEV_FLOPPY 0x00
-#define BDEV_USB 0x80 /* hard drive */
+#define BDEV_FLOPPY 0x00
+#define BDEV_USB 0x80 /* hard drive */
-#define BDEV BDEV_USB /* default */
+#define BDEV BDEV_USB /* default */
/*
** Bootstrap definitions
*/
-#define BOOT_SEG 0x07c0 /* 07c0:0000 */
-#define BOOT_DISP 0x0000
-#define BOOT_ADDR ((BOOT_SEG << 4) + BOOT_DISP)
+#define BOOT_SEG 0x07c0 /* 07c0:0000 */
+#define BOOT_DISP 0x0000
+#define BOOT_ADDR ((BOOT_SEG << 4) + BOOT_DISP)
-#define PART2_DISP 0x0200 /* 07c0:0200 */
-#define PART2_ADDR ((BOOT_SEG << 4) + PART2_DISP)
+#define PART2_DISP 0x0200 /* 07c0:0200 */
+#define PART2_ADDR ((BOOT_SEG << 4) + PART2_DISP)
-#define SECTOR_SIZE 0x200 /* 512 bytes */
+#define SECTOR_SIZE 0x200 /* 512 bytes */
/* Note: this assumes the bootstrap is two sectors long! */
-#define BOOT_SIZE (SECTOR_SIZE + SECTOR_SIZE)
+#define BOOT_SIZE (SECTOR_SIZE + SECTOR_SIZE)
-#define OFFSET_LIMIT (0x10000 - SECTOR_SIZE)
+#define OFFSET_LIMIT (0x10000 - SECTOR_SIZE)
-#define BOOT_SP_DISP 0x4000 /* stack pointer 07c0:4000, or 0xbc00 */
-#define BOOT_SP_ADDR ((BOOT_SEG << 4) + BOOT_SP_DISP)
+#define BOOT_SP_DISP 0x4000 /* stack pointer 07c0:4000, or 0xbc00 */
+#define BOOT_SP_ADDR ((BOOT_SEG << 4) + BOOT_SP_DISP)
-#define SECTOR1_END (BOOT_ADDR + SECTOR_SIZE)
-#define SECTOR2_END (BOOT_ADDR + BOOT_SIZE)
+#define SECTOR1_END (BOOT_ADDR + SECTOR_SIZE)
+#define SECTOR2_END (BOOT_ADDR + BOOT_SIZE)
// location of the user blob data
// (three halfwords of data)
-#define USER_BLOB_DATA (SECTOR2_END - 12)
+#define USER_BLOB_DATA (SECTOR2_END - 12)
/*
** The target program itself
*/
-#define TARGET_SEG 0x00001000 /* 1000:0000 */
-#define TARGET_ADDR 0x00010000 /* and upward */
-#define TARGET_STACK 0x00010000 /* and downward */
+#define TARGET_SEG 0x00001000 /* 1000:0000 */
+#define TARGET_ADDR 0x00010000 /* and upward */
+#define TARGET_STACK 0x00010000 /* and downward */
/*
** The Global Descriptor Table (0000:0500 - 0000:2500)
*/
-#define GDT_SEG 0x00000050
-#define GDT_ADDR 0x00000500
+#define GDT_SEG 0x00000050
+#define GDT_ADDR 0x00000500
-/* segment register values */
-#define GDT_LINEAR 0x0008 /* All of memory, R/W */
-#define GDT_CODE 0x0010 /* All of memory, R/E */
-#define GDT_DATA 0x0018 /* All of memory, R/W */
-#define GDT_STACK 0x0020 /* All of memory, R/W */
+ /* segment register values */
+#define GDT_LINEAR 0x0008 /* All of memory, R/W */
+#define GDT_CODE 0x0010 /* All of memory, R/E */
+#define GDT_DATA 0x0018 /* All of memory, R/W */
+#define GDT_STACK 0x0020 /* All of memory, R/W */
/*
** The Interrupt Descriptor Table (0000:2500 - 0000:2D00)
*/
-#define IDT_SEG 0x00000250
-#define IDT_ADDR 0x00002500
+#define IDT_SEG 0x00000250
+#define IDT_ADDR 0x00002500
/*
** Additional I/O ports used by the bootstrap code
*/
// keyboard controller
-#define KBD_DATA 0x60
-#define KBD_CMD 0x64
-#define KBD_STAT 0x64
+#define KBD_DATA 0x60
+#define KBD_CMD 0x64
+#define KBD_STAT 0x64
// status register bits
-#define KBD_OBSTAT 0x01
-#define KBD_IBSTAT 0x02
-#define KBD_SYSFLAG 0x04
-#define KBD_CMDDAT 0x08
+#define KBD_OBSTAT 0x01
+#define KBD_IBSTAT 0x02
+#define KBD_SYSFLAG 0x04
+#define KBD_CMDDAT 0x08
// commands
-#define KBD_P1_DISABLE 0xad
-#define KBD_P1_ENABLE 0xae
-#define KBD_RD_OPORT 0xd0
-#define KBD_WT_OPORT 0xd1
+#define KBD_P1_DISABLE 0xad
+#define KBD_P1_ENABLE 0xae
+#define KBD_RD_OPORT 0xd0
+#define KBD_WT_OPORT 0xd1
#ifdef ASM_SRC
@@ -104,16 +104,17 @@
// .byte granularity byte
// .byte upper 8 bits of base
// we use 4K units, so we ignore the lower 12 bits of the limit
-#define SEGNULL .word 0, 0, 0, 0
+#define SEGNULL \
+ .word 0, 0, 0, 0
-#define SEGMENT(base, limit, dpl, type) \
- .word(((limit) >> 12) & 0xffff); \
- .word((base) & 0xffff); \
- .byte(((base) >> 16) & 0xff); \
- .byte(SEG_PRESENT | (dpl) | SEG_NON_SYSTEM | (type)); \
- .byte(SEG_GRAN_4KBYTE | SEG_DB_32BIT | (((limit) >> 28) & 0xf)); \
- .byte(((base) >> 24) & 0xff)
+#define SEGMENT(base,limit,dpl,type) \
+ .word (((limit) >> 12) & 0xffff); \
+ .word ((base) & 0xffff) ; \
+ .byte (((base) >> 16) & 0xff) ; \
+ .byte (SEG_PRESENT | (dpl) | SEG_NON_SYSTEM | (type)) ; \
+ .byte (SEG_GRAN_4KBYTE | SEG_DB_32BIT | (((limit) >> 28) & 0xf)) ; \
+ .byte (((base) >> 24) & 0xff)
-#endif /* ASM_SRC */
+#endif /* ASM_SRC */
#endif
diff --git a/kernel/old/include/cio.h b/kernel/old/include/cio.h
index 63bf827..1854f6e 100644
--- a/kernel/old/include/cio.h
+++ b/kernel/old/include/cio.h
@@ -11,7 +11,7 @@
** Declarations and descriptions of console I/O routines
**
** These routines provide a rudimentary capability for printing to
-** the screen and reading from the keyboard.
+** the screen and reading from the keyboard.
**
** Screen output:
** There are two families of functions. The first provides a window
@@ -50,7 +50,7 @@
** Keyboard input:
** Two functions are provided: getting a single character and getting
** a newline-terminated line. A third function returns a count of
-** the number of characters available for immediate reading.
+** the number of characters available for immediate reading.
** No conversions are provided (yet).
*/
@@ -77,7 +77,7 @@
**
** @param notify pointer to an input notification function, or NULL
*/
-void cio_init(void (*notify)(int));
+void cio_init( void (*notify)(int) );
/*****************************************************************************
**
@@ -102,8 +102,8 @@ void cio_init(void (*notify)(int));
** @param min_x,min_y upper-left corner of the region
** @param max_x,max_y lower-right corner of the region
*/
-void cio_setscroll(unsigned int min_x, unsigned int min_y, unsigned int max_x,
- unsigned int max_y);
+void cio_setscroll( unsigned int min_x, unsigned int min_y,
+ unsigned int max_x, unsigned int max_y );
/**
** cio_moveto
@@ -114,7 +114,7 @@ void cio_setscroll(unsigned int min_x, unsigned int min_y, unsigned int max_x,
**
** @param x,y desired coordinate position
*/
-void cio_moveto(unsigned int x, unsigned int y);
+void cio_moveto( unsigned int x, unsigned int y );
/**
** cio_putchar
@@ -123,7 +123,7 @@ void cio_moveto(unsigned int x, unsigned int y);
**
** @param c the character to be printed
*/
-void cio_putchar(unsigned int c);
+void cio_putchar( unsigned int c );
/**
** cio_puts
@@ -133,7 +133,7 @@ void cio_putchar(unsigned int c);
**
** @param str pointer to a NUL-terminated string to be printed
*/
-void cio_puts(const char *str);
+void cio_puts( const char *str );
/**
** cio_write
@@ -143,7 +143,7 @@ void cio_puts(const char *str);
** @param buf the buffer of characters
** @param length the number of characters to print
*/
-void cio_write(const char *buf, int length);
+void cio_write( const char *buf, int length );
/**
** cio_printf
@@ -154,7 +154,7 @@ void cio_write(const char *buf, int length);
** @param fmt a printf-style format control string
** @param ... optional additional values to be printed
*/
-void cio_printf(char *fmt, ...);
+void cio_printf( char *fmt, ... );
/**
** cio_scroll
@@ -165,7 +165,7 @@ void cio_printf(char *fmt, ...);
**
** @param lines the number of lines to scroll
*/
-void cio_scroll(unsigned int lines);
+void cio_scroll( unsigned int lines );
/**
** cio_clearscroll
@@ -173,7 +173,7 @@ void cio_scroll(unsigned int lines);
** Clears the entire scrolling region to blank spaces, and
** moves the cursor to (0,0).
*/
-void cio_clearscroll(void);
+void cio_clearscroll( void );
/*****************************************************************************
**
@@ -196,7 +196,7 @@ void cio_clearscroll(void);
** @param x,y desired coordinate position
** @param c the character to be printed
*/
-void cio_putchar_at(unsigned int x, unsigned int y, unsigned int c);
+void cio_putchar_at( unsigned int x, unsigned int y, unsigned int c );
/**
** cio_puts_at
@@ -207,7 +207,7 @@ void cio_putchar_at(unsigned int x, unsigned int y, unsigned int c);
** @param x,y desired coordinate position
** @param str pointer to a NUL-terminated string to be printed
*/
-void cio_puts_at(unsigned int x, unsigned int y, const char *str);
+void cio_puts_at( unsigned int x, unsigned int y, const char *str );
/**
** cio_printf_at
@@ -219,14 +219,14 @@ void cio_puts_at(unsigned int x, unsigned int y, const char *str);
** @param fmt a printf-style format control string
** @param ... optional additional values to be printed
*/
-void cio_printf_at(unsigned int x, unsigned int y, char *fmt, ...);
+void cio_printf_at( unsigned int x, unsigned int y, char *fmt, ... );
/**
** cio_clearscreen
**
** This function clears the entire screen, including the scrolling region.
*/
-void cio_clearscreen(void);
+void cio_clearscreen( void );
/*****************************************************************************
**
@@ -251,7 +251,7 @@ void cio_clearscreen(void);
**
** @return the next character from the keyboard input buffer
*/
-int cio_getchar(void);
+int cio_getchar( void );
/**
** cio_gets
@@ -270,7 +270,7 @@ int cio_getchar(void);
**
** @return count of the number of characters read into the buffer
*/
-int cio_gets(char *buffer, unsigned int size);
+int cio_gets( char *buffer, unsigned int size );
/**
** cio_input_queue
@@ -281,7 +281,7 @@ int cio_gets(char *buffer, unsigned int size);
**
** @return number of characters in the input queue
*/
-int cio_input_queue(void);
-#endif /* !ASM_SRC */
+int cio_input_queue( void );
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/clock.h b/kernel/old/include/clock.h
index 674d799..6eae41f 100644
--- a/kernel/old/include/clock.h
+++ b/kernel/old/include/clock.h
@@ -17,10 +17,10 @@
// conversion functions for seconds, ms, and ticks
// (SEC_TO_MS is defined in defs.h)
-#define MS_TO_TICKS(n) ((n))
-#define SEC_TO_TICKS(n) (MS_TO_TICKS(SEC_TO_MS(n)))
-#define TICKS_TO_SEC(n) ((n) / CLOCK_FREQ)
-#define TICKS_TO_SEC_ROUNDED(n) (((n) + (CLOCK_FREQ - 1)) / CLOCK_FREQ)
+#define MS_TO_TICKS(n) ((n))
+#define SEC_TO_TICKS(n) (MS_TO_TICKS(SEC_TO_MS(n)))
+#define TICKS_TO_SEC(n) ((n) / CLOCK_FREQ)
+#define TICKS_TO_SEC_ROUNDED(n) (((n)+(CLOCK_FREQ-1)) / CLOCK_FREQ)
#ifndef ASM_SRC
@@ -48,8 +48,8 @@ extern uint32_t system_time;
**
** Clock module initialization
*/
-void clk_init(void);
+void clk_init( void );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/common.h b/kernel/old/include/common.h
new file mode 100644
index 0000000..599c492
--- /dev/null
+++ b/kernel/old/include/common.h
@@ -0,0 +1,31 @@
+/**
+** @file common.h
+**
+** @author Warren R. Carithers
+**
+** @brief Common definitions for the baseline system.
+**
+** This header file pulls in the standard header information needed
+** by all parts of the system. It is purely for our convenience.
+*/
+
+#ifndef COMMON_H_
+#define COMMON_H_
+
+// everything needs these; they also pull in
+// the kernel- or user-level defs and lib headers
+#include <types.h>
+#include <params.h>
+#include <defs.h>
+#include <lib.h>
+
+#ifdef KERNEL_SRC
+
+// only kernel code needs these headers
+#include <common.h>
+#include <cio.h>
+#include <debug.h>
+
+#endif /* KERNEL_SRC */
+
+#endif
diff --git a/kernel/old/include/compat.h b/kernel/old/include/compat.h
index f0c8c97..ee62090 100644
--- a/kernel/old/include/compat.h
+++ b/kernel/old/include/compat.h
@@ -60,10 +60,10 @@
*/
// type name for the PCB
-#define PCBTYPE pcb_t
+#define PCBTYPE pcb_t
// type name for our queue
-#define QTYPE pcb_queue_t
+#define QTYPE pcb_queue_t
/*
** Section 3: interface and behavior
@@ -77,13 +77,13 @@
*/
// string functions
-#define SLENGTH strlen
+#define SLENGTH strlen
// scheduler
-#define SCHED schedule
+#define SCHED schedule
// dispatcher
-#define DISPATCH dispatch
+#define DISPATCH dispatch
/*
** blocked queue for reading processes
@@ -93,7 +93,7 @@
** Its value should be the name of the globally-visible
** queue to be used.
*/
-#define QNAME sioread
+#define QNAME sioread
#ifdef QNAME
@@ -105,27 +105,26 @@
// invoke the queue creation function
// examples:
//
-// #define QCREATE(q) do {
-// _que_create( &(q), NULL );
+// #define QCREATE(q) do {
+// _que_create( &(q), NULL );
// } while(0)
//
// #define QCREATE(q) // do nothing
-#define QCREATE(q) // handled elsewhere for us
+#define QCREATE(q) // handled elsewhere for us
// check to see if the queue is empty
// examples:
//
// #define QEMPTY(q) queue_is_empty(q)
// #define QEMPTY(q) (quene_length(q) > 0)
-#define QEMPTY(q) pcb_queue_empty(q)
+#define QEMPTY(q) pcb_queue_empty(q)
// this macro expands into code that removes a value from
// 'q' and places it into 'd'
-#define QDEQUE(q, d) \
- do { \
- assert(pcb_queue_remove((q), (pcb_t **)&(d)) == SUCCESS); \
- } while (0)
+#define QDEQUE(q,d) do { \
+ assert(pcb_queue_remove( (q), (pcb_t **) &(d) ) == SUCCESS ); \
+ } while(0)
#endif /* QNAME */
diff --git a/kernel/old/include/debug.h b/kernel/old/include/debug.h
index 41e38cb..487a592 100644
--- a/kernel/old/include/debug.h
+++ b/kernel/old/include/debug.h
@@ -35,17 +35,11 @@
// currently, these do not use the macro parameter, but could be
// modified to do so; instead, we use the __func__ CPP pseudo-macro
// to get the function name
-#define ENTERING(n) \
- do { \
- cio_puts(" enter " __func__); \
- } while (0)
-#define EXITING(n) \
- do { \
- cio_puts(" exit " __func__); \
- } while (0)
+#define ENTERING(n) do { cio_puts( " enter " __func__ ); } while(0)
+#define EXITING(n) do { cio_puts( " exit " __func__ ); } while(0)
#else
-#define ENTERING(m) // do nothing
-#define EXITING(m) // do nothing
+#define ENTERING(m) // do nothing
+#define EXITING(m) // do nothing
#endif
/*
@@ -54,22 +48,20 @@
// Warning messages to the console
// m: message (condition, etc.)
-#define WARNING(m) \
- do { \
- cio_printf("\n** %s (%s @ %d): ", __func__, __FILE__, __LINE__); \
- cio_puts(m); \
- cio_putchar('\n'); \
- } while (0)
+#define WARNING(m) do { \
+ cio_printf( "\n** %s (%s @ %d): ", __func__, __FILE__, __LINE__ ); \
+ cio_puts( m ); \
+ cio_putchar( '\n' ); \
+ } while(0)
// Panic messages to the console
// n: severity level
// m: message (condition, etc.)
-#define PANIC(n, m) \
- do { \
- sprint(b512, "%s (%s @ %d), %d: %s\n", __func__, __FILE__, __LINE__, \
- n, #m); \
- kpanic(b512); \
- } while (0)
+#define PANIC(n,m) do { \
+ sprint( b512, "%s (%s @ %d), %d: %s\n", \
+ __func__, __FILE__, __LINE__, n, # m ); \
+ kpanic( b512 ); \
+ } while(0)
/*
** Assertions are categorized by the "sanity level" being used in this
@@ -84,48 +76,30 @@
#ifndef SANITY
// default sanity check level: check everything!
-#define SANITY 9999
+#define SANITY 9999
#endif
// Always-active assertions
-#define assert(x) \
- if (!(x)) { \
- PANIC(0, x); \
- }
+#define assert(x) if( !(x) ) { PANIC(0,x); }
// only provide these macros if the sanity check level is positive
#if SANITY > 0
-#define assert1(x) \
- if (SANITY >= 1 && !(x)) { \
- PANIC(1, x); \
- }
-#define assert2(x) \
- if (SANITY >= 2 && !(x)) { \
- PANIC(2, x); \
- }
-#define assert3(x) \
- if (SANITY >= 3 && !(x)) { \
- PANIC(3, x); \
- }
-#define assert4(x) \
- if (SANITY >= 4 && !(x)) { \
- PANIC(4, x); \
- }
+#define assert1(x) if( SANITY >= 1 && !(x) ) { PANIC(1,x); }
+#define assert2(x) if( SANITY >= 2 && !(x) ) { PANIC(2,x); }
+#define assert3(x) if( SANITY >= 3 && !(x) ) { PANIC(3,x); }
+#define assert4(x) if( SANITY >= 4 && !(x) ) { PANIC(4,x); }
// arbitrary sanity level
-#define assertN(n, x) \
- if (SANITY >= (n) && !(x)) { \
- PANIC(n, x); \
- }
+#define assertN(n,x) if( SANITY >= (n) && !(x) ) { PANIC(n,x); }
#else
-#define assert1(x) // do nothing
-#define assert2(x) // do nothing
-#define assert3(x) // do nothing
-#define assert4(x) // do nothing
-#define assertN(n, x) // do nothing
+#define assert1(x) // do nothing
+#define assert2(x) // do nothing
+#define assert3(x) // do nothing
+#define assert4(x) // do nothing
+#define assertN(n,x) // do nothing
#endif /* SANITY > 0 */
@@ -169,185 +143,182 @@
// 2^0 bit
#ifdef T_PCB
-#define TRPCB 0x00000001
+#define TRPCB 0x00000001
#else
-#define TRPCB 0
+#define TRPCB 0
#endif
#ifdef T_VM
-#define TRVM 0x00000002
+#define TRVM 0x00000002
#else
-#define TRVM 0
+#define TRVM 0
#endif
#ifdef T_QUE
-#define TRQUEUE 0x00000004
+#define TRQUEUE 0x00000004
#else
-#define TRQUEUE 0
+#define TRQUEUE 0
#endif
#ifdef T_SCH
-#define TRSCHED 0x00000008
+#define TRSCHED 0x00000008
#else
-#define TRSCHED 0
+#define TRSCHED 0
#endif
// 2^4 bit
#ifdef T_DSP
-#define TRDISP 0x00000010
+#define TRDISP 0x00000010
#else
-#define TRDISP 0
+#define TRDISP 0
#endif
#ifdef T_SCALL
-#define TRSYSCALLS 0x00000020
+#define TRSYSCALLS 0x00000020
#else
-#define TRSYSCALLS 0
+#define TRSYSCALLS 0
#endif
#ifdef T_SRET
-#define TRSYSRETS 0x00000040
+#define TRSYSRETS 0x00000040
#else
-#define TRSYSRETS 0
+#define TRSYSRETS 0
#endif
#ifdef T_EXIT
-#define TREXIT 0x00000080
+#define TREXIT 0x00000080
#else
-#define TREXIT 0
+#define TREXIT 0
#endif
// 2^8 bit
#ifdef T_INIT
-#define TRINIT 0x00000100
+#define TRINIT 0x00000100
#else
-#define TRINIT 0
+#define TRINIT 0
#endif
#ifdef T_KM
-#define TRKMEM 0x00000200
+#define TRKMEM 0x00000200
#else
-#define TRKMEM 0
+#define TRKMEM 0
#endif
#ifdef T_KMFR
-#define TRKMEM_F 0x00000400
+#define TRKMEM_F 0x00000400
#else
-#define TRKMEM_F 0
+#define TRKMEM_F 0
#endif
#ifdef T_KMIN
-#define TRKMEM_I 0x00000800
+#define TRKMEM_I 0x00000800
#else
-#define TRKMEM_I 0
+#define TRKMEM_I 0
#endif
// 2^12 bit
#ifdef T_FORK
-#define TRFORK 0x00001000
+#define TRFORK 0x00001000
#else
-#define TRFORK 0
+#define TRFORK 0
#endif
#ifdef T_EXEC
-#define TREXEC 0x00002000
+#define TREXEC 0x00002000
#else
-#define TREXEC 0
+#define TREXEC 0
#endif
#ifdef T_SIO
-#define TRSIO_STAT 0x00004000
+#define TRSIO_STAT 0x00004000
#else
-#define TRSIO_STAT 0
+#define TRSIO_STAT 0
#endif
#ifdef T_SIOR
-#define TRSIO_RD 0x00008000
+#define TRSIO_RD 0x00008000
#else
-#define TRSIO_RD 0
+#define TRSIO_RD 0
#endif
// 2^16 bit
#ifdef T_SIOW
-#define TRSIO_WR 0x00010000
+#define TRSIO_WR 0x00010000
#else
-#define TRSIO_WR 0
+#define TRSIO_WR 0
#endif
#ifdef T_USER
-#define TRUSER 0x00020000
+#define TRUSER 0x00020000
#else
-#define TRUSER 0
+#define TRUSER 0
#endif
#ifdef T_ELF
-#define TRELF 0x00040000
+#define TRELF 0x00040000
#else
-#define TRELF 0
+#define TRELF 0
#endif
// 13 bits remaining for tracing options
// next available bit: 0x00080000
-#define TRACE \
- (TRDISP | TREXIT | TRINIT | TRKMEM | TRKMEM_F | TRKMEM_I | TRPCB | \
- TRQUEUE | TRSCHED | TREXEC | TRSIO_RD | TRSIO_STAT | TRSIO_WR | TRFORK | \
- TRVM | TRSYSCALLS | TRSYSRETS | TRUSER | TRELF)
+#define TRACE (TRDISP | TREXIT | TRINIT | TRKMEM | TRKMEM_F | TRKMEM_I | TRPCB | TRQUEUE | TRSCHED | TREXEC | TRSIO_RD | TRSIO_STAT | TRSIO_WR | TRFORK | TRVM | TRSYSCALLS | TRSYSRETS | TRUSER | TRELF)
#if TRACE > 0
// compile-time expressions for testing trace options
// usage: #if TRACING_thing
-#define TRACING_PCB ((TRACE & TRPCB) != 0)
-#define TRACING_VM ((TRACE & TRVM) != 0)
-#define TRACING_QUEUE ((TRACE & TRQUEUE) != 0)
-#define TRACING_SCHED ((TRACE & TRSCHED) != 0)
-#define TRACING_DISPATCH ((TRACE & TRDISPATCH) != 0)
-#define TRACING_SYSCALLS ((TRACE & TRSYSCALLS) != 0)
-#define TRACING_SYSRETS ((TRACE & TRSYSRETS) != 0)
-#define TRACING_EXIT ((TRACE & TREXIT) != 0)
-#define TRACING_INIT ((TRACE & TRINIT) != 0)
-#define TRACING_KMEM ((TRACE & TRKMEM) != 0)
-#define TRACING_KMEM_FREELIST ((TRACE & TRKMEM_F) != 0)
-#define TRACING_KMEM_INIT ((TRACE & TRKMEM_I) != 0)
-#define TRACING_FORK ((TRACE & TRFORK) != 0)
-#define TRACING_EXEC ((TRACE & TREXEC) != 0)
-#define TRACING_SIO_STAT ((TRACE & TRSIO_STAT) != 0)
-#define TRACING_SIO_ISR ((TRACE & TRSIO_ISR) != 0)
-#define TRACING_SIO_RD ((TRACE & TRSIO_RD) != 0)
-#define TRACING_SIO_WR ((TRACE & TRSIO_WR) != 0)
-#define TRACING_USER ((TRACE & TRUSER) != 0)
-#define TRACING_ELF ((TRACE & TRELF) != 0)
+#define TRACING_PCB ((TRACE & TRPCB) != 0)
+#define TRACING_VM ((TRACE & TRVM) != 0)
+#define TRACING_QUEUE ((TRACE & TRQUEUE) != 0)
+#define TRACING_SCHED ((TRACE & TRSCHED) != 0)
+#define TRACING_DISPATCH ((TRACE & TRDISPATCH) != 0)
+#define TRACING_SYSCALLS ((TRACE & TRSYSCALLS) != 0)
+#define TRACING_SYSRETS ((TRACE & TRSYSRETS) != 0)
+#define TRACING_EXIT ((TRACE & TREXIT) != 0)
+#define TRACING_INIT ((TRACE & TRINIT) != 0)
+#define TRACING_KMEM ((TRACE & TRKMEM) != 0)
+#define TRACING_KMEM_FREELIST ((TRACE & TRKMEM_F) != 0)
+#define TRACING_KMEM_INIT ((TRACE & TRKMEM_I) != 0)
+#define TRACING_FORK ((TRACE & TRFORK) != 0)
+#define TRACING_EXEC ((TRACE & TREXEC) != 0)
+#define TRACING_SIO_STAT ((TRACE & TRSIO_STAT) != 0)
+#define TRACING_SIO_ISR ((TRACE & TRSIO_ISR) != 0)
+#define TRACING_SIO_RD ((TRACE & TRSIO_RD) != 0)
+#define TRACING_SIO_WR ((TRACE & TRSIO_WR) != 0)
+#define TRACING_USER ((TRACE & TRUSER) != 0)
+#define TRACING_ELF ((TRACE & TRELF) != 0)
// more generic tests
-#define TRACING_SOMETHING (TRACE != 0)
+#define TRACING_SOMETHING (TRACE != 0)
#else
// TRACE == 0, so just define these all as "false"
-#define TRACING_PCB 0
-#define TRACING_STACK 0
-#define TRACING_QUEUE 0
-#define TRACING_SCHED 0
-#define TRACING_DISPATCH 0
-#define TRACING_SYSCALLS 0
-#define TRACING_SYSRET 0
-#define TRACING_EXIT 0
-#define TRACING_INIT 0
-#define TRACING_KMEM 0
-#define TRACING_KMEM_FREELIST 0
-#define TRACING_KMEM_INIT 0
-#define TRACING_FORK 0
-#define TRACING_EXEC 0
-#define TRACING_SI_STAT 0
-#define TRACING_SIO_ISR 0
-#define TRACING_SIO_RD 0
-#define TRACING_SIO_WR 0
-#define TRACING_USER 0
-#define TRACING_ELF 0
+#define TRACING_PCB 0
+#define TRACING_STACK 0
+#define TRACING_QUEUE 0
+#define TRACING_SCHED 0
+#define TRACING_DISPATCH 0
+#define TRACING_SYSCALLS 0
+#define TRACING_SYSRET 0
+#define TRACING_EXIT 0
+#define TRACING_INIT 0
+#define TRACING_KMEM 0
+#define TRACING_KMEM_FREELIST 0
+#define TRACING_KMEM_INIT 0
+#define TRACING_FORK 0
+#define TRACING_EXEC 0
+#define TRACING_SI_STAT 0
+#define TRACING_SIO_ISR 0
+#define TRACING_SIO_RD 0
+#define TRACING_SIO_WR 0
+#define TRACING_USER 0
+#define TRACING_ELF 0
-#define TRACING_SOMETHING 0
+#define TRACING_SOMETHING 0
#endif /* TRACE */
diff --git a/kernel/old/include/defs.h b/kernel/old/include/defs.h
index 018b14e..0280c47 100644
--- a/kernel/old/include/defs.h
+++ b/kernel/old/include/defs.h
@@ -29,21 +29,24 @@
// we define this the traditional way so that
// it's usable from both C and assembly
-#define NULL 0
+#define NULL 0
// predefined i/o channels
-#define CHAN_CIO 0
-#define CHAN_SIO 1
+#define CHAN_CIO 0
+#define CHAN_SIO 1
+
+// maximum allowable number of command-line arguments
+#define MAX_ARGS 10
// sizes of various things
-#define NUM_1KB 0x00000400 // 2^10
-#define NUM_4KB 0x00001000 // 2^12
-#define NUM_1MB 0x00100000 // 2^20
-#define NUM_4MB 0x00400000 // 2^22
-#define NUM_1GB 0x40000000 // 2^30
-#define NUM_2GB 0x80000000 // 2^31
-#define NUM_3GB 0xc0000000 // 1GB + 2GB
+#define NUM_1KB 0x00000400 // 2^10
+#define NUM_4KB 0x00001000 // 2^12
+#define NUM_1MB 0x00100000 // 2^20
+#define NUM_4MB 0x00400000 // 2^22
+#define NUM_1GB 0x40000000 // 2^30
+#define NUM_2GB 0x80000000 // 2^31
+#define NUM_3GB 0xc0000000
#ifndef ASM_SRC
@@ -60,63 +63,59 @@
** These can be returned to both system functions
** and to user system calls.
*/
-// success!
-#define SUCCESS (0)
-#define E_SUCCESS SUCCESS
-// generic "something went wrong"
-#define E_FAILURE (-1)
-// specific failure reasons
-#define E_BAD_PARAM (-2)
-#define E_BAD_CHAN (-3)
-#define E_NO_CHILDREN (-4)
-#define E_NO_MEMORY (-5)
-#define E_NOT_FOUND (-6)
-#define E_NO_PROCS (-7)
+ // success!
+#define SUCCESS (0)
+# define E_SUCCESS SUCCESS
+ // generic "something went wrong"
+#define E_FAILURE (-1)
+ // specific failure reasons
+#define E_BAD_PARAM (-2)
+#define E_BAD_CHAN (-3)
+#define E_NO_CHILDREN (-4)
+#define E_NO_MEMORY (-5)
+#define E_NOT_FOUND (-6)
+#define E_NO_PROCS (-7)
/*
** These error codes are internal to the OS.
*/
-#define E_EMPTY_QUEUE (-100)
-#define E_NO_PCBS (-101)
-#define E_NO_PTE (-102)
-#define E_LOAD_LIMIT (-103)
+#define E_EMPTY_QUEUE (-100)
+#define E_NO_PCBS (-101)
+#define E_NO_PTE (-102)
+#define E_LOAD_LIMIT (-103)
// exit status values
-#define EXIT_SUCCESS (0)
-#define EXIT_FAILURE (-1)
-#define EXIT_KILLED (-101)
-#define EXIT_BAD_SYSCALL (-102)
+#define EXIT_SUCCESS (0)
+#define EXIT_FAILURE (-1)
+#define EXIT_KILLED (-101)
+#define EXIT_BAD_SYSCALL (-102)
/*
** Process priority values
*/
enum priority_e {
- PRIO_HIGH,
- PRIO_STD,
- PRIO_LOW,
- PRIO_DEFERRED
+ PRIO_HIGH, PRIO_STD, PRIO_LOW, PRIO_DEFERRED
// sentinel
- ,
- N_PRIOS
+ , N_PRIOS
};
// halves of various data sizes
-#define UI16_UPPER 0xff00
-#define UI16_LOWER 0x00ff
+#define UI16_UPPER 0xff00
+#define UI16_LOWER 0x00ff
-#define UI32_UPPER 0xffff0000
-#define UI32_LOWER 0x0000ffff
+#define UI32_UPPER 0xffff0000
+#define UI32_LOWER 0x0000ffff
-#define UI64_UPPER 0xffffffff00000000LL
-#define UI64_LOWER 0x00000000ffffffffLL
+#define UI64_UPPER 0xffffffff00000000LL
+#define UI64_LOWER 0x00000000ffffffffLL
// Simple conversion pseudo-functions usable by everyone
// convert seconds to ms
-#define SEC_TO_MS(n) ((n) * 1000)
+#define SEC_TO_MS(n) ((n) * 1000)
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
/*
** Level-specific definitions
@@ -125,6 +124,6 @@ enum priority_e {
#include <kdefs.h>
#else
#include <udefs.h>
-#endif /* KERNEL_SRC */
+#endif /* KERNEL_SRC */
#endif
diff --git a/kernel/old/include/elf.h b/kernel/old/include/elf.h
new file mode 100644
index 0000000..a43e5c3
--- /dev/null
+++ b/kernel/old/include/elf.h
@@ -0,0 +1,235 @@
+/**
+** @file elf.h
+**
+** @author Warren R. Carithers
+**
+** @brief ELF format declarations
+*/
+
+#ifndef ELF_H_
+#define ELF_H_
+
+#include <common.h>
+
+#ifndef ASM_SRC
+
+/*
+** Start of C-only definitions
+*/
+
+// ELF data types (TIS ELF Spec v1.2, May 1995
+typedef uint32_t e32_a; // 32-bit unsigned address
+typedef uint16_t e32_h; // 16-bit unsigned "medium" integer
+typedef uint32_t e32_o; // 32-bit unsigned offset
+typedef int32_t e32_sw; // 32-bit signed "large" integer
+typedef uint32_t e32_w; // 32-bit unsigned "large" integer
+typedef uint8_t e32_si; // 8-bit unsigned "small" integer
+
+// ELF magic number - first four bytes
+#define ELF_MAGIC 0x464C457FU // "\x7FELF" in little-endian order
+#define EI_NIDENT 16
+
+union elfident_u {
+ uint8_t bytes[EI_NIDENT]; // array of 16 bytes
+ struct {
+ uint32_t magic; // magic number
+ uint8_t class; // file class
+ uint8_t data; // data encoding
+ uint8_t version; // file version
+ uint8_t osabi; // OS ABI identification
+ uint8_t abivers; // ABI version
+ uint8_t pad[7]; // padding to 16 bytes
+ } f;
+};
+
+// indices for byte fields in the ident array
+#define EI_MAGIC 0
+# define EI_MAG0 EI_MAGIC
+# define EI_MAG1 1
+# define EI_MAG2 2
+# define EI_MAG3 3
+#define EI_CLASS 4
+#define EI_DATA 5
+#define EI_VERSION 6
+#define EI_OSABI 7
+#define EI_ABIVERSION 8
+
+// ELF classes
+#define ELF_CLASS_NONE 0
+#define ELF_CLASS_32 1 // 32-bit objects
+#define ELF_CLASS_64 2 // 64-bit objects
+
+// ELF data encoding
+#define ELF_DATA_NONE 0 // invalid data encoding
+#define ELF_DATA_2LSB 1 // two's complement little-endian
+#define ELF_DATA_2MSB 2 // two's complement big-endian
+
+// ELF versions
+#define ELF_VERSION__NONE 0 // invalid version
+# define EV_NONE ELF_VERSION_NONE
+#define ELF_VERSION__CURRENT 1 // current version
+# define EV_CURRENT ELF_VERSION_CURRENT
+
+// ELF header
+//
+// field names are from the TIS ELF Spec v1.2, May 1995
+typedef struct elfhdr_s {
+ union elfident_u e_ident; // file identification
+ e32_h e_type; // file type
+ e32_h e_machine; // required architecture
+ e32_w e_version; // object file version
+ e32_a e_entry; // entry point (VA)
+ e32_o e_phoff; // offset to program header table (PHT)
+ e32_o e_shoff; // offset to section header table (SHT)
+ e32_w e_flags; // processor-specific flags
+ e32_h e_ehsize; // ELF header size (bytes)
+ e32_h e_phentsize; // size of one PHT entry (bytes)
+ e32_h e_phnum; // number of PHT entries
+ e32_h e_shentsize; // size of one SHT entry (bytes)
+ e32_h e_shnum; // number of SHT entries
+ e32_h e_shstrndx; // SHT index of the sect. name string table
+} elfhdr_t;
+
+#define SZ_ELFHDR sizeof(elfhdr_t)
+
+// field values
+// e_type
+#define ET_NONE 0 // no file type
+#define ET_REL 1 // relocatable file
+#define ET_EXEC 2 // executable file
+#define ET_DYN 3 // shared object file
+#define ET_CORE 4 // core file
+#define ET_LO_OS 0xfe00 // processor-specific
+#define ET_HI_OS 0xfeff // processor-specific
+#define ET_LO_CP 0xff00 // processor-specific
+#define ET_HI_CP 0xffff // processor-specific
+
+// e_machine
+#define EM_NONE 0x00 // no machine type
+#define EM_M32 0x01 // AT&T WE 32100
+#define EM_SPARC 0x02 // SUN SPARC
+#define EM_386 0x03 // Intel Architecture
+#define EM_68K 0x04 // Motorola 68000
+#define EM_88K 0x05 // Motorola 88000
+#define EM_IAMCU 0x06 // Intel MCU
+#define EM_860 0x07 // Intel 80860
+#define EM_MIPS 0x08 // MIPS RS3000 Big-Endian
+#define EM_S370 0x09 // IBM System/370
+#define EM_MIPS_RS3_LE 0x0a // MIPS RS3000 Big-Endian
+#define EM_SPARC32PLLUS 0x12 // Sun "v8plus"
+#define EM_PPC 0x14 // IBM PowerPC
+#define EM_PPC64 0x15 // IBM PowerPC 64-bit
+#define EM_S390 0x16 // IBM System/390
+#define EM_ARM 0x28 // ARM up to V7/AArch32
+#define EM_SPARCV9 0x2b // SPARC V9 64-bit
+#define EM_IA_64 0x32 // Intel Itanium (Merced)
+#define EM_MIPS_X 0x32 // Stanford MIPS-X
+#define EM_X86_64 0x3E // AMD x86-64 (Intel64)
+#define EM_PDP11 0x40 // DEC PDP-11
+#define EM_VAX 0x4b // DEC VAX
+#define EM_AARCH64 0xb7 // ARM AArch64
+#define EM_Z80 0xec // Zilog Z-80
+#define EM_AMDGPU 0xf0 // AMD GPU
+#define EM_RISCV 0xf3 // RISC-V
+#define EM_BPF 0xf7 // Berkeley Packet Filter
+
+// ELF section header
+//
+// field names are from the TIS ELF Spec v1.2, May 1995
+typedef struct shdr_s {
+ e32_w sh_name; // section name (index into string table)
+ e32_w sh_type; // section contents/semantics
+ e32_w sh_flags; // attribute flag bits
+ e32_a sh_addr; // 0, or load point of this section in memory
+ e32_o sh_offset; // byte offset within the file
+ e32_w sh_size; // section size in bytes
+ e32_w sh_link; // section header index table link
+ e32_w sh_info; // "extra information"
+ e32_w sh_addralign; // required alignment
+ e32_w sh_entsize; // 0, or size of each entry in the section
+} elfsecthdr_t;
+
+#define SZ_ELFSECTHDR sizeof(elfsecthdr_t)
+
+// sh_name
+#define SHN_UNDEF 0
+
+// sh_type
+#define SHT_NULL 0x00
+#define SHT_PROGBITS 0x01
+#define SHT_SYMTAB 0x02
+#define SHT_STRTAB 0x03
+#define SHT_RELA 0x04
+#define SHT_HASH 0x05
+#define SHT_DYNAMIC 0x06
+#define SHT_NOTE 0x07
+#define SHT_NOBITS 0x08
+#define SHT_REL 0x09
+#define SHT_SHLIB 0x0a
+#define SHT_DYNSYM 0x0b
+#define SHT_LO_CP 0x70000000
+#define SHT_HI_CP 0x7fffffff
+#define SHT_LO_US 0x80000000
+#define SHT_HI_US 0x8fffffff
+
+// sh_flags
+#define SHF_WRITE 0x001
+#define SHF_ALLOC 0x002
+#define SHF_EXECINSTR 0x004
+#define SHF_MERGE 0x010
+#define SHF_STRINGS 0x020
+#define SHF_INFO_LINK 0x040
+#define SHF_LINK_ORDER 0x080
+#define SHF_OS_NONCON 0x100
+#define SHF_GROUP 0x200
+#define SHF_TLS 0x400
+#define SHF_MASKOS 0x0ff00000
+#define SHF_MASKPROC 0xf0000000
+
+// ELF program header
+//
+// field names are from the TIS ELF Spec v1.2, May 1995
+typedef struct phdr_s {
+ e32_w p_type; // type of segment
+ e32_o p_offset; // byte offset in file
+ e32_a p_va; // load point in memory (virtual address)
+ e32_a p_pa; // load point in memory (physical address)
+ e32_w p_filesz; // number of bytes in this file
+ e32_w p_memsz; // number of bytes in memory
+ e32_w p_flags; // attribute flag bits
+ e32_w p_align; // required alignment
+} elfproghdr_t;
+
+#define SZ_ELFPROGHDR sizeof(elfproghdr_t)
+
+// p_type
+#define PT_NULL 0
+#define PT_LOAD 1
+#define PT_DYNAMIC 2
+#define PT_INTERP 3
+#define PT_NOTE 4
+#define PT_SHLIB 5
+#define PT_PHDR 6
+#define PT_TLS 7
+#define PT_LO_OS 0x70000000
+#define PT_HI_OS 0x7fffffff
+#define PT_LO_CP 0x70000000
+#define PT_HI_CP 0x7fffffff
+
+// p_flags
+#define PF_E 0x1
+#define PF_W 0x2
+#define PF_R 0x4
+#define PF_MASKPROC 0xf0000000
+
+/*
+** Globals
+*/
+
+/*
+** Prototypes
+*/
+
+#endif /* !ASM_SRC */
+
+#endif
diff --git a/kernel/old/include/kdefs.h b/kernel/old/include/kdefs.h
index d26fa3d..794516b 100644
--- a/kernel/old/include/kdefs.h
+++ b/kernel/old/include/kdefs.h
@@ -17,58 +17,53 @@
*/
// page sizes
-#define SZ_PAGE NUM_4KB
-#define SZ_BIGPAGE NUM_4MB
+#define SZ_PAGE NUM_4KB
+#define SZ_BIGPAGE NUM_4MB
// kernel stack size (bytes)
-#define N_KSTKPAGES 1
-#define SZ_KSTACK (N_KSTKPAGES * SZ_PAGE)
+#define N_KSTKPAGES 1
+#define SZ_KSTACK (N_KSTKPAGES * SZ_PAGE)
// user stack size
-#define N_USTKPAGES 2
-#define SZ_USTACK (N_USTKPAGES * SZ_PAGE)
+#define N_USTKPAGES 2
+#define SZ_USTACK (N_USTKPAGES * SZ_PAGE)
// declarations for modulus checking of (e.g.) sizes and addresses
-#define LOW_9_BITS 0x00000fff
-#define LOW_22_BITS 0x003fffff
-#define HIGH_20_BITS 0xfffff000
-#define HIGH_10_BITS 0xffc00000
+#define MOD4_BITS 0x00000003
+#define MOD4_MASK 0xfffffffc
+#define MOD4_INC 0x00000004
+#define MOD4_SHIFT 2
-#define MOD4_BITS 0x00000003
-#define MOD4_MASK 0xfffffffc
-#define MOD4_INC 0x00000004
-#define MOD4_SHIFT 2
+#define MOD16_BITS 0x0000000f
+#define MOD16_MASK 0xfffffff0
+#define MOD16_INC 0x00000010
+#define MOD16_SHIFT 4
-#define MOD16_BITS 0x0000000f
-#define MOD16_MASK 0xfffffff0
-#define MOD16_INC 0x00000010
-#define MOD16_SHIFT 4
+#define MOD1K_BITS 0x000003ff
+#define MOD1K_MASK 0xfffffc00
+#define MOD1K_INC 0x00000400
+#define MOD1K_SHIFT 10
-#define MOD1K_BITS 0x000003ff
-#define MOD1K_MASK 0xfffffc00
-#define MOD1K_INC 0x00000400
-#define MOD1K_SHIFT 10
+#define MOD4K_BITS 0x00000fff
+#define MOD4K_MASK 0xfffff000
+#define MOD4K_INC 0x00001000
+#define MOD4K_SHIFT 12
-#define MOD4K_BITS 0x00000fff
-#define MOD4K_MASK 0xfffff000
-#define MOD4K_INC 0x00001000
-#define MOD4K_SHIFT 12
+#define MOD1M_BITS 0x000fffff
+#define MOD1M_MASK 0xfff00000
+#define MOD1M_INC 0x00100000
+#define MOD1M_SHIFT 20
-#define MOD1M_BITS 0x000fffff
-#define MOD1M_MASK 0xfff00000
-#define MOD1M_INC 0x00100000
-#define MOD1M_SHIFT 20
+#define MOD4M_BITS 0x003fffff
+#define MOD4M_MASK 0xffc00000
+#define MOD4M_INC 0x00400000
+#define MOD4M_SHIFT 22
-#define MOD4M_BITS 0x003fffff
-#define MOD4M_MASK 0xffc00000
-#define MOD4M_INC 0x00400000
-#define MOD4M_SHIFT 22
-
-#define MOD1G_BITS 0x3fffffff
-#define MOD1G_MASK 0xc0000000
-#define MOD1G_INC 0x40000000
-#define MOD1G_SHIFT 30
+#define MOD1G_BITS 0x3fffffff
+#define MOD1G_MASK 0xc0000000
+#define MOD1G_INC 0x40000000
+#define MOD1G_SHIFT 30
#ifndef ASM_SRC
@@ -77,26 +72,26 @@
*/
// unit conversion macros
-#define B_TO_KB(x) (((uint_t)(x)) >> 10)
-#define B_TO_MB(x) (((uint_t)(x)) >> 20)
-#define B_TO_GB(x) (((uint_t)(x)) >> 30)
+#define B_TO_KB(x) (((uint_t)(x))>>10)
+#define B_TO_MB(x) (((uint_t)(x))>>20)
+#define B_TO_GB(x) (((uint_t)(x))>>30)
-#define KB_TO_B(x) (((uint_t)(x)) << 10)
-#define KB_TO_MB(x) (((uint_t)(x)) >> 10)
-#define KB_TO_GB(x) (((uint_t)(x)) >> 20)
+#define KB_TO_B(x) (((uint_t)(x))<<10)
+#define KB_TO_MB(x) (((uint_t)(x))>>10)
+#define KB_TO_GB(x) (((uint_t)(x))>>20)
-#define MB_TO_B(x) (((uint_t)(x)) << 20)
-#define MB_TO_KB(x) (((uint_t)(x)) << 10)
-#define MB_TO_GB(x) (((uint_t)(x)) >> 10)
+#define MB_TO_B(x) (((uint_t)(x))<<20)
+#define MB_TO_KB(x) (((uint_t)(x))<<10)
+#define MB_TO_GB(x) (((uint_t)(x))>>10)
-#define GB_TO_B(x) (((uint_t)(x)) << 30)
-#define GB_TO_KB(x) (((uint_t)(x)) << 20)
-#define GB_TO_MB(x) (((uint_t)(x)) << 10)
+#define GB_TO_B(x) (((uint_t)(x))<<30)
+#define GB_TO_KB(x) (((uint_t)(x))<<20)
+#define GB_TO_MB(x) (((uint_t)(x))<<10)
// potetially useful compiler attributes
#define ATTR_ALIGNED(x) __attribute__((__aligned__(x)))
-#define ATTR_PACKED __attribute__((__packed__))
-#define ATTR_UNUSED __attribute__((__unused__))
+#define ATTR_PACKED __attribute__((__packed__))
+#define ATTR_UNUSED __attribute__((__unused__))
/*
** Utility macros
@@ -107,18 +102,18 @@
//
// these are usable for clearing single-valued data items (e.g.,
// a PCB, etc.)
-#define CLEAR(v) memclr(&v, sizeof(v))
-#define CLEAR_PTR(p) memclr(p, sizeof(*p))
+#define CLEAR(v) memclr( &v, sizeof(v) )
+#define CLEAR_PTR(p) memclr( p, sizeof(*p) )
//
// macros for access registers and system call arguments
//
// REG(pcb,x) -- access a specific register in a process context
-#define REG(pcb, x) ((pcb)->context->x)
+#define REG(pcb,x) ((pcb)->context->x)
// RET(pcb) -- access return value register in a process context
-#define RET(pcb) ((pcb)->context->eax)
+#define RET(pcb) ((pcb)->context->eax)
// ARG(pcb,n) -- access argument #n from the indicated process
//
@@ -129,7 +124,7 @@
//
// ASSUMES THE STANDARD 32-BIT ABI, WITH PARAMETERS PUSHED ONTO THE
// STACK. IF THE PARAMETER PASSING MECHANISM CHANGES, SO MUST THIS!
-#define ARG(pcb, n) (((uint32_t *)(((pcb)->context) + 1))[(n)])
+#define ARG(pcb,n) ( ( (uint32_t *) (((pcb)->context) + 1) ) [(n)] )
/*
** Types
@@ -152,6 +147,6 @@ extern uint8_t kstack[SZ_KSTACK];
** Prototypes
*/
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/klib.h b/kernel/old/include/klib.h
index 60f59da..c1d270c 100644
--- a/kernel/old/include/klib.h
+++ b/kernel/old/include/klib.h
@@ -24,7 +24,7 @@
**
** @param ch The character to be printed
*/
-void put_char_or_code(int ch);
+void put_char_or_code( int ch );
/**
** Name: backtrace
@@ -35,7 +35,7 @@ void put_char_or_code(int ch);
** @param ebp Initial EBP to use
** @param args Number of function argument values to print
*/
-void backtrace(uint32_t *ebp, uint_t args);
+void backtrace( uint32_t *ebp, uint_t args );
/**
** Name: kpanic
@@ -50,8 +50,8 @@ void backtrace(uint32_t *ebp, uint_t args);
** @param msg[in] String containing a relevant message to be printed,
** or NULL
*/
-void kpanic(const char *msg);
+void kpanic( const char *msg );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/kmem.h b/kernel/old/include/kmem.h
index 631f7ab..5a98765 100644
--- a/kernel/old/include/kmem.h
+++ b/kernel/old/include/kmem.h
@@ -28,8 +28,8 @@
// Slab and slice sizes, in bytes
-#define SZ_SLAB SZ_PAGE
-#define SZ_SLICE (SZ_SLAB >> 2)
+#define SZ_SLAB SZ_PAGE
+#define SZ_SLICE (SZ_SLAB >> 2)
// memory limits
//
@@ -37,8 +37,8 @@
// module will manage
//
// we won't map any memory below 1MB or above 1GB
-#define KM_LOW_CUTOFF NUM_1MB
-#define KM_HIGH_CUTOFF NUM_1GB
+#define KM_LOW_CUTOFF NUM_1MB
+#define KM_HIGH_CUTOFF NUM_1GB
#ifndef ASM_SRC
@@ -68,7 +68,7 @@
** Must be called before any other init routine that uses
** dynamic storage is called.
*/
-void km_init(void);
+void km_init( void );
/**
** Name: km_dump
@@ -81,7 +81,7 @@ void km_init(void);
** @param addrs Also dump page addresses
** @param both Also dump slice addresses
*/
-void km_dump(bool_t addrs, bool_t both);
+void km_dump( bool_t addrs, bool_t both );
/*
** Functions that manipulate free memory blocks.
@@ -95,7 +95,7 @@ void km_dump(bool_t addrs, bool_t both);
** @return a pointer to the beginning of the allocated page,
** or NULL if no memory is available
*/
-void *km_page_alloc(void);
+void *km_page_alloc( void );
/**
** Name: km_page_free
@@ -108,7 +108,7 @@ void *km_page_alloc(void);
**
** @param[in] block Pointer to the page to be returned to the free list
*/
-void km_page_free(void *block);
+void km_page_free( void *block );
/**
** Name: km_slice_alloc
@@ -119,7 +119,7 @@ void km_page_free(void *block);
**
** @return a pointer to the allocated slice
*/
-void *km_slice_alloc(void);
+void *km_slice_alloc( void );
/**
** Name: km_slice_free
@@ -131,7 +131,7 @@ void *km_slice_alloc(void);
**
** @param[in] block Pointer to the slice (1/4 page) to be freed
*/
-void km_slice_free(void *block);
+void km_slice_free( void *block );
#endif /* !ASM_SRC */
diff --git a/kernel/old/include/lib.h b/kernel/old/include/lib.h
new file mode 100644
index 0000000..bde0554
--- /dev/null
+++ b/kernel/old/include/lib.h
@@ -0,0 +1,314 @@
+/**
+** @file lib.h
+**
+** @author Numerous CSCI-452 classes
+**
+** @brief C declarations of common library functions
+**
+** These are callable from either kernel or user code. Care should be taken
+** that user code is linked against these separately from kernel code, to
+** ensure separation of the address spaces.
+*/
+
+#ifndef LIB_H_
+#define LIB_H_
+
+#ifndef ASM_SRC
+
+#include <common.h>
+
+/*
+**********************************************
+** MEMORY MANIPULATION FUNCTIONS
+**********************************************
+*/
+
+/**
+** blkmov(dst,src,len)
+**
+** Copy a word-aligned block from src to dst. Deals with overlapping
+** buffers.
+**
+** If the buffer addresses aren't word-aligned or the length is not a
+** multiple of four, calls memmove().
+**
+** @param dst Destination buffer
+** @param src Source buffer
+** @param len Buffer size (in bytes)
+*/
+void blkmov( void *dst, const void *src, register uint32_t len );
+
+/**
+** memset(buf,len,value)
+**
+** initialize all bytes of a block of memory to a specific value
+**
+** @param buf The buffer to initialize
+** @param len Buffer size (in bytes)
+** @param value Initialization value
+*/
+void memset( void *buf, register uint32_t len, register uint32_t value );
+
+/**
+** memclr(buf,len)
+**
+** Initialize all bytes of a block of memory to zero
+**
+** @param buf The buffer to initialize
+** @param len Buffer size (in bytes)
+*/
+void memclr( void *buf, register uint32_t len );
+
+/**
+** memcpy(dst,src,len)
+**
+** Copy a block from one place to another
+**
+** May not correctly deal with overlapping buffers
+**
+** @param dst Destination buffer
+** @param src Source buffer
+** @param len Buffer size (in bytes)
+*/
+void memcpy( void *dst, register const void *src, register uint32_t len );
+
+/**
+** memmove(dst,src,len)
+**
+** Copy a block from one place to another. Deals with overlapping
+** buffers
+**
+** @param dst Destination buffer
+** @param src Source buffer
+** @param len Buffer size (in bytes)
+*/
+void memmove( void *dst, register const void *src, register uint32_t len );
+
+/*
+**********************************************
+** STRING MANIPULATION FUNCTIONS
+**********************************************
+*/
+
+/**
+** str2int(str,base) - convert a string to a number in the specified base
+**
+** @param str The string to examine
+** @param base The radix to use in the conversion
+**
+** @return The converted integer
+*/
+int str2int( register const char *str, register int base );
+
+/**
+** strlen(str) - return length of a NUL-terminated string
+**
+** @param str The string to examine
+**
+** @return The length of the string, or 0
+*/
+uint32_t strlen( register const char *str );
+
+/**
+** strcmp(s1,s2) - compare two NUL-terminated strings
+**
+** @param s1 The first source string
+** @param s2 The second source string
+**
+** @return negative if s1 < s2, zero if equal, and positive if s1 > s2
+*/
+int strcmp( register const char *s1, register const char *s2 );
+
+/**
+** strcpy(dst,src) - copy a NUL-terminated string
+**
+** @param dst The destination buffer
+** @param src The source buffer
+**
+** @return The dst parameter
+**
+** NOTE: assumes dst is large enough to hold the copied string
+*/
+char *strcpy( register char *dst, register const char *src );
+
+/**
+** strcat(dst,src) - append one string to another
+**
+** @param dst The destination buffer
+** @param src The source buffer
+**
+** @return The dst parameter
+**
+** NOTE: assumes dst is large enough to hold the resulting string
+*/
+char *strcat( register char *dst, register const char *src );
+
+/**
+** pad(dst,extra,padchar) - generate a padding string
+**
+** @param dst Pointer to where the padding should begin
+** @param extra How many padding bytes to add
+** @param padchar What character to pad with
+**
+** @return Pointer to the first byte after the padding
+**
+** NOTE: does NOT NUL-terminate the buffer
+*/
+char *pad( char *dst, int extra, int padchar );
+
+/**
+** padstr(dst,str,len,width,leftadjust,padchar - add padding characters
+** to a string
+**
+** @param dst The destination buffer
+** @param str The string to be padded
+** @param len The string length, or -1
+** @param width The desired final length of the string
+** @param leftadjust Should the string be left-justified?
+** @param padchar What character to pad with
+**
+** @return Pointer to the first byte after the padded string
+**
+** NOTE: does NOT NUL-terminate the buffer
+*/
+char *padstr( char *dst, char *str, int len, int width,
+ int leftadjust, int padchar );
+
+/**
+** sprint(dst,fmt,...) - formatted output into a string buffer
+**
+** @param dst The string buffer
+** @param fmt Format string
+**
+** The format string parameter is followed by zero or more additional
+** parameters which are interpreted according to the format string.
+**
+** NOTE: assumes the buffer is large enough to hold the result string
+**
+** NOTE: relies heavily on the x86 parameter passing convention
+** (parameters are pushed onto the stack in reverse order as
+** 32-bit values).
+*/
+void sprint( char *dst, char *fmt, ... );
+
+/*
+**********************************************
+** CONVERSION FUNCTIONS
+**********************************************
+*/
+
+/**
+** cvtuns0(buf,value) - local support routine for cvtuns()
+**
+** Convert a 32-bit unsigned value into a NUL-terminated character string
+**
+** @param buf Result buffer
+** @param value Value to be converted
+**
+** @return Pointer to the first unused byte in the buffer
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+char *cvtuns0( char *buf, uint32_t value );
+
+/**
+** cvtuns(buf,value)
+**
+** Convert a 32-bit unsigned value into a NUL-terminated character string
+**
+** @param buf Result buffer
+** @param value Value to be converted
+**
+** @return Length of the resulting buffer
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+int cvtuns( char *buf, uint32_t value );
+
+/**
+** cvtdec0(buf,value) - local support routine for cvtdec()
+**
+** convert a 32-bit unsigned integer into a NUL-terminated character string
+**
+** @param buf Destination buffer
+** @param value Value to convert
+**
+** @return The number of characters placed into the buffer
+** (not including the NUL)
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+char *cvtdec0( char *buf, int value );
+
+/**
+** cvtdec(buf,value)
+**
+** convert a 32-bit signed value into a NUL-terminated character string
+**
+** @param buf Destination buffer
+** @param value Value to convert
+**
+** @return The number of characters placed into the buffer
+** (not including the NUL)
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+int cvtdec( char *buf, int32_t value );
+
+/**
+** cvthex(buf,value)
+**
+** convert a 32-bit unsigned value into a mininal-length (up to
+** 8-character) NUL-terminated character string
+**
+** @param buf Destination buffer
+** @param value Value to convert
+**
+** @return The number of characters placed into the buffer
+** (not including the NUL)
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+int cvthex( char *buf, uint32_t value );
+
+/**
+** cvtoct(buf,value)
+**
+** convert a 32-bit unsigned value into a mininal-length (up to
+** 11-character) NUL-terminated character string
+**
+** @param buf Destination buffer
+** @param value Value to convert
+**
+** @return The number of characters placed into the buffer
+** (not including the NUL)
+**
+** NOTE: assumes buf is large enough to hold the resulting string
+*/
+int cvtoct( char *buf, uint32_t value );
+
+/**
+** bound(min,value,max)
+**
+** This function confines an argument within specified bounds.
+**
+** @param min Lower bound
+** @param value Value to be constrained
+** @param max Upper bound
+**
+** @return The constrained value
+*/
+uint32_t bound( uint32_t min, uint32_t value, uint32_t max );
+
+#endif /* !ASM_SRC */
+
+/*
+** Finally, pull in the level-specific library headers
+*/
+#ifdef KERNEL_SRC
+#include <klib.h>
+#else
+#include <ulib.h>
+#endif /* KERNEL_SRC */
+
+#endif
diff --git a/kernel/old/include/list.h b/kernel/old/include/list.h
index 0be11e9..28c2377 100644
--- a/kernel/old/include/list.h
+++ b/kernel/old/include/list.h
@@ -35,7 +35,7 @@
// The list structure
typedef struct list_s {
- struct list_s *next; // link to the successor
+ struct list_s *next; // link to the successor
} list_t;
/*
@@ -50,7 +50,7 @@ typedef struct list_s {
** @param[in,out] list The address of a list_t variable
** @param[in] data The data to prepend to the list
*/
-void list_add(list_t *list, void *data);
+void list_add( list_t *list, void *data );
/**
** Name: list_remove
@@ -61,7 +61,7 @@ void list_add(list_t *list, void *data);
**
** @return a pointer to the removed data, or NULL if the list was empty
*/
-void *list_remove(list_t *list);
+void *list_remove( list_t *list );
#endif /* !ASM_SRC */
diff --git a/kernel/old/include/offsets.h b/kernel/old/include/offsets.h
deleted file mode 100644
index bf19776..0000000
--- a/kernel/old/include/offsets.h
+++ /dev/null
@@ -1,83 +0,0 @@
-/**
-** @file offsets.h
-**
-** GENERATED AUTOMATICALLY - DO NOT EDIT
-**
-** This header file contains C Preprocessor macros which expand
-** into the byte offsets needed to reach fields within structs
-** used in the baseline system. Should those struct declarations
-** change, the Offsets program should be modified (if needed),
-** recompiled, and re-run to recreate this file.
-*/
-
-#ifndef OFFSETS_H_
-#define OFFSETS_H_
-
-// Sizes of basic types
-
-#define SZ_char 1
-#define SZ_short 2
-#define SZ_int 4
-#define SZ_long 4
-#define SZ_long_long 8
-#define SZ_pointer 4
-
-// Sizes of our types
-
-#define SZ_int8_t 1
-#define SZ_uint8_t 1
-#define SZ_int16_t 2
-#define SZ_uint16_t 2
-#define SZ_int32_t 4
-#define SZ_uint32_t 4
-#define SZ_int64_t 8
-#define SZ_uint64_t 8
-#define SZ_bool_t 1
-
-// context_t structure
-
-#define SZ_CTX 72
-
-#define CTX_ss 0
-#define CTX_gs 4
-#define CTX_fs 8
-#define CTX_es 12
-#define CTX_ds 16
-#define CTX_edi 20
-#define CTX_esi 24
-#define CTX_ebp 28
-#define CTX_esp 32
-#define CTX_ebx 36
-#define CTX_edx 40
-#define CTX_ecx 44
-#define CTX_eax 48
-#define CTX_vector 52
-#define CTX_code 56
-#define CTX_eip 60
-#define CTX_cs 64
-#define CTX_eflags 68
-
-// section_t structure
-
-#define SZ_SCT 8
-
-#define SCT_length 0
-#define SCT_addr 4
-
-// pcb_t structure
-
-#define SZ_PCB 72
-
-#define PCB_context 0
-#define PCB_pdir 4
-#define PCB_sects 8
-#define PCB_next 40
-#define PCB_parent 44
-#define PCB_wakeup 48
-#define PCB_exit_status 52
-#define PCB_pid 56
-#define PCB_state 60
-#define PCB_priority 64
-#define PCB_ticks 68
-
-#endif
diff --git a/kernel/old/include/params.h b/kernel/old/include/params.h
index 7a41e02..52eb81d 100644
--- a/kernel/old/include/params.h
+++ b/kernel/old/include/params.h
@@ -20,14 +20,12 @@
// Upper bound on the number of simultaneous user-level
// processes in the system (completely arbitrary)
-#define N_PROCS 25
-// Limit on the number of entries in argv[], INCLUDING
-// the trailing NULL pointer (also completely arbitrary)
-#define N_ARGS 10
+#define N_PROCS 25
// Clock frequency (Hz)
-#define CLOCK_FREQ 1000
-#define TICKS_PER_MS 1
+
+#define CLOCK_FREQ 1000
+#define TICKS_PER_MS 1
#endif
diff --git a/kernel/old/include/procs.h b/kernel/old/include/procs.h
index bc5b705..9db4ac8 100644
--- a/kernel/old/include/procs.h
+++ b/kernel/old/include/procs.h
@@ -30,28 +30,22 @@
*/
enum state_e {
// pre-viable
- STATE_UNUSED = 0,
- STATE_NEW,
+ STATE_UNUSED = 0, STATE_NEW,
// runnable
- STATE_READY,
- STATE_RUNNING,
+ STATE_READY, STATE_RUNNING,
// runnable, but waiting for some event
- STATE_SLEEPING,
- STATE_BLOCKED,
- STATE_WAITING,
+ STATE_SLEEPING, STATE_BLOCKED, STATE_WAITING,
// no longer runnable
- STATE_KILLED,
- STATE_ZOMBIE
+ STATE_KILLED, STATE_ZOMBIE
// sentinel value
- ,
- N_STATES
+ , N_STATES
};
// these may be handy for checking general conditions of processes
// they depend on the order of the state names in the enum!
-#define FIRST_VIABLE STATE_READY
-#define FIRST_BLOCKED STATE_SLEEPING
-#define LAST_VIABLE STATE_WAITING
+#define FIRST_VIABLE STATE_READY
+#define FIRST_BLOCKED STATE_SLEEPING
+#define LAST_VIABLE STATE_WAITING
/*
** Process priorities are defined in <defs.h>
@@ -60,13 +54,17 @@ enum state_e {
/*
** Quantum lengths - values are number of clock ticks
*/
-enum quantum_e { QUANTUM_SHORT = 1, QUANTUM_STANDARD = 3, QUANTUM_LONG = 5 };
+enum quantum_e {
+ QUANTUM_SHORT = 1,
+ QUANTUM_STANDARD = 3,
+ QUANTUM_LONG = 5
+};
/*
** PID-related definitions
*/
-#define PID_INIT 1
-#define FIRST_USER_PID 2
+#define PID_INIT 1
+#define FIRST_USER_PID 2
/*
** Process context structure
@@ -80,7 +78,7 @@ enum quantum_e { QUANTUM_SHORT = 1, QUANTUM_STANDARD = 3, QUANTUM_LONG = 5 };
*/
typedef struct context_s {
- uint32_t ss; // pushed by isr_save
+ uint32_t ss; // pushed by isr_save
uint32_t gs;
uint32_t fs;
uint32_t es;
@@ -94,34 +92,34 @@ typedef struct context_s {
uint32_t ecx;
uint32_t eax;
uint32_t vector;
- uint32_t code; // pushed by isr_save or the hardware
- uint32_t eip; // pushed by the hardware
+ uint32_t code; // pushed by isr_save or the hardware
+ uint32_t eip; // pushed by the hardware
uint32_t cs;
uint32_t eflags;
} context_t;
-#define SZ_CONTEXT sizeof(context_t)
+#define SZ_CONTEXT sizeof(context_t)
/*
** program section information for user processes
*/
typedef struct section_s {
- uint_t length; // length, in some units
- uint_t addr; // location, in some units
+ uint_t length; // length, in some units
+ uint_t addr; // location, in some units
} section_t;
// note: these correspond to the PT_LOAD sections found in
// an ELF file, not necessarily to text/data/bss
-#define SECT_L1 0
-#define SECT_L2 1
-#define SECT_L3 2
-#define SECT_STACK 3
+#define SECT_L1 0
+#define SECT_L2 1
+#define SECT_L3 2
+#define SECT_STACK 3
// total number of section table entries in our PCB
-#define N_SECTS 4
+#define N_SECTS 4
// number of those that can be loaded from an ELF module
-#define N_LOADABLE 3
+#define N_LOADABLE 3
/*
** The process control block
@@ -134,31 +132,32 @@ typedef struct section_s {
*/
typedef struct pcb_s {
+
// four-byte fields
// start with these four bytes, for easy access in assembly
- context_t *context; // pointer to context save area on stack
+ context_t *context; // pointer to context save area on stack
// VM information
- pde_t *pdir; // page directory for this process
- section_t sects[N_SECTS]; // per-section memory information
+ pde_t *pdir; // page directory for this process
+ section_t sects[N_SECTS]; // per-section memory information
// queue linkage
- struct pcb_s *next; // next PCB in queue
+ struct pcb_s *next; // next PCB in queue
// process state information
- struct pcb_s *parent; // pointer to PCB of our parent process
- uint32_t wakeup; // wakeup time, for sleeping processes
- int32_t exit_status; // termination status, for parent's use
+ struct pcb_s *parent; // pointer to PCB of our parent process
+ uint32_t wakeup; // wakeup time, for sleeping processes
+ int32_t exit_status; // termination status, for parent's use
// these things may not need to be four bytes
- uint_t pid; // PID of this process
- enum state_e state; // process' current state
- enum priority_e priority; // process priority level
- uint_t ticks; // remaining ticks in this time slice
+ uint_t pid; // PID of this process
+ enum state_e state; // process' current state
+ enum priority_e priority; // process priority level
+ uint_t ticks; // remaining ticks in this time slice
} pcb_t;
-#define SZ_PCB sizeof(pcb_t)
+#define SZ_PCB sizeof(pcb_t)
/*
** PCB queue structure (opaque to the rest of the kernel)
@@ -169,16 +168,12 @@ typedef struct pcb_queue_s *pcb_queue_t;
** Queue ordering methods
*/
enum pcb_queue_order_e {
- O_FIFO,
- O_PRIO,
- O_PID,
- O_WAKEUP
+ O_FIFO, O_PRIO, O_PID, O_WAKEUP
// sentinel
- ,
- N_ORDERINGS
+ , N_ORDERINGS
};
-#define O_FIRST_STYLE O_FIFO
-#define O_LAST_STYLE O_WAKEUP
+#define O_FIRST_STYLE O_FIFO
+#define O_LAST_STYLE O_WAKEUP
/*
** Globals
@@ -205,13 +200,13 @@ extern uint_t next_pid;
extern pcb_t *init_pcb;
// table of state name strings
-extern const char state_str[N_STATES][4];
+extern const char *state_str[N_STATES];
// table of priority name strings
-extern const char prio_str[N_PRIOS][5];
+extern const char *prio_str[N_PRIOS];
// table of queue ordering name strings
-extern const char ord_str[N_ORDERINGS][5];
+extern const char *ord_str[N_ORDERINGS];
/*
** Prototypes
@@ -222,7 +217,7 @@ extern const char ord_str[N_ORDERINGS][5];
**
** Initialization for the Process module.
*/
-void pcb_init(void);
+void pcb_init( void );
/**
** Name: pcb_alloc
@@ -233,7 +228,7 @@ void pcb_init(void);
**
** @return status of the allocation attempt
*/
-int pcb_alloc(pcb_t **pcb);
+int pcb_alloc( pcb_t **pcb );
/**
** Name: pcb_free
@@ -242,7 +237,7 @@ int pcb_alloc(pcb_t **pcb);
**
** @param pcb Pointer to the PCB to be deallocated.
*/
-void pcb_free(pcb_t *pcb);
+void pcb_free( pcb_t *pcb );
/**
** Name: pcb_zombify
@@ -253,7 +248,7 @@ void pcb_free(pcb_t *pcb);
**
** @param pcb Pointer to the newly-undead PCB
*/
-void pcb_zombify(register pcb_t *victim);
+void pcb_zombify( register pcb_t *victim );
/**
** Name: pcb_cleanup
@@ -262,7 +257,7 @@ void pcb_zombify(register pcb_t *victim);
**
** @param pcb The PCB to reclaim
*/
-void pcb_cleanup(pcb_t *pcb);
+void pcb_cleanup( pcb_t *pcb );
/**
** Name: pcb_find_pid
@@ -273,7 +268,7 @@ void pcb_cleanup(pcb_t *pcb);
**
** @return Pointer to the PCB, or NULL
*/
-pcb_t *pcb_find_pid(uint_t pid);
+pcb_t *pcb_find_pid( uint_t pid );
/**
** Name: pcb_find_ppid
@@ -284,7 +279,7 @@ pcb_t *pcb_find_pid(uint_t pid);
**
** @return Pointer to the PCB, or NULL
*/
-pcb_t *pcb_find_ppid(uint_t pid);
+pcb_t *pcb_find_ppid( uint_t pid );
/**
** Name: pcb_queue_reset
@@ -296,7 +291,7 @@ pcb_t *pcb_find_ppid(uint_t pid);
**
** @return status of the init request
*/
-int pcb_queue_reset(pcb_queue_t queue, enum pcb_queue_order_e style);
+int pcb_queue_reset( pcb_queue_t queue, enum pcb_queue_order_e style );
/**
** Name: pcb_queue_empty
@@ -308,7 +303,7 @@ int pcb_queue_reset(pcb_queue_t queue, enum pcb_queue_order_e style);
**
** @return true if the queue is empty, else false
*/
-bool_t pcb_queue_empty(pcb_queue_t queue);
+bool_t pcb_queue_empty( pcb_queue_t queue );
/**
** Name: pcb_queue_length
@@ -319,7 +314,7 @@ bool_t pcb_queue_empty(pcb_queue_t queue);
**
** @return the count (0 if the queue is empty)
*/
-uint_t pcb_queue_length(const pcb_queue_t queue);
+uint_t pcb_queue_length( const pcb_queue_t queue );
/**
** Name: pcb_queue_insert
@@ -331,7 +326,7 @@ uint_t pcb_queue_length(const pcb_queue_t queue);
**
** @return status of the insertion request
*/
-int pcb_queue_insert(pcb_queue_t queue, pcb_t *pcb);
+int pcb_queue_insert( pcb_queue_t queue, pcb_t *pcb );
/**
** Name: pcb_queue_peek
@@ -343,7 +338,7 @@ int pcb_queue_insert(pcb_queue_t queue, pcb_t *pcb);
**
** @return the PCB pointer, or NULL if the queue is empty
*/
-pcb_t *pcb_queue_peek(const pcb_queue_t queue);
+pcb_t *pcb_queue_peek( const pcb_queue_t queue );
/**
** Name: pcb_queue_remove
@@ -355,7 +350,7 @@ pcb_t *pcb_queue_peek(const pcb_queue_t queue);
**
** @return status of the removal request
*/
-int pcb_queue_remove(pcb_queue_t queue, pcb_t **pcb);
+int pcb_queue_remove( pcb_queue_t queue, pcb_t **pcb );
/**
** Name: pcb_queue_remove_this
@@ -367,7 +362,7 @@ int pcb_queue_remove(pcb_queue_t queue, pcb_t **pcb);
**
** @return status of the removal request
*/
-int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb);
+int pcb_queue_remove_this( pcb_queue_t queue, pcb_t *pcb );
/*
** Scheduler routines
@@ -380,14 +375,14 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb);
**
** @param pcb Pointer to the PCB of the process to be scheduled
*/
-void schedule(pcb_t *pcb);
+void schedule( pcb_t *pcb );
/**
** dispatch()
**
** Select the next process to receive the CPU
*/
-void dispatch(void);
+void dispatch( void );
/*
** Debugging/tracing routines
@@ -401,7 +396,7 @@ void dispatch(void);
** @param msg[in] An optional message to print before the dump
** @param c[in] The context to dump out
*/
-void ctx_dump(const char *msg, register context_t *c);
+void ctx_dump( const char *msg, register context_t *c );
/**
** Name: ctx_dump_all
@@ -410,7 +405,7 @@ void ctx_dump(const char *msg, register context_t *c);
**
** @param msg[in] Optional message to print
*/
-void ctx_dump_all(const char *msg);
+void ctx_dump_all( const char *msg );
/**
** Name: pcb_dump
@@ -421,7 +416,7 @@ void ctx_dump_all(const char *msg);
** @param p[in] The PCB to dump
** @param all[in] Dump all the contents?
*/
-void pcb_dump(const char *msg, register pcb_t *p, bool_t all);
+void pcb_dump( const char *msg, register pcb_t *p, bool_t all );
/**
** Name: pcb_queue_dump
@@ -432,7 +427,7 @@ void pcb_dump(const char *msg, register pcb_t *p, bool_t all);
** @param queue[in] The queue to dump
** @param contents[in] Also dump (some) contents?
*/
-void pcb_queue_dump(const char *msg, pcb_queue_t queue, bool_t contents);
+void pcb_queue_dump( const char *msg, pcb_queue_t queue, bool_t contents );
/**
** Name: ptable_dump
@@ -442,7 +437,7 @@ void pcb_queue_dump(const char *msg, pcb_queue_t queue, bool_t contents);
** @param msg[in] Optional message to print
** @param all[in] Dump all or only part of the relevant data
*/
-void ptable_dump(const char *msg, bool_t all);
+void ptable_dump( const char *msg, bool_t all );
/**
** Name: ptable_dump_counts
@@ -450,8 +445,8 @@ void ptable_dump(const char *msg, bool_t all);
** Prints basic information about the process table (number of
** entries, number with each process state, etc.).
*/
-void ptable_dump_counts(void);
+void ptable_dump_counts( void );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/serial.h b/kernel/old/include/serial.h
deleted file mode 100644
index 20bf192..0000000
--- a/kernel/old/include/serial.h
+++ /dev/null
@@ -1,3 +0,0 @@
-#pragma once
-
-#include <stdint.h>
diff --git a/kernel/old/include/sio.h b/kernel/old/include/sio.h
index 629fda2..dca80ed 100644
--- a/kernel/old/include/sio.h
+++ b/kernel/old/include/sio.h
@@ -18,9 +18,9 @@
// sio interrupt settings
-#define SIO_TX 0x01
-#define SIO_RX 0x02
-#define SIO_BOTH (SIO_TX | SIO_RX)
+#define SIO_TX 0x01
+#define SIO_RX 0x02
+#define SIO_BOTH (SIO_TX | SIO_RX)
#ifndef ASM_SRC
@@ -48,7 +48,7 @@ extern QTYPE QNAME;
**
** Initialize the UART chip.
*/
-void sio_init(void);
+void sio_init( void );
/**
** sio_enable()
@@ -61,7 +61,7 @@ void sio_init(void);
**
** @return the prior IER setting
*/
-uint8_t sio_enable(uint8_t which);
+uint8_t sio_enable( uint8_t which );
/**
** sio_disable()
@@ -74,7 +74,7 @@ uint8_t sio_enable(uint8_t which);
**
** @return the prior IER setting
*/
-uint8_t sio_disable(uint8_t which);
+uint8_t sio_disable( uint8_t which );
/**
** sio_inq_length()
@@ -85,7 +85,7 @@ uint8_t sio_disable(uint8_t which);
**
** @return the count of characters still in the input queue
*/
-int sio_inq_length(void);
+int sio_inq_length( void );
/**
** sio_readc()
@@ -96,7 +96,7 @@ int sio_inq_length(void);
**
** @return the next character, or -1 if no character is available
*/
-int sio_readc(void);
+int sio_readc( void );
/**
** sio_read()
@@ -110,7 +110,7 @@ int sio_readc(void);
**
** @return the number of bytes copied, or 0 if no characters were available
*/
-int sio_read(char *buffer, int length);
+int sio_read( char *buffer, int length );
/**
** sio_writec( ch )
@@ -121,7 +121,7 @@ int sio_read(char *buffer, int length);
**
** @param ch Character to be written (in the low-order 8 bits)
*/
-void sio_writec(int ch);
+void sio_writec( int ch );
/**
** sio_write( ch )
@@ -135,7 +135,7 @@ void sio_writec(int ch);
**
** @return the number of characters copied into the SIO output buffer
*/
-int sio_write(const char *buffer, int length);
+int sio_write( const char *buffer, int length );
/**
** sio_puts( buf )
@@ -148,7 +148,7 @@ int sio_write(const char *buffer, int length);
**
** @return the count of bytes transferred
*/
-int sio_puts(const char *buffer);
+int sio_puts( const char *buffer );
/**
** sio_dump( full )
@@ -161,8 +161,8 @@ int sio_puts(const char *buffer);
** is being requested (which includes the contents
** of the queues)
*/
-void sio_dump(bool_t full);
+void sio_dump( bool_t full );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/support.h b/kernel/old/include/support.h
index ac75a64..bdc5dc6 100644
--- a/kernel/old/include/support.h
+++ b/kernel/old/include/support.h
@@ -30,14 +30,14 @@
**
** Ultimately, just remember that THESE VALUES ARE APPROXIMATE AT BEST.
*/
-#define DELAY_1_SEC 40
-#define DELAY_1_25_SEC 50
-#define DELAY_2_SEC 80
-#define DELAY_2_5_SEC 100
-#define DELAY_3_SEC 120
-#define DELAY_5_SEC 200
-#define DELAY_7_SEC 280
-#define DELAY_10_SEC 400
+#define DELAY_1_SEC 40
+#define DELAY_1_25_SEC 50
+#define DELAY_2_SEC 80
+#define DELAY_2_5_SEC 100
+#define DELAY_3_SEC 120
+#define DELAY_5_SEC 200
+#define DELAY_7_SEC 280
+#define DELAY_10_SEC 400
#ifndef ASM_SRC
/**
@@ -49,7 +49,7 @@
**
** @param reason NUL-terminated message to be printed.
*/
-void panic(char *reason);
+void panic( char *reason );
/**
** init_interrupts
@@ -58,7 +58,7 @@ void panic(char *reason);
** IDT and the PIC. It is up to the user to enable processor interrupts
** when they're ready.
*/
-void init_interrupts(void);
+void init_interrupts( void );
/*
** install_isr
@@ -71,7 +71,8 @@ void init_interrupts(void);
**
** @return a pointer to the previously-registered ISR
*/
-void (*install_isr(int vector, void (*handler)(int, int)))(int, int);
+void (*install_isr( int vector,
+ void ( *handler )(int,int) ) )( int, int );
/*
** Name: delay
@@ -79,8 +80,8 @@ void (*install_isr(int vector, void (*handler)(int, int)))(int, int);
** See the comment above about the relative accuracy of the 'length'
** parameter.
*/
-void delay(int length);
+void delay( int length );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/syscalls.h b/kernel/old/include/syscalls.h
index 27392a1..e66f6c0 100644
--- a/kernel/old/include/syscalls.h
+++ b/kernel/old/include/syscalls.h
@@ -23,28 +23,28 @@
** so that they can be used from assembly
*/
-#define SYS_exit 0
-#define SYS_waitpid 1
-#define SYS_fork 2
-#define SYS_exec 3
-#define SYS_read 4
-#define SYS_write 5
-#define SYS_getpid 6
-#define SYS_getppid 7
-#define SYS_gettime 8
-#define SYS_getprio 9
-#define SYS_setprio 10
-#define SYS_kill 11
-#define SYS_sleep 12
+#define SYS_exit 0
+#define SYS_waitpid 1
+#define SYS_fork 2
+#define SYS_exec 3
+#define SYS_read 4
+#define SYS_write 5
+#define SYS_getpid 6
+#define SYS_getppid 7
+#define SYS_gettime 8
+#define SYS_getprio 9
+#define SYS_setprio 10
+#define SYS_kill 11
+#define SYS_sleep 12
// UPDATE THIS DEFINITION IF MORE SYSCALLS ARE ADDED!
-#define N_SYSCALLS 13
+#define N_SYSCALLS 13
// dummy system call code for testing our ISR
-#define SYS_bogus 0xbad
+#define SYS_bogus 0xbad
// interrupt vector entry for system calls
-#define VEC_SYSCALL 0x80
+#define VEC_SYSCALL 0x80
#ifndef ASM_SRC
@@ -71,10 +71,10 @@
**
** Syscall module initialization routine
*/
-void sys_init(void);
+void sys_init( void );
-#endif /* KERNEL_SRC */
+#endif /* KERNEL_SRC */
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/types.h b/kernel/old/include/types.h
index 9435954..2f934f1 100644
--- a/kernel/old/include/types.h
+++ b/kernel/old/include/types.h
@@ -1,13 +1,58 @@
+/**
+** @file types.h
+**
+** @author Warren R. Carithers
+**
+** @brief Common type declarations.
+**
+** This header file contains type declarations used throughout
+** the kernel and user code.
+*/
+
#ifndef TYPES_H_
#define TYPES_H_
+
#ifndef ASM_SRC
+/*
+** Start of C-only definitions
+**
+** Anything that should not be visible to something other than
+** the C compiler should be put here.
+*/
+
+/*
+** Types
+*/
+
+// standard integer sized types
+typedef char int8_t;
+typedef unsigned char uint8_t;
+typedef short int16_t;
+typedef unsigned short uint16_t;
+typedef int int32_t;
+typedef unsigned int uint32_t;
+typedef long long int int64_t;
+typedef unsigned long long int uint64_t;
+
+// other integer types
+typedef unsigned char uchar_t;
+typedef unsigned int uint_t;
+typedef unsigned long int ulong_t;
+
+// Boolean values
+typedef uint8_t bool_t;
+
+#define true 1
+#define false 0
+
#ifdef KERNEL_SRC
// we define these here instead of in vm.h in order to get around a
// nasty chick/egg dependency between procs.h and vm.h
-typedef uint32_t pde_t; // page directory entry
-typedef uint32_t pte_t; // page table entry
-#endif /* KERNEL_SRC */
+typedef uint32_t pde_t; // page directory entry
+typedef uint32_t pte_t; // page table entry
+#endif /* KERNEL_SRC */
+
+#endif /* !ASM_SRC */
-#endif
#endif
diff --git a/kernel/old/include/udefs.h b/kernel/old/include/udefs.h
new file mode 100644
index 0000000..50b6952
--- /dev/null
+++ b/kernel/old/include/udefs.h
@@ -0,0 +1,113 @@
+/**
+** @file udefs.h
+**
+** @author CSCI-452 class of 20245
+**
+** @brief "Userland" configuration information
+*/
+
+#ifndef UDEFS_H_
+#define UDEFS_H_
+
+#include <common.h>
+
+/*
+** General (C and/or assembly) definitions
+**
+** This section of the header file contains definitions that can be
+** used in either C or assembly-language source code.
+*/
+
+// delay loop counts
+
+#define DELAY_LONG 100000000
+#define DELAY_MED 4500000
+#define DELAY_SHORT 2500000
+
+#define DELAY_STD DELAY_SHORT
+
+#ifndef ASM_SRC
+
+/*
+** Start of C-only definitions
+*/
+
+// convenience macros
+
+// a delay loop - kind of ugly, but it works
+
+#define DELAY(n) do { \
+ for(int _dlc = 0; _dlc < (DELAY_##n); ++_dlc) continue; \
+ } while(0)
+
+/*
+** We need the list of program IDs so that we can request
+** their execution
+*/
+
+#include <userids.h>
+
+/*
+** All user main() functions have the following prototype:
+**
+** int name( int argc, char *argv[] );
+**
+** To simplify declaring them, we define a macro that expands into
+** that header. This can be used both in the implementation (followed
+** by the function body) and in places where we just need the prototype
+** (following it with a semicolon).
+*/
+
+#define USERMAIN(f) int f( int argc, char *argv[] )
+
+/*
+** User process controls.
+**
+** To enable a specific test, define the symbol SPAWN_name here, and
+** guard the places in other code that use or refer to that test. For
+** example, test 'A' is enabled by definining SPAWN_A here, and all
+** places that refer to test 'A' are guarded with:
+**
+** #ifdef SPAWN_A
+** ... conditionally-compiled code
+** #endif
+**
+** Generally, most of these will exit with a status of 0. If a process
+** returns from its main function when it shouldn't (e.g., if it had
+** called exit() but continued to run), it will usually return a status
+** of ?.
+*/
+
+/*
+** The standard set of test programs, start by the shell (which is started
+** automatically from the initial user process)
+**
+** There is no user 'O' program, and programs 'W' through 'Z' are spawned
+** from other processes and are never spawned directly.
+*/
+
+#define SPAWN_A
+#define SPAWN_B
+#define SPAWN_C
+#define SPAWN_D
+#define SPAWN_E
+#define SPAWN_F
+#define SPAWN_G
+#define SPAWN_H
+#define SPAWN_I
+#define SPAWN_J
+#define SPAWN_K
+#define SPAWN_L
+#define SPAWN_M
+#define SPAWN_N
+#define SPAWN_P
+#define SPAWN_Q
+#define SPAWN_R
+#define SPAWN_S
+#define SPAWN_T
+#define SPAWN_U
+#define SPAWN_V
+
+#endif /* !ASM_SRC */
+
+#endif
diff --git a/kernel/old/include/ulib.h b/kernel/old/include/ulib.h
new file mode 100644
index 0000000..d254d6a
--- /dev/null
+++ b/kernel/old/include/ulib.h
@@ -0,0 +1,315 @@
+/**
+** @file ulib.h
+**
+** @author CSCI-452 class of 20245
+**
+** @brief Declarations for user-level library functions
+**
+** This module implements a simple collection of support functions
+** similar to the standard C library.
+*/
+
+#ifndef ULIB_H_
+#define ULIB_H_
+
+#include <common.h>
+
+/*
+** General (C and/or assembly) definitions
+*/
+
+#ifndef ASM_SRC
+
+/*
+** Start of C-only definitions
+*/
+
+/*
+** Types
+*/
+
+/*
+** Globals
+*/
+
+/*
+** Prototypes
+*/
+
+/*
+*************************************************
+** SYSTEM CALLS *********************************
+*************************************************
+*/
+
+/**
+** exit - terminate the calling process
+**
+** usage: exit(status);
+**
+** @param status Termination status of this process
+**
+** Does not return.
+*/
+void exit( int32_t status );
+
+/**
+** waitpid - wait for a child process to terminate
+**
+** usage: pid = waitpid(pid,&status);
+**
+** @param pid PID of the desired child, or 0 for any child
+** @param status Pointer to int32_t into which the child's status is placed,
+** or NULL
+**
+** @return The PID of the terminated child, or an error code
+**
+** If there are no children in the system, returns an error code (*status
+** is unchanged).
+**
+** If there are one or more children in the system and at least one has
+** terminated but hasn't yet been cleaned up, cleans up that process and
+** returns its information; otherwise, blocks until a child terminates.
+*/
+int waitpid( uint_t pid, int32_t *status );
+
+/**
+** fork - create a duplicate of the calling process
+**
+** usage: pid = fork();
+**
+** @return parent - the pid of the new child, or an error code
+** child - 0
+*/
+int fork( void );
+
+/**
+** exec - replace the memory image of the calling process
+**
+** usage: exec( what, args )
+**
+** @param what program table index of the program to exec
+** @param args the command-line argument vector
+**
+** Does not return if it succeeds; if it returns, something has
+** gone wrong.
+*/
+void exec( uint_t what, char **args );
+
+/**
+** read - read into a buffer from a stream
+**
+** usage: n = read(channel,buf,length)
+**
+** @param chan I/O stream to read from
+** @param buf Buffer to read into
+** @param length Maximum capacity of the buffer
+**
+** @return The count of bytes transferred, or an error code
+*/
+int read( uint_t chan, void *buffer, uint_t length );
+
+/**
+** write - write from a buffer to a stream
+**
+** usage: n = write(channel,buf,length)
+**
+** @param chan I/O stream to write to
+** @param buf Buffer to write from
+** @param length Maximum capacity of the buffer
+**
+** @return The count of bytes transferred, or an error code
+*/
+int write( uint_t chan, const void *buffer, uint_t length );
+
+/**
+** getpid - get the PID of the calling process
+**
+** usage: pid = getpid()
+**
+** @return the PID of this process
+*/
+uint_t getpid( void );
+
+/**
+** getppid - get the PID of the calling process' parent
+**
+** usage: pid = getppid()
+**
+** @return the PID of this process' parent
+*/
+uint_t getppid( void );
+
+/**
+** gettime - get the current system time
+**
+** usage: pid = gettime()
+**
+** @return the system time
+*/
+uint32_t gettime( void );
+
+/**
+** getprio - get the scheduling priority of the calling process
+**
+** usage: prio = getprio()
+**
+** @return the process' priority
+*/
+int getprio( void );
+
+/**
+** setprio - set the scheduling priority of the calling process
+**
+** usage: oldprio = setprio(newprio)
+**
+** @param new the desired new priority
+**
+** @return the old priority value
+*/
+int setprio( int new );
+
+/**
+** kill - terminate a process with extreme prejudice
+**
+** usage: n = kill( pid )
+**
+** @param pid the intended victim
+**
+** @return 0 on success, else an error code
+*/
+int32_t kill( uint_t pid );
+
+/**
+** sleep - put the current process to sleep for some length of time
+**
+** usage: sleep(n);
+**
+** @param ms Desired sleep time (in ms), or 0 to yield the CPU
+**
+** @return the time the process spent sleeping (in ms)
+*/
+int sleep( uint32_t ms );
+
+/**
+** bogus - a nonexistent system call, to test our syscall ISR
+**
+** usage: bogus()
+**
+** Does not return.
+*/
+void bogus( void );
+
+/*
+*************************************************
+** CONVENIENT "SHORTHAND" VERSIONS OF SYSCALLS **
+*************************************************
+**
+** These are library functions that perform specific common
+** variants of system calls. This helps reduce the total number
+** of system calls, keeping our baseline OS as lean and mean
+** as we can make it. :-)
+*/
+
+/**
+** wait - wait for any child to exit
+**
+** usage: pid = wait(&status)
+**
+** Calls waitpid(0,status)
+**
+** @param status Pointer to int32_t into which the child's status is placed,
+** or NULL
+**
+** @return The PID of the terminated child, or an error code
+*/
+int wait( int32_t *status );
+
+/**
+** spawn - create a new process running a different program
+**
+** usage: n = spawn(what,args)
+**
+** Creates a new process and then execs 'what'
+**
+** @param what Program table index of the program to spawn
+** @param args The command-line argument vector for the process
+**
+** @return The PID of the child, or an error code
+*/
+int spawn( uint_t what, char **args );
+
+/**
+** cwritech(ch) - write a single character to the console
+**
+** @param ch The character to write
+**
+** @return The return value from calling write()
+*/
+int cwritech( char ch );
+
+/**
+** cwrites(str) - write a NUL-terminated string to the console
+**
+** @param str The string to write
+**
+*/
+int cwrites( const char *str );
+
+/**
+** cwrite(buf,leng) - write a sized buffer to the console
+**
+** @param buf The buffer to write
+** @param leng The number of bytes to write
+**
+** @return The return value from calling write()
+*/
+int cwrite( const char *buf, uint32_t leng );
+
+/**
+** swritech(ch) - write a single character to the SIO
+**
+** @param ch The character to write
+**
+** @return The return value from calling write()
+*/
+int swritech( char ch );
+
+/**
+** swrites(str) - write a NUL-terminated string to the SIO
+**
+** @param str The string to write
+**
+** @return The return value from calling write()
+*/
+int swrites( const char *str );
+
+/**
+** swrite(buf,leng) - write a sized buffer to the SIO
+**
+** @param buf The buffer to write
+** @param leng The number of bytes to write
+**
+** @return The return value from calling write()
+*/
+int swrite( const char *buf, uint32_t leng );
+
+/*
+*************************************************
+** MISCELLANEOUS USEFUL SUPPORT FUNCTIONS *******
+*************************************************
+*/
+
+/**
+** fake_exit()
+**
+** dummy "startup" function
+**
+** calls exit(%eax) - serves as the "return to" code for
+** main() functions, in case they don't call exit() themselves
+*/
+void fake_exit( void );
+
+#endif /* !ASM_SRC */
+
+#endif
diff --git a/kernel/old/include/user.h b/kernel/old/include/user.h
index 672f916..4d9402f 100644
--- a/kernel/old/include/user.h
+++ b/kernel/old/include/user.h
@@ -15,7 +15,7 @@
#include <x86/arch.h>
// default value for EFLAGS in new processes
-#define DEFAULT_EFLAGS (EFL_MB1 | EFL_IF)
+#define DEFAULT_EFLAGS (EFL_MB1 | EFL_IF)
/*
** General (C and/or assembly) definitions
@@ -61,14 +61,14 @@ typedef struct header_s {
} header_t;
// length of the file name field
-#define NAMELEN 20
+#define NAMELEN 20
// program descriptor
typedef struct prog_s {
- char name[NAMELEN]; // truncated name (15 chars)
- uint32_t offset; // offset from the beginning of the blob
- uint32_t size; // size of this ELF module
- uint32_t flags; // miscellaneous flags
+ char name[NAMELEN]; // truncated name (15 chars)
+ uint32_t offset; // offset from the beginning of the blob
+ uint32_t size; // size of this ELF module
+ uint32_t flags; // miscellaneous flags
} prog_t;
/*
@@ -84,7 +84,7 @@ typedef struct prog_s {
**
** Initializes the user support module.
*/
-void user_init(void);
+void user_init( void );
/**
** Name: user_locate
@@ -95,7 +95,7 @@ void user_init(void);
**
** @return pointer to the program table entry in the code archive, or NULL
*/
-prog_t *user_locate(uint_t what);
+prog_t *user_locate( uint_t what );
/**
** Name: user_duplicate
@@ -107,7 +107,7 @@ prog_t *user_locate(uint_t what);
**
** @return the status of the duplicate attempt
*/
-int user_duplicate(pcb_t *new, pcb_t *old);
+int user_duplicate( pcb_t *new, pcb_t *old );
/**
** Name: user_load
@@ -118,11 +118,10 @@ int user_duplicate(pcb_t *new, pcb_t *old);
** @param prog A pointer to the program table entry to be loaded
** @param pcb The PCB for the program being loaded
** @param args The argument vector for the program
-** @param sys Is the argument vector from kernel code?
**
** @return the status of the load attempt
*/
-int user_load(prog_t *prog, pcb_t *pcb, const char **args, bool_t sys);
+int user_load( prog_t *prog, pcb_t *pcb, const char **args );
/**
** Name: user_cleanup
@@ -132,8 +131,8 @@ int user_load(prog_t *prog, pcb_t *pcb, const char **args, bool_t sys);
**
** @param pcb The PCB of the program to be cleaned up
*/
-void user_cleanup(pcb_t *pcb);
+void user_cleanup( pcb_t *pcb );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/userids.h b/kernel/old/include/userids.h
new file mode 100644
index 0000000..284f3ee
--- /dev/null
+++ b/kernel/old/include/userids.h
@@ -0,0 +1,33 @@
+/**
+** @file userids.h
+**
+** @author Warren R. Carithers
+**
+** @brief IDs for user-level programs
+**
+** NOTE: this file is automatically generated when the user.img file
+** is created. Do not edit this manually!
+*/
+
+#ifndef USERIDS_H_
+#define USERIDS_H_
+
+#ifndef ASM_SRC
+/*
+** These IDs are used to identify the various user programs.
+** Each call to exec() will provide one of these as the first
+** argument.
+**
+** This list should be updated if/when the collection of
+** user processes changes.
+*/
+enum users_e {
+ Init, Idle, Shell, ProgABC, ProgDE, ProgFG, ProgH, ProgI,
+ ProgJ, ProgKL, ProgMN, ProgP, ProgQ, ProgR, ProgS, ProgTUV,
+ ProgW, ProgX, ProgY, ProgZ
+ // sentinel
+ , N_USERS
+};
+#endif /* !ASM_SRC */
+
+#endif
diff --git a/kernel/old/include/vm.h b/kernel/old/include/vm.h
index dc12568..6e3935e 100644
--- a/kernel/old/include/vm.h
+++ b/kernel/old/include/vm.h
@@ -64,91 +64,87 @@
*/
// user virtual addresses
-#define USER_BASE 0x00000000
-#define USER_MAX 0x003fffff
-#define USER_TEXT 0x00001000
-#define USER_STACK 0x003fe000
-#define USER_STACK_P1 USER_STACK
-#define USER_STACK_P2 0x003ff000
-#define USER_STK_END 0x00400000
+#define USER_TEXT 0x00001000
+#define USER_STACK 0x003fe000
+#define USER_STK_END 0x00400000
// how to find the addresses of the stack pages in the VM hierarchy
// user address space is the first 4MB of virtual memory
-#define USER_PDE 0
-// the stack occupies this range of pages in the user address space
-#define USER_STK_FIRST_PTE 1022
-#define USER_STK_LAST_PTE 1023
+#define USER_PDE 0
+// the stack occupies the last two pages of the address space
+#define USER_STK_PTE1 1022
+#define USER_STK_PTE2 1023
// some important memory addresses
-#define KERN_BASE 0x80000000 // start of "kernel" memory
-#define EXT_BASE 0x00100000 // start of "extended" memory (1MB)
-#define DEV_BASE 0xfe000000 // "device" memory
-#define PHYS_TOP 0x3fffffff // last usable physical address (1GB - 1)
+#define KERN_BASE 0x80000000 // start of "kernel" memory
+#define EXT_BASE 0x00100000 // start of "extended" memory (1MB)
+#define DEV_BASE 0xfe000000 // "device" memory
+#define PHYS_TOP 0x3fffffff // last usable physical address (1GB - 1)
// where the kernel actually lives
-#define KERN_PLINK 0x00010000
-#define KERN_VLINK (KERN_BASE + KERN_PLINK)
+#define KERN_PLINK 0x00010000
+#define KERN_VLINK (KERN_BASE + KERN_PLINK)
// number of entries in a page directory or page table
-#define N_PDE 1024
-#define N_PTE 1024
+#define N_PDE 1024
+#define N_PTE 1024
// index field shift counts and masks
-#define PDIX_SHIFT 22
-#define PTIX_SHIFT 12
-#define PIX2I_MASK 0x3ff
+#define PDIX_SHIFT 22
+#define PTIX_SHIFT 12
+#define PIX2I_MASK 0x3ff
// physical/virtual converters that don't use casting
// (usable from anywhere)
-#define V2PNC(a) ((a) - KERN_BASE)
-#define P2VNC(a) ((a) + KERN_BASE)
+#define V2PNC(a) ((a) - KERN_BASE)
+#define P2VNC(a) ((a) + KERN_BASE)
// page-size address rounding macros
-#define SZ_PG_M1 MOD4K_BITS
-#define SZ_PG_MASK MOD4K_MASK
-#define PGUP(a) (((a) + SZ_PG_M1) & SZ_PG_MASK)
-#define PGDOWN(a) ((a) & SZ_PG_MASK)
+#define SZ_PG_M1 MOD4K_BITS
+#define SZ_PG_MASK MOD4K_MASK
+#define PGUP(a) (((a)+SZ_PG_M1) & SZ_PG_MASK)
+#define PGDOWN(a) ((a) & SZ_PG_MASK)
// page directory entry bit fields
-#define PDE_P 0x00000001 // 1 = present
-#define PDE_RW 0x00000002 // 1 = writable
-#define PDE_US 0x00000004 // 1 = user and system usable
-#define PDE_PWT 0x00000008 // cache: 1 = write-through
-#define PDE_PCD 0x00000010 // cache: 1 = disabled
-#define PDE_A 0x00000020 // accessed
-#define PDE_D 0x00000040 // dirty (4MB pages)
-#define PDE_AVL1 0x00000040 // ignored (4KB pages)
-#define PDE_PS 0x00000080 // 1 = 4MB page size
-#define PDE_G 0x00000100 // global
-#define PDE_AVL2 0x00000e00 // ignored
-#define PDE_PAT 0x00001000 // (4MB pages) use page attribute table
-#define PDE_PTA 0xfffff000 // page table address field (4KB pages)
-#define PDE_FA 0xffc00000 // frame address field (4MB pages)
+#define PDE_P 0x00000001 // 1 = present
+#define PDE_RW 0x00000002 // 1 = writable
+#define PDE_US 0x00000004 // 1 = user and system usable
+#define PDE_PWT 0x00000008 // cache: 1 = write-through
+#define PDE_PCD 0x00000010 // cache: 1 = disabled
+#define PDE_A 0x00000020 // accessed
+#define PDE_D 0x00000040 // dirty (4MB pages)
+#define PDE_AVL1 0x00000040 // ignored (4KB pages)
+#define PDE_PS 0x00000080 // 1 = 4MB page size
+#define PDE_G 0x00000100 // global
+#define PDE_AVL2 0x00000e00 // ignored
+#define PDE_PAT 0x00001000 // (4MB pages) use page attribute table
+#define PDE_PTA 0xfffff000 // page table address field (4KB pages)
+#define PDE_FA 0xffc00000 // frame address field (4MB pages)
// page table entry bit fields
-#define PTE_P 0x00000001 // present
-#define PTE_RW 0x00000002 // 1 = writable
-#define PTE_US 0x00000004 // 1 = user and system usable
-#define PTE_PWT 0x00000008 // cache: 1 = write-through
-#define PTE_PCD 0x00000010 // cache: 1 = disabled
-#define PTE_A 0x00000020 // accessed
-#define PTE_D 0x00000040 // dirty
-#define PTE_PAT 0x00000080 // use page attribute table
-#define PTE_G 0x00000100 // global
-#define PTE_AVL2 0x00000e00 // ignored
-#define PTE_FA 0xfffff000 // frame address field
+#define PTE_P 0x00000001 // present
+#define PTE_RW 0x00000002 // 1 = writable
+#define PTE_US 0x00000004 // 1 = user and system usable
+#define PTE_PWT 0x00000008 // cache: 1 = write-through
+#define PTE_PCD 0x00000010 // cache: 1 = disabled
+#define PTE_A 0x00000020 // accessed
+#define PTE_D 0x00000040 // dirty
+#define PTE_PAT 0x00000080 // use page attribute table
+#define PTE_G 0x00000100 // global
+#define PTE_AVL2 0x00000e00 // ignored
+#define PTE_FA 0xfffff000 // frame address field
// error code bit assignments for page faults
-#define PFLT_P 0x00000001
-#define PFLT_W 0x00000002
-#define PFLT_US 0x00000004
-#define PFLT_RSVD 0x00000008
-#define PFLT_ID 0x00000010
-#define PFLT_PK 0x00000020
-#define PFLT_SS 0x00000040
-#define PFLT_HLAT 0x00000080
-#define PFLT_SGX 0x00008000
-#define PFLT_UNUSED 0xffff7f00
+#define PFLT_P 0x00000001
+#define PFLT_W 0x00000002
+#define PFLT_US 0x00000004
+#define PFLT_RSVD 0x00000008
+#define PFLT_ID 0x00000010
+#define PFLT_PK 0x00000020
+#define PFLT_SS 0x00000040
+#define PFLT_HLAT 0x00000080
+#define PFLT_SGX 0x00008000
+#define PFLT_UNUSED 0xffff7f00
#ifndef ASM_SRC
@@ -158,59 +154,54 @@
// physical/virtual converters that do use casting
// (not usable from assembly)
-#define V2P(a) (((uint32_t)(a)) - KERN_BASE)
-#define P2V(a) (((uint32_t)(a)) + KERN_BASE)
+#define V2P(a) (((uint32_t)(a)) - KERN_BASE)
+#define P2V(a) (((uint32_t)(a)) + KERN_BASE)
// create a pde/pte from an integer frame number and permission bits
-#define MKPDE(f, p) ((pde_t)(TO_FRAME((f)) | (p)))
-#define MKPTE(f, p) ((pte_t)(TO_FRAME((f)) | (p)))
+#define MKPDE(f,p) ((pde_t)( TO_FRAME((f)) | (p) ))
+#define MKPTE(f,p) ((pte_t)( TO_FRAME((f)) | (p) ))
// is a PDE/PTE present?
// (P bit is in the same place in both)
-#define IS_PRESENT(entry) (((entry) & PDE_P) != 0)
+#define IS_PRESENT(entry) (((entry) & PDE_P) != 0 )
// is a PDE a 4MB page entry?
-#define IS_LARGE(pde) (((pde) & PDE_PS) != 0)
+#define IS_LARGE(pde) (((pde) & PDE_PS) != 0 )
// is this entry "system only" or "system and user"?
-#define IS_SYSTEM(entry) (((entry) & PDE_US) == 0)
-#define IS_USER(entry) (((entry) & PDE_US) != 0)
+#define IS_SYSTEM(entry) (((entry) & PDE_US) == 0 )
+#define IS_USER(entry) (((entry) & PDE_US) != 0 )
// low-order nine bits of PDEs and PTEs hold "permission" flag bits
-#define PERMS_MASK MOD4K_BITS
+#define PERMS_MASK MOD4K_MASK
// 4KB frame numbers are 20 bits wide
-#define FRAME_4K_SHIFT 12
-#define FRAME2I_4K_MASK 0x000fffff
-#define TO_4KFRAME(n) (((n) & FRAME2I_4K_MASK) << FRAME_4K_SHIFT)
-#define GET_4KFRAME(n) (((n) >> FRAME_4K_SHIFT) & FRAME2I_4K_MASK)
-#define PDE_4K_ADDR(n) ((n) & MOD4K_MASK)
-#define PTE_4K_ADDR(n) ((n) & MOD4K_MASK)
+#define FRAME_4K_SHIFT 12
+#define FRAME2I_4K_MASK 0x000fffff
+#define TO_4KFRAME(n) (((n)&FRAME2I_4K_MASK) << FRAME_4K_SHIFT)
+#define GET_4KFRAME(n) (((n) >> FRAME_4K_SHIFT)&F2I_4K_MASK)
+#define PDE_4K_ADDR(n) ((n) & MOD4K_MASK)
+#define PTE_4K_ADDR(n) ((n) & MOD4K_MASK)
// 4MB frame numbers are 10 bits wide
-#define FRAME_4M_SHIFT 22
-#define FRAME2I_4M_MASK 0x000003ff
-#define TO_4MFRAME(n) (((n) & FRAME2I_4M_MASK) << FRAME_4M_SHIFT)
-#define GET_4MFRAME(n) (((n) >> FRAME_4M_SHIFT) & FRAME2I_4M_MASK)
-#define PDE_4M_ADDR(n) ((n) & MOD4M_MASK)
-#define PTE_4M_ADDR(n) ((n) & MOD4M_MASK)
+#define FRAME_4M_SHIFT 22
+#define FRAME2I_4M_MASK 0x000003ff
+#define TO_4MFRAME(n) (((n)&FRAME2I_4M_MASK) << FRAME_4M_SHIFT)
+#define GET_4MFRAME(n) (((n) >> FRAME_4M_SHIFT)&F2I_4M_MASK)
+#define PDE_4M_ADDR(n) ((n) & MOD4M_MASK)
+#define PTE_4M_ADDR(n) ((n) & MOD4M_MASK)
// extract the PMT address or frame address from a table entry
// PDEs could point to 4MB pages, or 4KB PMTs
-#define PDE_ADDR(p) \
- (IS_LARGE(p) ? (((uint32_t)p) & PDE_FA) : (((uint32_t)p) & PDE_PTA))
+#define PDE_ADDR(p) (IS_LARGE(p)?(((uint32_t)p)&PDE_FA):(((uint32_t)p)&PDE_PTA))
// PTEs always point to 4KB pages
-#define PTE_ADDR(p) (((uint32_t)(p)) & PTE_FA)
+#define PTE_ADDR(p) (((uint32_t)(p))&PTE_FA)
// everything has nine bits of permission flags
-#define PERMS(p) (((uint32_t)(p)) & PERMS_MASK)
+#define PERMS(p) (((uint32_t)(p))&PERMS_MASK)
-// extract the table indices from a 32-bit VA
-#define PDIX(v) ((((uint32_t)(v)) >> PDIX_SHIFT) & PIX2I_MASK)
-#define PTIX(v) ((((uint32_t)(v)) >> PTIX_SHIFT) & PIX2I_MASK)
-
-// extract the byte offset from a 32-bit VA
-#define OFFSET_4K(v) (((uint32_t)(v)) & MOD4K_BITS)
-#define OFFSET_4M(v) (((uint32_t)(v)) & MOD4M_BITS)
+// extract the table indices from a 32-bit address
+#define PDIX(v) ((((uint32_t)(v)) >> PDIX_SHIFT) & PIX2I_MASK)
+#define PTIX(v) ((((uint32_t)(v)) >> PTIX_SHIFT) & PIX2I_MASK)
/*
** Types
@@ -223,34 +214,31 @@
// PDE for 4KB pages
typedef struct pdek_s {
- uint_t p : 1; // 0: present
- uint_t rw : 1; // 1: writable
- uint_t us : 1; // 2: user/supervisor
- uint_t pwt : 1; // 3: cache write-through
- uint_t pcd : 1; // 4: cache disable
- uint_t a : 1; // 5: accessed
- uint_t avl1 : 1; // 6: ignored (available)
- uint_t ps : 1; // 7: page size (must be 0)
- uint_t avl2 : 4; // 11-8: ignored (available)
- uint_t fa : 20; // 31-12: frame address
+ uint_t p :1; // present
+ uint_t rw :1; // writable
+ uint_t us :1; // user/supervisor
+ uint_t pwt :1; // cache write-through
+ uint_t pcd :1; // cache disable
+ uint_t a :1; // accessed
+ uint_t avl1 :1; // ignored (available)
+ uint_t ps :1; // page size (must be 0)
+ uint_t avl2 :4; // ignored (available)
+ uint_t fa :20; // frame address
} pdek_f_t;
// PDE for 4MB pages
typedef struct pdem_s {
- uint_t p : 1; // 0: present
- uint_t rw : 1; // 1: writable
- uint_t us : 1; // 2: user/supervisor
- uint_t pwt : 1; // 3: cache write-through
- uint_t pcd : 1; // 4: cache disable
- uint_t a : 1; // 5: accessed
- uint_t d : 1; // 6: dirty
- uint_t ps : 1; // 7: page size (must be 1)
- uint_t g : 1; // 8: global
- uint_t avl : 3; // 11-9: ignored (available)
- uint_t pat : 1; // 12: page attribute table in use
- uint_t fa2 : 4; // 16-13: bits 35-32 of frame address (36-bit addrs)
- uint_t rsv : 5; // 21-17: reserved - must be zero
- uint_t fa : 10; // 31-22: bits 31-22 of frame address
+ uint_t p :1; // present
+ uint_t rw :1; // writable
+ uint_t us :1; // user/supervisor
+ uint_t pwt :1; // cache write-through
+ uint_t pcd :1; // cache disable
+ uint_t a :1; // accessed
+ uint_t d :1; // dirty
+ uint_t ps :1; // page size (must be 1)
+ uint_t g :1; // global
+ uint_t avl :3; // ignored (available)
+ uint_t fa :20; // frame address
} pdem_f_t;
// page table entries
@@ -260,33 +248,33 @@ typedef struct pdem_s {
// broken out into fields
typedef struct pte_s {
- uint_t p : 1; // 0: present
- uint_t rw : 1; // 1: writable
- uint_t us : 1; // 2: user/supervisor
- uint_t pwt : 1; // 3: cache write-through
- uint_t pcd : 1; // 4: cache disable
- uint_t a : 1; // 5: accessed
- uint_t d : 1; // 6: dirty
- uint_t pat : 1; // 7: page attribute table in use
- uint_t g : 1; // 8: global
- uint_t avl : 3; // 11-9: ignored (available)
- uint_t fa : 20; // 31-12: frame address
+ uint_t p :1; // present
+ uint_t rw :1; // writable
+ uint_t us :1; // user/supervisor
+ uint_t pwt :1; // cache write-through
+ uint_t pcd :1; // cache disable
+ uint_t a :1; // accessed
+ uint_t d :1; // dirty
+ uint_t pat :1; // page attribute table in use
+ uint_t g :1; // global
+ uint_t avl :3; // ignored (available)
+ uint_t fa :20; // frame address
} ptef_t;
// page fault error code bits
// comment: meaning when 1 / meaning when 0
struct pfec_s {
- uint_t p : 1; // page-level protection violation / !present
- uint_t w : 1; // write / read
- uint_t us : 1; // user-mode access / supervisor-mode access
- uint_t rsvd : 1; // reserved bit violation / not
- uint_t id : 1; // instruction fetch / data fetch
- uint_t pk : 1; // protection-key violation / !pk
- uint_t ss : 1; // shadow stack access / !ss
- uint_t hlat : 1; // HLAT paging / ordinary paging or access rights
- uint_t xtr1 : 7; // unused
- uint_t sgz : 1; // SGX-specific access control violation / !SGX
- uint_t xtr2 : 16; // more unused
+ uint_t p :1; // page-level protection violation / !present
+ uint_t w :1; // write / read
+ uint_t us :1; // user-mode access / supervisor-mode access
+ uint_t rsvd :1; // reserved bit violation / not
+ uint_t id :1; // instruction fetch / data fetch
+ uint_t pk :1; // protection-key violation / !pk
+ uint_t ss :1; // shadow stack access / !ss
+ uint_t hlat :1; // HLAT paging / ordinary paging or access rights
+ uint_t xtr1 :7; // unused
+ uint_t sgz :1; // SGX-specific access control violation / !SGX
+ uint_t xtr2 :16; // more unused
};
typedef union pfec_u {
@@ -296,23 +284,12 @@ typedef union pfec_u {
// Mapping descriptor for VA::PA mappings
typedef struct mapping_t {
- uint32_t va_start; // starting virtual address for this range
- uint32_t pa_start; // first physical address in the range
- uint32_t pa_end; // last physical address in the range
- uint32_t perm; // access control
+ uint32_t va_start; // starting virtual address for this range
+ uint32_t pa_start; // first physical address in the range
+ uint32_t pa_end; // last physical address in the range
+ uint32_t perm; // access control
} mapping_t;
-// Modes for dumping out page hierarchies
-enum vmmode_e {
- Simple = 0, // just count 'present' entries at each level
- OneLevel, // top-level only: count entries, decode 'present'
- TwoLevel, // count entries & decode at each level
- Full // ??? in case we need more?
- // sentinel
- ,
- N_VMMODES
-};
-
/*
** Globals
*/
@@ -332,20 +309,7 @@ extern pde_t *kpdir;
** Note: should not be called until after the memory free list has
** been set up.
*/
-void vm_init(void);
-
-/**
-** Name: vm_uva2kva
-**
-** Convert a user VA into a kernel address. Works for all addresses -
-** if the address is a page address, the low-order nine bits will be
-** zeroes; otherwise, they is the offset into the page, which is
-** unchanged within the address spaces.
-**
-** @param pdir Pointer to the page directory to examine
-** @param va Virtual address to check
-*/
-void *vm_uva2kva(pde_t *pdir, void *va);
+void vm_init( void );
/**
** Name: vm_pagedup
@@ -356,18 +320,7 @@ void *vm_uva2kva(pde_t *pdir, void *va);
**
** @return a pointer to the new, duplicate page, or NULL
*/
-void *vm_pagedup(void *old);
-
-/**
-** Name: vm_pdedup
-**
-** Duplicate a page directory entry
-**
-** @param entry The entry to be duplicated
-**
-** @return the new entry, or -1 on error.
-*/
-pde_t vm_pdedup(pde_t entry);
+void *vm_pagedup( void *old );
/**
** Name: vm_ptdup
@@ -379,7 +332,7 @@ pde_t vm_pdedup(pde_t entry);
**
** @return true on success, else false
*/
-bool_t vm_ptdup(pde_t *dst, pde_t *curr);
+bool_t vm_ptdup( pde_t *dst, pde_t *curr );
/**
** Name: vm_getpte
@@ -395,28 +348,28 @@ bool_t vm_ptdup(pde_t *dst, pde_t *curr);
**
** @return A pointer to the page table entry for this VA, or NULL
*/
-pte_t *vm_getpte(pde_t *pdir, const void *va, bool_t alloc);
+pte_t *vm_getpte( pde_t *pdir, const void *va, bool_t alloc );
/**
** Name: vm_mkkvm
**
** Create the kernel's page table hierarchy
*/
-pde_t *vm_mkkvm(void);
+pde_t *vm_mkkvm( void );
/**
** Name: vm_mkuvm
**
** Create the page table hierarchy for a user process
*/
-pde_t *vm_mkuvm(void);
+pde_t *vm_mkuvm( void );
/**
** Name: vm_set_kvm
**
** Switch the page table register to the kernel's page directory
*/
-void vm_set_kvm(void);
+void vm_set_kvm( void );
/**
** Name: vm_set_uvm
@@ -425,7 +378,7 @@ void vm_set_kvm(void);
**
** @param p The PCB of the user process
*/
-void vm_set_uvm(pcb_t *p);
+void vm_set_uvm( pcb_t *p );
/**
** Name: vm_add
@@ -443,8 +396,8 @@ void vm_set_uvm(pcb_t *p);
**
** @return status of the allocation attempt
*/
-int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
- char *data, uint32_t bytes);
+int vm_add( pde_t *pdir, bool_t wr, bool_t sys,
+ void *va, uint32_t size, char *data, uint32_t bytes );
/**
** Name: vm_free
@@ -454,7 +407,7 @@ int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
**
** @param pdir Pointer to the page directory
*/
-void vm_free(pde_t *pdir);
+void vm_free( pde_t *pdir );
/*
** Name: vm_map
@@ -465,11 +418,11 @@ void vm_free(pde_t *pdir);
**
** @param pdir Page directory for this address space
** @param va The starting virtual address
-** @param pa The starting physical address
** @param size Length of the range to be mapped
+** @param pa The starting physical address
** @param perm Permission bits for the PTEs
*/
-int vm_map(pde_t *pdir, void *va, uint32_t pa, uint32_t size, int perm);
+int vm_map( pde_t *pdir, void *va, uint_t size, uint_t pa, int perm );
/**
** Name: vm_uvmdup
@@ -478,24 +431,13 @@ int vm_map(pde_t *pdir, void *va, uint32_t pa, uint32_t size, int perm);
** hierarchy. We assume that the "new" page directory exists and
** the system portions of it should not be touched.
**
-** @param new New page directory
** @param old Existing page directory
+** @param new New page directory
**
** @return status of the duplication attempt
*/
-int vm_uvmdup(pde_t *new, pde_t *old);
-
-/**
-** Name: vm_print
-**
-** Print out a paging hierarchy.
-**
-** @param pt Page table to display
-** @param dir Is it a page directory (vs. a page table)?
-** @param mode How to display the entries
-*/
-void vm_print(void *pt, bool_t dir, enum vmmode_e mode);
+int vm_uvmdup( pde_t *old, pde_t *new );
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/vmtables.h b/kernel/old/include/vmtables.h
index 83c0881..17f6e0a 100644
--- a/kernel/old/include/vmtables.h
+++ b/kernel/old/include/vmtables.h
@@ -38,6 +38,6 @@ extern pte_t id_map[];
extern mapping_t kmap[];
extern const uint32_t n_kmap;
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/x86/arch.h b/kernel/old/include/x86/arch.h
index df0b2e2..113c76b 100644
--- a/kernel/old/include/x86/arch.h
+++ b/kernel/old/include/x86/arch.h
@@ -15,25 +15,25 @@
/*
** Video stuff
*/
-#define VID_BASE_ADDR 0xB8000
+#define VID_BASE_ADDR 0xB8000
/*
** Memory management
*/
-#define SEG_PRESENT 0x80
-#define SEG_PL_0 0x00
-#define SEG_PL_1 0x20
-#define SEG_PL_2 0x40
-#define SEG_PL_3 0x50
-#define SEG_SYSTEM 0x00
-#define SEG_NON_SYSTEM 0x10
-#define SEG_32BIT 0x04
-#define DESC_IGATE 0x06
+#define SEG_PRESENT 0x80
+#define SEG_PL_0 0x00
+#define SEG_PL_1 0x20
+#define SEG_PL_2 0x40
+#define SEG_PL_3 0x50
+#define SEG_SYSTEM 0x00
+#define SEG_NON_SYSTEM 0x10
+#define SEG_32BIT 0x04
+#define DESC_IGATE 0x06
/*
** Exceptions
*/
-#define N_EXCEPTIONS 256
+#define N_EXCEPTIONS 256
/*
** Bit definitions in registers
@@ -41,94 +41,95 @@
** See IA-32 Intel Architecture SW Dev. Manual, Volume 3: System
** Programming Guide, page 2-8.
*/
+
/*
** EFLAGS
*/
-#define EFL_RSVD 0xffc00000 /* reserved */
-#define EFL_MB0 0x00008020 /* must be zero */
-#define EFL_MB1 0x00000002 /* must be 1 */
+#define EFL_RSVD 0xffc00000 /* reserved */
+#define EFL_MB0 0x00008020 /* must be zero */
+#define EFL_MB1 0x00000002 /* must be 1 */
-#define EFL_ID 0x00200000
-#define EFL_VIP 0x00100000
-#define EFL_VIF 0x00080000
-#define EFL_AC 0x00040000
-#define EFL_VM 0x00020000
-#define EFL_RF 0x00010000
-#define EFL_NT 0x00004000
+#define EFL_ID 0x00200000
+#define EFL_VIP 0x00100000
+#define EFL_VIF 0x00080000
+#define EFL_AC 0x00040000
+#define EFL_VM 0x00020000
+#define EFL_RF 0x00010000
+#define EFL_NT 0x00004000
#define EFL_IOPL 0x00003000
-#define EFL_OF 0x00000800
-#define EFL_DF 0x00000400
-#define EFL_IF 0x00000200
-#define EFL_TF 0x00000100
-#define EFL_SF 0x00000080
-#define EFL_ZF 0x00000040
-#define EFL_AF 0x00000010
-#define EFL_PF 0x00000004
-#define EFL_CF 0x00000001
+#define EFL_OF 0x00000800
+#define EFL_DF 0x00000400
+#define EFL_IF 0x00000200
+#define EFL_TF 0x00000100
+#define EFL_SF 0x00000080
+#define EFL_ZF 0x00000040
+#define EFL_AF 0x00000010
+#define EFL_PF 0x00000004
+#define EFL_CF 0x00000001
/*
** CR0, CR1, CR2, CR3, CR4
**
** IA-32 V3, page 2-12.
*/
-#define CR0_RSVD 0x1ffaffc0
-#define CR0_PG 0x80000000
-#define CR0_CD 0x40000000
-#define CR0_NW 0x20000000
-#define CR0_AM 0x00040000
-#define CR0_WP 0x00010000
-#define CR0_NE 0x00000020
-#define CR0_ET 0x00000010
-#define CR0_TS 0x00000008
-#define CR0_EM 0x00000004
-#define CR0_MP 0x00000002
-#define CR0_PE 0x00000001
+#define CR0_RSVD 0x1ffaffc0
+#define CR0_PG 0x80000000
+#define CR0_CD 0x40000000
+#define CR0_NW 0x20000000
+#define CR0_AM 0x00040000
+#define CR0_WP 0x00010000
+#define CR0_NE 0x00000020
+#define CR0_ET 0x00000010
+#define CR0_TS 0x00000008
+#define CR0_EM 0x00000004
+#define CR0_MP 0x00000002
+#define CR0_PE 0x00000001
-#define CR1_RSVD 0xffffffff
+#define CR1_RSVD 0xffffffff
-#define CR2_RSVD 0x00000000
+#define CR2_RSVD 0x00000000
#define CR2_PF_LIN_ADDR 0xffffffff
-#define CR3_RSVD 0x00000fe7
-#define CR3_PD_BASE 0xfffff000
-#define CR3_PCD 0x00000010
-#define CR3_PWT 0x00000008
+#define CR3_RSVD 0x00000fe7
+#define CR3_PD_BASE 0xfffff000
+#define CR3_PCD 0x00000010
+#define CR3_PWT 0x00000008
-#define CR4_RSVD 0xfd001000
-#define CR4_UINT 0x02000000
-#define CR4_PKS 0x01000000
-#define CR4_CET 0x00800000
-#define CR4_PKE 0x00400000
-#define CR4_SMAP 0x00200000
-#define CR4_SMEP 0x00100000
-#define CR4_KL 0x00080000
-#define CR4_OSXS 0x00040000
-#define CR4_PCID 0x00020000
-#define CR4_FSGS 0x00010000
-#define CR4_SMXE 0x00004000
-#define CR4_VMXE 0x00002000
-#define CR4_LA57 0x00001000
-#define CR4_UMIP 0x00000800
-#define CR4_OSXMMEXCPT 0x00000400
-#define CR4_OSFXSR 0x00000200
-#define CR4_PCE 0x00000100
-#define CR4_PGE 0x00000080
-#define CR4_MCE 0x00000040
-#define CR4_PAE 0x00000020
-#define CR4_PSE 0x00000010
-#define CR4_DE 0x00000008
-#define CR4_TSD 0x00000004
-#define CR4_PVI 0x00000002
-#define CR4_VME 0x00000001
+#define CR4_RSVD 0xfd001000
+#define CR4_UINT 0x02000000
+#define CR4_PKS 0x01000000
+#define CR4_CET 0x00800000
+#define CR4_PKE 0x00400000
+#define CR4_SMAP 0x00200000
+#define CR4_SMEP 0x00100000
+#define CR4_KL 0x00080000
+#define CR4_OSXS 0x00040000
+#define CR4_PCID 0x00020000
+#define CR4_FSGS 0x00010000
+#define CR4_SMXE 0x00004000
+#define CR4_VMXE 0x00002000
+#define CR4_LA57 0x00001000
+#define CR4_UMIP 0x00000800
+#define CR4_OSXMMEXCPT 0x00000400
+#define CR4_OSFXSR 0x00000200
+#define CR4_PCE 0x00000100
+#define CR4_PGE 0x00000080
+#define CR4_MCE 0x00000040
+#define CR4_PAE 0x00000020
+#define CR4_PSE 0x00000010
+#define CR4_DE 0x00000008
+#define CR4_TSD 0x00000004
+#define CR4_PVI 0x00000002
+#define CR4_VME 0x00000001
/*
** PMode segment selector field masks
**
** IA-32 V3, page 3-8.
*/
-#define SEG_SEL_IX_MASK 0xfff8
-#define SEG_SEL_TI_MASK 0x0004
-#define SEG_SEL_RPL_MASK 0x0003
+#define SEG_SEL_IX_MASK 0xfff8
+#define SEG_SEL_TI_MASK 0x0004
+#define SEG_SEL_RPL_MASK 0x0003
/*
** Segment descriptor bytes
@@ -141,6 +142,7 @@
** 4: base address 23:16
** 7: base address 31:24
*/
+
/*
** Byte 5: access control bits
** 7: present
@@ -148,43 +150,43 @@
** 4: system/user
** 3-0: type
*/
-#define SEG_ACCESS_P_MASK 0x80
-#define SEG_PRESENT 0x80
-#define SEG_NOT_PRESENT 0x00
+#define SEG_ACCESS_P_MASK 0x80
+# define SEG_PRESENT 0x80
+# define SEG_NOT_PRESENT 0x00
-#define SEG_ACCESS_DPL_MASK 0x60
-#define SEG_DPL_0 0x00
-#define SEG_DPL_1 0x20
-#define SEG_DPL_2 0x40
-#define SEG_DPL_3 0x60
+#define SEG_ACCESS_DPL_MASK 0x60
+# define SEG_DPL_0 0x00
+# define SEG_DPL_1 0x20
+# define SEG_DPL_2 0x40
+# define SEG_DPL_3 0x60
-#define SEG_ACCESS_S_MASK 0x10
-#define SEG_SYSTEM 0x00
-#define SEG_NON_SYSTEM 0x10
+#define SEG_ACCESS_S_MASK 0x10
+# define SEG_SYSTEM 0x00
+# define SEG_NON_SYSTEM 0x10
-#define SEG_TYPE_MASK 0x0f
-#define SEG_DATA_A_BIT 0x1
-#define SEG_DATA_W_BIT 0x2
-#define SEG_DATA_E_BIT 0x4
-#define SEG_CODE_A_BIT 0x1
-#define SEG_CODE_R_BIT 0x2
-#define SEG_CODE_C_BIT 0x4
-#define SEG_DATA_RO 0x0
-#define SEG_DATA_ROA 0x1
-#define SEG_DATA_RW 0x2
-#define SEG_DATA_RWA 0x3
-#define SEG_DATA_RO_XD 0x4
-#define SEG_DATA_RO_XDA 0x5
-#define SEG_DATA_RW_XW 0x6
-#define SEG_DATA_RW_XWA 0x7
-#define SEG_CODE_XO 0x8
-#define SEG_CODE_XOA 0x9
-#define SEG_CODE_XR 0xa
-#define SEG_CODE_XRA 0xb
-#define SEG_CODE_XO_C 0xc
-#define SEG_CODE_XO_CA 0xd
-#define SEG_CODE_XR_C 0xe
-#define SEG_CODE_XR_CA 0xf
+#define SEG_TYPE_MASK 0x0f
+# define SEG_DATA_A_BIT 0x1
+# define SEG_DATA_W_BIT 0x2
+# define SEG_DATA_E_BIT 0x4
+# define SEG_CODE_A_BIT 0x1
+# define SEG_CODE_R_BIT 0x2
+# define SEG_CODE_C_BIT 0x4
+# define SEG_DATA_RO 0x0
+# define SEG_DATA_ROA 0x1
+# define SEG_DATA_RW 0x2
+# define SEG_DATA_RWA 0x3
+# define SEG_DATA_RO_XD 0x4
+# define SEG_DATA_RO_XDA 0x5
+# define SEG_DATA_RW_XW 0x6
+# define SEG_DATA_RW_XWA 0x7
+# define SEG_CODE_XO 0x8
+# define SEG_CODE_XOA 0x9
+# define SEG_CODE_XR 0xa
+# define SEG_CODE_XRA 0xb
+# define SEG_CODE_XO_C 0xc
+# define SEG_CODE_XO_CA 0xd
+# define SEG_CODE_XR_C 0xe
+# define SEG_CODE_XR_CA 0xf
/*
** Byte 6: sizes
@@ -195,47 +197,48 @@
** 3-0: upper 4 bits of limit
** 7: base address 31:24
*/
-#define SEG_SIZE_G_MASK 0x80
-#define SEG_GRAN_BYTE 0x00
-#define SEG_GRAN_4KBYTE 0x80
+#define SEG_SIZE_G_MASK 0x80
+# define SEG_GRAN_BYTE 0x00
+# define SEG_GRAN_4KBYTE 0x80
-#define SEG_SIZE_D_B_MASK 0x40
-#define SEG_DB_16BIT 0x00
-#define SEG_DB_32BIT 0x40
+#define SEG_SIZE_D_B_MASK 0x40
+# define SEG_DB_16BIT 0x00
+# define SEG_DB_32BIT 0x40
-#define SEG_SIZE_L_MASK 0x20
-#define SEG_L_64BIT 0x20
-#define SEG_L_32BIT 0x00
+#define SEG_SIZE_L_MASK 0x20
+# define SEG_L_64BIT 0x20
+# define SEG_L_32BIT 0x00
-#define SEG_SIZE_AVL_MASK 0x10
+#define SEG_SIZE_AVL_MASK 0x10
#define SEG_SIZE_LIM_19_16_MASK 0x0f
+
/*
** System-segment and gate-descriptor types
**
** IA-32 V3, page 3-15.
*/
-// type 0: reserved
+ // type 0: reserved
#define SEG_SYS_16BIT_TSS_AVAIL 0x1
-#define SEG_SYS_LDT 0x2
-#define SEG_SYS_16BIT_TSS_BUSY 0x3
+#define SEG_SYS_LDT 0x2
+#define SEG_SYS_16BIT_TSS_BUSY 0x3
#define SEG_SYS_16BIT_CALL_GATE 0x4
-#define SEG_SYS_TASK_GATE 0x5
-#define SEG_SYS_16BIT_INT_GATE 0x6
+#define SEG_SYS_TASK_GATE 0x5
+#define SEG_SYS_16BIT_INT_GATE 0x6
#define SEG_SYS_16BIT_TRAP_GATE 0x7
-// type 8: reserved
+ // type 8: reserved
#define SEG_SYS_32BIT_TSS_AVAIL 0x9
-// type A: reserved
-#define SEG_SYS_32BIT_TSS_BUSY 0xb
+ // type A: reserved
+#define SEG_SYS_32BIT_TSS_BUSY 0xb
#define SEG_SYS_32BIT_CALL_GATE 0xc
-// type D: reserved
-#define SEG_SYS_32BIT_INT_GATE 0xe
+ // type D: reserved
+#define SEG_SYS_32BIT_INT_GATE 0xe
#define SEG_SYS_32BIT_TRAP_GATE 0xf
/*
** IDT Descriptors
-**
+**
** IA-32 V3, page 5-13.
**
** All have a segment selector in bytes 2 and 3; Task Gate descriptors
@@ -243,57 +246,58 @@
** and 7 devoted to the 16 bits of the Offset, with the low nybble of
** byte 4 reserved.
*/
-#define IDT_PRESENT 0x8000
-#define IDT_DPL_MASK 0x6000
-#define IDT_DPL_0 0x0000
-#define IDT_DPL_1 0x2000
-#define IDT_DPL_2 0x4000
-#define IDT_DPL_3 0x6000
-#define IDT_GATE_TYPE 0x0f00
-#define IDT_TASK_GATE 0x0500
-#define IDT_INT16_GATE 0x0600
-#define IDT_INT32_GATE 0x0e00
-#define IDT_TRAP16_GATE 0x0700
-#define IDT_TRAP32_GATE 0x0f00
+#define IDT_PRESENT 0x8000
+#define IDT_DPL_MASK 0x6000
+# define IDT_DPL_0 0x0000
+# define IDT_DPL_1 0x2000
+# define IDT_DPL_2 0x4000
+# define IDT_DPL_3 0x6000
+#define IDT_GATE_TYPE 0x0f00
+# define IDT_TASK_GATE 0x0500
+# define IDT_INT16_GATE 0x0600
+# define IDT_INT32_GATE 0x0e00
+# define IDT_TRAP16_GATE 0x0700
+# define IDT_TRAP32_GATE 0x0f00
/*
** Interrupt vectors
*/
+
// predefined by the architecture
-#define VEC_DIVIDE_ERROR 0x00
-#define VEC_DEBUG_EXCEPTION 0x01
-#define VEC_NMI_INTERRUPT 0x02
-#define VEC_BREAKPOINT 0x03
-#define VEC_OVERFLOW 0x04
-#define VEC_BOUND_RANGE_EXCEEDED 0x05
-#define VEC_INVALID_OPCODE 0x06
-#define VEC_DEVICE_NOT_AVAILABLE 0x07
-#define VEC_DOUBLE_FAULT 0x08
-#define VEC_COPROCESSOR_OVERRUN 0x09
-#define VEC_INVALID_TSS 0x0a
-#define VEC_SEGMENT_NOT_PRESENT 0x0b
-#define VEC_STACK_FAULT 0x0c
-#define VEC_GENERAL_PROTECTION 0x0d
-#define VEC_PAGE_FAULT 0x0e
+#define VEC_DIVIDE_ERROR 0x00
+#define VEC_DEBUG_EXCEPTION 0x01
+#define VEC_NMI_INTERRUPT 0x02
+#define VEC_BREAKPOINT 0x03
+#define VEC_OVERFLOW 0x04
+#define VEC_BOUND_RANGE_EXCEEDED 0x05
+#define VEC_INVALID_OPCODE 0x06
+#define VEC_DEVICE_NOT_AVAILABLE 0x07
+#define VEC_DOUBLE_FAULT 0x08
+#define VEC_COPROCESSOR_OVERRUN 0x09
+#define VEC_INVALID_TSS 0x0a
+#define VEC_SEGMENT_NOT_PRESENT 0x0b
+#define VEC_STACK_FAULT 0x0c
+#define VEC_GENERAL_PROTECTION 0x0d
+#define VEC_PAGE_FAULT 0x0e
// 0x0f is reserved - unused
-#define VEC_FPU_ERROR 0x10
-#define VEC_ALIGNMENT_CHECK 0x11
-#define VEC_MACHINE_CHECK 0x12
-#define VEC_SIMD_FP_EXCEPTION 0x13
-#define VEC_VIRT_EXCEPTION 0x14
-#define VEC_CTRL_PROT_EXCEPTION 0x15
+#define VEC_FPU_ERROR 0x10
+#define VEC_ALIGNMENT_CHECK 0x11
+#define VEC_MACHINE_CHECK 0x12
+#define VEC_SIMD_FP_EXCEPTION 0x13
+#define VEC_VIRT_EXCEPTION 0x14
+#define VEC_CTRL_PROT_EXCEPTION 0x15
// 0x16 through 0x1f are reserved
// 0x20 through 0xff are user-defined, non-reserved
// IRQ0 through IRQ15 will use vectors 0x20 through 0x2f
-#define VEC_TIMER 0x20
-#define VEC_KBD 0x21
-#define VEC_COM2 0x23
-#define VEC_COM1 0x24
-#define VEC_PARALLEL 0x25
-#define VEC_FLOPPY 0x26
-#define VEC_MYSTERY 0x27
-#define VEC_MOUSE 0x2c
+#define VEC_TIMER 0x20
+#define VEC_KBD 0x21
+#define VEC_COM2 0x23
+#define VEC_COM1 0x24
+#define VEC_PARALLEL 0x25
+#define VEC_FLOPPY 0x26
+#define VEC_MYSTERY 0x27
+#define VEC_MOUSE 0x2c
#endif
diff --git a/kernel/old/include/x86/bios.h b/kernel/old/include/x86/bios.h
new file mode 100644
index 0000000..a19e570
--- /dev/null
+++ b/kernel/old/include/x86/bios.h
@@ -0,0 +1,73 @@
+/*
+** @file bios.h
+**
+** @author Warren R. Carithers
+**
+** BIOS-related declarations
+*/
+
+#ifndef BIOS_H_
+#define BIOS_H_
+
+/*
+** BIOS-related memory addresses
+*/
+
+#define BIOS_BDA 0x0400
+
+/*
+** Selected BIOS interrupt numbers
+*/
+
+#define BIOS_TIMER 0x08
+#define BIOS_KBD 0x09
+#define BIOS_VIDEO 0x10
+#define BIOS_EQUIP 0x11
+#define BIOS_MSIZ 0x12
+#define BIOS_DISK 0x13
+#define BIOS_SERIAL 0x14
+#define BIOS_MISC 0x15
+#define BIOS_KBDSVC 0x16
+#define BIOS_PRTSVC 0x17
+#define BIOS_BOOT 0x19
+#define BIOS_RTCPCI 0x1a
+
+// BIOS video commands (AH)
+#define BV_W_ADV 0x0e
+
+// BIOS disk commands (AH)
+#define BD_RESET 0x00
+#define BD_CHECK 0x01
+#define BD_RDSECT 0x02
+#define BD_WRSECT 0x03
+#define BD_PARAMS 0x08
+
+// BIOS disk commands with parameters (AX)
+#define BD_READ(n) ((BD_RDSECT << 8) | (n))
+#define BD_READ1 0x0201
+
+// CMOS ports (used for masking NMIs)
+#define CMOS_ADDR 0x70
+#define CMOS_DATA 0x71
+
+// important related commands
+#define NMI_ENABLE 0x00
+#define NMI_DISABLE 0x80
+
+/*
+** Physical Memory Map Table (0000:2D00 - 0000:7c00)
+**
+** Primarily used with the BIOS_MISC interrupt
+*/
+#define MMAP_SEG 0x02D0
+#define MMAP_DISP 0x0000
+#define MMAP_ADDR ((MMAP_SEG << 4) + MMAP_DISP)
+#define MMAP_SECTORS 0x0a
+
+#define MMAP_ENT 24 /* bytes per entry */
+#define MMAP_MAX_ENTS (BOOT_ADDR - MMAP_ADDR - 4) / 24
+
+#define MMAP_CODE 0xE820 /* int 0x15 code */
+#define MMAP_MAGIC_NUM 0x534D4150 /* for 0xE820 interrupt */
+
+#endif
diff --git a/kernel/old/include/x86/ops.h b/kernel/old/include/x86/ops.h
index 81167a1..ad795b9 100644
--- a/kernel/old/include/x86/ops.h
+++ b/kernel/old/include/x86/ops.h
@@ -10,7 +10,7 @@
** MIT's xv6, https://github.com/mit-pdos/xv6-public
**
** Note: normally, GCC doesn't inline unless the optimization level is
-** over 1. This can be forced by adding
+** over 1. This can be forced by adding
**
** __attribute__((always_inline))
**
@@ -27,10 +27,10 @@
// control "forced" inlining
#ifdef FORCE_INLINING
-#define OPSINLINED __attribute__((always_inline))
+#define OPSINLINED __attribute__((always_inline))
#else
-#define OPSINLINED /* no-op */
-#endif /* FORCE_INLINING */
+#define OPSINLINED /* no-op */
+#endif /* FORCE_INLINING */
/****************************
** Data movement
@@ -47,33 +47,36 @@
** @param src Source buffer
** @param len Byte count
*/
-static inline void movsb(void *dst, const void *src, uint32_t len) OPSINLINED
+static inline void
+movsb( void* dst, const void* src, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep movsb"
- : "+D"(dst), "+S"(src), "+c"(len)
- :
- : "memory");
+ __asm__ __volatile__( "cld; rep movsb"
+ : "+D"(dst), "+S"(src), "+c"(len)
+ : : "memory" );
}
-static inline void movsw(void *dst, const void *src, uint32_t len) OPSINLINED
+
+static inline void
+movsw( void* dst, const void* src, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep movsw"
- : "+D"(dst), "+S"(src), "+c"(len)
- :
- : "memory");
+ __asm__ __volatile__( "cld; rep movsw"
+ : "+D"(dst), "+S"(src), "+c"(len)
+ : : "memory" );
}
-static inline void movsl(void *dst, const void *src, uint32_t len) OPSINLINED
+
+static inline void
+movsl( void* dst, const void* src, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep movsl"
- : "+D"(dst), "+S"(src), "+c"(len)
- :
- : "memory");
+ __asm__ __volatile__( "cld; rep movsl"
+ : "+D"(dst), "+S"(src), "+c"(len)
+ : : "memory" );
}
-static inline void movsq(void *dst, const void *src, uint32_t len) OPSINLINED
+
+static inline void
+movsq( void* dst, const void* src, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep movsq"
- : "+D"(dst), "+S"(src), "+c"(len)
- :
- : "memory");
+ __asm__ __volatile__( "cld; rep movsq"
+ : "+D"(dst), "+S"(src), "+c"(len)
+ : : "memory" );
}
/**
@@ -87,26 +90,31 @@ static inline void movsq(void *dst, const void *src, uint32_t len) OPSINLINED
** @param val Data to copy
** @param len Byte count
*/
-static inline void stosb(void *dst, uint8_t val, uint32_t len) OPSINLINED
+static inline void
+stosb( void *dst, uint8_t val, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep stosb"
- : "=D"(dst), "=c"(len)
- : "0"(dst), "1"(len), "a"(val)
- : "memory", "cc");
+ __asm__ __volatile__( "cld; rep stosb"
+ : "=D" (dst), "=c" (len)
+ : "0" (dst), "1" (len), "a" (val)
+ : "memory", "cc" );
}
-static inline void stosw(void *dst, uint16_t val, uint32_t len) OPSINLINED
+
+static inline void
+stosw( void *dst, uint16_t val, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep stos2"
- : "=D"(dst), "=c"(len)
- : "0"(dst), "1"(len), "a"(val)
- : "memory", "cc");
+ __asm__ __volatile__( "cld; rep stos2"
+ : "=D" (dst), "=c" (len)
+ : "0" (dst), "1" (len), "a" (val)
+ : "memory", "cc" );
}
-static inline void stosl(void *dst, uint32_t val, uint32_t len) OPSINLINED
+
+static inline void
+stosl( void *dst, uint32_t val, uint32_t len ) OPSINLINED
{
- __asm__ __volatile__("cld; rep stosl"
- : "=D"(dst), "=c"(len)
- : "0"(dst), "1"(len), "a"(val)
- : "memory", "cc");
+ __asm__ __volatile__( "cld; rep stosl"
+ : "=D" (dst), "=c" (len)
+ : "0" (dst), "1" (len), "a" (val)
+ : "memory", "cc" );
}
/****************************
@@ -123,46 +131,59 @@ static inline void stosl(void *dst, uint32_t val, uint32_t len) OPSINLINED
**
** @return Contents of the register
*/
-static inline uint32_t r_cr0(void) OPSINLINED
+static inline uint32_t
+r_cr0( void ) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%cr0,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%cr0,%0" : "=r" (val) );
return val;
}
-static inline uint32_t r_cr2(void) OPSINLINED
+
+static inline uint32_t
+r_cr2( void ) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%cr2,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%cr2,%0" : "=r" (val) );
return val;
}
-static inline uint32_t r_cr3(void) OPSINLINED
+
+static inline uint32_t
+r_cr3( void ) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%cr3,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%cr3,%0" : "=r" (val) );
return val;
}
-static inline uint32_t r_cr4(void) OPSINLINED
+
+static inline uint32_t
+r_cr4( void ) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%cr4,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%cr4,%0" : "=r" (val) );
return val;
}
-static inline uint32_t r_eflags(void) OPSINLINED
+
+static inline uint32_t
+r_eflags(void) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("pushfl; popl %0" : "=r"(val));
+ __asm__ __volatile__( "pushfl; popl %0" : "=r" (val) );
return val;
}
-static inline uint32_t r_ebp(void) OPSINLINED
+
+static inline uint32_t
+r_ebp(void) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%ebp,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%ebp,%0" : "=r" (val) );
return val;
}
-static inline uint32_t r_esp(void) OPSINLINED
+
+static inline uint32_t
+r_esp(void) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl %%esp,%0" : "=r"(val));
+ __asm__ __volatile__( "movl %%esp,%0" : "=r" (val) );
return val;
}
@@ -173,25 +194,34 @@ static inline uint32_t r_esp(void) OPSINLINED
**
** Description: Writes a value into the CR indicated by its name
*/
-static inline void w_cr0(uint32_t val) OPSINLINED
+static inline void
+w_cr0( uint32_t val ) OPSINLINED
{
- __asm__ __volatile__("movl %0,%%cr0" : : "r"(val));
+ __asm__ __volatile__( "movl %0,%%cr0" : : "r" (val) );
}
-static inline void w_cr2(uint32_t val) OPSINLINED
+
+static inline void
+w_cr2( uint32_t val ) OPSINLINED
{
- __asm__ __volatile__("movl %0,%%cr2" : : "r"(val));
+ __asm__ __volatile__( "movl %0,%%cr2" : : "r" (val) );
}
-static inline void w_cr3(uint32_t val) OPSINLINED
+
+static inline void
+w_cr3( uint32_t val ) OPSINLINED
{
- __asm__ __volatile__("movl %0,%%cr3" : : "r"(val));
+ __asm__ __volatile__( "movl %0,%%cr3" : : "r" (val) );
}
-static inline void w_cr4(uint32_t val) OPSINLINED
+
+static inline void
+w_cr4( uint32_t val ) OPSINLINED
{
- __asm__ __volatile__("movl %0,%%cr4" : : "r"(val));
+ __asm__ __volatile__( "movl %0,%%cr4" : : "r" (val) );
}
-static inline void w_eflags(uint32_t eflags) OPSINLINED
+
+static inline void
+w_eflags(uint32_t eflags) OPSINLINED
{
- __asm__ __volatile__("pushl %0; popfl" : : "r"(eflags));
+ __asm__ __volatile__( "pushl %0; popfl" : : "r" (eflags) );
}
/**
@@ -203,13 +233,16 @@ static inline void w_eflags(uint32_t eflags) OPSINLINED
**
** @param addr The value to be loaded into the register
*/
-static inline void w_gdt(void *addr) OPSINLINED
+static inline void
+w_gdt( void *addr ) OPSINLINED
{
- __asm__ __volatile__("lgdt (%0)" : : "r"(addr));
+ __asm__ __volatile__( "lgdt (%0)" : : "r" (addr) );
}
-static inline void w_idt(void *addr) OPSINLINED
+
+static inline void
+w_idt( void *addr ) OPSINLINED
{
- __asm__ __volatile__("lidt (%0)" : : "r"(addr));
+ __asm__ __volatile__( "lidt (%0)" : : "r" (addr) );
}
/**
@@ -223,21 +256,19 @@ static inline void w_idt(void *addr) OPSINLINED
** @param cp Pointer to where %ecx contents should be saved, or NULL
** @param dp Pointer to where %edx contents should be saved, or NULL
*/
-static inline void cpuid(uint32_t op, uint32_t *ap, uint32_t *bp, uint32_t *cp,
- uint32_t *dp) OPSINLINED
+static inline void
+cpuid( uint32_t op, uint32_t *ap, uint32_t *bp,
+ uint32_t *cp, uint32_t *dp ) OPSINLINED
{
uint32_t eax, ebx, ecx, edx;
- __asm__ __volatile__("cpuid"
- : "=a"(eax), "=b"(ebx), "=c"(ecx), "=d"(edx)
- : "a"(op));
- if (ap)
- *ap = eax;
- if (bp)
- *bp = ebx;
- if (cp)
- *cp = ecx;
- if (dp)
- *dp = edx;
+ __asm__ __volatile__( "cpuid"
+ : "=a" (eax), "=b" (ebx), "=c" (ecx), "=d" (edx)
+ : "a" (op) );
+
+ if( ap ) *ap = eax;
+ if( bp ) *bp = ebx;
+ if( cp ) *cp = ecx;
+ if( dp ) *dp = edx;
}
/****************************
@@ -251,9 +282,10 @@ static inline void cpuid(uint32_t op, uint32_t *ap, uint32_t *bp, uint32_t *cp,
**
** @param addr An address within the page to be flushed
*/
-static inline void invlpg(uint32_t addr) OPSINLINED
+static inline void
+invlpg( uint32_t addr ) OPSINLINED
{
- __asm__ __volatile__("invlpg (%0)" : : "r"(addr) : "memory");
+ __asm__ __volatile__( "invlpg (%0)" : : "r" (addr) : "memory" );
}
/**
@@ -263,11 +295,12 @@ static inline void invlpg(uint32_t addr) OPSINLINED
**
** We do this by changing CR3.
*/
-static inline void flushtlb(void) OPSINLINED
+static inline void
+flushtlb( void ) OPSINLINED
{
uint32_t cr3;
- __asm__ __volatile__("movl %%cr3,%0" : "=r"(cr3));
- __asm__ __volatile__("movl %0,%%cr2" : : "r"(cr3));
+ __asm__ __volatile__( "movl %%cr3,%0" : "=r" (cr3) );
+ __asm__ __volatile__( "movl %0,%%cr2" : : "r" (cr3) );
}
/****************************
@@ -285,22 +318,27 @@ static inline void flushtlb(void) OPSINLINED
**
** @return The data read from the specified port
*/
-static inline uint8_t inb(int port) OPSINLINED
+static inline uint8_t
+inb( int port ) OPSINLINED
{
uint8_t data;
- __asm__ __volatile__("inb %w1,%0" : "=a"(data) : "d"(port));
+ __asm__ __volatile__( "inb %w1,%0" : "=a" (data) : "d" (port) );
return data;
}
-static inline uint16_t inw(int port) OPSINLINED
+
+static inline uint16_t
+inw( int port ) OPSINLINED
{
uint16_t data;
- __asm__ __volatile__("inw %w1,%0" : "=a"(data) : "d"(port));
+ __asm__ __volatile__( "inw %w1,%0" : "=a" (data) : "d" (port) );
return data;
}
-static inline uint32_t inl(int port) OPSINLINED
+
+static inline uint32_t
+inl( int port ) OPSINLINED
{
uint32_t data;
- __asm__ __volatile__("inl %w1,%0" : "=a"(data) : "d"(port));
+ __asm__ __volatile__( "inl %w1,%0" : "=a" (data) : "d" (port) );
return data;
}
@@ -316,17 +354,22 @@ static inline uint32_t inl(int port) OPSINLINED
**
** @return The data read from the specified port
*/
-static inline void outb(int port, uint8_t data) OPSINLINED
+static inline void
+outb( int port, uint8_t data ) OPSINLINED
{
- __asm__ __volatile__("outb %0,%w1" : : "a"(data), "d"(port));
+ __asm__ __volatile__( "outb %0,%w1" : : "a" (data), "d" (port) );
}
-static inline void outw(int port, uint16_t data) OPSINLINED
+
+static inline void
+outw( int port, uint16_t data ) OPSINLINED
{
- __asm__ __volatile__("outw %0,%w1" : : "a"(data), "d"(port));
+ __asm__ __volatile__( "outw %0,%w1" : : "a" (data), "d" (port) );
}
-static inline void outl(int port, uint32_t data) OPSINLINED
+
+static inline void
+outl( int port, uint32_t data ) OPSINLINED
{
- __asm__ __volatile__("outl %0,%w1" : : "a"(data), "d"(port));
+ __asm__ __volatile__( "outl %0,%w1" : : "a" (data), "d" (port) );
}
/****************************
@@ -338,9 +381,10 @@ static inline void outl(int port, uint32_t data) OPSINLINED
**
** Description: Cause a breakpoint interrupt for debugging purposes
*/
-static inline void breakpoint(void) OPSINLINED
+static inline void
+breakpoint( void ) OPSINLINED
{
- __asm__ __volatile__("int3");
+ __asm__ __volatile__( "int3" );
}
/**
@@ -351,10 +395,11 @@ static inline void breakpoint(void) OPSINLINED
**
** @return The address the calling routine will return to as a uint32_t
*/
-static inline uint32_t get_ra(void) OPSINLINED
+static inline uint32_t
+get_ra( void ) OPSINLINED
{
uint32_t val;
- __asm__ __volatile__("movl 4(%%ebp),%0" : "=r"(val));
+ __asm__ __volatile__( "movl 4(%%ebp),%0" : "=r" (val) );
return val;
}
@@ -363,11 +408,13 @@ static inline uint32_t get_ra(void) OPSINLINED
**
** Description: Pause until something happens
*/
-static inline void ev_wait(void) OPSINLINED
+static inline void
+ev_wait( void ) OPSINLINED
{
- __asm__ __volatile__("sti ; hlt");
+ __asm__ __volatile__( "sti ; hlt" );
}
+
/**
** Name: xchgl
**
@@ -378,18 +425,19 @@ static inline void ev_wait(void) OPSINLINED
**
** @return The old contents of the memory location
*/
-static inline uint32_t xchgl(volatile uint32_t *addr, uint32_t data) OPSINLINED
+static inline uint32_t
+xchgl( volatile uint32_t *addr, uint32_t data ) OPSINLINED
{
uint32_t old;
// + indicates a read-modify-write operand
- __asm__ __volatile__("lock; xchgl %0, %1"
- : "+m"(*addr), "=a"(old)
- : "1"(data)
- : "cc");
+ __asm__ __volatile__( "lock; xchgl %0, %1"
+ : "+m" (*addr), "=a" (old)
+ : "1" (data)
+ : "cc");
return old;
}
-#endif /* !ASM_SRC */
+#endif /* !ASM_SRC */
#endif
diff --git a/kernel/old/include/x86/pic.h b/kernel/old/include/x86/pic.h
index ae3fe6c..d4fa93b 100644
--- a/kernel/old/include/x86/pic.h
+++ b/kernel/old/include/x86/pic.h
@@ -16,14 +16,15 @@
** Our expected configuration is two PICs, with the secondary connected
** through the IRQ2 pin of the primary.
*/
+
/*
** Port addresses for the command port and interrupt mask register port
** for both the primary and secondary PICs.
*/
-#define PIC1_CMD 0x20 // primary command
-#define PIC1_DATA (PIC1_CMD + 1) // primary data / int mask register
-#define PIC2_CMD 0xA0 // secondary command
-#define PIC2_DATA (PIC2_CMD + 1) // secondary data / int mask register
+#define PIC1_CMD 0x20 // primary command
+#define PIC1_DATA (PIC1_CMD + 1) // primary data / int mask register
+#define PIC2_CMD 0xA0 // secondary command
+#define PIC2_DATA (PIC2_CMD + 1) // secondary data / int mask register
/*
** Initialization Command Word (ICW) definitions
@@ -41,96 +42,98 @@
** PIC2_* defines are intended for the secondary PIC
** PIC_* defines are sent to both PICs
*/
+
/*
** ICW1: initialization, send to command port
*/
-#define PIC_CW1_INIT 0x10 // start initialization sequence
-#define PIC_CW1_NEED4 0x01 // ICW4 will also be set
-#define PIC_CW1_SINGLE 0x02 // select single (vs. cascade) mode
-#define PIC_CW1_INTVAL 0x04 // set call interval to 4 (vs. 8)
-#define PIC_CW1_LEVEL 0x08 // use level-triggered mode (vs. edge)
+#define PIC_CW1_INIT 0x10 // start initialization sequence
+#define PIC_CW1_NEED4 0x01 // ICW4 will also be set
+#define PIC_CW1_SINGLE 0x02 // select single (vs. cascade) mode
+#define PIC_CW1_INTVAL 0x04 // set call interval to 4 (vs. 8)
+#define PIC_CW1_LEVEL 0x08 // use level-triggered mode (vs. edge)
/*
** ICW2: interrupt vector base offsets, send to data port
*/
-#define PIC1_CW2_VECBASE 0x20 // IRQ0 int vector number
-#define PIC2_CW2_VECBASE 0x28 // IRQ8 int vector number
+#define PIC1_CW2_VECBASE 0x20 // IRQ0 int vector number
+#define PIC2_CW2_VECBASE 0x28 // IRQ8 int vector number
/*
** ICW3: secondary::primary attachment, send to data port
*/
-#define PIC1_CW3_SEC_IRQ2 0x04 // bit mask: secondary is on pin 2
-#define PIC2_CW3_SEC_ID 0x02 // integer: secondary id
+#define PIC1_CW3_SEC_IRQ2 0x04 // bit mask: secondary is on pin 2
+#define PIC2_CW3_SEC_ID 0x02 // integer: secondary id
/*
** ICW4: operating mode, send to data port
*/
-#define PIC_CW4_PM86 0x01 // 8086 mode (vs. 8080/8085)
-#define PIC_CW4_AUTOEOI 0x02 // do auto eoi's
-#define PIC_CW4_UNBUF 0x00 // unbuffered mode
-#define PIC_CW4_SEC_BUF 0x08 // put secondary in buffered mode
-#define PIC_CW4_PRI_BUF 0x0C // put primary in buffered mode
-#define PIC_CW4_SFNMODE 0x10 // "special fully nested" mode
+#define PIC_CW4_PM86 0x01 // 8086 mode (vs. 8080/8085)
+#define PIC_CW4_AUTOEOI 0x02 // do auto eoi's
+#define PIC_CW4_UNBUF 0x00 // unbuffered mode
+#define PIC_CW4_SEC_BUF 0x08 // put secondary in buffered mode
+#define PIC_CW4_PRI_BUF 0x0C // put primary in buffered mode
+#define PIC_CW4_SFNMODE 0x10 // "special fully nested" mode
/*
** Operation Control Words (OCWs)
**
** After the init sequence, can send these
*/
+
/*
** OCW1: interrupt mask; send to data port
*/
-#define PIC_MASK_NONE 0x00 // allow all interrupts
-#define PIC_MASK_NO_IRQ0 0x01 // prevent IRQ0 interrupts
-#define PIC_MASK_NO_IRQ1 0x02 // prevent IRQ1 interrupts
-#define PIC_MASK_NO_IRQ2 0x04 // prevent IRQ2 interrupts
-#define PIC_MASK_NO_IRQ3 0x08 // prevent IRQ3 interrupts
-#define PIC_MASK_NO_IRQ4 0x10 // prevent IRQ4 interrupts
-#define PIC_MASK_NO_IRQ5 0x20 // prevent IRQ5 interrupts
-#define PIC_MASK_NO_IRQ6 0x40 // prevent IRQ6 interrupts
-#define PIC_MASK_NO_IRQ7 0x80 // prevent IRQ7 interrupts
-#define PIC_MASK_ALL 0xff // prevent all interrupts
+#define PIC_MASK_NONE 0x00 // allow all interrupts
+#define PIC_MASK_NO_IRQ0 0x01 // prevent IRQ0 interrupts
+#define PIC_MASK_NO_IRQ1 0x02 // prevent IRQ1 interrupts
+#define PIC_MASK_NO_IRQ2 0x04 // prevent IRQ2 interrupts
+#define PIC_MASK_NO_IRQ3 0x08 // prevent IRQ3 interrupts
+#define PIC_MASK_NO_IRQ4 0x10 // prevent IRQ4 interrupts
+#define PIC_MASK_NO_IRQ5 0x20 // prevent IRQ5 interrupts
+#define PIC_MASK_NO_IRQ6 0x40 // prevent IRQ6 interrupts
+#define PIC_MASK_NO_IRQ7 0x80 // prevent IRQ7 interrupts
+#define PIC_MASK_ALL 0xff // prevent all interrupts
/*
** OCW2: EOI control, interrupt level; send to command port
*/
-#define PIC_LVL_0 0x00 // act on IRQ level 0
-#define PIC_LVL_1 0x01 // act on IRQ level 1
-#define PIC_LVL_2 0x02 // act on IRQ level 2
-#define PIC_LVL_3 0x03 // act on IRQ level 3
-#define PIC_LVL_4 0x04 // act on IRQ level 4
-#define PIC_LVL_5 0x05 // act on IRQ level 5
-#define PIC_LVL_6 0x06 // act on IRQ level 6
-#define PIC_LVL_7 0x07 // act on IRQ level 7
+#define PIC_LVL_0 0x00 // act on IRQ level 0
+#define PIC_LVL_1 0x01 // act on IRQ level 1
+#define PIC_LVL_2 0x02 // act on IRQ level 2
+#define PIC_LVL_3 0x03 // act on IRQ level 3
+#define PIC_LVL_4 0x04 // act on IRQ level 4
+#define PIC_LVL_5 0x05 // act on IRQ level 5
+#define PIC_LVL_6 0x06 // act on IRQ level 6
+#define PIC_LVL_7 0x07 // act on IRQ level 7
-#define PIC_EOI_NON_SPEC 0x20 // non-specific EOI command
-#define PIC_EOI PIC_EOI_NON_SPEC
+#define PIC_EOI_NON_SPEC 0x20 // non-specific EOI command
+# define PIC_EOI PIC_EOI_NON_SPEC
-#define PIC_EOI_SPEC 0x60 // specific EOI command
-#define PIC_SEOI PIC_EOI_SPEC
-#define PIC_SEOI_LVL0 (PIC_EOI_SPEC | PIC_LVL_0)
-#define PIC_SEOI_LVL1 (PIC_EOI_SPEC | PIC_LVL_1)
-#define PIC_SEOI_LVL2 (PIC_EOI_SPEC | PIC_LVL_2)
-#define PIC_SEOI_LVL3 (PIC_EOI_SPEC | PIC_LVL_3)
-#define PIC_SEOI_LVL4 (PIC_EOI_SPEC | PIC_LVL_4)
-#define PIC_SEOI_LVL5 (PIC_EOI_SPEC | PIC_LVL_5)
-#define PIC_SEOI_LVL6 (PIC_EOI_SPEC | PIC_LVL_6)
-#define PIC_SEOI_LVL7 (PIC_EOI_SPEC | PIC_LVL_7)
+#define PIC_EOI_SPEC 0x60 // specific EOI command
+# define PIC_SEOI PIC_EOI_SPEC
+# define PIC_SEOI_LVL0 (PIC_EOI_SPEC | PIC_LVL_0)
+# define PIC_SEOI_LVL1 (PIC_EOI_SPEC | PIC_LVL_1)
+# define PIC_SEOI_LVL2 (PIC_EOI_SPEC | PIC_LVL_2)
+# define PIC_SEOI_LVL3 (PIC_EOI_SPEC | PIC_LVL_3)
+# define PIC_SEOI_LVL4 (PIC_EOI_SPEC | PIC_LVL_4)
+# define PIC_SEOI_LVL5 (PIC_EOI_SPEC | PIC_LVL_5)
+# define PIC_SEOI_LVL6 (PIC_EOI_SPEC | PIC_LVL_6)
+# define PIC_SEOI_LVL7 (PIC_EOI_SPEC | PIC_LVL_7)
-#define PIC_EOI_ROT_NONSP 0xa0 // rotate on non-spec EOI cmd
-#define PIC_EOI_SET_ROT_AUTO 0x80 // set "rotate in auto EOI mode"
-#define PIC_EOI_CLR_ROT_AUTO 0x00 // clear "rotate in auto EOI mode"
-#define PIC_EOI_ROT_SPEC 0xe0 // rotate on spec EOI cmd (+ level)
-#define PIC_EOI_SET_PRIO 0xc0 // set priority (+ level)
-#define PIC_EOI_NOP 0x40 // no operation
+#define PIC_EOI_ROT_NONSP 0xa0 // rotate on non-spec EOI cmd
+#define PIC_EOI_SET_ROT_AUTO 0x80 // set "rotate in auto EOI mode"
+#define PIC_EOI_CLR_ROT_AUTO 0x00 // clear "rotate in auto EOI mode"
+#define PIC_EOI_ROT_SPEC 0xe0 // rotate on spec EOI cmd (+ level)
+#define PIC_EOI_SET_PRIO 0xc0 // set priority (+ level)
+#define PIC_EOI_NOP 0x40 // no operation
/*
-** OCW3: read requests, special mask mode; send to command port
+** OCW3: read requests, special mask mode; send to command port
*/
-#define PIC_READIRR 0x0a // read the IR register
-#define PIC_READISR 0x0b // read the IS register
-#define PIC_POLL 0x0c // poll
-#define PIC_MASK_RESET 0x48 // reset special mask mode
-#define PIC_MASK_SET 0x68 // set special mask mode
+#define PIC_READIRR 0x0a // read the IR register
+#define PIC_READISR 0x0b // read the IS register
+#define PIC_POLL 0x0c // poll
+#define PIC_MASK_RESET 0x48 // reset special mask mode
+#define PIC_MASK_SET 0x68 // set special mask mode
#endif
diff --git a/kernel/old/include/x86/pit.h b/kernel/old/include/x86/pit.h
index 0c54539..269fcec 100644
--- a/kernel/old/include/x86/pit.h
+++ b/kernel/old/include/x86/pit.h
@@ -12,6 +12,7 @@
#ifndef X86PIT_H_
#define X86PIT_H_
+
/*
** Hardware timer (Intel 8254 Programmable Interval Timer)
**
@@ -25,57 +26,57 @@
** M - mode
** BCD - binary or BCD counter
*/
+
/* Frequency settings */
-#define PIT_DEFAULT_TICKS_PER_SECOND 18 // actually 18.2065Hz
-#define PIT_DEFAULT_MS_PER_TICK (1000 / PIT_DEFAULT_TICKS_PER_SECOND)
-#define PIT_FREQ 1193182 // clock cycles/sec
+#define PIT_DEFAULT_TICKS_PER_SECOND 18 // actually 18.2065Hz
+#define PIT_DEFAULT_MS_PER_TICK (1000/PIT_DEFAULT_TICKS_PER_SECOND)
+#define PIT_FREQ 1193182 // clock cycles/sec
/* Port assignments */
-#define PIT_BASE_PORT 0x40 // I/O port for the timer
-#define PIT_0_PORT (PIT_BASE_PORT)
-#define PIT_1_PORT (PIT_BASE_PORT + 1)
-#define PIT_2_PORT (PIT_BASE_PORT + 2)
-#define PIT_CONTROL_PORT (PIT_BASE_PORT + 3)
+#define PIT_BASE_PORT 0x40 // I/O port for the timer
+# define PIT_0_PORT (PIT_BASE_PORT)
+# define PIT_1_PORT (PIT_BASE_PORT+1)
+# define PIT_2_PORT (PIT_BASE_PORT+2)
+# define PIT_CONTROL_PORT (PIT_BASE_PORT+3)
/* BCD field */
-#define PIT_USE_DECIMAL 0x00 // 16-bit binary counter (default)
-#define PIT_USE_BCD 0x01 // BCD counter
+#define PIT_USE_DECIMAL 0x00 // 16-bit binary counter (default)
+#define PIT_USE_BCD 0x01 // BCD counter
/* Timer modes */
-#define PIT_MODE_0 0x00 // int on terminal count
-#define PIT_MODE_1 0x02 // one-shot
-#define PIT_MODE_2 0x04 // divide-by-N
-#define PIT_MODE_3 0x06 // square-wave
-#define PIT_MODE_4 0x08 // software strobe
-#define PIT_MODE_5 0x0a // hardware strobe
+#define PIT_MODE_0 0x00 // int on terminal count
+#define PIT_MODE_1 0x02 // one-shot
+#define PIT_MODE_2 0x04 // divide-by-N
+#define PIT_MODE_3 0x06 // square-wave
+#define PIT_MODE_4 0x08 // software strobe
+#define PIT_MODE_5 0x0a // hardware strobe
/* Timer 0 settings */
-#define PIT_0_SELECT 0x00 // select timer 0
-#define PIT_0_LOAD 0x30 // load LSB, then MSB
-#define PIT_0_NDIV PIT_MODE_2 // divide-by-N counter
-#define PIT_0_SQUARE PIT_MODE_3 // square-wave mode
-#define PIT_0_ENDSIGNAL 0x00 // assert OUT at end of count
+#define PIT_0_SELECT 0x00 // select timer 0
+#define PIT_0_LOAD 0x30 // load LSB, then MSB
+#define PIT_0_NDIV PIT_MODE_2 // divide-by-N counter
+#define PIT_0_SQUARE PIT_MODE_3 // square-wave mode
+#define PIT_0_ENDSIGNAL 0x00 // assert OUT at end of count
/* Timer 1 settings */
-#define PIT_1_SELECT 0x40 // select timer 1
-#define PIT_1_READ 0x30 // read/load LSB then MSB
-#define PIT_1_RATE 0x06 // square-wave, for USART
+#define PIT_1_SELECT 0x40 // select timer 1
+#define PIT_1_READ 0x30 // read/load LSB then MSB
+#define PIT_1_RATE 0x06 // square-wave, for USART
/* Timer 2 settings */
-#define PIT_2_SELECT 0x80 // select timer 1
-#define PIT_2_READ 0x30 // read/load LSB then MSB
-#define PIT_2_RATE 0x06 // square-wave, for USART
+#define PIT_2_SELECT 0x80 // select timer 1
+#define PIT_2_READ 0x30 // read/load LSB then MSB
+#define PIT_2_RATE 0x06 // square-wave, for USART
/* Timer read-back */
-
-#define PIT_READBACK 0xc0 // perform a read-back
-#define PIT_RB_NOT_COUNT 0x20 // don't latch the count
-#define PIT_RB_NOT_STATUS 0x10 // don't latch the status
-#define PIT_RB_CHAN_2 0x08 // read back channel 2
-#define PIT_RB_CHAN_1 0x04 // read back channel 1
-#define PIT_RB_CHAN_0 0x02 // read back channel 0
-#define PIT_RB_ACCESS_MASK 0x30 // access mode field
-#define PIT_RB_OP_MASK 0x0e // oper mode field
-#define PIT_RB_BCD_MASK 0x01 // BCD mode field
+#define PIT_READBACK 0xc0 // perform a read-back
+#define PIT_RB_NOT_COUNT 0x20 // don't latch the count
+#define PIT_RB_NOT_STATUS 0x10 // don't latch the status
+#define PIT_RB_CHAN_2 0x08 // read back channel 2
+#define PIT_RB_CHAN_1 0x04 // read back channel 1
+#define PIT_RB_CHAN_0 0x02 // read back channel 0
+#define PIT_RB_ACCESS_MASK 0x30 // access mode field
+#define PIT_RB_OP_MASK 0x0e // oper mode field
+#define PIT_RB_BCD_MASK 0x01 // BCD mode field
#endif
diff --git a/kernel/old/include/x86/uart.h b/kernel/old/include/x86/uart.h
index 293b7b7..0c6194b 100644
--- a/kernel/old/include/x86/uart.h
+++ b/kernel/old/include/x86/uart.h
@@ -20,7 +20,7 @@
*/
#ifndef UART_H
-#define UART_H
+#define UART_H
/*********************************************************************
***************************** I/O PORTS ******************************
@@ -29,14 +29,14 @@
/*
** Base port number assigned to the device
*/
-#define UA4_COM1_PORT 0x3f8
-#define UA4_COM2_PORT 0x2f8
-#define UA4_COM3_PORT 0x3e8
-#define UA4_COM4_PORT 0x2e8
+#define UA4_COM1_PORT 0x3f8
+#define UA4_COM2_PORT 0x2f8
+#define UA4_COM3_PORT 0x3e8
+#define UA4_COM4_PORT 0x2e8
// short name for the one we'll use
-#define UA4_PORT UA4_COM1_PORT
-#define UA5_PORT UA4_COM1_PORT
+#define UA4_PORT UA4_COM1_PORT
+#define UA5_PORT UA4_COM1_PORT
/*
** Registers
@@ -47,7 +47,7 @@
** Index Register(s)
** ===== =========================================
** 0 Receiver Data (RO), Transmitter Data (WO)
-** 1 Interrupt Enable
+** 1 Interrupt Enable
** 2 Interrupt ID (RO), FIFO Control (WO)
** 3 Line Control, Divisor Latch
** 4 Modem Control
@@ -66,156 +66,157 @@
** accessed (0 selects Line Control, 1 selects Divisor Latch), with the
** remaining bits selecting fields within the indicated register.
*/
+
/*
** Receiver Data Register (read-only)
*/
-#define UA4_RXD (UA4_PORT + 0)
-#define UA4_RX_DATA UA4_RXD
+#define UA4_RXD (UA4_PORT+0)
+# define UA4_RX_DATA UA4_RXD
/*
** Transmitter Data Register (write-only)
*/
-#define UA4_TXD (UA4_PORT + 0)
-#define UA4_TX_DATA UA4_TXD
+#define UA4_TXD (UA4_PORT+0)
+# define UA4_TX_DATA UA4_TXD
/*
** Interrupt Enable Register
*/
-#define UA4_IER (UA4_PORT + 1)
-#define UA4_INT_ENABLE_REG UA4_IER
+#define UA4_IER (UA4_PORT+1)
+# define UA4_INT_ENABLE_REG UA4_IER
// fields
-#define UA4_IER_RX_IE 0x01 // Rcvr High-Data-Level Int Enable
-#define UA4_IER_TX_IE 0x02 // Xmitter Low-data-level Int Enable
-#define UA4_IER_LS_IE 0x04 // Line Status Int Enable
-#define UA4_IER_MS_IE 0x08 // Modem Status Int Enable
+#define UA4_IER_RX_IE 0x01 // Rcvr High-Data-Level Int Enable
+#define UA4_IER_TX_IE 0x02 // Xmitter Low-data-level Int Enable
+#define UA4_IER_LS_IE 0x04 // Line Status Int Enable
+#define UA4_IER_MS_IE 0x08 // Modem Status Int Enable
// aliases
-#define UA4_IER_RX_INT_ENABLE UA4_IER_RX_IE
-#define UA4_IER_TX_INT_ENABLE UA4_IER_TX_IE
-#define UA4_IER_LINE_STATUS_INT_ENABLE UA4_IER_LS_IE
-#define UA4_IER_MODEM_STATUS_INT_ENABLE UA4_IER_MS_IE
+#define UA4_IER_RX_INT_ENABLE UA4_IER_RX_IE
+#define UA4_IER_TX_INT_ENABLE UA4_IER_TX_IE
+#define UA4_IER_LINE_STATUS_INT_ENABLE UA4_IER_LS_IE
+#define UA4_IER_MODEM_STATUS_INT_ENABLE UA4_IER_MS_IE
/*
** Interrupt Identification Register (read-only)
**
** a.k.a. Event Identification Register
*/
-#define UA4_IIR (UA4_PORT + 2)
-#define UA4_EVENT_ID UA4_IIR
+#define UA4_IIR (UA4_PORT+2)
+# define UA4_EVENT_ID UA4_IIR
// fields
-#define UA4_IIR_IPF 0x01 // Interrupt Pending flag
+#define UA4_IIR_IPF 0x01 // Interrupt Pending flag
-#define UA4_IIR_IPR_MASK 0x06 // Interrupt Priority mask
-#define UA4_IIR_IPR0_MASK 0x02 // IPR bit 0 mask
-#define UA4_IIR_IPR1_MASK 0x04 // IPR bit 1 mask
+#define UA4_IIR_IPR_MASK 0x06 // Interrupt Priority mask
+# define UA4_IIR_IPR0_MASK 0x02 // IPR bit 0 mask
+# define UA4_IIR_IPR1_MASK 0x04 // IPR bit 1 mask
-#define UA5_IIR_RXFT 0x08 // RX_FIFO Timeout
-#define UA5_IIR_FEN0 0x40 // FIFOs Enabled
-#define UA5_IIR_FEN1 0x80 // FIFOs Enabled
+#define UA5_IIR_RXFT 0x08 // RX_FIFO Timeout
+#define UA5_IIR_FEN0 0x40 // FIFOs Enabled
+#define UA5_IIR_FEN1 0x80 // FIFOs Enabled
// aliases
-#define UA4_IIR_INT_PENDING UA4_IIR_IPF
-#define UA4_IIR_INT_PRIORITY UA4_IIR_IPR
-#define UA5_IIR_RX_FIFO_TIMEOUT UA5_IIR_RXFT
-#define UA5_IIR_FIFO_ENABLED_0 UA5_IIR_FEN0
-#define UA5_IIR_FIFO_ENABLED_1 UA5_IIR_FEN1
+#define UA4_IIR_INT_PENDING UA4_IIR_IPF
+#define UA4_IIR_INT_PRIORITY UA4_IIR_IPR
+#define UA5_IIR_RX_FIFO_TIMEOUT UA5_IIR_RXFT
+#define UA5_IIR_FIFO_ENABLED_0 UA5_IIR_FEN0
+#define UA5_IIR_FIFO_ENABLED_1 UA5_IIR_FEN1
// IIR interrupt priorities (four-bit values)
-#define UA4_IIR_INT_PRI_MASK 0x0f // Mask for extracting int priority
-#define UA4_IIR_NO_INT 0x01 // no interrupt
-#define UA4_IIR_LINE_STATUS 0x06 // line status interrupt
-#define UA4_IIR_RX 0x04 // Receiver High Data Level
-#define UA5_IIR_RX_FIFO 0x0c // Receiver FIFO timeout (16550)
-#define UA4_IIR_TX 0x02 // Transmitter Low Data level
-#define UA4_IIR_MODEM_STATUS 0x00 // Modem Status
+#define UA4_IIR_INT_PRI_MASK 0x0f // Mask for extracting int priority
+# define UA4_IIR_NO_INT 0x01 // no interrupt
+# define UA4_IIR_LINE_STATUS 0x06 // line status interrupt
+# define UA4_IIR_RX 0x04 // Receiver High Data Level
+# define UA5_IIR_RX_FIFO 0x0c // Receiver FIFO timeout (16550)
+# define UA4_IIR_TX 0x02 // Transmitter Low Data level
+# define UA4_IIR_MODEM_STATUS 0x00 // Modem Status
// aliases
-#define UA4_IIR_NO_INT_PENDING UA4_IIR_NO_INT
-#define UA4_IIR_LINE_STATUS_INT_PENDING UA4_IIR_LINE_STATUS
-#define UA4_IIR_RX_INT_PENDING UA4_IIR_RX
-#define UA5_IIR_RX_FIFO_TIMEOUT_INT_PENDING UA5_IIR_RX_FIFO
-#define UA4_IIR_TX_INT_PENDING UA4_IIR_TX
-#define UA4_IIR_MODEM_STATUS_INT_PENDING UA4_IIR_MODEM_STATUS
+#define UA4_IIR_NO_INT_PENDING UA4_IIR_NO_INT
+#define UA4_IIR_LINE_STATUS_INT_PENDING UA4_IIR_LINE_STATUS
+#define UA4_IIR_RX_INT_PENDING UA4_IIR_RX
+#define UA5_IIR_RX_FIFO_TIMEOUT_INT_PENDING UA5_IIR_RX_FIFO
+#define UA4_IIR_TX_INT_PENDING UA4_IIR_TX
+#define UA4_IIR_MODEM_STATUS_INT_PENDING UA4_IIR_MODEM_STATUS
/*
** FIFO Control Register (16550 only, write-only)
*/
-#define UA5_FCR (UA5_PORT + 2)
-#define UA5_FIFO_CTL UA5_FCR
+#define UA5_FCR (UA5_PORT+2)
+# define UA5_FIFO_CTL UA5_FCR
-#define UA5_FCR_FIFO_RESET 0x00 // Reset the FIFO
-#define UA5_FCR_FIFO_EN 0x01 // FIFO Enable
-#define UA5_FCR_RXSR 0x02 // Receiver Soft Reset
-#define UA5_FCR_TXSR 0x04 // Transmitter Soft Reset
+#define UA5_FCR_FIFO_RESET 0x00 // Reset the FIFO
+#define UA5_FCR_FIFO_EN 0x01 // FIFO Enable
+#define UA5_FCR_RXSR 0x02 // Receiver Soft Reset
+#define UA5_FCR_TXSR 0x04 // Transmitter Soft Reset
-#define UA5_FCR_TXFT_MASK 0x30 // TX_FIFO threshold level mask
-#define UA5_FCR_TXFT0_MASK 0x10 // TXFT bit 0 mask
-#define UA5_FCR_TXFT1_MASK 0x20 // TXFT bit 1 mask
-#define UA5_FCR_TX_FIFO_1 0x00 // 1 char
-#define UA5_FCR_TX_FIFO_3 0x10 // 3 char
-#define UA5_FCR_TX_FIFO_9 0x20 // 9 char
-#define UA5_FCR_TX_FIFO_13 0x30 // 13 char
+#define UA5_FCR_TXFT_MASK 0x30 // TX_FIFO threshold level mask
+# define UA5_FCR_TXFT0_MASK 0x10 // TXFT bit 0 mask
+# define UA5_FCR_TXFT1_MASK 0x20 // TXFT bit 1 mask
+# define UA5_FCR_TX_FIFO_1 0x00 // 1 char
+# define UA5_FCR_TX_FIFO_3 0x10 // 3 char
+# define UA5_FCR_TX_FIFO_9 0x20 // 9 char
+# define UA5_FCR_TX_FIFO_13 0x30 // 13 char
-#define UA5_FCR_RXFT_MASK 0xc0 // RX_FIFO threshold level mask
-#define UA5_FCR_RXFT0_MASK 0x40 // RXFT bit 0 mask
-#define UA5_FCR_RXFT1_MASK 0x80 // RXFT bit 1 mask
-#define UA5_FCR_RX_FIFO_1 0x00 // 1 char
-#define UA5_FCR_RX_FIFO_4 0x40 // 4 char
-#define UA5_FCR_RX_FIFO_8 0x80 // 8 char
-#define UA5_FCR_RX_FIFO_14 0xc0 // 14 char
+#define UA5_FCR_RXFT_MASK 0xc0 // RX_FIFO threshold level mask
+# define UA5_FCR_RXFT0_MASK 0x40 // RXFT bit 0 mask
+# define UA5_FCR_RXFT1_MASK 0x80 // RXFT bit 1 mask
+# define UA5_FCR_RX_FIFO_1 0x00 // 1 char
+# define UA5_FCR_RX_FIFO_4 0x40 // 4 char
+# define UA5_FCR_RX_FIFO_8 0x80 // 8 char
+# define UA5_FCR_RX_FIFO_14 0xc0 // 14 char
// aliases
-#define UA5_FCR_FIFO_ENABLED UA5_FCR_FIFO_EN
-#define UA5_FCR_RX_SOFT_RESET UA5_FCR_RXSR
-#define UA5_FCR_TX_SOFT_RESET UA5_FCR_TXSR
-#define UA5_FCR_TX_FIFO_1_CHAR UA5_FCR_TX_FIFO_1
-#define UA5_FCR_TX_FIFO_3_CHAR UA5_FCR_TX_FIFO_3
-#define UA5_FCR_TX_FIFO_9_CHAR UA5_FCR_TX_FIFO_9
-#define UA5_FCR_TX_FIFO_13_CHAR UA5_FCR_TX_FIFO_13
-#define UA5_FCR_RX_FIFO_1_CHAR UA5_FCR_RX_FIFO_1
-#define UA5_FCR_RX_FIFO_4_CHAR UA5_FCR_RX_FIFO_4
-#define UA5_FCR_RX_FIFO_8_CHAR UA5_FCR_RX_FIFO_8
-#define UA5_FCR_RX_FIFO_14_CHAR UA5_FCR_RX_FIFO_14
+#define UA5_FCR_FIFO_ENABLED UA5_FCR_FIFO_EN
+#define UA5_FCR_RX_SOFT_RESET UA5_FCR_RXSR
+#define UA5_FCR_TX_SOFT_RESET UA5_FCR_TXSR
+#define UA5_FCR_TX_FIFO_1_CHAR UA5_FCR_TX_FIFO_1
+#define UA5_FCR_TX_FIFO_3_CHAR UA5_FCR_TX_FIFO_3
+#define UA5_FCR_TX_FIFO_9_CHAR UA5_FCR_TX_FIFO_9
+#define UA5_FCR_TX_FIFO_13_CHAR UA5_FCR_TX_FIFO_13
+#define UA5_FCR_RX_FIFO_1_CHAR UA5_FCR_RX_FIFO_1
+#define UA5_FCR_RX_FIFO_4_CHAR UA5_FCR_RX_FIFO_4
+#define UA5_FCR_RX_FIFO_8_CHAR UA5_FCR_RX_FIFO_8
+#define UA5_FCR_RX_FIFO_14_CHAR UA5_FCR_RX_FIFO_14
/*
** Line Control Register (available in all banks)
**
** Selected when bit 7 of the value written to the port is a 0.
*/
-#define UA4_LCR (UA4_PORT + 3)
-#define UA4_LINE_CTL UA4_LCR
+#define UA4_LCR (UA4_PORT+3)
+# define UA4_LINE_CTL UA4_LCR
-#define UA4_LCR_WLS_MASK 0x03 // Word Length Select mask
-#define UA4_LCR_WLS0_MASK 0x01 // WLS bit 0 mask
-#define UA4_LCR_WLS1_MASK 0x02 // WLS bit 1 mask
-#define UA4_LCR_WLS_5 0x00 // 5 bits per char
-#define UA4_LCR_WLS_6 0x01 // 6 bits per char
-#define UA4_LCR_WLS_7 0x02 // 7 bits per char
-#define UA4_LCR_WLS_8 0x03 // 8 bits per char
+#define UA4_LCR_WLS_MASK 0x03 // Word Length Select mask
+# define UA4_LCR_WLS0_MASK 0x01 // WLS bit 0 mask
+# define UA4_LCR_WLS1_MASK 0x02 // WLS bit 1 mask
+# define UA4_LCR_WLS_5 0x00 // 5 bits per char
+# define UA4_LCR_WLS_6 0x01 // 6 bits per char
+# define UA4_LCR_WLS_7 0x02 // 7 bits per char
+# define UA4_LCR_WLS_8 0x03 // 8 bits per char
-#define UA4_LCR_STB 0x04 // Stop Bits
-#define UA4_LCR_1_STOP_BIT 0x00
-#define UA4_LCR_2_STOP_BIT 0x04
+#define UA4_LCR_STB 0x04 // Stop Bits
+# define UA4_LCR_1_STOP_BIT 0x00
+# define UA4_LCR_2_STOP_BIT 0x04
-#define UA4_LCR_PEN 0x08 // Parity Enable
-#define UA4_LCR_EPS 0x10 // Even Parity Select
-#define UA4_LCR_STKP 0x20 // Sticky Parity
-#define UA4_LCR_NO_PARITY 0x00
-#define UA4_LCR_ODD_PARITY UA4_LCR_PEN
-#define UA4_LCR_EVEN_PARITY (UA4_LCR_PEN | UA4_LCR_EPS)
-#define UA4_LCR_PARITY_LOGIC_1 (UA4_LCR_PEN | UA4_LCR_STKP)
-#define UA4_LCR_PARITY_LOGIC_0 (UA4_LCR_PEN | UA4_LCR_EPS | UA4_LCR_STKP)
+#define UA4_LCR_PEN 0x08 // Parity Enable
+#define UA4_LCR_EPS 0x10 // Even Parity Select
+#define UA4_LCR_STKP 0x20 // Sticky Parity
+# define UA4_LCR_NO_PARITY 0x00
+# define UA4_LCR_ODD_PARITY UA4_LCR_PEN
+# define UA4_LCR_EVEN_PARITY (UA4_LCR_PEN|UA4_LCR_EPS)
+# define UA4_LCR_PARITY_LOGIC_1 (UA4_LCR_PEN|UA4_LCR_STKP)
+# define UA4_LCR_PARITY_LOGIC_0 (UA4_LCR_PEN|UA4_LCR_EPS|UA4_LCR_STKP)
-#define UA4_LCR_SBRK 0x40 // Set Break
-#define UA4_LCR_DLAB 0x80 // Divisor Latch select bit
+#define UA4_LCR_SBRK 0x40 // Set Break
+#define UA4_LCR_DLAB 0x80 // Divisor Latch select bit
// aliases
-#define UA4_LCR_STOP_BITS UA4_LCR_STB
-#define UA4_LCR_PARITY_ENABLE UA4_LCR_PEN
-#define UA4_LCR_SET_BREAK UA4_LCR_SBRK
-#define UA4_LCR_BANK_SELECT_ENABLE UA4_LCR_BKSE
+# define UA4_LCR_STOP_BITS UA4_LCR_STB
+# define UA4_LCR_PARITY_ENABLE UA4_LCR_PEN
+# define UA4_LCR_SET_BREAK UA4_LCR_SBRK
+# define UA4_LCR_BANK_SELECT_ENABLE UA4_LCR_BKSE
/*
** Divisor Latch Registers
@@ -232,109 +233,109 @@
** "re-lock" the Divisor Latch registers, write a command byte to
** LCR with 0 in the DLAB bit.
*/
-#define UA4_DLL (UA4_PORT + 0) // Divisor Latch (least sig.)
-#define UA4_DLM (UA4_PORT + 1) // Divisor Latch (most sig.)
+#define UA4_DLL (UA4_PORT+0) // Divisor Latch (least sig.)
+#define UA4_DLM (UA4_PORT+1) // Divisor Latch (most sig.)
// aliases
-#define UA4_DIVISOR_LATCH_LS UA4_DLL
-#define UA4_DIVISOR_LATCH_MS UA4_DLM
+#define UA4_DIVISOR_LATCH_LS UA4_DLL
+#define UA4_DIVISOR_LATCH_MS UA4_DLM
// Baud rate divisor high and low bytes
-#define BAUD_HIGH_BYTE(x) (((x) >> 8) & 0xff)
-#define BAUD_LOW_BYTE(x) ((x) & 0xff)
+#define BAUD_HIGH_BYTE(x) (((x) >> 8) & 0xff)
+#define BAUD_LOW_BYTE(x) ((x) & 0xff)
// Baud rate divisors
-#define DL_BAUD_50 2304
-#define DL_BAUD_75 1536
-#define DL_BAUD_110 1047
-#define DL_BAUD_150 768
-#define DL_BAUD_300 384
-#define DL_BAUD_600 192
-#define DL_BAUD_1200 96
-#define DL_BAUD_1800 64
-#define DL_BAUD_2000 58
-#define DL_BAUD_2400 48
-#define DL_BAUD_3600 32
-#define DL_BAUD_4800 24
-#define DL_BAUD_7200 16
-#define DL_BAUD_9600 12
-#define DL_BAUD_14400 8
-#define DL_BAUD_19200 6
-#define DL_BAUD_28800 4
-#define DL_BAUD_38400 3
-#define DL_BAUD_57600 2
-#define DL_BAUD_115200 1
+#define DL_BAUD_50 2304
+#define DL_BAUD_75 1536
+#define DL_BAUD_110 1047
+#define DL_BAUD_150 768
+#define DL_BAUD_300 384
+#define DL_BAUD_600 192
+#define DL_BAUD_1200 96
+#define DL_BAUD_1800 64
+#define DL_BAUD_2000 58
+#define DL_BAUD_2400 48
+#define DL_BAUD_3600 32
+#define DL_BAUD_4800 24
+#define DL_BAUD_7200 16
+#define DL_BAUD_9600 12
+#define DL_BAUD_14400 8
+#define DL_BAUD_19200 6
+#define DL_BAUD_28800 4
+#define DL_BAUD_38400 3
+#define DL_BAUD_57600 2
+#define DL_BAUD_115200 1
/*
** Modem Control Register
*/
-#define UA4_MCR (UA4_PORT + 4)
-#define UA4_MODEM_CTL UA4_MCR
+#define UA4_MCR (UA4_PORT+4)
+# define UA4_MODEM_CTL UA4_MCR
-#define UA4_MCR_DTR 0x01 // Data Terminal Ready
-#define UA4_MCR_RTS 0x02 // Ready to Send
-#define UA4_MCR_RILP 0x04 // Loopback Interrupt Request
-#define UA4_MCR_ISEN 0x08 // Interrupt Signal Enable
-#define UA4_MCR_DCDLP 0x08 // DCD Loopback
-#define UA4_MCR_LOOP 0x10 // Loopback Enable
+#define UA4_MCR_DTR 0x01 // Data Terminal Ready
+#define UA4_MCR_RTS 0x02 // Ready to Send
+#define UA4_MCR_RILP 0x04 // Loopback Interrupt Request
+#define UA4_MCR_ISEN 0x08 // Interrupt Signal Enable
+#define UA4_MCR_DCDLP 0x08 // DCD Loopback
+#define UA4_MCR_LOOP 0x10 // Loopback Enable
// aliases
-#define UA4_MCR_DATA_TERMINAL_READY UA4_MCR_DTR
-#define UA4_MCR_READY_TO_SEND UA4_MCR_RTS
-#define UA4_MCR_LOOPBACK_INT_REQ UA4_MCR_RILP
-#define UA4_MCR_INT_SIGNAL_ENABLE UA4_MCR_ISEN
-#define UA4_MCR_LOOPBACK_DCD UA4_MCR_DCDLP
-#define UA4_MCR_LOOPBACK_ENABLE UA4_MCR_LOOP
+#define UA4_MCR_DATA_TERMINAL_READY UA4_MCR_DTR
+#define UA4_MCR_READY_TO_SEND UA4_MCR_RTS
+#define UA4_MCR_LOOPBACK_INT_REQ UA4_MCR_RILP
+#define UA4_MCR_INT_SIGNAL_ENABLE UA4_MCR_ISEN
+#define UA4_MCR_LOOPBACK_DCD UA4_MCR_DCDLP
+#define UA4_MCR_LOOPBACK_ENABLE UA4_MCR_LOOP
/*
** Line Status Register
*/
-#define UA4_LSR (UA4_PORT + 5)
-#define UA4_LINE_STATUS UA4_LSR
+#define UA4_LSR (UA4_PORT+5)
+# define UA4_LINE_STATUS UA4_LSR
-#define UA4_LSR_RXDA 0x01 // Receiver Data Available
-#define UA4_LSR_OE 0x02 // Overrun Error
-#define UA4_LSR_PE 0x04 // Parity Error
-#define UA4_LSR_FE 0x08 // Framing Error
-#define UA4_LSR_BRK 0x10 // Break Event Detected
-#define UA4_LSR_TXRDY 0x20 // Transmitter Ready
-#define UA4_LSR_TXEMP 0x40 // Transmitter Empty
-#define UA4_LSR_ER_INF 0x80 // Error in RX_FIFO
+#define UA4_LSR_RXDA 0x01 // Receiver Data Available
+#define UA4_LSR_OE 0x02 // Overrun Error
+#define UA4_LSR_PE 0x04 // Parity Error
+#define UA4_LSR_FE 0x08 // Framing Error
+#define UA4_LSR_BRK 0x10 // Break Event Detected
+#define UA4_LSR_TXRDY 0x20 // Transmitter Ready
+#define UA4_LSR_TXEMP 0x40 // Transmitter Empty
+#define UA4_LSR_ER_INF 0x80 // Error in RX_FIFO
// aliases
-#define UA4_LSR_RX_DATA_AVAILABLE UA4_LSR_RXDA
-#define UA4_LSR_OVERRUN_ERROR UA4_LSR_OE
-#define UA4_LSR_PARITY_ERROR UA4_LSR_PE
-#define UA4_LSR_FRAMING_ERROR UA4_LSR_FE
-#define UA4_LSR_BREAK_DETECTED UA4_LSR_BRK
-#define UA4_LSR_TX_READY UA4_LSR_TXRDY
-#define UA4_LSR_TX_EMPTY UA4_LSR_TXEMP
-#define UA4_LSR_RX_FIFO_ERROR UA4_LSR_ER_INF
+#define UA4_LSR_RX_DATA_AVAILABLE UA4_LSR_RXDA
+#define UA4_LSR_OVERRUN_ERROR UA4_LSR_OE
+#define UA4_LSR_PARITY_ERROR UA4_LSR_PE
+#define UA4_LSR_FRAMING_ERROR UA4_LSR_FE
+#define UA4_LSR_BREAK_DETECTED UA4_LSR_BRK
+#define UA4_LSR_TX_READY UA4_LSR_TXRDY
+#define UA4_LSR_TX_EMPTY UA4_LSR_TXEMP
+#define UA4_LSR_RX_FIFO_ERROR UA4_LSR_ER_INF
/*
** Modem Status Register
*/
-#define UA4_MSR (UA4_PORT + 6)
-#define UA4_MODEM_STATUS UA4_MSR
+#define UA4_MSR (UA4_PORT+6)
+# define UA4_MODEM_STATUS UA4_MSR
-#define UA4_MSR_DCTS 0x01 // Delta Clear to Send
-#define UA4_MSR_DDSR 0x02 // Delta Data Set Ready
-#define UA4_MSR_TERI 0x04 // Trailing Edge Ring Indicate
-#define UA4_MSR_DDCD 0x08 // Delta Data Carrier Detect
-#define UA4_MSR_CTS 0x10 // Clear to Send
-#define UA4_MSR_DSR 0x20 // Data Set Ready
-#define UA4_MSR_RI 0x40 // Ring Indicate
-#define UA4_MSR_DCD 0x80 // Data Carrier Detect
+#define UA4_MSR_DCTS 0x01 // Delta Clear to Send
+#define UA4_MSR_DDSR 0x02 // Delta Data Set Ready
+#define UA4_MSR_TERI 0x04 // Trailing Edge Ring Indicate
+#define UA4_MSR_DDCD 0x08 // Delta Data Carrier Detect
+#define UA4_MSR_CTS 0x10 // Clear to Send
+#define UA4_MSR_DSR 0x20 // Data Set Ready
+#define UA4_MSR_RI 0x40 // Ring Indicate
+#define UA4_MSR_DCD 0x80 // Data Carrier Detect
// aliases
-#define UA4_MSR_DELTA_CLEAR_TO_SEND UA4_MSR_DCTS
-#define UA4_MSR_DELTA_DATA_SET_READY UA4_MSR_DDSR
-#define UA4_MSR_TRAILING_EDGE_RING UA4_MSR_TERI
-#define UA4_MSR_DELTA_DATA_CARRIER_DETECT UA4_MSR_DDCD
-#define UA4_MSR_CLEAR_TO_SEND UA4_MSR_CTS
-#define UA4_MSR_DATA_SET_READY UA4_MSR_DSR
-#define UA4_MSR_RING_INDICATE UA4_MSR_RI
-#define UA4_MSR_DATA_CARRIER_DETECT UA4_MSR_DCD
+#define UA4_MSR_DELTA_CLEAR_TO_SEND UA4_MSR_DCTS
+#define UA4_MSR_DELTA_DATA_SET_READY UA4_MSR_DDSR
+#define UA4_MSR_TRAILING_EDGE_RING UA4_MSR_TERI
+#define UA4_MSR_DELTA_DATA_CARRIER_DETECT UA4_MSR_DDCD
+#define UA4_MSR_CLEAR_TO_SEND UA4_MSR_CTS
+#define UA4_MSR_DATA_SET_READY UA4_MSR_DSR
+#define UA4_MSR_RING_INDICATE UA4_MSR_RI
+#define UA4_MSR_DATA_CARRIER_DETECT UA4_MSR_DCD
/*
** Scratch Register
@@ -342,7 +343,7 @@
** Not used by the UART; usable as a "scratchpad" register for
** temporary storage.
*/
-#define UA4_SCR (UA4_PORT + 7)
-#define UA4_SCRATCH UA4_UA5_SCR
+#define UA4_SCR (UA4_PORT+7)
+# define UA4_SCRATCH UA4_UA5_SCR
-#endif /* uart.h */
+#endif /* uart.h */
diff --git a/kernel/old/isrs.S b/kernel/old/isrs.S
index f5fdbca..f6bd662 100644
--- a/kernel/old/isrs.S
+++ b/kernel/old/isrs.S
@@ -19,8 +19,6 @@
# .arch i386
#include <bootstrap.h>
-#include <offsets.h>
-#include <vm.h>
/*
** Configuration options - define in Makefile
@@ -102,8 +100,8 @@ isr_save:
**
** Set up parameters for the ISR call.
*/
- movl CTX_vector(%esp),%eax // get vector number and error code
- movl CTX_code(%esp),%ebx
+ movl 52(%esp),%eax // get vector number and error code
+ movl 56(%esp),%ebx
/*
***********************
@@ -122,12 +120,11 @@ isr_save:
// save the context pointer
movl current, %edx
- movl %esp, PCB_context(%edx)
+ movl %esp, (%edx)
// also save the page directory pointer
movl %cr3, %ecx
- addl $KERN_BASE, %ecx // convert to a virtual address
- movl %ecx, PCB_pdir(%edx)
+ movl %ecx, 4(%edx)
// switch to the system stack
//
@@ -169,9 +166,8 @@ isr_restore:
***********************
*/
movl current, %ebx // return to the user stack
- movl PCB_context(%ebx), %esp // ESP --> context save area
- movl PCB_pdir(%ebx), %ecx // page directory pointer
- subl $KERN_BASE, %ecx // convert to a physical address
+ movl (%ebx), %esp // ESP --> context save area
+ movl 4(%ebx), %ecx // page directory pointer
movl %ecx, %cr3
// now we're operating with the user process'
@@ -187,7 +183,7 @@ isr_restore:
/*
** DEBUGGING CODE PART 1
**
-** This code will execute during each context restore, and
+** This code will execute during each context restore, and
** should be modified to print out whatever debugging information
** is desired.
**
diff --git a/kernel/old/kernel.c b/kernel/old/kernel.c
index ce2e9dd..14e8b02 100644
--- a/kernel/old/kernel.c
+++ b/kernel/old/kernel.c
@@ -6,7 +6,7 @@
** @brief Kernel support routines
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
#include <cio.h>
@@ -37,8 +37,8 @@
// character buffers, usable throughout the OS
// nto guaranteed to retain their contents across an exception return
-char b256[256]; // primarily used for message creation
-char b512[512]; // used by PANIC macro
+char b256[256]; // primarily used for message creation
+char b512[512]; // used by PANIC macro
/*
** PRIVATE FUNCTIONS
@@ -55,117 +55,119 @@ char b512[512]; // used by PANIC macro
**
** @param dtrace Decode the TRACE options
*/
-static void kreport(bool_t dtrace)
-{
- cio_puts("\n-------------------------------\n");
- cio_printf("Config: N_PROCS = %d", N_PROCS);
- cio_printf(" N_PRIOS = %d", N_PRIOS);
- cio_printf(" N_STATES = %d", N_STATES);
- cio_printf(" CLOCK = %dHz\n", CLOCK_FREQ);
+static void kreport( bool_t dtrace ) {
+
+ cio_puts( "\n-------------------------------\n" );
+ cio_printf( "Config: N_PROCS = %d", N_PROCS );
+ cio_printf( " N_PRIOS = %d", N_PRIOS );
+ cio_printf( " N_STATES = %d", N_STATES );
+ cio_printf( " CLOCK = %dHz\n", CLOCK_FREQ );
// This code is ugly, but it's the simplest way to
// print out the values of compile-time options
// without spending a lot of execution time at it.
- cio_puts("Options: "
+ cio_puts( "Options: "
#ifdef RPT_INT_UNEXP
- " R-uint"
+ " R-uint"
#endif
#ifdef RPT_INT_MYSTERY
- " R-mint"
+ " R-mint"
#endif
#ifdef TRACE_CX
- " CX"
+ " CX"
#endif
#ifdef CONSOLE_STATS
- " Cstats"
+ " Cstats"
#endif
- ); // end of cio_puts() call
+ ); // end of cio_puts() call
#ifdef SANITY
- cio_printf(" SANITY = %d", SANITY);
+ cio_printf( " SANITY = %d", SANITY );
#endif
#ifdef STATUS
- cio_printf(" STATUS = %d", STATUS);
+ cio_printf( " STATUS = %d", STATUS );
#endif
#if TRACE > 0
- cio_printf(" TRACE = 0x%04x\n", TRACE);
+ cio_printf( " TRACE = 0x%04x\n", TRACE );
// decode the trace settings if that was requested
- if (TRACING_SOMETHING && dtrace) {
+ if( TRACING_SOMETHING && dtrace ) {
+
// this one is simpler - we rely on string literal
// concatenation in the C compiler to create one
// long string to print out
- cio_puts("Tracing:"
+ cio_puts( "Tracing:"
#if TRACING_PCB
- " PCB"
+ " PCB"
#endif
#if TRACING_VM
- " VM"
+ " VM"
#endif
#if TRACING_QUEUE
- " QUE"
+ " QUE"
#endif
#if TRACING_SCHED
- " SCHED"
+ " SCHED"
#endif
#if TRACING_DISPATCH
- " DISPATCH"
+ " DISPATCH"
#endif
#if TRACING_SYSCALLS
- " SCALL"
+ " SCALL"
#endif
#if TRACING_SYSRETS
- " SRET"
+ " SRET"
#endif
#if TRACING_EXIT
- " EXIT"
+ " EXIT"
#endif
#if TRACING_INIT
- " INIT"
+ " INIT"
#endif
#if TRACING_KMEM
- " KM"
+ " KM"
#endif
#if TRACING_KMEM_FREELIST
- " KMFL"
+ " KMFL"
#endif
#if TRACING_KMEM_INIT
- " KMIN"
+ " KMIN"
#endif
#if TRACING_FORK
- " FORK"
+ " FORK"
#endif
#if TRACING_EXEC
- " EXEC"
+ " EXEC"
#endif
#if TRACING_SIO_STAT
- " S_STAT"
+ " S_STAT"
#endif
#if TRACING_SIO_ISR
- " S_ISR"
+ " S_ISR"
#endif
#if TRACING_SIO_RD
- " S_RD"
+ " S_RD"
#endif
#if TRACING_SIO_WR
- " S_WR"
+ " S_WR"
#endif
#if TRACING_USER
- " USER"
+ " USER"
#endif
#if TRACING_ELF
- " ELF"
+ " ELF"
#endif
- ); // end of cio_puts() call
+ ); // end of cio_puts() call
}
-#endif /* TRACE > 0 */
+#endif /* TRACE > 0 */
- cio_putchar('\n');
+ cio_puts( "\n-------------------------------\n" );
}
+
#if defined(CONSOLE_STATS)
/**
** stats - callback routine for console statistics
@@ -177,51 +179,53 @@ static void kreport(bool_t dtrace)
**
** This code runs as part of the CIO ISR.
*/
-static void stats(int code)
-{
- switch (code) {
- case 'a': // dump the active table
- ptable_dump("\nActive processes", false);
+static void stats( int code ) {
+
+ switch( code ) {
+
+ case 'a': // dump the active table
+ ptable_dump( "\nActive processes", false );
break;
- case 'c': // dump context info for all active PCBs
- ctx_dump_all("\nContext dump");
+ case 'c': // dump context info for all active PCBs
+ ctx_dump_all( "\nContext dump" );
break;
- case 'p': // dump the active table and all PCBs
- ptable_dump("\nActive processes", true);
+ case 'p': // dump the active table and all PCBs
+ ptable_dump( "\nActive processes", true );
break;
- case 'q': // dump the queues
+ case 'q': // dump the queues
// code to dump out any/all queues
- pcb_queue_dump("R", ready, true);
- pcb_queue_dump("W", waiting, true);
- pcb_queue_dump("S", sleeping, true);
- pcb_queue_dump("Z", zombie, true);
- pcb_queue_dump("I", sioread, true);
+ pcb_queue_dump( "R", ready );
+ pcb_queue_dump( "W", waiting );
+ pcb_queue_dump( "S", sleeping );
+ pcb_queue_dump( "Z", zombie );
+ pcb_queue_dump( "I", sioread );
break;
- case 'r': // print system configuration information
- report(true);
+ case 'r': // print system configuration information
+ report( true );
break;
// ignore CR and LF
case '\r': // FALL THROUGH
case '\n':
break;
-
+
default:
- cio_printf("console: unknown request '0x%02x'\n", code);
+ cio_printf( "console: unknown request '0x%02x'\n", code );
// FALL THROUGH
- case 'h': // help message
- cio_puts("\nCommands:\n"
- " a -- dump the active table\n"
- " c -- dump contexts for active processes\n"
- " h -- this message\n"
- " p -- dump the active table and all PCBs\n"
- " q -- dump the queues\n"
- " r -- print system configuration\n");
+ case 'h': // help message
+ cio_puts( "\nCommands:\n"
+ " a -- dump the active table\n"
+ " c -- dump contexts for active processes\n"
+ " h -- this message\n"
+ " p -- dump the active table and all PCBs\n"
+ " q -- dump the queues\n"
+ " r -- print system configuration\n"
+ );
break;
}
}
@@ -239,15 +243,15 @@ static void stats(int code)
**
** Making this type 'int' keeps the compiler happy.
*/
-int main(void)
-{
+int main( void ) {
+
/*
** BOILERPLATE CODE - taken from basic framework
**
** Initialize interrupt stuff.
*/
- init_interrupts(); // IDT and PIC initialization
+ init_interrupts(); // IDT and PIC initialization
/*
** Console I/O system.
@@ -257,13 +261,13 @@ int main(void)
** and queue modules.
*/
-#if defined(CONSOLE_STATS)
- cio_init(stats);
+#if defined(CONSOLE_STATS)
+ cio_init( stats );
#else
- cio_init(NULL); // no console callback routine
+ cio_init( NULL ); // no console callback routine
#endif
- cio_clearscreen(); // wipe out whatever is there
+ cio_clearscreen(); // wipe out whatever is there
/*
** TERM-SPECIFIC CODE STARTS HERE
@@ -276,40 +280,40 @@ int main(void)
** install their own ISRs in their initialization routines.
*/
- cio_puts("System initialization starting.\n");
- cio_puts("-------------------------------\n");
+ cio_puts( "System initialization starting.\n" );
+ cio_puts( "-------------------------------\n" );
- cio_puts("Modules:");
+ cio_puts( "Modules:" );
// call the module initialization functions, being
// careful to follow any module precedence requirements
- km_init(); // MUST BE FIRST
+ km_init(); // MUST BE FIRST
#if TRACING_KMEM || TRACING_KMEM_FREE
- delay(DELAY_2_SEC); // approximately
+ delay( DELAY_2_SEC ); // approximately
#endif
// other module initialization calls here
- clk_init(); // clock
- pcb_init(); // process (PCBs, queues, scheduler)
+ clk_init(); // clock
+ pcb_init(); // process (PCBs, queues, scheduler)
#if TRACING_PCB
- delay(DELAY_2_SEC);
+ delay( DELAY_2_SEC );
#endif
- sio_init(); // serial i/o
- sys_init(); // system call
+ sio_init(); // serial i/o
+ sys_init(); // system call
#if TRACING_SYSCALLS || TRACING_SYSRETS
- delay(DELAY_2_SEC);
+ delay( DELAY_2_SEC );
#endif
- vm_init(); // virtual memory
- user_init(); // user code handling
+ vm_init(); // virtual memory
+ user_init(); // user code handling
- cio_puts("\nModule initialization complete.\n");
+ cio_puts( "\nModule initialization complete.\n" );
+ cio_puts( "-------------------------------\n" );
// report our configuration options
- kreport(true);
- cio_puts("-------------------------------\n");
+ kreport( true );
- delay(DELAY_2_SEC);
+ delay( DELAY_3_SEC );
/*
** Other tasks typically performed here:
@@ -319,14 +323,14 @@ int main(void)
/*
** Create the initial user process
- **
+ **
** This code is largely stolen from the fork() and exec()
** implementations in syscalls.c; if those change, this must
** also change.
*/
// if we can't get a PCB, there's no use continuing!
- assert(pcb_alloc(&init_pcb) == SUCCESS);
+ assert( pcb_alloc(&init_pcb) == SUCCESS );
// fill in the necessary details
init_pcb->pid = PID_INIT;
@@ -334,67 +338,47 @@ int main(void)
init_pcb->priority = PRIO_HIGH;
// find the 'init' program
- prog_t *prog = user_locate(Init);
- assert(prog != NULL);
+ prog_t *prog = user_locate( Init );
+ assert( prog != NULL );
// command-line arguments for 'init'
const char *args[2] = { "init", NULL };
// load it
- assert(user_load(prog, init_pcb, args, true) == SUCCESS);
+ assert( user_load(prog,init_pcb,args) == SUCCESS );
// send it on its merry way
- schedule(init_pcb);
- dispatch();
+ schedule( init_pcb );
#ifdef TRACE_CX
// if we're using a scrolling region, wait a bit more and then set it up
- delay(DELAY_7_SEC);
+ delay( DELAY_7_SEC );
// define a scrolling region in the top 7 lines of the screen
- cio_setscroll(0, 7, 99, 99);
+ cio_setscroll( 0, 7, 99, 99 );
// clear it
cio_clearscroll();
// clear the top line
- cio_puts_at(
- 0, 0,
- "* ");
+ cio_puts_at( 0, 0, "* " );
// separator
- cio_puts_at(
- 0, 6,
- "================================================================================");
+ cio_puts_at( 0, 6, "================================================================================" );
#endif
+ // switch to the "real" kernel page directory
+ vm_set_kvm();
+
/*
** END OF TERM-SPECIFIC CODE
**
** Finally, report that we're all done.
*/
- cio_puts("System initialization complete.\n");
- cio_puts("-------------------------------\n");
-
- sio_enable(SIO_RX);
-
-#if 0
- // produce a "system state" report
- cio_puts( "System status: Queues " );
- pcb_queue_dump( "R", ready, true );
- pcb_queue_dump( "W", waiting, true );
- pcb_queue_dump( "S", sleeping, true );
- pcb_queue_dump( "Z", zombie, true );
- pcb_queue_dump( "I", sioread, true );
- ptable_dump_counts();
- pcb_dump( "Current: ", current, true );
+ cio_puts( "System initialization complete.\n" );
+ cio_puts( "-------------------------------\n" );
- delay( DELAY_3_SEC );
-
- vm_print( current->pdir, true, TwoLevel );
-
- delay( DELAY_3_SEC );
-#endif
+ sio_enable( SIO_RX );
return 0;
}
diff --git a/kernel/old/kernel.ld b/kernel/old/kernel.ld
new file mode 100644
index 0000000..1534aad
--- /dev/null
+++ b/kernel/old/kernel.ld
@@ -0,0 +1,71 @@
+/*
+** Simple linker script for the 20245 kernel.
+*/
+
+OUTPUT_FORMAT("elf32-i386", "elf32-i386", "elf32-i386")
+OUTPUT_ARCH(i386)
+ENTRY(_start)
+
+SECTIONS
+{
+ /* Link the kernel at this address. */
+ /* Must match what is defined in vm.h! */
+ . = 0x80010000;
+
+ .text : AT(0x10000) {
+ *(.text .stub .text.* .gnu.linkonce.t.*)
+ }
+
+ /* standard symbols */
+ PROVIDE(etext = .);
+ PROVIDE(_etext = .);
+
+ /* put read-only data next */
+ .rodata : {
+ *(.rodata .rodata.* .gnu.linkonce.r.*)
+ }
+
+ /* Could put STABs here */
+ .stab : {
+ PROVIDE(__STAB_BEGIN__ = .);
+ *(.stab);
+ PROVIDE(__STAB_END__ = .);
+ }
+ .stabstr : {
+ PROVIDE(__STABSTR_BEGIN__ = .);
+ *(.stabstr);
+ PROVIDE(__STABSTR_END__ = .);
+ }
+
+ /* Align the data segment at the next page boundary */
+ . = ALIGN(0x1000);
+
+ PROVIDE(data = .);
+ PROVIDE(_data = .);
+
+ /* The data segment */
+ .data : {
+ *(.data .data.*)
+ }
+
+ PROVIDE(edata = .);
+ PROVIDE(_edata = .);
+
+ /* page-align the BSS */
+ . = ALIGN(0x1000);
+
+ PROVIDE(__bss_start = .);
+
+ .bss : {
+ *(.bss .bss.*)
+ *(COMMON)
+ }
+
+ PROVIDE(end = .);
+ PROVIDE(_end = .);
+
+ /DISCARD/ : {
+ /* *(.stab .stab_info .stabstr) */
+ *(.eh_frame .note.GNU-stack .note.gnu.property .comment)
+ }
+}
diff --git a/kernel/old/kmem.c b/kernel/old/kmem.c
index fe0c7de..febc6b9 100644
--- a/kernel/old/kmem.c
+++ b/kernel/old/kmem.c
@@ -69,22 +69,22 @@
*/
// combination tracing tests
-#define ANY_KMEM (TRACING_KMEM | TRACING_KMEM_INIT | TRACING_KMEM_FREELIST)
-#define KMEM_OR_INIT (TRACING_KMEM | TRACING_KMEM_INIT)
+#define ANY_KMEM (TRACING_KMEM|TRACING_KMEM_INIT|TRACING_KMEM_FREELIST)
+#define KMEM_OR_INIT (TRACING_KMEM|TRACING_KMEM_INIT)
// parameters related to word and block sizes
-#define WORD_SIZE sizeof(int)
-#define LOG2_OF_WORD_SIZE 2
+#define WORD_SIZE sizeof(int)
+#define LOG2_OF_WORD_SIZE 2
-#define LOG2_OF_PAGE_SIZE 12
+#define LOG2_OF_PAGE_SIZE 12
-#define LOG2_OF_SLICE_SIZE 10
+#define LOG2_OF_SLICE_SIZE 10
// converters: pages to bytes, bytes to pages
-#define P2B(x) ((x) << LOG2_OF_PAGE_SIZE)
-#define B2P(x) ((x) >> LOG2_OF_PAGE_SIZE)
+#define P2B(x) ((x) << LOG2_OF_PAGE_SIZE)
+#define B2P(x) ((x) >> LOG2_OF_PAGE_SIZE)
/*
** Name: adjacent
@@ -94,8 +94,8 @@
** Description: Determines whether the second block immediately
** follows the first one.
*/
-#define adjacent(first, second) \
- ((void *)(first) + P2B((first)->pages) == (void *)(second))
+#define adjacent(first,second) \
+ ( (void *) (first) + P2B((first)->pages) == (void *) (second) )
/*
** PRIVATE DATA TYPES
@@ -115,44 +115,44 @@ typedef union b64_u {
} b64_t;
// the halves of a 64-bit address
-#define LOW part[0]
-#define HIGH part[1]
+#define LOW part[0]
+#define HIGH part[1]
// memory region descriptor
typedef struct memregion_s {
- b64_t base; // base address
- b64_t length; // region length
- uint32_t type; // type of region
- uint32_t acpi; // ACPI 3.0 info
+ b64_t base; // base address
+ b64_t length; // region length
+ uint32_t type; // type of region
+ uint32_t acpi; // ACPI 3.0 info
} ATTR_PACKED region_t;
/*
** Region types
*/
-#define REGION_USABLE 1
-#define REGION_RESERVED 2
-#define REGION_ACPI_RECL 3
-#define REGION_ACPI_NVS 4
-#define REGION_BAD 5
+#define REGION_USABLE 1
+#define REGION_RESERVED 2
+#define REGION_ACPI_RECL 3
+#define REGION_ACPI_NVS 4
+#define REGION_BAD 5
/*
** ACPI 3.0 bit fields
*/
-#define REGION_IGNORE 0x01
-#define REGION_NONVOL 0x02
+#define REGION_IGNORE 0x01
+#define REGION_NONVOL 0x02
/*
** 32-bit and 64-bit address values as 64-bit literals
*/
-#define ADDR_BIT_32 0x0000000100000000LL
-#define ADDR_LOW_HALF 0x00000000ffffffffLL
-#define ADDR_HIGH_HALR 0xffffffff00000000LL
+#define ADDR_BIT_32 0x0000000100000000LL
+#define ADDR_LOW_HALF 0x00000000ffffffffLL
+#define ADDR_HIGH_HALR 0xffffffff00000000LL
-#define ADDR_32_MAX ADDR_LOW_HALF
-#define ADDR_64_FIRST ADDR_BIT_32
+#define ADDR_32_MAX ADDR_LOW_HALF
+#define ADDR_64_FIRST ADDR_BIT_32
/*
** PRIVATE GLOBAL VARIABLES
@@ -196,19 +196,19 @@ static int km_initialized;
** @param[in] base Base physical address of the block
** @param[in] length Block length, in bytes
*/
-static void add_block(uint32_t base, uint32_t length)
-{
+static void add_block( uint32_t base, uint32_t length ) {
+
// don't add it if it isn't at least 4K
- if (length < SZ_PAGE) {
+ if( length < SZ_PAGE ) {
return;
}
#if ANY_KMEM
- cio_printf(" add(%08x,%08x): ", base, length);
+ cio_printf( " add(%08x,%08x): ", base, length );
#endif
// verify that the base address is a 4K boundary
- if ((base & MOD4K_BITS) != 0) {
+ if( (base & MOD4K_BITS) != 0 ) {
// nope - how many bytes will we lose from the beginning
uint_t loss = base & MOD4K_BITS;
// adjust the starting address: (n + 4K - 1) / 4K
@@ -218,7 +218,7 @@ static void add_block(uint32_t base, uint32_t length)
}
// only want to add multiples of 4K; check the lower bits
- if ((length & MOD4K_BITS) != 0) {
+ if( (length & MOD4K_BITS) != 0 ) {
// round it down to 4K
length &= MOD4K_MASK;
}
@@ -235,21 +235,21 @@ static void add_block(uint32_t base, uint32_t length)
int npages = 0;
#if ANY_KMEM
- cio_printf("-> base %08x len %08x: ", base, length);
+ cio_printf( "-> base %08x len %08x: ", base, length );
#endif
// iterate through the block page by page
- while (base < blend) {
- list_add(&free_pages, (void *)base);
+ while( base < blend ) {
+ list_add( &free_pages, (void *) base );
++npages;
- base += SZ_PAGE;
+ base += SZ_PAGE;
}
// add the count to our running total
n_pages += npages;
#if ANY_KMEM
- cio_printf(" -> %d pages\n", npages);
+ cio_printf( " -> %d pages\n", npages );
#endif
}
@@ -263,14 +263,13 @@ static void add_block(uint32_t base, uint32_t length)
** Must be called before any other init routine that uses
** dynamic storage is called.
*/
-void km_init(void)
-{
+void km_init( void ) {
int32_t entries;
region_t *region;
#if TRACING_INIT
// announce that we're starting initialization
- cio_puts(" Kmem");
+ cio_puts( " Kmem" );
#endif
// initially, nothing in the free lists
@@ -280,28 +279,32 @@ void km_init(void)
km_initialized = 0;
// get the list length
- entries = *((int32_t *)MMAP_ADDR);
+ entries = *((int32_t *) MMAP_ADDR);
#if KMEM_OR_INIT
- cio_printf("\nKmem: %d regions\n", entries);
+ cio_printf( "\nKmem: %d regions\n", entries );
#endif
// if there are no entries, we have nothing to do!
- if (entries < 1) { // note: entries == -1 could occur!
+ if( entries < 1 ) { // note: entries == -1 could occur!
return;
}
// iterate through the entries, adding things to the freelist
- region = ((region_t *)(MMAP_ADDR + 4));
+ region = ((region_t *) (MMAP_ADDR + 4));
+
+ for( int i = 0; i < entries; ++i, ++region ) {
- for (int i = 0; i < entries; ++i, ++region) {
#if KMEM_OR_INIT
// report this region
- cio_printf("%3d: ", i);
- cio_printf(" B %08x%08x", region->base.HIGH, region->base.LOW);
- cio_printf(" L %08x%08x", region->length.HIGH, region->length.LOW);
- cio_printf(" T %08x A %08x", region->type, region->acpi);
+ cio_printf( "%3d: ", i );
+ cio_printf( " B %08x%08x",
+ region->base.HIGH, region->base.LOW );
+ cio_printf( " L %08x%08x",
+ region->length.HIGH, region->length.LOW );
+ cio_printf( " T %08x A %08x",
+ region->type, region->acpi );
#endif
/*
@@ -321,27 +324,27 @@ void km_init(void)
// first, check the ACPI one-bit flags
- if (((region->acpi) & REGION_IGNORE) == 0) {
+ if( ((region->acpi) & REGION_IGNORE) == 0 ) {
#if KMEM_OR_INIT
- cio_puts(" IGN\n");
+ cio_puts( " IGN\n" );
#endif
continue;
}
- if (((region->acpi) & REGION_NONVOL) != 0) {
+ if( ((region->acpi) & REGION_NONVOL) != 0 ) {
#if KMEM_OR_INIT
- cio_puts(" NVOL\n");
+ cio_puts( " NVOL\n" );
#endif
- continue; // we'll ignore this, too
+ continue; // we'll ignore this, too
}
// next, the region type
- if ((region->type) != REGION_USABLE) {
+ if( (region->type) != REGION_USABLE ) {
#if KMEM_OR_INIT
- cio_puts(" RCLM\n");
+ cio_puts( " RCLM\n" );
#endif
- continue; // we won't attempt to reclaim ACPI memory (yet)
+ continue; // we won't attempt to reclaim ACPI memory (yet)
}
/*
@@ -361,17 +364,18 @@ void km_init(void)
*/
// grab the two 64-bit values to simplify things
- uint64_t base = region->base.all;
+ uint64_t base = region->base.all;
uint64_t length = region->length.all;
- uint64_t endpt = base + length;
+ uint64_t endpt = base + length;
// ignore it if it's above our high cutoff point
- if (base >= KM_HIGH_CUTOFF || endpt >= KM_HIGH_CUTOFF) {
+ if( base >= KM_HIGH_CUTOFF || endpt >= KM_HIGH_CUTOFF ) {
+
// is the whole thing too high, or just part?
- if (base >= KM_HIGH_CUTOFF) {
+ if( base >= KM_HIGH_CUTOFF ) {
// it's all too high!
#if KMEM_OR_INIT
- cio_puts(" HIGH\n");
+ cio_puts( " HIGH\n" );
#endif
continue;
}
@@ -381,12 +385,13 @@ void km_init(void)
}
// see if it's below our low cutoff point
- if (base < KM_LOW_CUTOFF || endpt < KM_LOW_CUTOFF) {
+ if( base < KM_LOW_CUTOFF || endpt < KM_LOW_CUTOFF ) {
+
// is the whole thing too low, or just part?
- if (endpt < KM_LOW_CUTOFF) {
+ if( endpt < KM_LOW_CUTOFF ) {
// it's all below the cutoff!
#if KMEM_OR_INIT
- cio_puts(" LOW\n");
+ cio_puts( " LOW\n" );
#endif
continue;
}
@@ -405,20 +410,20 @@ void km_init(void)
length = endpt - base;
#if KMEM_OR_INIT
- cio_puts(" OK\n");
+ cio_puts( " OK\n" );
#endif
- uint32_t b32 = base & ADDR_LOW_HALF;
+ uint32_t b32 = base & ADDR_LOW_HALF;
uint32_t l32 = length & ADDR_LOW_HALF;
- add_block(b32, l32);
+ add_block( b32, l32 );
}
// record the initialization
km_initialized = 1;
#if KMEM_OR_INIT
- delay(DELAY_3_SEC);
+ delay( DELAY_3_SEC );
#endif
}
@@ -433,38 +438,39 @@ void km_init(void)
** @param addrs Also dump page addresses
** @param both Also dump slice addresses
*/
-void km_dump(bool_t addrs, bool_t both)
-{
+void km_dump( bool_t addrs, bool_t both ) {
+
// report the sizes
- cio_printf("&free_pages %08x, &free_slices %08x, %u pages, %u slices\n",
- (uint32_t)&free_pages, (uint32_t)&free_slices, n_pages,
- n_slices);
+ cio_printf( "&free_pages %08x, &free_slices %08x, %u pages, %u slices\n",
+ (uint32_t) &free_pages, (uint32_t) &free_slices,
+ n_pages, n_slices );
// was that all?
- if (!addrs) {
+ if( !addrs ) {
return;
}
// dump the addresses of the pages in the free list
uint32_t n = 0;
list_t *block = free_pages.next;
- while (block != NULL) {
- if (n && !(n & MOD4_BITS)) {
+ while( block != NULL ) {
+ if( n && !(n & MOD4_BITS) ) {
// four per line
- cio_putchar('\n');
+ cio_putchar( '\n' );
}
- cio_printf(" page @ 0x%08x", (uint32_t)block);
+ cio_printf( " page @ 0x%08x", (uint32_t) block );
block = block->next;
++n;
}
// sanity check - verify that the counts match
- if (n != n_pages) {
- sprint(b256, "km_dump: n_pages %u, counted %u!!!\n", n_pages, n);
- WARNING(b256);
+ if( n != n_pages ) {
+ sprint( b256, "km_dump: n_pages %u, counted %u!!!\n",
+ n_pages, n );
+ WARNING( b256);
}
- if (!both) {
+ if( !both ) {
return;
}
@@ -473,20 +479,21 @@ void km_dump(bool_t addrs, bool_t both)
// also dump the addresses of slices in the slice free list
n = 0;
block = free_slices.next;
- while (block != NULL) {
- if (n && !(n & MOD4_BITS)) {
+ while( block != NULL ) {
+ if( n && !(n & MOD4_BITS) ) {
// four per line
- cio_putchar('\n');
+ cio_putchar( '\n' );
}
- cio_printf(" slc @ 0x%08x", (uint32_t)block);
+ cio_printf( " slc @ 0x%08x", (uint32_t) block );
block = block->next;
++n;
}
// sanity check - verify that the counts match
- if (n != n_slices) {
- sprint(b256, "km_dump: n_slices %u, counted %u!!!\n", n_slices, n);
- WARNING(b256);
+ if( n != n_slices ) {
+ sprint( b256, "km_dump: n_slices %u, counted %u!!!\n",
+ n_slices, n );
+ WARNING( b256);
}
}
@@ -502,26 +509,26 @@ void km_dump(bool_t addrs, bool_t both)
** @return a pointer to the beginning of the allocated page,
** or NULL if no memory is available
*/
-void *km_page_alloc(void)
-{
+void *km_page_alloc( void ) {
+
// if km_init() wasn't called first, stop us in our tracks
- assert(km_initialized);
+ assert( km_initialized );
#if TRACING_KMEM_FREELIST
- cio_puts("KM: pg_alloc()");
+ cio_puts( "KM: pg_alloc()" );
#endif
// pointer to the first block
- void *page = list_remove(&free_pages);
+ void *page = list_remove( &free_pages );
// was a page available?
- if (page == NULL) {
+ if( page == NULL ){
// nope!
#if TRACING_KMEM_FREELIST
- cio_puts(" FAIL\n");
+ cio_puts( " FAIL\n" );
#endif
#if ALLOC_FAIL_PANIC
- PANIC(0, "page alloc failed");
+ PANIC( 0, "page alloc failed" );
#else
return NULL;
#endif
@@ -531,10 +538,10 @@ void *km_page_alloc(void)
--n_pages;
#if TRACING_KMEM_FREELIST
- cio_printf(" -> %08x\n", (uint32_t)page);
+ cio_printf( " -> %08x\n", (uint32_t) page );
#endif
- return (page);
+ return( page );
}
/**
@@ -544,22 +551,23 @@ void *km_page_alloc(void)
**
** @param[in] page Pointer to the page to be returned to the free list
*/
-void km_page_free(void *page)
-{
+void km_page_free( void *page ){
+
// verify that km_init() was called first
- assert(km_initialized);
+ assert( km_initialized );
#if TRACING_KMEM_FREELIST
- cio_printf("KM: pg_free(%08x)\n", (uint32_t)page);
+ cio_printf( "KM: pg_free(%08x)\n", (uint32_t) page );
#endif
/*
** Don't do anything if the address is NULL.
*/
- if (page == NULL) {
+ if( page == NULL ){
return;
}
+
/*
** CRITICAL ASSUMPTION
**
@@ -581,7 +589,7 @@ void km_page_free(void *page)
*/
// link this into the free list
- list_add(&free_pages, page);
+ list_add( &free_pages, page );
// one more in the pool
++n_pages;
@@ -605,19 +613,19 @@ void km_page_free(void *page)
**
** @param page Pointer to the page to be carved up
*/
-static void carve_slices(void *page)
-{
+static void carve_slices( void *page ) {
+
// sanity check
- assert1(page != NULL);
+ assert1( page != NULL );
#if TRACING_KMEM_FREELIST
- cio_printf("KM: carve_slices(%08x)\n", (uint32_t)page);
+ cio_printf( "KM: carve_slices(%08x)\n", (uint32_t) page );
#endif
// create the four slices from it
- uint8_t *ptr = (uint8_t *)page;
- for (int i = 0; i < 4; ++i) {
- km_slice_free((void *)ptr);
+ uint8_t *ptr = (uint8_t *) page;
+ for( int i = 0; i < 4; ++i ) {
+ km_slice_free( (void *) ptr );
ptr += SZ_SLICE;
++n_slices;
}
@@ -632,38 +640,38 @@ static void carve_slices(void *page)
**
** @return a pointer to the allocated slice
*/
-void *km_slice_alloc(void)
-{
+void *km_slice_alloc( void ) {
+
// verify that km_init() was called first
- assert(km_initialized);
+ assert( km_initialized );
#if TRACING_KMEM_FREELIST
- cio_printf("KM: sl_alloc()\n");
+ cio_printf( "KM: sl_alloc()\n" );
#endif
// if we are out of slices, create a few more
- if (free_slices.next == NULL) {
+ if( free_slices.next == NULL ) {
void *new = km_page_alloc();
- if (new == NULL) {
+ if( new == NULL ) {
// can't get any more space
#if ALLOC_FAIL_PANIC
- PANIC(0, "slice new alloc failed");
+ PANIC( 0, "slice new alloc failed" );
#else
return NULL;
#endif
}
- carve_slices(new);
+ carve_slices( new );
}
// take the first one from the free list
- void *slice = list_remove(&free_slices);
- assert(slice != NULL);
+ void *slice = list_remove( &free_slices );
+ assert( slice != NULL );
--n_slices;
// make it nice and shiny for the caller
- memclr((void *)slice, SZ_SLICE);
+ memclr( (void *) slice, SZ_SLICE );
- return (slice);
+ return( slice );
}
/**
@@ -676,16 +684,16 @@ void *km_slice_alloc(void)
**
** @param[in] block Pointer to the slice (1/4 page) to be freed
*/
-void km_slice_free(void *block)
-{
+void km_slice_free( void *block ) {
+
// verify that km_init() was called first
- assert(km_initialized);
+ assert( km_initialized );
#if TRACING_KMEM_FREELIST
- cio_printf("KM: sl_free(%08x)\n", (uint32_t)block);
+ cio_printf( "KM: sl_free(%08x)\n", (uint32_t) block );
#endif
// just add it to the front of the free list
- list_add(&free_slices, block);
+ list_add( &free_slices, block );
--n_slices;
}
diff --git a/kernel/old/list.c b/kernel/old/list.c
index 5492615..084000a 100644
--- a/kernel/old/list.c
+++ b/kernel/old/list.c
@@ -29,11 +29,11 @@
** @param[in,out] list The address of a list_t variable
** @param[in] data The data to prepend to the list
*/
-void list_add(list_t *list, void *data)
-{
+void list_add( list_t *list, void *data ) {
+
// sanity checks
- assert1(list != NULL);
- assert1(data != NULL);
+ assert1( list != NULL );
+ assert1( data != NULL );
list_t *tmp = (list_t *)data;
tmp->next = list->next;
@@ -49,15 +49,16 @@ void list_add(list_t *list, void *data)
**
** @return a pointer to the removed data, or NULL if the list was empty
*/
-void *list_remove(list_t *list)
-{
- assert1(list != NULL);
+void *list_remove( list_t *list ) {
+
+ assert1( list != NULL );
list_t *data = list->next;
- if (data != NULL) {
+ if( data != NULL ) {
list->next = data->next;
data->next = NULL;
}
return (void *)data;
}
+
diff --git a/kernel/old/procs.c b/kernel/old/procs.c
index 82c4c98..96bb3fd 100644
--- a/kernel/old/procs.c
+++ b/kernel/old/procs.c
@@ -6,7 +6,7 @@
** @brief Process-related implementations
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
@@ -18,7 +18,7 @@
*/
// determine if a queue is empty; assumes 'q' is a valid pointer
-#define PCB_QUEUE_EMPTY(q) ((q)->head == NULL)
+#define PCB_QUEUE_EMPTY(q) ((q)->head == NULL)
/*
** PRIVATE DATA TYPES
@@ -74,29 +74,33 @@ uint_t next_pid;
pcb_t *init_pcb;
// table of state name strings
-const char state_str[N_STATES][4] = {
- [STATE_UNUSED] = "Unu", // "Unused"
- [STATE_NEW] = "New",
- [STATE_READY] = "Rdy", // "Ready"
- [STATE_RUNNING] = "Run", // "Running"
- [STATE_SLEEPING] = "Slp", // "Sleeping"
- [STATE_BLOCKED] = "Blk", // "Blocked"
- [STATE_WAITING] = "Wat", // "Waiting"
- [STATE_KILLED] = "Kil", // "Killed"
- [STATE_ZOMBIE] = "Zom" // "Zombie"
+const char *state_str[N_STATES] = {
+ [ STATE_UNUSED ] = "Unu", // "Unused"
+ [ STATE_NEW ] = "New",
+ [ STATE_READY ] = "Rdy", // "Ready"
+ [ STATE_RUNNING ] = "Run", // "Running"
+ [ STATE_SLEEPING ] = "Slp", // "Sleeping"
+ [ STATE_BLOCKED ] = "Blk", // "Blocked"
+ [ STATE_WAITING ] = "Wat", // "Waiting"
+ [ STATE_KILLED ] = "Kil", // "Killed"
+ [ STATE_ZOMBIE ] = "Zom" // "Zombie"
};
// table of priority name strings
-const char prio_str[N_PRIOS][5] = { [PRIO_HIGH] = "High",
- [PRIO_STD] = "User",
- [PRIO_LOW] = "Low ",
- [PRIO_DEFERRED] = "Def " };
+const char *prio_str[N_PRIOS] = {
+ [ PRIO_HIGH ] = "High",
+ [ PRIO_STD ] = "User",
+ [ PRIO_LOW ] = "Low ",
+ [ PRIO_DEFERRED ] = "Def "
+};
// table of queue ordering name strings
-const char ord_str[N_PRIOS][5] = { [O_FIFO] = "FIFO",
- [O_PRIO] = "PRIO",
- [O_PID] = "PID ",
- [O_WAKEUP] = "WAKE" };
+const char *ord_str[N_PRIOS] = {
+ [ O_FIFO ] = "FIFO",
+ [ O_PRIO ] = "PRIO",
+ [ O_PID ] = "PID ",
+ [ O_WAKEUP ] = "WAKE"
+};
/*
** PRIVATE FUNCTIONS
@@ -121,16 +125,16 @@ const char ord_str[N_PRIOS][5] = { [O_FIFO] = "FIFO",
** @return a pointer to the predecessor in the queue, or NULL if
** this PCB would be at the beginning of the queue.
*/
-static pcb_t *find_prev_wakeup(pcb_queue_t queue, pcb_t *pcb)
-{
+static pcb_t *find_prev_wakeup( pcb_queue_t queue, pcb_t *pcb ) {
+
// sanity checks!
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
pcb_t *prev = NULL;
pcb_t *curr = queue->head;
- while (curr != NULL && curr->wakeup <= pcb->wakeup) {
+ while( curr != NULL && curr->wakeup <= pcb->wakeup ) {
prev = curr;
curr = curr->next;
}
@@ -138,16 +142,16 @@ static pcb_t *find_prev_wakeup(pcb_queue_t queue, pcb_t *pcb)
return prev;
}
-static pcb_t *find_prev_priority(pcb_queue_t queue, pcb_t *pcb)
-{
+static pcb_t *find_prev_priority( pcb_queue_t queue, pcb_t *pcb ) {
+
// sanity checks!
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
pcb_t *prev = NULL;
pcb_t *curr = queue->head;
- while (curr != NULL && curr->priority <= pcb->priority) {
+ while( curr != NULL && curr->priority <= pcb->priority ) {
prev = curr;
curr = curr->next;
}
@@ -155,16 +159,16 @@ static pcb_t *find_prev_priority(pcb_queue_t queue, pcb_t *pcb)
return prev;
}
-static pcb_t *find_prev_pid(pcb_queue_t queue, pcb_t *pcb)
-{
+static pcb_t *find_prev_pid( pcb_queue_t queue, pcb_t *pcb ) {
+
// sanity checks!
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
pcb_t *prev = NULL;
pcb_t *curr = queue->head;
- while (curr != NULL && curr->pid <= pcb->pid) {
+ while( curr != NULL && curr->pid <= pcb->pid ) {
prev = curr;
curr = curr->next;
}
@@ -177,10 +181,10 @@ static pcb_t *find_prev_pid(pcb_queue_t queue, pcb_t *pcb)
*/
// a macro to simplify queue setup
-#define QINIT(q, s) \
- q = &q##_queue; \
- if (pcb_queue_reset(q, s) != SUCCESS) { \
- PANIC(0, "pcb_init can't reset " #q); \
+#define QINIT(q,s) \
+ q = &q##_queue; \
+ if( pcb_queue_reset(q,s) != SUCCESS ) { \
+ PANIC( 0, "pcb_init can't reset " # q ); \
}
/**
@@ -188,22 +192,22 @@ static pcb_t *find_prev_pid(pcb_queue_t queue, pcb_t *pcb)
**
** Initialization for the Process module.
*/
-void pcb_init(void)
-{
+void pcb_init( void ) {
+
#if TRACING_INIT
- cio_puts(" Procs");
+ cio_puts( " Procs" );
#endif
// there is no current process
current = NULL;
// set up the external links to the queues
- QINIT(pcb_freelist, O_FIFO);
- QINIT(ready, O_PRIO);
- QINIT(waiting, O_PID);
- QINIT(sleeping, O_WAKEUP);
- QINIT(zombie, O_PID);
- QINIT(sioread, O_FIFO);
+ QINIT( pcb_freelist, O_FIFO );
+ QINIT( ready, O_PRIO );
+ QINIT( waiting, O_PID );
+ QINIT( sleeping, O_WAKEUP );
+ QINIT( zombie, O_PID );
+ QINIT( sioread, O_FIFO );
/*
** We statically allocate our PCBs, so we need to add them
@@ -214,8 +218,8 @@ void pcb_init(void)
*/
pcb_t *ptr = ptable;
- for (int i = 0; i < N_PROCS; ++i) {
- pcb_free(ptr);
+ for( int i = 0; i < N_PROCS; ++i ) {
+ pcb_free( ptr );
++ptr;
}
}
@@ -229,14 +233,14 @@ void pcb_init(void)
**
** @return status of the allocation attempt
*/
-int pcb_alloc(pcb_t **pcb)
-{
+int pcb_alloc( pcb_t **pcb ) {
+
// sanity check!
- assert1(pcb != NULL);
+ assert1( pcb != NULL );
// remove the first PCB from the free list
pcb_t *tmp;
- if (pcb_queue_remove(pcb_freelist, &tmp) != SUCCESS) {
+ if( pcb_queue_remove(pcb_freelist,&tmp) != SUCCESS ) {
return E_NO_PCBS;
}
@@ -251,19 +255,20 @@ int pcb_alloc(pcb_t **pcb)
**
** @param pcb Pointer to the PCB to be deallocated.
*/
-void pcb_free(pcb_t *pcb)
-{
- if (pcb != NULL) {
+void pcb_free( pcb_t *pcb ) {
+
+ if( pcb != NULL ) {
// mark the PCB as available
pcb->state = STATE_UNUSED;
// add it to the free list
- int status = pcb_queue_insert(pcb_freelist, pcb);
+ int status = pcb_queue_insert( pcb_freelist, pcb );
// if that failed, we're in trouble
- if (status != SUCCESS) {
- sprint(b256, "pcb_free(0x%08x) status %d", (uint32_t)pcb, status);
- PANIC(0, b256);
+ if( status != SUCCESS ) {
+ sprint( b256, "pcb_free(0x%08x) status %d", (uint32_t) pcb,
+ status );
+ PANIC( 0, b256 );
}
}
}
@@ -277,15 +282,15 @@ void pcb_free(pcb_t *pcb)
**
** @param pcb Pointer to the newly-undead PCB
*/
-void pcb_zombify(register pcb_t *victim)
-{
+void pcb_zombify( register pcb_t *victim ) {
+
// should this be an error?
- if (victim == NULL) {
+ if( victim == NULL ) {
return;
}
// every process must have a parent, even if it's 'init'
- assert(victim->parent != NULL);
+ assert( victim->parent != NULL );
/*
** We need to locate the parent of this process. We also need
@@ -301,24 +306,26 @@ void pcb_zombify(register pcb_t *victim)
// speed up access to the process table entries
register pcb_t *curr = ptable;
- for (int i = 0; i < N_PROCS; ++i, ++curr) {
+ for( int i = 0; i < N_PROCS; ++i, ++curr ) {
+
// make sure this is a valid entry
- if (curr->state == STATE_UNUSED) {
+ if( curr->state == STATE_UNUSED ) {
continue;
}
// if this is our parent, just keep going - we continue
// iterating to find all the children of this process.
- if (curr == parent) {
+ if( curr == parent ) {
continue;
}
- if (curr->parent == victim) {
+ if( curr->parent == victim ) {
+
// found a child - reparent it
curr->parent = init_pcb;
// see if this child is already undead
- if (curr->state == STATE_ZOMBIE) {
+ if( curr->state == STATE_ZOMBIE ) {
// if it's already a zombie, remember it, so we
// can pass it on to 'init'; also, if there are
// two or more zombie children, it doesn't matter
@@ -326,6 +333,7 @@ void pcb_zombify(register pcb_t *victim)
// collected when 'init' loops
zchild = curr;
}
+
}
}
@@ -339,25 +347,26 @@ void pcb_zombify(register pcb_t *victim)
**
** Also note: it's possible that the exiting process' parent is
** also init, which means we're letting one of zombie children
- ** of the exiting process be cleaned up by init before the
+ ** of the exiting process be cleaned up by init before the
** existing process itself is cleaned up by init. This will work,
** because after init cleans up the zombie, it will loop and
** call waitpid() again, by which time this exiting process will
** be marked as a zombie.
*/
- if (zchild != NULL && init_pcb->state == STATE_WAITING) {
+ if( zchild != NULL && init_pcb->state == STATE_WAITING ) {
+
// dequeue the zombie
- assert(pcb_queue_remove_this(zombie, zchild) == SUCCESS);
+ assert( pcb_queue_remove_this(zombie,zchild) == SUCCESS );
- assert(pcb_queue_remove_this(waiting, init_pcb) == SUCCESS);
+ assert( pcb_queue_remove_this(waiting,init_pcb) == SUCCESS );
// intrinsic return value is the PID
RET(init_pcb) = zchild->pid;
// may also want to return the exit status
- int32_t *ptr = (int32_t *)ARG(init_pcb, 2);
+ int32_t *ptr = (int32_t *) ARG(init_pcb,2);
- if (ptr != NULL) {
+ if( ptr != NULL ) {
// ********************************************************
// ** Potential VM issue here! This code assigns the exit
// ** status into a variable in the parent's address space.
@@ -370,8 +379,8 @@ void pcb_zombify(register pcb_t *victim)
}
// all done - schedule 'init', and clean up the zombie
- schedule(init_pcb);
- pcb_cleanup(zchild);
+ schedule( init_pcb );
+ pcb_cleanup( zchild );
}
/*
@@ -385,12 +394,14 @@ void pcb_zombify(register pcb_t *victim)
** worry about it being scheduled twice.
*/
- if (parent->state == STATE_WAITING) {
+ if( parent->state == STATE_WAITING ) {
+
// verify that the parent is either waiting for this process
// or is waiting for any of its children
- uint32_t target = ARG(parent, 1);
+ uint32_t target = ARG(parent,1);
+
+ if( target == 0 || target == vicpid ) {
- if (target == 0 || target == vicpid) {
// the parent is waiting for this child or is waiting
// for any of its children, so we can wake it up.
@@ -398,9 +409,9 @@ void pcb_zombify(register pcb_t *victim)
RET(parent) = vicpid;
// may also want to return the exit status
- int32_t *ptr = (int32_t *)ARG(parent, 2);
+ int32_t *ptr = (int32_t *) ARG(parent,2);
- if (ptr != NULL) {
+ if( ptr != NULL ) {
// ********************************************************
// ** Potential VM issue here! This code assigns the exit
// ** status into a variable in the parent's address space.
@@ -413,8 +424,8 @@ void pcb_zombify(register pcb_t *victim)
}
// all done - schedule the parent, and clean up the zombie
- schedule(parent);
- pcb_cleanup(victim);
+ schedule( parent );
+ pcb_cleanup( victim );
return;
}
@@ -432,7 +443,7 @@ void pcb_zombify(register pcb_t *victim)
*/
victim->state = STATE_ZOMBIE;
- assert(pcb_queue_insert(zombie, victim) == SUCCESS);
+ assert( pcb_queue_insert(zombie,victim) == SUCCESS );
/*
** Note: we don't call _dispatch() here - we leave that for
@@ -448,23 +459,23 @@ void pcb_zombify(register pcb_t *victim)
**
** @param pcb The PCB to reclaim
*/
-void pcb_cleanup(pcb_t *pcb)
-{
+void pcb_cleanup( pcb_t *pcb ) {
+
#if TRACING_PCB
- cio_printf("** pcb_cleanup(0x%08x)\n", (uint32_t)pcb);
+ cio_printf( "** pcb_cleanup(0x%08x)\n", (uint32_t) pcb );
#endif
// avoid deallocating a NULL pointer
- if (pcb == NULL) {
+ if( pcb == NULL ) {
// should this be an error?
return;
}
// we need to release all the VM data structures and frames
- user_cleanup(pcb);
+ user_cleanup( pcb );
// release the PCB itself
- pcb_free(pcb);
+ pcb_free( pcb );
}
/**
@@ -476,18 +487,18 @@ void pcb_cleanup(pcb_t *pcb)
**
** @return Pointer to the PCB, or NULL
*/
-pcb_t *pcb_find_pid(uint_t pid)
-{
+pcb_t *pcb_find_pid( uint_t pid ) {
+
// must be a valid PID
- if (pid < 1) {
+ if( pid < 1 ) {
return NULL;
}
// scan the process table
pcb_t *p = ptable;
- for (int i = 0; i < N_PROCS; ++i, ++p) {
- if (p->pid == pid && p->state != STATE_UNUSED) {
+ for( int i = 0; i < N_PROCS; ++i, ++p ) {
+ if( p->pid == pid && p->state != STATE_UNUSED ) {
return p;
}
}
@@ -505,19 +516,19 @@ pcb_t *pcb_find_pid(uint_t pid)
**
** @return Pointer to the PCB, or NULL
*/
-pcb_t *pcb_find_ppid(uint_t pid)
-{
+pcb_t *pcb_find_ppid( uint_t pid ) {
+
// must be a valid PID
- if (pid < 1) {
+ if( pid < 1 ) {
return NULL;
}
// scan the process table
pcb_t *p = ptable;
- for (int i = 0; i < N_PROCS; ++i, ++p) {
- assert1(p->parent != NULL);
- if (p->parent->pid == pid && p->parent->state != STATE_UNUSED) {
+ for( int i = 0; i < N_PROCS; ++i, ++p ) {
+ assert1( p->parent != NULL );
+ if( p->parent->pid == pid && p->parent->state != STATE_UNUSED ) {
return p;
}
}
@@ -537,13 +548,13 @@ pcb_t *pcb_find_ppid(uint_t pid)
**
** @return status of the init request
*/
-int pcb_queue_reset(pcb_queue_t queue, enum pcb_queue_order_e style)
-{
+int pcb_queue_reset( pcb_queue_t queue, enum pcb_queue_order_e style ) {
+
// sanity check
- assert1(queue != NULL);
+ assert1( queue != NULL );
// make sure the style is valid
- if (style < O_FIRST_STYLE || style > O_LAST_STYLE) {
+ if( style < O_FIRST_STYLE || style > O_LAST_STYLE ) {
return E_BAD_PARAM;
}
@@ -564,10 +575,10 @@ int pcb_queue_reset(pcb_queue_t queue, enum pcb_queue_order_e style)
**
** @return true if the queue is empty, else false
*/
-bool_t pcb_queue_empty(pcb_queue_t queue)
-{
+bool_t pcb_queue_empty( pcb_queue_t queue ) {
+
// if there is no queue, blow up
- assert1(queue != NULL);
+ assert1( queue != NULL );
return PCB_QUEUE_EMPTY(queue);
}
@@ -581,16 +592,16 @@ bool_t pcb_queue_empty(pcb_queue_t queue)
**
** @return the count (0 if the queue is empty)
*/
-uint_t pcb_queue_length(const pcb_queue_t queue)
-{
+uint_t pcb_queue_length( const pcb_queue_t queue ) {
+
// sanity check
- assert1(queue != NULL);
+ assert1( queue != NULL );
// this is pretty simple
register pcb_t *tmp = queue->head;
register int num = 0;
-
- while (tmp != NULL) {
+
+ while( tmp != NULL ) {
++num;
tmp = tmp->next;
}
@@ -608,41 +619,41 @@ uint_t pcb_queue_length(const pcb_queue_t queue)
**
** @return status of the insertion request
*/
-int pcb_queue_insert(pcb_queue_t queue, pcb_t *pcb)
-{
+int pcb_queue_insert( pcb_queue_t queue, pcb_t *pcb ) {
+
// sanity checks
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
// if this PCB is already in a queue, we won't touch it
- if (pcb->next != NULL) {
+ if( pcb->next != NULL ) {
// what to do? we let the caller decide
return E_BAD_PARAM;
}
// is the queue empty?
- if (queue->head == NULL) {
+ if( queue->head == NULL ) {
queue->head = queue->tail = pcb;
return SUCCESS;
}
- assert1(queue->tail != NULL);
+ assert1( queue->tail != NULL );
// no, so we need to search it
pcb_t *prev = NULL;
// find the predecessor node
- switch (queue->order) {
+ switch( queue->order ) {
case O_FIFO:
prev = queue->tail;
break;
case O_PRIO:
- prev = find_prev_priority(queue, pcb);
+ prev = find_prev_priority(queue,pcb);
break;
case O_PID:
- prev = find_prev_pid(queue, pcb);
+ prev = find_prev_pid(queue,pcb);
break;
case O_WAKEUP:
- prev = find_prev_wakeup(queue, pcb);
+ prev = find_prev_wakeup(queue,pcb);
break;
default:
// do we need something more specific here?
@@ -651,25 +662,29 @@ int pcb_queue_insert(pcb_queue_t queue, pcb_t *pcb)
// OK, we found the predecessor node; time to do the insertion
- if (prev == NULL) {
+ if( prev == NULL ) {
+
// there is no predecessor, so we're
// inserting at the front of the queue
pcb->next = queue->head;
- if (queue->head == NULL) {
+ if( queue->head == NULL ) {
// empty queue!?! - should we panic?
queue->tail = pcb;
}
queue->head = pcb;
- } else if (prev->next == NULL) {
+ } else if( prev->next == NULL ) {
+
// append at end
prev->next = pcb;
queue->tail = pcb;
} else {
+
// insert between prev & prev->next
pcb->next = prev->next;
prev->next = pcb;
+
}
return SUCCESS;
@@ -685,14 +700,14 @@ int pcb_queue_insert(pcb_queue_t queue, pcb_t *pcb)
**
** @return status of the removal request
*/
-int pcb_queue_remove(pcb_queue_t queue, pcb_t **pcb)
-{
+int pcb_queue_remove( pcb_queue_t queue, pcb_t **pcb ) {
+
//sanity checks
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
// can't get anything if there's nothing to get!
- if (PCB_QUEUE_EMPTY(queue)) {
+ if( PCB_QUEUE_EMPTY(queue) ) {
return E_EMPTY_QUEUE;
}
@@ -704,7 +719,7 @@ int pcb_queue_remove(pcb_queue_t queue, pcb_t **pcb)
tmp->next = NULL;
// was this the last thing in the queue?
- if (queue->head == NULL) {
+ if( queue->head == NULL ) {
// yes, so clear the tail pointer for consistency
queue->tail = NULL;
}
@@ -729,14 +744,14 @@ int pcb_queue_remove(pcb_queue_t queue, pcb_t **pcb)
**
** @return status of the removal request
*/
-int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
-{
+int pcb_queue_remove_this( pcb_queue_t queue, pcb_t *pcb ) {
+
//sanity checks
- assert1(queue != NULL);
- assert1(pcb != NULL);
+ assert1( queue != NULL );
+ assert1( pcb != NULL );
// can't get anything if there's nothing to get!
- if (PCB_QUEUE_EMPTY(queue)) {
+ if( PCB_QUEUE_EMPTY(queue) ) {
return E_EMPTY_QUEUE;
}
@@ -744,7 +759,7 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
pcb_t *prev = NULL;
pcb_t *curr = queue->head;
- while (curr != NULL && curr != pcb) {
+ while( curr != NULL && curr != pcb ) {
prev = curr;
curr = curr->next;
}
@@ -758,15 +773,15 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
// 5. !0 !0 0 removing from end
// 6. !0 !0 !0 removing from middle
- if (curr == NULL) {
+ if( curr == NULL ) {
// case 1
- assert(prev != NULL);
+ assert( prev != NULL );
// case 4
return E_NOT_FOUND;
}
// connect predecessor to successor
- if (prev != NULL) {
+ if( prev != NULL ) {
// not the first element
// cases 5 and 6
prev->next = curr->next;
@@ -778,7 +793,7 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
// if this was the last node (cases 2 and 5),
// also need to reset the tail pointer
- if (curr->next == NULL) {
+ if( curr->next == NULL ) {
// if this was the only entry (2), prev is NULL,
// so this works for that case, too
queue->tail = prev;
@@ -791,8 +806,10 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
// one of the queue pointers is NULL and the other one
// is not NULL
- assert1((queue->head == NULL && queue->tail == NULL) ||
- (queue->head != NULL && queue->tail != NULL));
+ assert1(
+ (queue->head == NULL && queue->tail == NULL) ||
+ (queue->head != NULL && queue->tail != NULL)
+ );
return SUCCESS;
}
@@ -807,13 +824,13 @@ int pcb_queue_remove_this(pcb_queue_t queue, pcb_t *pcb)
**
** @return the PCB poiner, or NULL if the queue is empty
*/
-pcb_t *pcb_queue_peek(const pcb_queue_t queue)
-{
+pcb_t *pcb_queue_peek( const pcb_queue_t queue ) {
+
//sanity check
- assert1(queue != NULL);
+ assert1( queue != NULL );
// can't get anything if there's nothing to get!
- if (PCB_QUEUE_EMPTY(queue)) {
+ if( PCB_QUEUE_EMPTY(queue) ) {
return NULL;
}
@@ -832,13 +849,13 @@ pcb_t *pcb_queue_peek(const pcb_queue_t queue)
**
** @param pcb Pointer to the PCB of the process to be scheduled
*/
-void schedule(pcb_t *pcb)
-{
+void schedule( pcb_t *pcb ) {
+
// sanity check
- assert1(pcb != NULL);
+ assert1( pcb != NULL );
// check for a killed process
- if (pcb->state == STATE_KILLED) {
+ if( pcb->state == STATE_KILLED ) {
// TODO figure out what to do now
return;
}
@@ -847,8 +864,8 @@ void schedule(pcb_t *pcb)
pcb->state = STATE_READY;
// add it to the ready queue
- if (pcb_queue_insert(ready, pcb) != SUCCESS) {
- PANIC(0, "schedule insert fail");
+ if( pcb_queue_insert(ready,pcb) != SUCCESS ) {
+ PANIC( 0, "schedule insert fail" );
}
}
@@ -857,16 +874,16 @@ void schedule(pcb_t *pcb)
**
** Select the next process to receive the CPU
*/
-void dispatch(void)
-{
+void dispatch( void ) {
+
// verify that there is no current process
- assert(current == NULL);
+ assert( current == NULL );
// grab whoever is at the head of the queue
- int status = pcb_queue_remove(ready, &current);
- if (status != SUCCESS) {
- sprint(b256, "dispatch queue remove failed, code %d", status);
- PANIC(0, b256);
+ int status = pcb_queue_remove( ready, &current );
+ if( status != SUCCESS ) {
+ sprint( b256, "dispatch queue remove failed, code %d", status );
+ PANIC( 0, b256 );
}
// set the process up for success
@@ -874,6 +891,7 @@ void dispatch(void)
current->ticks = QUANTUM_STANDARD;
}
+
/*
** Debugging/tracing routines
*/
@@ -886,32 +904,32 @@ void dispatch(void)
** @param msg[in] An optional message to print before the dump
** @param c[in] The context to dump out
*/
-void ctx_dump(const char *msg, register context_t *c)
-{
+void ctx_dump( const char *msg, register context_t *c ) {
+
// first, the message (if there is one)
- if (msg) {
- cio_puts(msg);
+ if( msg ) {
+ cio_puts( msg );
}
// the pointer
- cio_printf(" @ %08x: ", (uint32_t)c);
+ cio_printf( " @ %08x: ", (uint32_t) c );
// if it's NULL, why did you bother calling me?
- if (c == NULL) {
- cio_puts(" NULL???\n");
+ if( c == NULL ) {
+ cio_puts( " NULL???\n" );
return;
}
// now, the contents
- cio_printf("ss %04x gs %04x fs %04x es %04x ds %04x cs %04x\n",
- c->ss & 0xff, c->gs & 0xff, c->fs & 0xff, c->es & 0xff,
- c->ds & 0xff, c->cs & 0xff);
- cio_printf(" edi %08x esi %08x ebp %08x esp %08x\n", c->edi, c->esi,
- c->ebp, c->esp);
- cio_printf(" ebx %08x edx %08x ecx %08x eax %08x\n", c->ebx, c->edx,
- c->ecx, c->eax);
- cio_printf(" vec %08x cod %08x eip %08x eflags %08x\n", c->vector, c->code,
- c->eip, c->eflags);
+ cio_printf( "ss %04x gs %04x fs %04x es %04x ds %04x cs %04x\n",
+ c->ss & 0xff, c->gs & 0xff, c->fs & 0xff,
+ c->es & 0xff, c->ds & 0xff, c->cs & 0xff );
+ cio_printf( " edi %08x esi %08x ebp %08x esp %08x\n",
+ c->edi, c->esi, c->ebp, c->esp );
+ cio_printf( " ebx %08x edx %08x ecx %08x eax %08x\n",
+ c->ebx, c->edx, c->ecx, c->eax );
+ cio_printf( " vec %08x cod %08x eip %08x eflags %08x\n",
+ c->vector, c->code, c->eip, c->eflags );
}
/**
@@ -921,25 +939,25 @@ void ctx_dump(const char *msg, register context_t *c)
**
** @param msg[in] Optional message to print
*/
-void ctx_dump_all(const char *msg)
-{
- if (msg != NULL) {
- cio_puts(msg);
+void ctx_dump_all( const char *msg ) {
+
+ if( msg != NULL ) {
+ cio_puts( msg );
}
int n = 0;
register pcb_t *pcb = ptable;
- for (int i = 0; i < N_PROCS; ++i, ++pcb) {
- if (pcb->state != STATE_UNUSED) {
+ for( int i = 0; i < N_PROCS; ++i, ++pcb ) {
+ if( pcb->state != STATE_UNUSED ) {
++n;
- cio_printf("%2d(%d): ", n, pcb->pid);
- ctx_dump(NULL, pcb->context);
+ cio_printf( "%2d(%d): ", n, pcb->pid );
+ ctx_dump( NULL, pcb->context );
}
}
}
/**
-** pcb_dump(msg,pcb,all)
+** _pcb_dump(msg,pcb)
**
** Dumps the contents of this PCB to the console
**
@@ -947,85 +965,88 @@ void ctx_dump_all(const char *msg)
** @param pcb[in] The PCB to dump
** @param all[in] Dump all the contents?
*/
-void pcb_dump(const char *msg, register pcb_t *pcb, bool_t all)
-{
+void pcb_dump( const char *msg, register pcb_t *pcb, bool_t all ) {
+
// first, the message (if there is one)
- if (msg) {
- cio_puts(msg);
+ if( msg ) {
+ cio_puts( msg );
}
// the pointer
- cio_printf(" @ %08x:", (uint32_t)pcb);
+ cio_printf( " @ %08x:", (uint32_t) pcb );
// if it's NULL, why did you bother calling me?
- if (pcb == NULL) {
- cio_puts(" NULL???\n");
+ if( pcb == NULL ) {
+ cio_puts( " NULL???\n" );
return;
}
- cio_printf(" %d %s", pcb->pid,
- pcb->state >= N_STATES ? "???" : state_str[pcb->state]);
+ cio_printf( " %d", pcb->pid );
+ cio_printf( " %s",
+ pcb->state >= N_STATES ? "???" : state_str[pcb->state] );
- if (!all) {
+ if( !all ) {
// just printing IDs and states on one line
return;
}
// now, the rest of the contents
- cio_printf(" %s",
- pcb->priority >= N_PRIOS ? "???" : prio_str[pcb->priority]);
+ cio_printf( " %s",
+ pcb->priority >= N_PRIOS ? "???" : prio_str[pcb->priority] );
- cio_printf(" ticks %u xit %d wake %08x\n", pcb->ticks, pcb->exit_status,
- pcb->wakeup);
+ cio_printf( " ticks %u xit %d wake %08x\n",
+ pcb->ticks, pcb->exit_status, pcb->wakeup );
- cio_printf(" parent %08x", (uint32_t)pcb->parent);
- if (pcb->parent != NULL) {
- cio_printf(" (%u)", pcb->parent->pid);
+ cio_printf( " parent %08x", (uint32_t)pcb->parent );
+ if( pcb->parent != NULL ) {
+ cio_printf( " (%u)", pcb->parent->pid );
}
- cio_printf(" next %08x context %08x pde %08x", (uint32_t)pcb->next,
- (uint32_t)pcb->context, (uint32_t)pcb->pdir);
+ cio_printf( " next %08x context %08x pde %08x", (uint32_t) pcb->next,
+ (uint32_t) pcb->context, (uint32_t) pcb->pdir );
- cio_putchar('\n');
+ cio_putchar( '\n' );
}
/**
** pcb_queue_dump(msg,queue,contents)
**
+** Dump the contents of the specified queue to the console
+**
** @param msg[in] Optional message to print
** @param queue[in] The queue to dump
** @param contents[in] Also dump (some) contents?
*/
-void pcb_queue_dump(const char *msg, pcb_queue_t queue, bool_t contents)
-{
+void pcb_queue_dump( const char *msg, pcb_queue_t queue, bool_t contents ) {
+
// report on this queue
- cio_printf("%s: ", msg);
- if (queue == NULL) {
- cio_puts("NULL???\n");
+ cio_printf( "%s: ", msg );
+ if( queue == NULL ) {
+ cio_puts( "NULL???\n" );
return;
}
// first, the basic data
- cio_printf("head %08x tail %08x", (uint32_t)queue->head,
- (uint32_t)queue->tail);
+ cio_printf( "head %08x tail %08x",
+ (uint32_t) queue->head, (uint32_t) queue->tail );
// next, how the queue is ordered
- cio_printf(" order %s\n",
- queue->order >= N_ORDERINGS ? "????" : ord_str[queue->order]);
+ cio_printf( " order %s\n",
+ queue->order >= N_ORDERINGS ? "????" : ord_str[queue->order] );
// if there are members in the queue, dump the first few PIDs
- if (contents && queue->head != NULL) {
- cio_puts(" PIDs: ");
+ if( contents && queue->head != NULL ) {
+ cio_puts( " PIDs: " );
pcb_t *tmp = queue->head;
- for (int i = 0; i < 5 && tmp != NULL; ++i, tmp = tmp->next) {
- cio_printf(" [%u]", tmp->pid);
+ for( int i = 0; i < 5 && tmp != NULL; ++i, tmp = tmp->next ) {
+ cio_printf( " [%u]", tmp->pid );
}
- if (tmp != NULL) {
- cio_puts(" ...");
+ if( tmp != NULL ) {
+ cio_puts( " ..." );
}
- cio_putchar('\n');
+ cio_putchar( '\n' );
}
}
@@ -1037,48 +1058,50 @@ void pcb_queue_dump(const char *msg, pcb_queue_t queue, bool_t contents)
** @param msg[in] Optional message to print
** @param all[in] Dump all or only part of the relevant data
*/
-void ptable_dump(const char *msg, bool_t all)
-{
- if (msg) {
- cio_puts(msg);
+void ptable_dump( const char *msg, bool_t all ) {
+
+ if( msg ) {
+ cio_puts( msg );
}
- cio_putchar(' ');
+ cio_putchar( ' ' );
int used = 0;
int empty = 0;
register pcb_t *pcb = ptable;
- for (int i = 0; i < N_PROCS; ++i) {
- if (pcb->state == STATE_UNUSED) {
+ for( int i = 0; i < N_PROCS; ++i ) {
+ if( pcb->state == STATE_UNUSED ) {
+
// an empty slot
++empty;
} else {
+
// a non-empty slot
++used;
// if not dumping everything, add commas if needed
- if (!all && used) {
- cio_putchar(',');
+ if( !all && used ) {
+ cio_putchar( ',' );
}
// report the table slot #
- cio_printf(" #%d:", i);
+ cio_printf( " #%d:", i );
// and dump the contents
- pcb_dump(NULL, pcb, all);
+ pcb_dump( NULL, pcb, all );
}
}
// only need this if we're doing one-line output
- if (!all) {
- cio_putchar('\n');
+ if( !all ) {
+ cio_putchar( '\n' );
}
// sanity check - make sure we saw the correct number of table slots
- if ((used + empty) != N_PROCS) {
- cio_printf("Table size %d, used %d + empty %d = %d???\n", N_PROCS, used,
- empty, used + empty);
+ if( (used + empty) != N_PROCS ) {
+ cio_printf( "Table size %d, used %d + empty %d = %d???\n",
+ N_PROCS, used, empty, used + empty );
}
}
@@ -1088,15 +1111,14 @@ void ptable_dump(const char *msg, bool_t all)
** Prints basic information about the process table (number of
** entries, number with each process state, etc.).
*/
-void ptable_dump_counts(void)
-{
+void ptable_dump_counts( void ) {
uint_t nstate[N_STATES] = { 0 };
uint_t unknown = 0;
int n = 0;
pcb_t *ptr = ptable;
- while (n < N_PROCS) {
- if (ptr->state < 0 || ptr->state >= N_STATES) {
+ while( n < N_PROCS ) {
+ if( ptr->state < 0 || ptr->state >= N_STATES ) {
++unknown;
} else {
++nstate[ptr->state];
@@ -1105,12 +1127,10 @@ void ptable_dump_counts(void)
++ptr;
}
- cio_printf("Ptable: %u ***", unknown);
- for (n = 0; n < N_STATES; ++n) {
- if (nstate[n]) {
- cio_printf(" %u %s", nstate[n],
- state_str[n] != NULL ? state_str[n] : "???");
- }
+ cio_printf( "Ptable: %u ***", unknown );
+ for( n = 0; n < N_STATES; ++n ) {
+ cio_printf( " %u %s", nstate[n],
+ state_str[n] != NULL ? state_str[n] : "???" );
}
- cio_putchar('\n');
+ cio_putchar( '\n' );
}
diff --git a/kernel/old/drivers/serial.c b/kernel/old/sio.c
index d6572e5..a5c7b75 100644
--- a/kernel/old/drivers/serial.c
+++ b/kernel/old/sio.c
@@ -1,3 +1,64 @@
+/**
+** @file sio.c
+**
+** @author Warren R. Carithers
+**
+** @brief SIO module
+**
+** For maximum compatibility from semester to semester, this code uses
+** several "stand-in" type names and macros which should be defined
+** in the accompanying "compat.h" header file if they're not part of
+** the baseline system:
+**
+** standard-sized integer types: intN_t, uintN_t
+** other types: PCBTYPE, QTYPE
+** scheduler functions: SCHED, DISPATCH
+** queue functions: QCREATE, QLENGTH, QDEQUE
+** other functions: SLENGTH
+** sio read queue: QNAME
+**
+** Our SIO scheme is very simple:
+**
+** Input: We maintain a buffer of incoming characters that haven't
+** yet been read by processes. When a character comes in, if
+** there is no process waiting for it, it goes in the buffer;
+** otherwise, the first waiting process is awakeneda and it
+** gets the character.
+**
+** When a process invokes readch(), if there is a character in
+** the input buffer, the process gets it; otherwise, it is
+** blocked until input appears
+**
+** Communication with system calls is via two routines.
+** sio_readc() returns the first available character (if
+** there is one), resetting the input variables if this was
+** the last character in the buffer. If there are no
+** characters in the buffer, sio_read() returns a -1
+** (presumably so the requesting process can be blocked).
+**
+** sio_read() copies the contents of the input buffer into
+** a user-supplied buffer. It returns the number of characters
+** copied. If there are no characters available, return a -1.
+**
+** Output: We maintain a buffer of outgoing characters that haven't
+** yet been sent to the device, and an indication of whether
+** or not we are in the middle of a transmit sequence. When
+** an interrupt comes in, if there is another character to
+** send we copy it to the transmitter buffer; otherwise, we
+** end the transmit sequence.
+**
+** Communication with user processes is via three functions.
+** sio_writec() writes a single character; sio_write()
+** writes a sized buffer full of characters; sio_puts()
+** prints a NUL-terminated string. If we are in the middle
+** of a transmit sequence, all characters will be added
+** to the output buffer (from where they will be sent
+** automatically); otherwise, we send the first character
+** directly, add the rest of the characters (if there are
+** any) to the output buffer, and set the "sending" flag
+** to indicate that we're expecting a transmitter interrupt.
+*/
+
#define KERNEL_SRC
// this should do all includes required for this OS
@@ -15,28 +76,28 @@
** PRIVATE DEFINITIONS
*/
-#define BUF_SIZE 2048
+#define BUF_SIZE 2048
/*
** PRIVATE GLOBALS
*/
-// input character buffer
-static char inbuffer[BUF_SIZE];
+ // input character buffer
+static char inbuffer[ BUF_SIZE ];
static char *inlast;
static char *innext;
static uint32_t incount;
-// output character buffer
-static char outbuffer[BUF_SIZE];
+ // output character buffer
+static char outbuffer[ BUF_SIZE ];
static char *outlast;
static char *outnext;
static uint32_t outcount;
-// output control flag
+ // output control flag
static int sending;
-// interrupt register status
+ // interrupt register status
static uint8_t ier;
/*
@@ -45,7 +106,7 @@ static uint8_t ier;
// queue for read-blocked processes
#ifdef QNAME
-extern QTYPE QNAME;
+QTYPE QNAME;
#endif
/*
@@ -61,40 +122,41 @@ extern QTYPE QNAME;
** @param vector The interrupt vector number for this interrupt
** @param ecode The error code associated with this interrupt
*/
-static void sio_isr(int vector, int ecode)
-{
+static void sio_isr( int vector, int ecode ) {
int ch;
#if TRACING_SIO_ISR
- cio_puts("SIO: int:");
+ cio_puts( "SIO: int:" );
#endif
//
// Must process all pending events; loop until the IRR
// says there's nothing else to do.
//
- for (;;) {
+ for(;;) {
+
// get the "pending event" indicator
- int iir = inb(UA4_IIR) & UA4_IIR_INT_PRI_MASK;
+ int iir = inb( UA4_IIR ) & UA4_IIR_INT_PRI_MASK;
// process this event
- switch (iir) {
+ switch( iir ) {
+
case UA4_IIR_LINE_STATUS:
// shouldn't happen, but just in case....
- cio_printf("** SIO int, LSR = %02x\n", inb(UA4_LSR));
+ cio_printf( "** SIO int, LSR = %02x\n", inb(UA4_LSR) );
break;
case UA4_IIR_RX:
#if TRACING_SIO_ISR
- cio_puts(" RX");
+ cio_puts( " RX" );
#endif
// get the character
- ch = inb(UA4_RXD);
- if (ch == '\r') { // map CR to LF
+ ch = inb( UA4_RXD );
+ if( ch == '\r' ) { // map CR to LF
ch = '\n';
}
#if TRACING_SIO_ISR
- cio_printf(" ch %02x", ch);
+ cio_printf( " ch %02x", ch );
#endif
#ifdef QNAME
@@ -104,18 +166,18 @@ static void sio_isr(int vector, int ecode)
// process and awaken the process.
//
- if (!QEMPTY(QNAME)) {
+ if( !QEMPTY(QNAME) ) {
PCBTYPE *pcb;
- QDEQUE(QNAME, pcb);
+ QDEQUE( QNAME, pcb );
// make sure we got a non-NULL result
- assert(pcb);
+ assert( pcb );
// return char via arg #2 and count in EAX
- char *buf = (char *)ARG(pcb, 2);
+ char *buf = (char *) ARG(pcb,2);
*buf = ch & 0xff;
RET(pcb) = 1;
- SCHED(pcb);
+ SCHED( pcb );
} else {
#endif /* QNAME */
@@ -125,7 +187,7 @@ static void sio_isr(int vector, int ecode)
// if there is room, otherwise just ignore it.
//
- if (incount < BUF_SIZE) {
+ if( incount < BUF_SIZE ) {
*inlast++ = ch;
++incount;
}
@@ -137,64 +199,65 @@ static void sio_isr(int vector, int ecode)
case UA5_IIR_RX_FIFO:
// shouldn't happen, but just in case....
- ch = inb(UA4_RXD);
- cio_printf("** SIO FIFO timeout, RXD = %02x\n", ch);
+ ch = inb( UA4_RXD );
+ cio_printf( "** SIO FIFO timeout, RXD = %02x\n", ch );
break;
case UA4_IIR_TX:
#if TRACING_SIO_ISR
- cio_puts(" TX");
+ cio_puts( " TX" );
#endif
// if there is another character, send it
- if (sending && outcount > 0) {
+ if( sending && outcount > 0 ) {
#if TRACING_SIO_ISR
- cio_printf(" ch %02x", *outnext);
+ cio_printf( " ch %02x", *outnext );
#endif
- outb(UA4_TXD, *outnext);
+ outb( UA4_TXD, *outnext );
++outnext;
// wrap around if necessary
- if (outnext >= (outbuffer + BUF_SIZE)) {
+ if( outnext >= (outbuffer + BUF_SIZE) ) {
outnext = outbuffer;
}
--outcount;
#if TRACING_SIO_ISR
- cio_printf(" (outcount %d)", outcount);
+ cio_printf( " (outcount %d)", outcount );
#endif
} else {
#if TRACING_SIO_ISR
- cio_puts(" EOS");
+ cio_puts( " EOS" );
#endif
// no more data - reset the output vars
outcount = 0;
outlast = outnext = outbuffer;
sending = 0;
// disable TX interrupts
- sio_disable(SIO_TX);
+ sio_disable( SIO_TX );
}
break;
case UA4_IIR_NO_INT:
#if TRACING_SIO_ISR
- cio_puts(" EOI\n");
+ cio_puts( " EOI\n" );
#endif
// nothing to do - tell the PIC we're done
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
return;
case UA4_IIR_MODEM_STATUS:
// shouldn't happen, but just in case....
- cio_printf("** SIO int, MSR = %02x\n", inb(UA4_MSR));
+ cio_printf( "** SIO int, MSR = %02x\n", inb(UA4_MSR) );
break;
default:
// uh-oh....
- sprint(b256, "sio isr: IIR %02x\n", ((uint32_t)iir) & 0xff);
- PANIC(0, b256);
+ sprint( b256, "sio isr: IIR %02x\n", ((uint32_t) iir) & 0xff );
+ PANIC( 0, b256 );
}
+
}
// should never reach this point!
- assert(false);
+ assert( false );
}
/*
@@ -206,27 +269,27 @@ static void sio_isr(int vector, int ecode)
**
** Initialize the UART chip.
*/
-void sio_init(void)
-{
+void sio_init( void ) {
+
#if TRACING_INIT
- cio_puts(" Sio");
+ cio_puts( " Sio" );
#endif
/*
** Initialize SIO variables.
*/
- memclr((void *)inbuffer, sizeof(inbuffer));
+ memclr( (void *) inbuffer, sizeof(inbuffer) );
inlast = innext = inbuffer;
incount = 0;
- memclr((void *)outbuffer, sizeof(outbuffer));
+ memclr( (void *) outbuffer, sizeof(outbuffer) );
outlast = outnext = outbuffer;
outcount = 0;
sending = 0;
// queue of read-blocked processes
- QCREATE(QNAME);
+ QCREATE( QNAME );
/*
** Next, initialize the UART.
@@ -236,11 +299,11 @@ void sio_init(void)
** this is a bizarre little sequence of operations
*/
- outb(UA5_FCR, 0x20);
- outb(UA5_FCR, UA5_FCR_FIFO_RESET); // 0x00
- outb(UA5_FCR, UA5_FCR_FIFO_EN); // 0x01
- outb(UA5_FCR, UA5_FCR_FIFO_EN | UA5_FCR_RXSR); // 0x03
- outb(UA5_FCR, UA5_FCR_FIFO_EN | UA5_FCR_RXSR | UA5_FCR_TXSR); // 0x07
+ outb( UA5_FCR, 0x20 );
+ outb( UA5_FCR, UA5_FCR_FIFO_RESET ); // 0x00
+ outb( UA5_FCR, UA5_FCR_FIFO_EN ); // 0x01
+ outb( UA5_FCR, UA5_FCR_FIFO_EN | UA5_FCR_RXSR ); // 0x03
+ outb( UA5_FCR, UA5_FCR_FIFO_EN | UA5_FCR_RXSR | UA5_FCR_TXSR ); // 0x07
/*
** disable interrupts
@@ -249,36 +312,36 @@ void sio_init(void)
** called to switch them back on
*/
- outb(UA4_IER, 0);
+ outb( UA4_IER, 0 );
ier = 0;
/*
** select the divisor latch registers and set the data rate
*/
- outb(UA4_LCR, UA4_LCR_DLAB);
- outb(UA4_DLL, BAUD_LOW_BYTE(DL_BAUD_9600));
- outb(UA4_DLM, BAUD_HIGH_BYTE(DL_BAUD_9600));
+ outb( UA4_LCR, UA4_LCR_DLAB );
+ outb( UA4_DLL, BAUD_LOW_BYTE( DL_BAUD_9600 ) );
+ outb( UA4_DLM, BAUD_HIGH_BYTE( DL_BAUD_9600 ) );
/*
** deselect the latch registers, by setting the data
** characteristics in the LCR
*/
- outb(UA4_LCR, UA4_LCR_WLS_8 | UA4_LCR_1_STOP_BIT | UA4_LCR_NO_PARITY);
-
+ outb( UA4_LCR, UA4_LCR_WLS_8 | UA4_LCR_1_STOP_BIT | UA4_LCR_NO_PARITY );
+
/*
** Set the ISEN bit to enable the interrupt request signal,
** and the DTR and RTS bits to enable two-way communication.
*/
- outb(UA4_MCR, UA4_MCR_ISEN | UA4_MCR_DTR | UA4_MCR_RTS);
+ outb( UA4_MCR, UA4_MCR_ISEN | UA4_MCR_DTR | UA4_MCR_RTS );
/*
** Install our ISR
*/
- install_isr(VEC_COM1, sio_isr);
+ install_isr( VEC_COM1, sio_isr );
}
/**
@@ -292,8 +355,7 @@ void sio_init(void)
**
** @return the prior IER setting
*/
-uint8_t sio_enable(uint8_t which)
-{
+uint8_t sio_enable( uint8_t which ) {
uint8_t old;
// remember the current status
@@ -302,23 +364,23 @@ uint8_t sio_enable(uint8_t which)
// figure out what to enable
- if (which & SIO_TX) {
+ if( which & SIO_TX ) {
ier |= UA4_IER_TX_IE;
}
- if (which & SIO_RX) {
+ if( which & SIO_RX ) {
ier |= UA4_IER_RX_IE;
}
// if there was a change, make it
- if (old != ier) {
- outb(UA4_IER, ier);
+ if( old != ier ) {
+ outb( UA4_IER, ier );
}
// return the prior settings
- return (old);
+ return( old );
}
/**
@@ -332,8 +394,7 @@ uint8_t sio_enable(uint8_t which)
**
** @return the prior IER setting
*/
-uint8_t sio_disable(uint8_t which)
-{
+uint8_t sio_disable( uint8_t which ) {
uint8_t old;
// remember the current status
@@ -342,23 +403,23 @@ uint8_t sio_disable(uint8_t which)
// figure out what to disable
- if (which & SIO_TX) {
+ if( which & SIO_TX ) {
ier &= ~UA4_IER_TX_IE;
}
- if (which & SIO_RX) {
+ if( which & SIO_RX ) {
ier &= ~UA4_IER_RX_IE;
}
// if there was a change, make it
- if (old != ier) {
- outb(UA4_IER, ier);
+ if( old != ier ) {
+ outb( UA4_IER, ier );
}
// return the prior settings
- return (old);
+ return( old );
}
/**
@@ -370,9 +431,8 @@ uint8_t sio_disable(uint8_t which)
**
** @return the count of characters still in the input queue
*/
-int sio_inq_length(void)
-{
- return (incount);
+int sio_inq_length( void ) {
+ return( incount );
}
/**
@@ -384,29 +444,31 @@ int sio_inq_length(void)
**
** @return the next character, or -1 if no character is available
*/
-int sio_readc(void)
-{
+int sio_readc( void ) {
int ch;
// assume there is no character available
ch = -1;
- //
+ //
// If there is a character, return it
//
- if (incount > 0) {
+ if( incount > 0 ) {
+
// take it out of the input buffer
ch = ((int)(*innext++)) & 0xff;
--incount;
// reset the buffer variables if this was the last one
- if (incount < 1) {
+ if( incount < 1 ) {
inlast = innext = inbuffer;
}
+
}
- return (ch);
+ return( ch );
+
}
/**
@@ -422,15 +484,14 @@ int sio_readc(void)
** @return the number of bytes copied, or 0 if no characters were available
*/
-int sio_read(char *buf, int length)
-{
+int sio_read( char *buf, int length ) {
char *ptr = buf;
int copied = 0;
// if there are no characters, just return 0
- if (incount < 1) {
- return (0);
+ if( incount < 1 ) {
+ return( 0 );
}
//
@@ -438,9 +499,9 @@ int sio_read(char *buf, int length)
// buffer as will fit.
//
- while (incount > 0 && copied < length) {
+ while( incount > 0 && copied < length ) {
*ptr++ = *innext++ & 0xff;
- if (innext > (inbuffer + BUF_SIZE)) {
+ if( innext > (inbuffer + BUF_SIZE) ) {
innext = inbuffer;
}
--incount;
@@ -449,15 +510,16 @@ int sio_read(char *buf, int length)
// reset the input buffer if necessary
- if (incount < 1) {
+ if( incount < 1 ) {
inlast = innext = inbuffer;
}
// return the copy count
- return (copied);
+ return( copied );
}
+
/**
** sio_writec( ch )
**
@@ -467,21 +529,22 @@ int sio_read(char *buf, int length)
**
** @param ch Character to be written (in the low-order 8 bits)
*/
-void sio_writec(int ch)
-{
+void sio_writec( int ch ){
+
+
//
// Must do LF -> CRLF mapping
//
- if (ch == '\n') {
- sio_writec('\r');
+ if( ch == '\n' ) {
+ sio_writec( '\r' );
}
//
// If we're currently transmitting, just add this to the buffer
//
- if (sending) {
+ if( sending ) {
*outlast++ = ch;
++outcount;
return;
@@ -492,11 +555,12 @@ void sio_writec(int ch)
//
sending = 1;
- outb(UA4_TXD, ch);
+ outb( UA4_TXD, ch );
// Also must enable transmitter interrupts
- sio_enable(SIO_TX);
+ sio_enable( SIO_TX );
+
}
/**
@@ -511,8 +575,7 @@ void sio_writec(int ch)
**
** @return the number of characters copied into the SIO output buffer
*/
-int sio_write(const char *buffer, int length)
-{
+int sio_write( const char *buffer, int length ) {
int first = *buffer;
const char *ptr = buffer;
int copied = 0;
@@ -524,15 +587,15 @@ int sio_write(const char *buffer, int length)
// sio_writec() to send the first one out.
//
- if (!sending) {
+ if( !sending ) {
ptr += 1;
copied++;
}
- while (copied < length && outcount < BUF_SIZE) {
+ while( copied < length && outcount < BUF_SIZE ) {
*outlast++ = *ptr++;
// wrap around if necessary
- if (outlast >= (outbuffer + BUF_SIZE)) {
+ if( outlast >= (outbuffer + BUF_SIZE) ) {
outlast = outbuffer;
}
++outcount;
@@ -545,13 +608,15 @@ int sio_write(const char *buffer, int length)
// variables for us.
//
- if (!sending) {
- sio_writec(first);
+ if( !sending ) {
+ sio_writec( first );
}
// Return the transfer count
- return (copied);
+
+ return( copied );
+
}
/**
@@ -565,14 +630,13 @@ int sio_write(const char *buffer, int length)
**
** @return the count of bytes transferred
*/
-int sio_puts(const char *buffer)
-{
- int n; // must be outside the loop so we can return it
+int sio_puts( const char *buffer ) {
+ int n; // must be outside the loop so we can return it
- n = SLENGTH(buffer);
- sio_write(buffer, n);
+ n = SLENGTH( buffer );
+ sio_write( buffer, n );
- return (n);
+ return( n );
}
/**
@@ -587,43 +651,44 @@ int sio_puts(const char *buffer)
** of the queues)
*/
-void sio_dump(bool_t full)
-{
+void sio_dump( bool_t full ) {
int n;
char *ptr;
// dump basic info into the status region
- cio_printf_at(48, 0, "SIO: IER %02x (%c%c%c) in %d ot %d",
- ((uint32_t)ier) & 0xff, sending ? '*' : '.',
- (ier & UA4_IER_TX_IE) ? 'T' : 't',
- (ier & UA4_IER_RX_IE) ? 'R' : 'r', incount, outcount);
+ cio_printf_at( 48, 0,
+ "SIO: IER %02x (%c%c%c) in %d ot %d",
+ ((uint32_t)ier) & 0xff, sending ? '*' : '.',
+ (ier & UA4_IER_TX_IE) ? 'T' : 't',
+ (ier & UA4_IER_RX_IE) ? 'R' : 'r',
+ incount, outcount );
// if we're not doing a full dump, stop now
- if (!full) {
+ if( !full ) {
return;
}
// also want the queue contents, but we'll
// dump them into the scrolling region
- if (incount) {
- cio_puts("SIO input queue: \"");
- ptr = innext;
- for (n = 0; n < incount; ++n) {
- put_char_or_code(*ptr++);
+ if( incount ) {
+ cio_puts( "SIO input queue: \"" );
+ ptr = innext;
+ for( n = 0; n < incount; ++n ) {
+ put_char_or_code( *ptr++ );
}
- cio_puts("\"\n");
+ cio_puts( "\"\n" );
}
- if (outcount) {
- cio_puts("SIO output queue: \"");
- cio_puts(" ot: \"");
- ptr = outnext;
- for (n = 0; n < outcount; ++n) {
- put_char_or_code(*ptr++);
+ if( outcount ) {
+ cio_puts( "SIO output queue: \"" );
+ cio_puts( " ot: \"" );
+ ptr = outnext;
+ for( n = 0; n < outcount; ++n ) {
+ put_char_or_code( *ptr++ );
}
- cio_puts("\"\n");
+ cio_puts( "\"\n" );
}
}
diff --git a/kernel/old/startup.S b/kernel/old/startup.S
new file mode 100644
index 0000000..73a081e
--- /dev/null
+++ b/kernel/old/startup.S
@@ -0,0 +1,153 @@
+/*
+** @file startup.S
+**
+** @author Jon Coles
+** @authors Warren R. Carithers, K. Reek
+**
+** SP startup code.
+**
+** This code prepares the various registers for execution of
+** the program. It sets up all the segment registers and the
+** runtime stack. By the time this code is running, we're in
+** protected mode already.
+*/
+
+#define KERNEL_SRC
+#define ASM_SRC
+
+# .arch i386
+
+#include <common.h>
+#include <bootstrap.h>
+#include <x86/arch.h>
+#include <x86/bios.h>
+#include <vm.h>
+
+/*
+** Configuration options - define in Makefile
+**
+** CLEAR_BSS include code to clear all BSS space
+** OS_CONFIG OS-related (vs. just standalone) variations
+*/
+
+/*
+** A symbol for locating the beginning of the code.
+*/
+ .globl begtext
+
+ .text
+begtext:
+
+/*
+** The entry point. When we get here, we have just entered protected
+** mode, so all the segment registers are incorrect except for CS.
+*/
+ .globl _start
+
+_start:
+ cli /* seems to be reset on entry to p. mode */
+ movb $NMI_ENABLE, %al /* re-enable NMIs (bootstrap */
+ outb $CMOS_ADDR /* turned them off) */
+
+/*
+** Set the data and stack segment registers (code segment register
+** was set by the long jump that switched us into protected mode).
+*/
+ xorl %eax, %eax /* clear EAX */
+ movw $GDT_DATA, %ax /* GDT entry #3 - data segment */
+ movw %ax, %ds /* for all four data segment registers */
+ movw %ax, %es
+ movw %ax, %fs
+ movw %ax, %gs
+
+ movw $GDT_STACK, %ax /* entry #4 is the stack segment */
+ movw %ax, %ss
+
+ movl $TARGET_STACK, %esp /* set up the system stack pointer */
+
+#ifdef CLEAR_BSS
+/*
+** Zero the BSS segment
+**
+** These symbols are defined automatically by the linker, but they're
+** defined at their virtual addresses rather than their physical addresses,
+** and we haven't enabled paging yet.
+*/
+ .globl __bss_start, _end
+
+ movl $V2PNC(__bss_start), %edi
+clearbss:
+ movl $0, (%edi)
+ addl $4, %edi
+ cmpl $V2PNC(_end), %edi
+ jb clearbss
+#endif /* CLEAR_BSS */
+
+/*
+** Enable paging. We use "large" pages for the initial page directory
+** so that a one-level hierarchy will work for us. Once we have set
+** up our memory freelist, we'll create a two-level hierarchy using
+** "normal" 4KB pages.
+*/
+ # enable large pages
+ movl %cr4, %eax
+ orl $(CR4_PSE), %eax
+ movl %eax, %cr4
+
+ # set the page directory
+ .globl firstpdir
+ movl $(V2PNC(firstpdir)), %eax
+ movl %eax, %cr3
+
+ # turn on paging
+ movl %cr0, %eax
+ orl $(CR0_PG), %eax
+ movl %eax, %cr0
+
+ # reset our stack pointer
+ movl $(kstack + SZ_KSTACK), %esp
+
+ # set the initial frame pointer
+ xorl %ebp, %ebp
+
+/*
+** Call the system initialization routine, and switch to
+** executing at high addresses. We use an indirect jump
+** here to avoid getting a PC-relative 'jmp' instruction.
+**
+** Alternate idea: push the address of isr_restore
+** and just do an indirect jump?
+*/
+ .globl main
+
+ movl $main, %eax
+ call *%eax
+
+/*
+** At this point, main() must have created the first user
+** process, and we're ready to shift into user mode. The user
+** stack for that process must have the initial context in it;
+** we treat this as a "return from interrupt" event, and just
+** transfer to the code that restores the user context.
+*/
+
+ .globl isr_restore
+ jmp isr_restore
+
+ .data
+
+/*
+** Define the kernel stack here, at a multiple-of-16 address
+*/
+ .p2align 4
+ .globl kstack
+kstack: .space SZ_KSTACK, 0
+
+/*
+** Define the initial kernel ESP here, as well. It should point
+** to the first byte after the stack.
+*/
+
+ .globl kernel_esp
+kernel_esp:
+ .long kstack + SZ_KSTACK
diff --git a/kernel/old/support.c b/kernel/old/support.c
index 89834ee..d48ce59 100644
--- a/kernel/old/support.c
+++ b/kernel/old/support.c
@@ -29,16 +29,16 @@
** each interrupt. These functions are called from the isr stub based
** on the interrupt number.
*/
-void (*isr_table[256])(int vector, int code);
+void ( *isr_table[ 256 ] )( int vector, int code );
/*
** Format of an IDT entry.
*/
-typedef struct {
- short offset_15_0;
- short segment_selector;
- short flags;
- short offset_31_16;
+typedef struct {
+ short offset_15_0;
+ short segment_selector;
+ short flags;
+ short offset_31_16;
} IDT_Gate;
/*
@@ -59,12 +59,11 @@ typedef struct {
#ifdef RPT_INT_UNEXP
/* add any header includes you need here */
#endif
-static void unexpected_handler(int vector, int code)
-{
+static void unexpected_handler( int vector, int code ) {
#ifdef RPT_INT_UNEXP
- cio_printf("\n** UNEXPECTED vector %d code %d\n", vector, code);
+ cio_printf( "\n** UNEXPECTED vector %d code %d\n", vector, code );
#endif
- panic("Unexpected interrupt");
+ panic( "Unexpected interrupt" );
}
/**
@@ -76,24 +75,23 @@ static void unexpected_handler(int vector, int code)
** @param vector vector number for the interrupt that occurred
** @param code error code, or a dummy value
*/
-static void default_handler(int vector, int code)
-{
+static void default_handler( int vector, int code ) {
#ifdef RPT_INT_UNEXP
- cio_printf("\n** vector %d code %d\n", vector, code);
+ cio_printf( "\n** vector %d code %d\n", vector, code );
#endif
- if (vector >= 0x20 && vector < 0x30) {
- if (vector > 0x27) {
+ if( vector >= 0x20 && vector < 0x30 ) {
+ if( vector > 0x27 ) {
// must also ACK the secondary PIC
- outb(PIC2_CMD, PIC_EOI);
+ outb( PIC2_CMD, PIC_EOI );
}
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
} else {
/*
** All the "expected" interrupts will be handled by the
** code above. If we get down here, the isr table may
** have been corrupted. Print a message and don't return.
*/
- panic("Unexpected \"expected\" interrupt!");
+ panic( "Unexpected \"expected\" interrupt!" );
}
}
@@ -108,12 +106,12 @@ static void default_handler(int vector, int code)
** @param vector vector number for the interrupt that occurred
** @param code error code, or a dummy value
*/
-static void mystery_handler(int vector, int code)
-{
+static void mystery_handler( int vector, int code ) {
#if defined(RPT_INT_MYSTERY) || defined(RPT_INT_UNEXP)
- cio_printf("\nMystery interrupt!\nVector=0x%02x, code=%d\n", vector, code);
+ cio_printf( "\nMystery interrupt!\nVector=0x%02x, code=%d\n",
+ vector, code );
#endif
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
}
/**
@@ -121,38 +119,37 @@ static void mystery_handler(int vector, int code)
**
** Initialize the 8259 Programmable Interrupt Controller.
*/
-static void init_pic(void)
-{
+static void init_pic( void ) {
/*
** ICW1: start the init sequence, update ICW4
*/
- outb(PIC1_CMD, PIC_CW1_INIT | PIC_CW1_NEED4);
- outb(PIC2_CMD, PIC_CW1_INIT | PIC_CW1_NEED4);
+ outb( PIC1_CMD, PIC_CW1_INIT | PIC_CW1_NEED4 );
+ outb( PIC2_CMD, PIC_CW1_INIT | PIC_CW1_NEED4 );
/*
** ICW2: primary offset of 0x20 in the IDT, secondary offset of 0x28
*/
- outb(PIC1_DATA, PIC1_CW2_VECBASE);
- outb(PIC2_DATA, PIC2_CW2_VECBASE);
+ outb( PIC1_DATA, PIC1_CW2_VECBASE );
+ outb( PIC2_DATA, PIC2_CW2_VECBASE );
/*
** ICW3: secondary attached to line 2 of primary, bit mask is 00000100
** secondary id is 2
*/
- outb(PIC1_DATA, PIC1_CW3_SEC_IRQ2);
- outb(PIC2_DATA, PIC2_CW3_SEC_ID);
+ outb( PIC1_DATA, PIC1_CW3_SEC_IRQ2 );
+ outb( PIC2_DATA, PIC2_CW3_SEC_ID );
/*
** ICW4: want 8086 mode, not 8080/8085 mode
*/
- outb(PIC1_DATA, PIC_CW4_PM86);
- outb(PIC2_DATA, PIC_CW4_PM86);
+ outb( PIC1_DATA, PIC_CW4_PM86 );
+ outb( PIC2_DATA, PIC_CW4_PM86 );
/*
** OCW1: allow interrupts on all lines
*/
- outb(PIC1_DATA, PIC_MASK_NONE);
- outb(PIC2_DATA, PIC_MASK_NONE);
+ outb( PIC1_DATA, PIC_MASK_NONE );
+ outb( PIC2_DATA, PIC_MASK_NONE );
}
/**
@@ -166,8 +163,7 @@ static void init_pic(void)
** Note: generally, the handler invoked from the IDT will be a "stub"
** that calls the second-level C handler via the isr_table array.
*/
-static void set_idt_entry(int entry, void (*handler)(void))
-{
+static void set_idt_entry( int entry, void ( *handler )( void ) ) {
IDT_Gate *g = (IDT_Gate *)IDT_ADDR + entry;
g->offset_15_0 = (int)handler & 0xffff;
@@ -185,18 +181,17 @@ static void set_idt_entry(int entry, void (*handler)(void))
** are then installed for those interrupts we may get before a real
** handler is set up.
*/
-static void init_idt(void)
-{
+static void init_idt( void ) {
int i;
- extern void (*isr_stub_table[256])(void);
+ extern void ( *isr_stub_table[ 256 ] )( void );
/*
** Make each IDT entry point to the stub for that vector. Also
** make each entry in the ISR table point to the default handler.
*/
- for (i = 0; i < 256; i++) {
- set_idt_entry(i, isr_stub_table[i]);
- install_isr(i, unexpected_handler);
+ for ( i=0; i < 256; i++ ) {
+ set_idt_entry( i, isr_stub_table[ i ] );
+ install_isr( i, unexpected_handler );
}
/*
@@ -205,13 +200,13 @@ static void init_idt(void)
** will eventually install the "real" handler.
*/
- install_isr(VEC_KBD, default_handler); // cio_init()
- install_isr(VEC_COM1, default_handler); // sio_init()
- install_isr(VEC_TIMER, default_handler); // clk_init()
- install_isr(VEC_SYSCALL, default_handler); // sys_init()
- install_isr(VEC_PAGE_FAULT, default_handler); // vm_init()
+ install_isr( VEC_KBD, default_handler ); // cio_init()
+ install_isr( VEC_COM1, default_handler ); // sio_init()
+ install_isr( VEC_TIMER, default_handler ); // clk_init()
+ install_isr( VEC_SYSCALL, default_handler ); // sys_init()
+ install_isr( VEC_PAGE_FAULT, default_handler ); // vm_init()
- install_isr(VEC_MYSTERY, mystery_handler);
+ install_isr( VEC_MYSTERY, mystery_handler );
}
/*
@@ -226,11 +221,10 @@ static void init_idt(void)
**
** Called when we find an unrecoverable error.
*/
-void panic(char *reason)
-{
- __asm__("cli");
- cio_printf("\nPANIC: %s\nHalting...", reason);
- for (;;) {
+void panic( char *reason ) {
+ __asm__( "cli" );
+ cio_printf( "\nPANIC: %s\nHalting...", reason );
+ for(;;) {
;
}
}
@@ -240,8 +234,7 @@ void panic(char *reason)
**
** (Re)initilizes the interrupt system.
*/
-void init_interrupts(void)
-{
+void init_interrupts( void ) {
init_idt();
init_pic();
}
@@ -251,12 +244,13 @@ void init_interrupts(void)
**
** Installs a second-level handler for a specific interrupt.
*/
-void (*install_isr(int vector, void (*handler)(int, int)))(int, int)
-{
- void (*old_handler)(int vector, int code);
+void (*install_isr( int vector,
+ void (*handler)(int,int) ) ) ( int, int ) {
- old_handler = isr_table[vector];
- isr_table[vector] = handler;
+ void ( *old_handler )( int vector, int code );
+
+ old_handler = isr_table[ vector ];
+ isr_table[ vector ] = handler;
return old_handler;
}
@@ -276,10 +270,10 @@ void (*install_isr(int vector, void (*handler)(int, int)))(int, int)
**
** Ultimately, just remember that DELAY VALUES ARE APPROXIMATE AT BEST.
*/
-void delay(int length)
-{
- while (--length >= 0) {
- for (int i = 0; i < 10000000; ++i)
+void delay( int length ) {
+
+ while( --length >= 0 ) {
+ for( int i = 0; i < 10000000; ++i )
;
}
}
diff --git a/kernel/old/syscalls.c b/kernel/old/syscalls.c
index 92a0a23..7176cda 100644
--- a/kernel/old/syscalls.c
+++ b/kernel/old/syscalls.c
@@ -6,7 +6,7 @@
** @brief System call implementations
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
@@ -33,30 +33,28 @@
#if TRACING_SYSCALLS
-#define SYSCALL_ENTER(x) \
- do { \
- cio_printf("--> %s, pid %08x", __func__, (uint32_t)(x)); \
- } while (0)
+#define SYSCALL_ENTER(x) do { \
+ cio_printf( "--> %s, pid %08x", __func__, (uint32_t) (x) ); \
+ } while(0)
#else
-#define SYSCALL_ENTER(x) /* */
+#define SYSCALL_ENTER(x) /* */
-#endif /* TRACING_SYSCALLS */
+#endif /* TRACING_SYSCALLS */
#if TRACING_SYSRETS
-#define SYSCALL_EXIT(x) \
- do { \
- cio_printf("<-- %s %08x\n", __func__, (uint32_t)(x)); \
- return; \
- } while (0)
+#define SYSCALL_EXIT(x) do { \
+ cio_printf( "<-- %s %08x\n", __func__, (uint32_t) (x) ); \
+ return; \
+ } while(0)
#else
#define SYSCALL_EXIT(x) return
-#endif /* TRACING_SYSRETS */
+#endif /* TRACING_SYSRETS */
/*
** PRIVATE DATA TYPES
@@ -73,7 +71,7 @@
// a macro to simplify syscall entry point specification
// we don't declare these static because we may want to call
// some of them from other parts of the kernel
-#define SYSIMPL(x) void sys_##x(pcb_t *pcb)
+#define SYSIMPL(x) void sys_##x( pcb_t * pcb )
/*
** Second-level syscall handlers
@@ -97,26 +95,26 @@
**
** Does not return
*/
-SYSIMPL(exit)
-{
+SYSIMPL(exit) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// retrieve the exit status of this process
- pcb->exit_status = (int32_t)ARG(pcb, 1);
+ pcb->exit_status = (int32_t) ARG(pcb,1);
// now, we need to do the following:
// reparent any children of this process and wake up init if need be
// find this process' parent and wake it up if it's waiting
-
- pcb_zombify(pcb);
+
+ pcb_zombify( pcb );
// pick a new winner
dispatch();
- SYSCALL_EXIT(0);
+ SYSCALL_EXIT( 0 );
}
/**
@@ -130,12 +128,12 @@ SYSIMPL(exit)
** terminated, or an error code; on success, returns the child's termination
** status via 'status' if that pointer is non-NULL.
*/
-SYSIMPL(waitpid)
-{
+SYSIMPL(waitpid) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
/*
** We need to do two things here: (1) find out whether or
@@ -153,42 +151,47 @@ SYSIMPL(waitpid)
*/
// verify that we aren't looking for ourselves!
- uint_t target = ARG(pcb, 1);
+ uint_t target = ARG(pcb,1);
- if (target == pcb->pid) {
+ if( target == pcb->pid ) {
RET(pcb) = E_BAD_PARAM;
- SYSCALL_EXIT(E_BAD_PARAM);
+ SYSCALL_EXIT( E_BAD_PARAM );
}
// Good. Now, figure out what we're looking for.
pcb_t *child = NULL;
- if (target != 0) {
+ if( target != 0 ) {
+
// we're looking for a specific child
- child = pcb_find_pid(target);
+ child = pcb_find_pid( target );
+
+ if( child != NULL ) {
- if (child != NULL) {
// found the process; is it one of our children:
- if (child->parent != pcb) {
+ if( child->parent != pcb ) {
// NO, so we can't wait for it
RET(pcb) = E_BAD_PARAM;
- SYSCALL_EXIT(E_BAD_PARAM);
+ SYSCALL_EXIT( E_BAD_PARAM );
}
// yes! is this one ready to be collected?
- if (child->state != STATE_ZOMBIE) {
+ if( child->state != STATE_ZOMBIE ) {
// no, so we'll have to block for now
child = NULL;
}
} else {
+
// no such child
RET(pcb) = E_BAD_PARAM;
- SYSCALL_EXIT(E_BAD_PARAM);
+ SYSCALL_EXIT( E_BAD_PARAM );
+
}
} else {
+
// looking for any child
// we need to find a process that is our child
@@ -201,13 +204,15 @@ SYSIMPL(waitpid)
// so we need to do the iteration ourselves
register pcb_t *curr = ptable;
- for (int i = 0; i < N_PROCS; ++i, ++curr) {
- if (curr->parent == pcb) {
+ for( int i = 0; i < N_PROCS; ++i, ++curr ) {
+
+ if( curr->parent == pcb ) {
+
// found one!
found = true;
// has it already exited?
- if (curr->state == STATE_ZOMBIE) {
+ if( curr->state == STATE_ZOMBIE ) {
// yes, so we're done here
child = curr;
break;
@@ -215,11 +220,12 @@ SYSIMPL(waitpid)
}
}
- if (!found) {
+ if( !found ) {
// got through the loop without finding a child!
RET(pcb) = E_NO_CHILDREN;
- SYSCALL_EXIT(E_NO_CHILDREN);
+ SYSCALL_EXIT( E_NO_CHILDREN );
}
+
}
/*
@@ -235,24 +241,25 @@ SYSIMPL(waitpid)
*/
// did we find one to collect?
- if (child == NULL) {
+ if( child == NULL ) {
+
// no - mark the parent as "Waiting"
pcb->state = STATE_WAITING;
- assert(pcb_queue_insert(waiting, pcb) == SUCCESS);
+ assert( pcb_queue_insert(waiting,pcb) == SUCCESS );
// select a new current process
dispatch();
- SYSCALL_EXIT((uint32_t)current);
+ SYSCALL_EXIT( (uint32_t) current );
}
// found a Zombie; collect its information and clean it up
RET(pcb) = child->pid;
// get "status" pointer from parent
- int32_t *stat = (int32_t *)ARG(pcb, 2);
+ int32_t *stat = (int32_t *) ARG(pcb,2);
// if stat is NULL, the parent doesn't want the status
- if (stat != NULL) {
+ if( stat != NULL ) {
// ********************************************************
// ** Potential VM issue here! This code assigns the exit
// ** status into a variable in the parent's address space.
@@ -265,9 +272,9 @@ SYSIMPL(waitpid)
}
// clean up the child
- pcb_cleanup(child);
+ pcb_cleanup( child );
- SYSCALL_EXIT(RET(pcb));
+ SYSCALL_EXIT( RET(pcb) );
}
/**
@@ -280,26 +287,26 @@ SYSIMPL(waitpid)
** Returns the child's PID to the parent, and 0 to the child, on success;
** else, returns an error code to the parent.
*/
-SYSIMPL(fork)
-{
+SYSIMPL(fork) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// Make sure there's room for another process!
pcb_t *new;
- if (pcb_alloc(&new) != SUCCESS || new == NULL) {
+ if( pcb_alloc(&new) != SUCCESS || new == NULL ) {
RET(pcb) = E_NO_PROCS;
- SYSCALL_EXIT(RET(pcb));
+ SYSCALL_EXIT( RET(pcb) );
}
// duplicate the memory image of the parent
- int status = user_duplicate(new, pcb);
- if (status != SUCCESS) {
- pcb_free(new);
+ int status = user_duplicate( new, pcb );
+ if( status != SUCCESS ) {
+ pcb_free( new );
RET(pcb) = status;
- SYSCALL_EXIT(status);
+ SYSCALL_EXIT( status );
}
// Set the child's identity.
@@ -315,9 +322,9 @@ SYSIMPL(fork)
RET(new) = 0;
// Schedule the child, and let the parent continue.
- schedule(new);
+ schedule( new );
- SYSCALL_EXIT(new->pid);
+ SYSCALL_EXIT( new->pid );
}
/**
@@ -334,30 +341,30 @@ SYSIMPL(fork)
SYSIMPL(exec)
{
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- uint_t what = ARG(pcb, 1);
- const char **args = (const char **)ARG(pcb, 2);
+ uint_t what = ARG(pcb,1);
+ const char **args = (const char **) ARG(pcb,2);
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// locate the requested program
- prog_t *prog = user_locate(what);
- if (prog == NULL) {
+ prog_t *prog = user_locate( what );
+ if( prog == NULL ) {
RET(pcb) = E_NOT_FOUND;
- SYSCALL_EXIT(E_NOT_FOUND);
+ SYSCALL_EXIT( E_NOT_FOUND );
}
// we have located the program, but before we can load it,
// we need to clean up the existing VM hierarchy
- vm_free(pcb->pdir);
+ vm_free( pcb->pdir );
pcb->pdir = NULL;
// "load" it and set up the VM tables for this process
- int status = user_load(prog, pcb, args, false);
- if (status != SUCCESS) {
+ int status = user_load( prog, pcb, args );
+ if( status != SUCCESS ) {
RET(pcb) = status;
- SYSCALL_EXIT(status);
+ SYSCALL_EXIT( status );
}
/*
@@ -373,7 +380,7 @@ SYSIMPL(exec)
** an error status to it.
*/
- schedule(pcb);
+ schedule( pcb );
dispatch();
}
@@ -387,49 +394,52 @@ SYSIMPL(exec)
** Reads up to 'length' bytes from 'chan' into 'buffer'. Returns the
** count of bytes actually transferred.
*/
-SYSIMPL(read)
-{
- // sanity check
- assert(pcb != NULL);
+SYSIMPL(read) {
- SYSCALL_ENTER(pcb->pid);
+ // sanity check
+ assert( pcb != NULL );
+ SYSCALL_ENTER( pcb->pid );
+
// grab the arguments
- uint_t chan = ARG(pcb, 1);
- char *buf = (char *)ARG(pcb, 2);
- uint_t len = ARG(pcb, 3);
+ uint_t chan = ARG(pcb,1);
+ char *buf = (char *) ARG(pcb,2);
+ uint_t len = ARG(pcb,3);
// if the buffer is of length 0, we're done!
- if (len == 0) {
+ if( len == 0 ) {
RET(pcb) = 0;
- SYSCALL_EXIT(0);
+ SYSCALL_EXIT( 0 );
}
// try to get the next character(s)
int n = 0;
- if (chan == CHAN_CIO) {
+ if( chan == CHAN_CIO ) {
+
// console input is non-blocking
- if (cio_input_queue() < 1) {
+ if( cio_input_queue() < 1 ) {
RET(pcb) = 0;
- SYSCALL_EXIT(0);
+ SYSCALL_EXIT( 0 );
}
// at least one character
- n = cio_gets(buf, len);
+ n = cio_gets( buf, len );
RET(pcb) = n;
- SYSCALL_EXIT(n);
+ SYSCALL_EXIT( n );
+
+ } else if( chan == CHAN_SIO ) {
- } else if (chan == CHAN_SIO) {
// SIO input is blocking, so if there are no characters
// available, we'll block this process
- n = sio_read(buf, len);
+ n = sio_read( buf, len );
RET(pcb) = n;
- SYSCALL_EXIT(n);
+ SYSCALL_EXIT( n );
+
}
// bad channel code
RET(pcb) = E_BAD_PARAM;
- SYSCALL_EXIT(E_BAD_PARAM);
+ SYSCALL_EXIT( E_BAD_PARAM );
}
/**
@@ -441,17 +451,17 @@ SYSIMPL(read)
** Writes 'length' bytes from 'buffer' to 'chan'. Returns the
** count of bytes actually transferred.
*/
-SYSIMPL(write)
-{
+SYSIMPL(write) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// grab the parameters
- uint_t chan = ARG(pcb, 1);
- char *buf = (char *)ARG(pcb, 2);
- uint_t length = ARG(pcb, 3);
+ uint_t chan = ARG(pcb,1);
+ char *buf = (char *) ARG(pcb,2);
+ uint_t length = ARG(pcb,3);
// this is almost insanely simple, but it does separate the
// low-level device access fromm the higher-level syscall implementation
@@ -460,21 +470,27 @@ SYSIMPL(write)
int rval = length;
// simplest case
- if (length >= 0) {
- if (chan == CHAN_CIO) {
- cio_write(buf, length);
+ if( length >= 0 ) {
+
+ if( chan == CHAN_CIO ) {
+
+ cio_write( buf, length );
- } else if (chan == CHAN_SIO) {
- sio_write(buf, length);
+ } else if( chan == CHAN_SIO ) {
+
+ sio_write( buf, length );
} else {
+
rval = E_BAD_CHAN;
+
}
+
}
RET(pcb) = rval;
- SYSCALL_EXIT(rval);
+ SYSCALL_EXIT( rval );
}
/**
@@ -483,12 +499,12 @@ SYSIMPL(write)
** Implements:
** uint_t getpid( void );
*/
-SYSIMPL(getpid)
-{
+SYSIMPL(getpid) {
+
// sanity check!
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// return the time
RET(pcb) = pcb->pid;
@@ -500,13 +516,13 @@ SYSIMPL(getpid)
** Implements:
** uint_t getppid( void );
*/
-SYSIMPL(getppid)
-{
+SYSIMPL(getppid) {
+
// sanity check!
- assert(pcb != NULL);
- assert(pcb->parent != NULL);
+ assert( pcb != NULL );
+ assert( pcb->parent != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// return the time
RET(pcb) = pcb->parent->pid;
@@ -518,12 +534,12 @@ SYSIMPL(getppid)
** Implements:
** uint32_t gettime( void );
*/
-SYSIMPL(gettime)
-{
+SYSIMPL(gettime) {
+
// sanity check!
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// return the time
RET(pcb) = system_time;
@@ -535,12 +551,12 @@ SYSIMPL(gettime)
** Implements:
** int getprio( void );
*/
-SYSIMPL(getprio)
-{
+SYSIMPL(getprio) {
+
// sanity check!
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// return the time
RET(pcb) = pcb->priority;
@@ -552,18 +568,18 @@ SYSIMPL(getprio)
** Implements:
** int setprio( int new );
*/
-SYSIMPL(setprio)
-{
+SYSIMPL(setprio) {
+
// sanity check!
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// remember the old priority
int old = pcb->priority;
// set the priority
- pcb->priority = ARG(pcb, 1);
+ pcb->priority = ARG(pcb,1);
// return the old value
RET(pcb) = old;
@@ -578,55 +594,56 @@ SYSIMPL(setprio)
** Marks the specified process (or the calling process, if PID is 0)
** as "killed". Returns 0 on success, else an error code.
*/
-SYSIMPL(kill)
-{
+SYSIMPL(kill) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// who is the victim?
- uint_t pid = ARG(pcb, 1);
+ uint_t pid = ARG(pcb,1);
// if it's this process, convert this into a call to exit()
- if (pid == pcb->pid) {
+ if( pid == pcb->pid ) {
pcb->exit_status = EXIT_KILLED;
- pcb_zombify(pcb);
+ pcb_zombify( pcb );
dispatch();
- SYSCALL_EXIT(EXIT_KILLED);
+ SYSCALL_EXIT( EXIT_KILLED );
}
// must be a valid "ordinary user" PID
// QUESTION: what if it's the idle process?
- if (pid < FIRST_USER_PID) {
+ if( pid < FIRST_USER_PID ) {
RET(pcb) = E_FAILURE;
- SYSCALL_EXIT(E_FAILURE);
+ SYSCALL_EXIT( E_FAILURE );
}
// OK, this is an acceptable victim; see if it exists
- pcb_t *victim = pcb_find_pid(pid);
- if (victim == NULL) {
+ pcb_t *victim = pcb_find_pid( pid );
+ if( victim == NULL ) {
// nope!
RET(pcb) = E_NOT_FOUND;
- SYSCALL_EXIT(E_NOT_FOUND);
+ SYSCALL_EXIT( E_NOT_FOUND );
}
// must have a state that is possible
- assert(victim->state >= FIRST_VIABLE && victim->state < N_STATES);
+ assert( victim->state >= FIRST_VIABLE && victim->state < N_STATES );
// how we perform the kill depends on the victim's state
int32_t status = SUCCESS;
- switch (victim->state) {
- case STATE_KILLED: // FALL THROUGH
+ switch( victim->state ) {
+
+ case STATE_KILLED: // FALL THROUGH
case STATE_ZOMBIE:
// you can't kill it if it's already dead
RET(pcb) = SUCCESS;
break;
- case STATE_READY: // FALL THROUGH
- case STATE_SLEEPING: // FALL THROUGH
- case STATE_BLOCKED: // FALL THROUGH
+ case STATE_READY: // FALL THROUGH
+ case STATE_SLEEPING: // FALL THROUGH
+ case STATE_BLOCKED: // FALL THROUGH
// here, the process is on a queue somewhere; mark
// it as "killed", and let the scheduler deal with it
victim->state = STATE_KILLED;
@@ -636,7 +653,7 @@ SYSIMPL(kill)
case STATE_RUNNING:
// we have met the enemy, and it is us!
pcb->exit_status = EXIT_KILLED;
- pcb_zombify(pcb);
+ pcb_zombify( pcb );
status = EXIT_KILLED;
// we need a new current process
dispatch();
@@ -646,8 +663,8 @@ SYSIMPL(kill)
// similar to the 'running' state, but we don't need
// to dispatch a new process
victim->exit_status = EXIT_KILLED;
- status = pcb_queue_remove_this(waiting, victim);
- pcb_zombify(victim);
+ status = pcb_queue_remove_this( waiting, victim );
+ pcb_zombify( victim );
RET(pcb) = status;
break;
@@ -655,14 +672,15 @@ SYSIMPL(kill)
// this is a really bad potential problem - we have an
// unexpected or bogus process state, but we didn't
// catch that earlier.
- sprint(b256, "*** kill(): victim %d, odd state %d\n", victim->pid,
- victim->state);
- PANIC(0, b256);
+ sprint( b256, "*** kill(): victim %d, odd state %d\n",
+ victim->pid, victim->state );
+ PANIC( 0, b256 );
}
- SYSCALL_EXIT(status);
+ SYSCALL_EXIT( status );
}
+
/**
** sys_sleep - put the calling process to sleep for some length of time
**
@@ -672,33 +690,35 @@ SYSIMPL(kill)
** Puts the calling process to sleep for 'ms' milliseconds (or just yields
** the CPU if 'ms' is 0). ** Returns the time the process spent sleeping.
*/
-SYSIMPL(sleep)
-{
+SYSIMPL(sleep) {
+
// sanity check
- assert(pcb != NULL);
+ assert( pcb != NULL );
- SYSCALL_ENTER(pcb->pid);
+ SYSCALL_ENTER( pcb->pid );
// get the desired duration
- uint_t length = ARG(pcb, 1);
+ uint_t length = ARG( pcb, 1 );
+
+ if( length == 0 ) {
- if (length == 0) {
// just yield the CPU
// sleep duration is 0
RET(pcb) = 0;
// back on the ready queue
- schedule(pcb);
+ schedule( pcb );
} else {
+
// sleep for a while
pcb->wakeup = system_time + length;
- if (pcb_queue_insert(sleeping, pcb) != SUCCESS) {
+ if( pcb_queue_insert(sleeping,pcb) != SUCCESS ) {
// something strange is happening
- WARNING("sleep pcb insert failed");
+ WARNING( "sleep pcb insert failed" );
// if this is the current process, report an error
- if (current == pcb) {
+ if( current == pcb ) {
RET(pcb) = -1;
}
// return without dispatching a new process
@@ -707,7 +727,7 @@ SYSIMPL(sleep)
}
// only dispatch if the current process called us
- if (pcb == current) {
+ if( pcb == current ) {
current = NULL;
dispatch();
}
@@ -726,14 +746,20 @@ SYSIMPL(sleep)
** position in the initialization list is irrelevant.
*/
-static void (*const syscalls[N_SYSCALLS])(pcb_t *) = {
- [SYS_exit] = sys_exit, [SYS_waitpid] = sys_waitpid,
- [SYS_fork] = sys_fork, [SYS_exec] = sys_exec,
- [SYS_read] = sys_read, [SYS_write] = sys_write,
- [SYS_getpid] = sys_getpid, [SYS_getppid] = sys_getppid,
- [SYS_gettime] = sys_gettime, [SYS_getprio] = sys_getprio,
- [SYS_setprio] = sys_setprio, [SYS_kill] = sys_kill,
- [SYS_sleep] = sys_sleep
+static void (* const syscalls[N_SYSCALLS])( pcb_t * ) = {
+ [ SYS_exit ] = sys_exit,
+ [ SYS_waitpid ] = sys_waitpid,
+ [ SYS_fork ] = sys_fork,
+ [ SYS_exec ] = sys_exec,
+ [ SYS_read ] = sys_read,
+ [ SYS_write ] = sys_write,
+ [ SYS_getpid ] = sys_getpid,
+ [ SYS_getppid ] = sys_getppid,
+ [ SYS_gettime ] = sys_gettime,
+ [ SYS_getprio ] = sys_getprio,
+ [ SYS_setprio ] = sys_setprio,
+ [ SYS_kill ] = sys_kill,
+ [ SYS_sleep ] = sys_sleep
};
/**
@@ -744,40 +770,40 @@ static void (*const syscalls[N_SYSCALLS])(pcb_t *) = {
** @param vector Vector number for this interrupt
** @param code Error code (0 for this interrupt)
*/
-static void sys_isr(int vector, int code)
-{
+static void sys_isr( int vector, int code ) {
+
// keep the compiler happy
- (void)vector;
- (void)code;
+ (void) vector;
+ (void) code;
// sanity check!
- assert(current != NULL);
- assert(current->context != NULL);
+ assert( current != NULL );
+ assert( current->context != NULL );
// retrieve the syscall code
- int num = REG(current, eax);
+ int num = REG( current, eax );
#if TRACING_SYSCALLS
- cio_printf("** --> SYS pid %u code %u\n", current->pid, num);
+ cio_printf( "** --> SYS pid %u code %u\n", current->pid, num );
#endif
// validate it
- if (num < 0 || num >= N_SYSCALLS) {
+ if( num < 0 || num >= N_SYSCALLS ) {
// bad syscall number
// could kill it, but we'll just force it to exit
num = SYS_exit;
- ARG(current, 1) = EXIT_BAD_SYSCALL;
+ ARG(current,1) = EXIT_BAD_SYSCALL;
}
// call the handler
- syscalls[num](current);
+ syscalls[num]( current );
#if TRACING_SYSCALLS
- cio_printf("** <-- SYS pid %u ret %u\n", current->pid, RET(current));
+ cio_printf( "** <-- SYS pid %u ret %u\n", current->pid, RET(current) );
#endif
// tell the PIC we're done
- outb(PIC1_CMD, PIC_EOI);
+ outb( PIC1_CMD, PIC_EOI );
}
/*
@@ -792,12 +818,12 @@ static void sys_isr(int vector, int code)
** Dependencies:
** Must be called after cio_init()
*/
-void sys_init(void)
-{
+void sys_init( void ) {
+
#if TRACING_INIT
- cio_puts(" Sys");
+ cio_puts( " Sys" );
#endif
// install the second-stage ISR
- install_isr(VEC_SYSCALL, sys_isr);
+ install_isr( VEC_SYSCALL, sys_isr );
}
diff --git a/kernel/old/user.c b/kernel/old/user.c
index 5759534..c41867e 100644
--- a/kernel/old/user.c
+++ b/kernel/old/user.c
@@ -6,7 +6,7 @@
** @brief User-level code manipulation routines
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
@@ -35,16 +35,16 @@
** Location of the "user blob" in memory.
**
** These variables are filled in by the code in startup.S using values
-** passed to it from the bootstrap.
+** passed to it from the bootstrap.
**
** These are visible so that the startup code can find them.
*/
-uint16_t user_offset; // byte offset from the segment base
-uint16_t user_segment; // segment base address
-uint16_t user_sectors; // number of 512-byte sectors it occupies
+uint16_t user_offset; // byte offset from the segment base
+uint16_t user_segment; // segment base address
+uint16_t user_sectors; // number of 512-byte sectors it occupies
-header_t *user_header; // filled in by the user_init routine
-prog_t *prog_table; // filled in by the user_init routine
+header_t *user_header; // filled in by the user_init routine
+prog_t *prog_table; // filled in by the user_init routine
/*
** PRIVATE FUNCTIONS
@@ -65,117 +65,78 @@ static char ebuf[16];
*/
// interpret the file class
-static const char *fh_eclass(e32_si class)
-{
- switch (class) {
- case ELF_CLASS_NONE:
- return ("None");
- break;
- case ELF_CLASS_32:
- return ("EC32");
- break;
- case ELF_CLASS_64:
- return ("EC64");
- break;
+static const char *fh_eclass( e32_si class ) {
+ switch( class ) {
+ case ELF_CLASS_NONE: return( "None" ); break;
+ case ELF_CLASS_32: return( "EC32" ); break;
+ case ELF_CLASS_64: return( "EC64" ); break;
}
- return ("????");
+ return( "????" );
}
// interpret the data encoding
-static const char *fh_edata(e32_si data)
-{
- switch (data) {
- case ELF_DATA_NONE:
- return ("Invd");
- break;
- case ELF_DATA_2LSB:
- return ("2CLE");
- break;
- case ELF_DATA_2MSB:
- return ("2CBE");
- break;
+static const char *fh_edata( e32_si data ) {
+ switch( data ) {
+ case ELF_DATA_NONE: return( "Invd" ); break;
+ case ELF_DATA_2LSB: return( "2CLE" ); break;
+ case ELF_DATA_2MSB: return( "2CBE" ); break;
}
- return ("????");
+ return( "????" );
}
// interpret the file type
-static const char *fh_htype(e32_h type)
-{
- switch (type) {
- case ET_NONE:
- return ("none");
- break;
- case ET_REL:
- return ("rel");
- break;
- case ET_EXEC:
- return ("exec");
- break;
- case ET_DYN:
- return ("dyn");
- break;
- case ET_CORE:
- return ("core");
- break;
+static const char *fh_htype( e32_h type ) {
+ switch( type ) {
+ case ET_NONE: return( "none" ); break;
+ case ET_REL: return( "rel" ); break;
+ case ET_EXEC: return( "exec" ); break;
+ case ET_DYN: return( "dyn" ); break;
+ case ET_CORE: return( "core" ); break;
default:
- if (type >= ET_LO_OS && type <= ET_HI_OS)
- return ("OSsp");
- else if (type >= ET_LO_CP && type <= ET_HI_CP)
- return ("CPsp");
+ if( type >= ET_LO_OS && type <= ET_HI_OS )
+ return( "OSsp" );
+ else if( type >= ET_LO_CP && type <= ET_HI_CP )
+ return( "CPsp" );
}
- sprint(ebuf, "0x%04x", type);
- return ((const char *)ebuf);
+ sprint( ebuf, "0x%04x", type );
+ return( (const char *) ebuf );
}
// interpret the machine type
-static const char *fh_mtype(e32_h machine)
-{
- switch (machine) {
- case EM_NONE:
- return ("None");
- break;
- case EM_386:
- return ("386");
- break;
- case EM_ARM:
- return ("ARM");
- break;
- case EM_X86_64:
- return ("AMD64");
- break;
- case EM_AARCH64:
- return ("AARCH64");
- break;
- case EM_RISCV:
- return ("RISC-V");
- break;
+static const char *fh_mtype( e32_h machine ) {
+ switch( machine ) {
+ case EM_NONE: return( "None" ); break;
+ case EM_386: return( "386" ); break;
+ case EM_ARM: return( "ARM" ); break;
+ case EM_X86_64: return( "AMD64" ); break;
+ case EM_AARCH64: return( "AARCH64" ); break;
+ case EM_RISCV: return( "RISC-V" ); break;
}
- return ("Other");
+ return( "Other" );
}
// dump the program header
-static void dump_fhdr(elfhdr_t *hdr)
-{
- cio_puts("File header: magic ");
- for (int i = EI_MAG0; i <= EI_MAG3; ++i)
- put_char_or_code(hdr->e_ident.bytes[i]);
- cio_printf(" class %s", fh_eclass(hdr->e_ident.f.class));
- cio_printf(" enc %s", fh_edata(hdr->e_ident.f.data));
- cio_printf(" ver %u\n", hdr->e_ident.f.version);
- cio_printf(" type %s", fh_htype(hdr->e_type));
- cio_printf(" mach %s", fh_mtype(hdr->e_machine));
- cio_printf(" vers %d", hdr->e_version);
- cio_printf(" entr %08x\n", hdr->e_entry);
+static void dump_fhdr( elfhdr_t *hdr ) {
+ cio_puts( "File header: magic " );
+ for( int i = EI_MAG0; i <= EI_MAG3; ++i )
+ put_char_or_code( hdr->e_ident.bytes[i] );
+ cio_printf( " class %s", fh_eclass(hdr->e_ident.f.class) );
+ cio_printf( " enc %s", fh_edata(hdr->e_ident.f.data) );
+ cio_printf( " ver %u\n", hdr->e_ident.f.version );
+ cio_printf( " type %s", fh_htype(hdr->e_type) );
+ cio_printf( " mach %s", fh_mtype(hdr->e_machine) );
+ cio_printf( " vers %d", hdr->e_version );
+ cio_printf( " entr %08x\n", hdr->e_entry );
- cio_printf(" phoff %08x", hdr->e_phoff);
- cio_printf(" shoff %08x", hdr->e_shoff);
- cio_printf(" flags %08x", (uint32_t)hdr->e_flags);
- cio_printf(" ehsize %u\n", hdr->e_ehsize);
- cio_printf(" phentsize %u", hdr->e_phentsize);
- cio_printf(" phnum %u", hdr->e_phnum);
- cio_printf(" shentsize %u", hdr->e_shentsize);
- cio_printf(" shnum %u", hdr->e_shnum);
- cio_printf(" shstrndx %u\n", hdr->e_shstrndx);
+ cio_printf( " phoff %08x", hdr->e_phoff );
+ cio_printf( " shoff %08x", hdr->e_shoff );
+ cio_printf( " flags %08x", (uint32_t) hdr->e_flags );
+ cio_printf( " ehsize %u\n", hdr->e_ehsize );
+ cio_printf( " phentsize %u", hdr->e_phentsize );
+ cio_printf( " phnum %u", hdr->e_phnum );
+ cio_printf( " shentsize %u", hdr->e_shentsize );
+ cio_printf( " shnum %u", hdr->e_shnum );
+ cio_printf( " shstrndx %u\n", hdr->e_shstrndx );
}
/*
@@ -183,67 +144,45 @@ static void dump_fhdr(elfhdr_t *hdr)
*/
// categorize the header type
-static const char *ph_type(e32_w type)
-{
- switch (type) {
- case PT_NULL:
- return ("Unused");
- break;
- case PT_LOAD:
- return ("Load");
- break;
- case PT_DYNAMIC:
- return ("DLI");
- break;
- case PT_INTERP:
- return ("Interp");
- break;
- case PT_NOTE:
- return ("Aux");
- break;
- case PT_SHLIB:
- return ("RSVD");
- break;
- case PT_PHDR:
- return ("PTentry");
- break;
- case PT_TLS:
- return ("TLS");
- break;
+static const char *ph_type( e32_w type ) {
+ switch( type ) {
+ case PT_NULL: return( "Unused" ); break;
+ case PT_LOAD: return( "Load" ); break;
+ case PT_DYNAMIC: return( "DLI" ); break;
+ case PT_INTERP: return( "Interp" ); break;
+ case PT_NOTE: return( "Aux" ); break;
+ case PT_SHLIB: return( "RSVD" ); break;
+ case PT_PHDR: return( "PTentry" ); break;
+ case PT_TLS: return( "TLS" ); break;
default:
- if (type >= PT_LO_OS && type <= PT_HI_OS)
- return ("OSsp");
- else if (type >= PT_LO_CP && type <= PT_HI_CP)
- return ("CPsp");
+ if( type >= PT_LO_OS && type <= PT_HI_OS )
+ return( "OSsp" );
+ else if( type >= PT_LO_CP && type <= PT_HI_CP )
+ return( "CPsp" );
}
- sprint(ebuf, "0x%08x", type);
- return ((const char *)ebuf);
+ sprint( ebuf, "0x%08x", type );
+ return( (const char *) ebuf );
}
// report the individual flags
-static void ph_flags(e32_w flags)
-{
- if ((flags & PF_R) != 0)
- cio_putchar('R');
- if ((flags & PF_W) != 0)
- cio_putchar('W');
- if ((flags & PF_E) != 0)
- cio_putchar('X');
+static void ph_flags( e32_w flags ) {
+ if( (flags & PF_R) != 0 ) cio_putchar( 'R' );
+ if( (flags & PF_W) != 0 ) cio_putchar( 'W' );
+ if( (flags & PF_E) != 0 ) cio_putchar( 'X' );
}
// dump a program header
-static void dump_phdr(elfproghdr_t *hdr, int n)
-{
- cio_printf("Prog header %d, type %s\n", n, ph_type(hdr->p_type));
- cio_printf(" offset %08x", hdr->p_offset);
- cio_printf(" va %08x", hdr->p_va);
- cio_printf(" pa %08x\n", hdr->p_pa);
- cio_printf(" filesz %08x", hdr->p_filesz);
- cio_printf(" memsz %08x", hdr->p_memsz);
- cio_puts(" flags ");
- ph_flags(hdr->p_flags);
- cio_printf(" align %08x", hdr->p_align);
- cio_putchar('\n');
+static void dump_phdr( elfproghdr_t *hdr, int n ) {
+ cio_printf( "Prog header %d, type %s\n", n, ph_type(hdr->p_type) );
+ cio_printf( " offset %08x", hdr->p_offset );
+ cio_printf( " va %08x", hdr->p_va );
+ cio_printf( " pa %08x\n", hdr->p_pa );
+ cio_printf( " filesz %08x", hdr->p_filesz );
+ cio_printf( " memsz %08x", hdr->p_memsz );
+ cio_puts( " flags " );
+ ph_flags( hdr->p_flags );
+ cio_printf( " align %08x", hdr->p_align );
+ cio_putchar( '\n' );
}
/*
@@ -251,95 +190,58 @@ static void dump_phdr(elfproghdr_t *hdr, int n)
*/
// interpret the header type
-static const char *sh_type(e32_w type)
-{
- switch (type) {
- case SHT_NULL:
- return ("Unused");
- break;
- case SHT_PROGBITS:
- return ("Progbits");
- break;
- case SHT_SYMTAB:
- return ("Symtab");
- break;
- case SHT_STRTAB:
- return ("Strtab");
- break;
- case SHT_RELA:
- return ("Rela");
- break;
- case SHT_HASH:
- return ("Hash");
- break;
- case SHT_DYNAMIC:
- return ("Dynamic");
- break;
- case SHT_NOTE:
- return ("Note");
- break;
- case SHT_NOBITS:
- return ("Nobits");
- break;
- case SHT_REL:
- return ("Rel");
- break;
- case SHT_SHLIB:
- return ("Shlib");
- break;
- case SHT_DYNSYM:
- return ("Dynsym");
- break;
+static const char *sh_type( e32_w type ) {
+ switch( type ) {
+ case SHT_NULL: return( "Unused" ); break;
+ case SHT_PROGBITS: return( "Progbits" ); break;
+ case SHT_SYMTAB: return( "Symtab" ); break;
+ case SHT_STRTAB: return( "Strtab" ); break;
+ case SHT_RELA: return( "Rela" ); break;
+ case SHT_HASH: return( "Hash" ); break;
+ case SHT_DYNAMIC: return( "Dynamic" ); break;
+ case SHT_NOTE: return( "Note" ); break;
+ case SHT_NOBITS: return( "Nobits" ); break;
+ case SHT_REL: return( "Rel" ); break;
+ case SHT_SHLIB: return( "Shlib" ); break;
+ case SHT_DYNSYM: return( "Dynsym" ); break;
default:
- if (type >= SHT_LO_CP && type <= SHT_HI_CP)
- return ("CCsp");
- else if (type >= SHT_LO_US && type <= SHT_HI_US)
- return ("User");
+ if( type >= SHT_LO_CP && type <= SHT_HI_CP )
+ return( "CCsp" );
+ else if( type >= SHT_LO_US && type <= SHT_HI_US )
+ return( "User" );
}
- sprint(ebuf, "0x%08x", type);
- return ((const char *)ebuf);
+ sprint( ebuf, "0x%08x", type );
+ return( (const char *) ebuf );
}
// report the various flags
-static void sh_flags(unsigned int flags)
-{
- if ((flags & SHF_WRITE) != 0)
- cio_putchar('W');
- if ((flags & SHF_ALLOC) != 0)
- cio_putchar('A');
- if ((flags & SHF_EXECINSTR) != 0)
- cio_putchar('X');
- if ((flags & SHF_MERGE) != 0)
- cio_putchar('M');
- if ((flags & SHF_STRINGS) != 0)
- cio_putchar('S');
- if ((flags & SHF_INFO_LINK) != 0)
- cio_putchar('L');
- if ((flags & SHF_LINK_ORDER) != 0)
- cio_putchar('o');
- if ((flags & SHF_OS_NONCON) != 0)
- cio_putchar('n');
- if ((flags & SHF_GROUP) != 0)
- cio_putchar('g');
- if ((flags & SHF_TLS) != 0)
- cio_putchar('t');
+static void sh_flags( unsigned int flags ) {
+ if( (flags & SHF_WRITE) != 0 ) cio_putchar( 'W' );
+ if( (flags & SHF_ALLOC) != 0 ) cio_putchar( 'A' );
+ if( (flags & SHF_EXECINSTR) != 0 ) cio_putchar( 'X' );
+ if( (flags & SHF_MERGE) != 0 ) cio_putchar( 'M' );
+ if( (flags & SHF_STRINGS) != 0 ) cio_putchar( 'S' );
+ if( (flags & SHF_INFO_LINK) != 0 ) cio_putchar( 'L' );
+ if( (flags & SHF_LINK_ORDER) != 0 ) cio_putchar( 'o' );
+ if( (flags & SHF_OS_NONCON) != 0 ) cio_putchar( 'n' );
+ if( (flags & SHF_GROUP) != 0 ) cio_putchar( 'g' );
+ if( (flags & SHF_TLS) != 0 ) cio_putchar( 't' );
}
// dump a section header
ATTR_UNUSED
-static void dump_shdr(elfsecthdr_t *hdr, int n)
-{
- cio_printf("Sect header %d, type %d (%s), name %s\n", n, hdr->sh_type,
- sh_type(hdr->sh_type));
- cio_printf(" flags %08x ", (uint32_t)hdr->sh_flags);
- sh_flags(hdr->sh_flags);
- cio_printf(" addr %08x", hdr->sh_addr);
- cio_printf(" offset %08x", hdr->sh_offset);
- cio_printf(" size %08x\n", hdr->sh_size);
- cio_printf(" link %08x", hdr->sh_link);
- cio_printf(" info %08x", hdr->sh_info);
- cio_printf(" align %08x", hdr->sh_addralign);
- cio_printf(" entsz %08x\n", hdr->sh_entsize);
+static void dump_shdr( elfsecthdr_t *hdr, int n ) {
+ cio_printf( "Sect header %d, type %d (%s), name %s\n",
+ n, hdr->sh_type, sh_type(hdr->sh_type) );
+ cio_printf( " flags %08x ", (uint32_t) hdr->sh_flags );
+ sh_flags( hdr->sh_flags );
+ cio_printf( " addr %08x", hdr->sh_addr );
+ cio_printf( " offset %08x", hdr->sh_offset );
+ cio_printf( " size %08x\n", hdr->sh_size );
+ cio_printf( " link %08x", hdr->sh_link );
+ cio_printf( " info %08x", hdr->sh_info );
+ cio_printf( " align %08x", hdr->sh_addralign );
+ cio_printf( " entsz %08x\n", hdr->sh_entsize );
}
#endif
@@ -356,51 +258,51 @@ static void dump_shdr(elfsecthdr_t *hdr, int n)
** E_LOAD_LIMIT more than N_LOADABLE PT_LOAD sections
** other status returned from vm_add()
*/
-static int read_phdrs(elfhdr_t *hdr, pcb_t *pcb)
-{
+static int read_phdrs( elfhdr_t *hdr, pcb_t *pcb ) {
+
// sanity check
- assert1(hdr != NULL);
- assert2(pcb != NULL);
+ assert1( hdr != NULL );
+ assert2( pcb != NULL );
#if TRACING_USER
- cio_printf("read_phdrs(%08x,%08x)\n", (uint32_t)hdr, (uint32_t)pcb);
+ cio_printf( "read_phdrs(%08x,%08x)\n", (uint32_t) hdr, (uint32_t) pcb );
#endif
// iterate through the program headers
uint_t nhdrs = hdr->e_phnum;
// pointer to the first header table entry
- elfproghdr_t *curr = (elfproghdr_t *)((uint32_t)hdr + hdr->e_phoff);
+ elfproghdr_t *curr = (elfproghdr_t *) ((uint32_t) hdr + hdr->e_phoff);
// process them all
int loaded = 0;
- for (uint_t i = 0; i < nhdrs; ++i, ++curr) {
+ for( uint_t i = 0; i < nhdrs; ++i, ++curr ) {
+
#if TRACING_ELF
- dump_phdr(curr, i);
+ dump_phdr( curr, i );
#endif
- if (curr->p_type != PT_LOAD) {
+ if( curr->p_type != PT_LOAD ) {
// not loadable --> we'll skip it
continue;
}
- if (loaded >= N_LOADABLE) {
+ if( loaded >= N_LOADABLE ) {
#if TRACING_USER
- cio_puts(" LIMIT\n");
+ cio_puts( " LIMIT\n" );
#endif
return E_LOAD_LIMIT;
}
// set a pointer to the bytes within the object file
- char *data = (char *)(((uint32_t)hdr) + curr->p_offset);
+ char *data = (char *) (((uint32_t)hdr) + curr->p_offset);
#if TRACING_USER
- cio_printf(" data @ %08x", (uint32_t)data);
+ cio_printf( " data @ %08x", (uint32_t) data );
#endif
// copy the pages into memory
- int stat = vm_add(pcb->pdir, curr->p_flags & PF_W, false,
- (char *)curr->p_va, curr->p_memsz, data,
- curr->p_filesz);
- if (stat != SUCCESS) {
+ int stat = vm_add( pcb->pdir, curr->p_flags & PF_W, false,
+ (char *) curr->p_va, curr->p_memsz, data, curr->p_filesz );
+ if( stat != SUCCESS ) {
// TODO what else should we do here? check for memory leak?
return stat;
}
@@ -409,8 +311,8 @@ static int read_phdrs(elfhdr_t *hdr, pcb_t *pcb)
pcb->sects[loaded].length = curr->p_memsz;
pcb->sects[loaded].addr = curr->p_va;
#if TRACING_USER
- cio_printf(" loaded %u @ %08x\n", pcb->sects[loaded].length,
- pcb->sects[loaded].addr);
+ cio_printf( " loaded %u @ %08x\n",
+ pcb->sects[loaded].length, pcb->sects[loaded].addr );
#endif
++loaded;
}
@@ -426,27 +328,39 @@ static int read_phdrs(elfhdr_t *hdr, pcb_t *pcb)
** @param pcb Pointer to the PCB for the process
** @param entry Entry point for the new process
** @param args Argument vector to be put in place
-** @param sys Is the argument vector from kernel code?
**
-** @return A (user VA) pointer to the context_t on the stack, or NULL
+** @return A pointer to the context_t on the stack, or NULL
*/
-static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
- bool_t sys)
-{
-#if TRACING_USER
- cio_printf("stksetup: pcb %08x, entry %08x, args %08x\n", (uint32_t)pcb,
- entry, (uint32_t)args);
-#endif
+static context_t *stack_setup( pcb_t *pcb, uint32_t entry, const char **args ) {
/*
- ** First, we need to calculate the space we'll need for the argument
+ ** First, we need to count the space we'll need for the argument
** vector and strings.
+ */
+
+ int argbytes = 0;
+ int argc = 0;
+
+ while( args[argc] != NULL ) {
+ int n = strlen( args[argc] ) + 1;
+ // can't go over one page in size
+ if( (argbytes + n) > SZ_PAGE ) {
+ // oops - ignore this and any others
+ break;
+ }
+ argbytes += n;
+ ++argc;
+ }
+
+ // Round up the byte count to the next multiple of four.
+ argbytes = (argbytes + 3) & MOD4_MASK;
+
+ /*
+ ** Allocate the arrays. We are safe using dynamic arrays here
+ ** because we're using the OS stack, not the user stack.
**
- ** Keeping track of kernel vs. user VAs is tricky, so we'll use
- ** a prefix on variable names: kv_* is a kernel virtual address;
- ** uv_* is a user virtual address.
- **
- ** We rely on the C standard, section 6.7.8, to clear these arrays:
+ ** We want the argstrings and argv arrays to contain all zeroes.
+ ** The C standard states, in section 6.7.8, that
**
** "21 If there are fewer initializers in a brace-enclosed list
** than there are elements or members of an aggregate, or
@@ -455,36 +369,31 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
** the remainder of the aggregate shall be initialized
** implicitly the same as objects that have static storage
** duration."
+ **
+ ** Sadly, because we're using variable-sized arrays, we can't
+ ** rely on this, so we have to call memclr() instead. :-( In
+ ** truth, it doesn't really cost us much more time, but it's an
+ ** annoyance.
*/
- int argbytes = 0; // total length of arg strings
- int argc = 0; // number of argv entries
- const char *kv_strs[N_ARGS] = { 0 }; // converted user arg string pointers
- int strlengths[N_ARGS] = { 0 }; // length of each string
- const char *uv_argv[N_ARGS] = { 0 }; // argv pointers
+ char argstrings[ argbytes ];
+ char *argv[ argc + 1 ];
- /*
- ** IF the argument list given to us came from user code, we need
- ** to convert its address and the addresses it contains to kernel
- ** VAs; otherwise, we can use them directly.
- */
- char **kv_args = sys ? args : vm_uva2kva(pcb->pdir, (void *)args);
+ CLEAR( argstrings );
+ CLEAR( argv );
- while (kv_args[argc] != NULL) {
- kv_strs[argc] = sys ? args[argc] :
- vm_uva2kva(pcb->pdir, (void *)(kv_args[argc]));
- strlengths[argc] = strlen(kv_strs[argc]) + 1;
- // can't go over one page in size
- if ((argbytes + strlengths[argc]) > SZ_PAGE) {
- // oops - ignore this and any others
- break;
- }
- argbytes += strlengths[argc];
- ++argc;
+ // Next, duplicate the argument strings, and create pointers to
+ // each one in our argv.
+ char *tmp = argstrings;
+ for( int i = 0; i < argc; ++i ) {
+ int nb = strlen(args[i]) + 1; // bytes (incl. NUL) in this string
+ strcpy( tmp, args[i] ); // add to our buffer
+ argv[i] = tmp; // remember where it was
+ tmp += nb; // move on
}
- // Round up the byte count to the next multiple of four.
- argbytes = (argbytes + 3) & MOD4_MASK;
+ // trailing NULL pointer
+ argv[argc] = NULL;
/*
** The pages for the stack were cleared when they were allocated,
@@ -496,7 +405,7 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
** The user code was linked with a startup function that defines
** the entry point (_start), calls main(), and then calls exit()
** if main() returns. We need to set up the stack this way:
- **
+ **
** esp -> context <- context save area
** ... <- context save area
** context <- context save area
@@ -510,73 +419,35 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
** Stack alignment rules for the SysV ABI i386 supplement dictate that
** the 'argc' parameter must be at an address that is a multiple of 16;
** see below for more information.
- **
- ** Ultimately, this is what the bottom end of the stack will look like:
- **
- ** kvavptr
- ** kvacptr |
- ** | |
- ** v v
- ** argc argv av[0] av[1] etc NULL str0 str1 etc.
- ** [....][....][....][....] ... [0000] ... [......0......0.........]
- ** | ^ | | ^ ^
- ** | | | | | |
- ** ------ | ---------------------|-------
- ** ---------------------------
- */
-
- /*
- ** We need to find the last page of the user stack. Find the page
- ** table for the 4MB user address space. The physical address of its
- ** frame is in the first page directory entry. Extract that from the
- ** entry and convert it into a virtual address for the kernel to use.
- */
- pde_t *kv_userpt = (pde_t *)P2V(PTE_ADDR(pcb->pdir[USER_PDE]));
- assert(kv_userpt != NULL);
-
- /*
- ** The final entries in that PMT are for the pages of the user stack.
- ** Grab the physical address of the frame for the last one. (Again,
- ** we need to convert it to a virtual address we can use.)
*/
- // the PMT entry for that page
- pte_t pmt_entry = kv_userpt[USER_STK_LAST_PTE];
- assert(IS_PRESENT(pmt_entry));
-
- // user VA for the first byte of that page
- uint32_t *uvptr = (uint32_t *)USER_STACK_P2;
+ // Pointer to the last word in stack. We get this from the
+ // VM hierarchy. Get the PDE entry for the user address space.
+ pde_t stack_pde = pcb->pdir[USER_PDE];
- // convert that address to a kernel VA
- uint32_t *kvptr = (uint32_t *)vm_uva2kva(pcb->pdir, (void *)uvptr);
+ // The PDE entry points to the PT, which is an array of PTE. The last
+ // two entries are for the stack; pull out the last one.
+ pte_t stack_pte = ((pte_t *)(stack_pde & MOD4K_MASK))[USER_STK_PTE2];
- /*
- ** Move these pointers to where the string area will begin. We
- ** will then back up to the next lower multiple-of-four address.
- */
+ // OK, now we have the PTE. The frame address of the last page is
+ // in this PTE. Find the address immediately after that.
+ uint32_t *ptr = (uint32_t *)
+ ((uint32_t)(stack_pte & MOD4K_MASK) + SZ_PAGE);
- uint32_t uvstrptr = ((uint32_t)uvptr) + SZ_PAGE - argbytes;
- uvstrptr &= MOD4_MASK;
+ // Pointer to where the arg strings should be filled in.
+ char *strings = (char *) ( (uint32_t) ptr - argbytes );
- uint32_t kvstrptr = ((uint32_t)kvptr) + SZ_PAGE - argbytes;
- kvstrptr &= MOD4_MASK;
+ // back the pointer up to the nearest word boundary; because we're
+ // moving toward location 0, the nearest word boundary is just the
+ // next smaller address whose low-order two bits are zeroes
+ strings = (char *) ((uint32_t) strings & MOD4_MASK);
- // Copy over the argv strings, remembering where each string begins
- for (int i = 0; i < argc; ++i) {
- // copy the string using kernel addresses
- strcpy((char *)kvstrptr, kv_args[i]);
-
- // remember the user address where this string went
- uv_argv[i] = (char *)uvstrptr;
-
- // adjust both string addresses
- kvstrptr += strlengths[i];
- uvstrptr += strlengths[i];
- }
+ // Copy over the argv strings.
+ memcpy( (void *)strings, argstrings, argbytes );
/*
- ** Next, we need to copy over the other data. Start by determining
- ** where 'argc' should go.
+ ** Next, we need to copy over the argv pointers. Start by
+ ** determining where 'argc' should go.
**
** Stack alignment is controlled by the SysV ABI i386 supplement,
** version 1.2 (June 23, 2016), which states in section 2.2.2:
@@ -590,43 +461,53 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
**
** Isn't technical documentation fun? Ultimately, this means that
** the first parameter to main() should be on the stack at an address
- ** that is a multiple of 16. In our case, that is 'argc'.
- */
-
- /*
+ ** that is a multiple of 16.
+ **
** The space needed for argc, argv, and the argv array itself is
** argc + 3 words (argc+1 for the argv entries, plus one word each
- ** for argc and argv). We back up that much from the string area.
+ ** for argc and argv). We back up that much from 'strings'.
*/
int nwords = argc + 3;
- uint32_t *kvacptr = ((uint32_t *)kvstrptr) - nwords;
- uint32_t *uvacptr = ((uint32_t *)uvstrptr) - nwords;
+ uint32_t *acptr = ((uint32_t *) strings) - nwords;
+
+ /*
+ ** Next, back up until we're at a multiple-of-16 address. Because we
+ ** are moving to a lower address, its upper 28 bits are identical to
+ ** the address we currently have, so we can do this with a bitwise
+ ** AND to just turn off the lower four bits.
+ */
- // back these up to multiple-of-16 addresses for stack alignment
- kvacptr = (uint32_t *)(((uint32_t)kvacptr) & MOD16_MASK);
- uvacptr = (uint32_t *)(((uint32_t)uvacptr) & MOD16_MASK);
+ acptr = (uint32_t *) ( ((uint32_t)acptr) & MOD16_MASK );
// copy in 'argc'
- *kvacptr = argc;
+ *acptr = argc;
- // 'argv' immediately follows 'argc', and 'argv[0]' immediately
- // follows 'argv'
- uint32_t *kvavptr = kvacptr + 2;
- *(kvavptr - 1) = (uint32_t)kvavptr;
+ // next, 'argv', which follows 'argc'; 'argv' points to the
+ // word that follows it in the stack
+ uint32_t *avptr = acptr + 2;
+ *(acptr+1) = (uint32_t) avptr;
- // now, the argv entries themselves
- for (int i = 0; i < argc; ++i) {
- *kvavptr++ = (uint32_t)uv_argv[i];
- }
+ /*
+ ** Next, we copy in all argc+1 pointers.
+ */
- // and the trailing NULL
- *kvavptr = NULL;
+ // Adjust and copy the string pointers.
+ for( int i = 0; i <= argc; ++i ) {
+ if( argv[i] != NULL ) {
+ // an actual pointer - adjust it and copy it in
+ *avptr = (uint32_t) strings;
+ // skip to the next entry in the array
+ strings += strlen(argv[i]) + 1;
+ } else {
+ // end of the line!
+ *avptr = NULL;
+ }
+ ++avptr;
+ }
/*
- ** Almost done!
- **
- ** Now we need to set up the initial context for the executing
+ ** Now, we need to set up the initial context for the executing
** process.
**
** When this process is dispatched, the context restore code will
@@ -635,34 +516,27 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
** the interrupt "returns" to the entry point of the process.
*/
- // Locate the context save area on the stack by backup up one
- // "context" from where the argc value is saved
- context_t *kvctx = ((context_t *)kvacptr) - 1;
- uint32_t uvctx = (uint32_t)(((context_t *)uvacptr) - 1);
+ // Locate the context save area on the stack.
+ context_t *ctx = ((context_t *) avptr) - 1;
/*
** We cleared the entire stack earlier, so all the context
** fields currently contain zeroes. We now need to fill in
** all the important fields.
- **
- ** Note: we don't need to set the ESP value for the process,
- ** as the 'popa' that restores the general registers doesn't
- ** actually restore ESP from the context area - it leaves it
- ** where it winds up.
*/
- kvctx->eflags = DEFAULT_EFLAGS; // IF enabled, IOPL 0
- kvctx->eip = entry; // initial EIP
- kvctx->cs = GDT_CODE; // segment registers
- kvctx->ss = GDT_STACK;
- kvctx->ds = kvctx->es = kvctx->fs = kvctx->gs = GDT_DATA;
+ ctx->eflags = DEFAULT_EFLAGS; // IE enabled, PPL 0
+ ctx->eip = entry; // initial EIP
+ ctx->cs = GDT_CODE; // segment registers
+ ctx->ss = GDT_STACK;
+ ctx->ds = ctx->es = ctx->fs = ctx->gs = GDT_DATA;
/*
- ** Return the new context pointer to the caller as a user
- ** space virtual address.
+ ** Return the new context pointer to the caller. It will be our
+ ** caller's responsibility to schedule this process.
*/
-
- return ((context_t *)uvctx);
+
+ return( ctx );
}
/*
@@ -674,36 +548,39 @@ static context_t *stack_setup(pcb_t *pcb, uint32_t entry, const char **args,
**
** Initializes the user support module.
*/
-void user_init(void)
-{
+void user_init( void ) {
+
#if TRACING_INIT
- cio_puts(" User");
-#endif
+ cio_puts( " User" );
+#endif
// This is gross, but we need to get this information somehow.
// Access the "user blob" data in the second bootstrap sector
- uint16_t *blobdata = (uint16_t *)P2V(USER_BLOB_DATA);
- user_offset = *blobdata++;
+ uint16_t *blobdata = (uint16_t *) USER_BLOB_DATA;
+ user_offset = *blobdata++;
user_segment = *blobdata++;
user_sectors = *blobdata++;
#if TRACING_USER
- cio_printf("\nUser blob: %u sectors @ %04x:%04x", user_sectors,
- user_segment, user_offset);
+ cio_printf( "\nUser blob: %u sectors @ %04x:%04x", user_sectors,
+ user_segment, user_offset );
#endif
// calculate the location of the user blob
- if (user_sectors > 0) {
+ if( user_sectors > 0 ) {
+
// calculate the address of the header
- user_header = (header_t *)(KERN_BASE + ((((uint_t)user_segment) << 4) +
- ((uint_t)user_offset)));
+ user_header = (header_t *)
+ ( KERN_BASE +
+ ( (((uint_t)user_segment) << 4) + ((uint_t)user_offset) )
+ );
// the program table immediate follows the blob header
- prog_table = (prog_t *)(user_header + 1);
+ prog_table = (prog_t *) (user_header + 1);
#if TRACING_USER
- cio_printf(", hdr %08x, %u progs, tbl %08x\n", (uint32_t)user_header,
- user_header->num, (uint32_t)prog_table);
+ cio_printf( ", hdr %08x, %u progs, tbl %08x\n", (uint32_t) user_header,
+ user_header->num, (uint32_t) prog_table );
#endif
} else {
@@ -711,7 +588,7 @@ void user_init(void)
user_header = NULL;
prog_table = NULL;
#if TRACING_USER
- cio_putchar('\n');
+ cio_putchar( '\n' );
#endif
}
}
@@ -725,19 +602,15 @@ void user_init(void)
**
** @return pointer to the program table entry in the code archive, or NULL
*/
-prog_t *user_locate(uint_t what)
-{
-#if TRACING_USER
- cio_printf("ulocate: %u\n", what);
-#endif
-
+prog_t *user_locate( uint_t what ) {
+
// no programs if there is no blob!
- if (user_header == NULL) {
+ if( user_header == NULL ) {
return NULL;
}
// make sure this is a reasonable program to request
- if (what >= user_header->num) {
+ if( what >= user_header->num ) {
// no such program!
return NULL;
}
@@ -746,7 +619,7 @@ prog_t *user_locate(uint_t what)
prog_t *prog = &prog_table[what];
// if there are no bytes, it's useless
- if (prog->size < 1) {
+ if( prog->size < 1 ) {
return NULL;
}
@@ -764,11 +637,7 @@ prog_t *user_locate(uint_t what)
**
** @return the status of the duplicate attempt
*/
-int user_duplicate(pcb_t *new, pcb_t *old)
-{
-#if TRACING_USER
- cio_printf("udup: old %08x new %08x\n", (uint32_t)old, (uint32_t)new);
-#endif
+int user_duplicate( pcb_t *new, pcb_t *old ) {
// We need to do a recursive duplication of the process address
// space of the current process. First, we create a new user
@@ -778,14 +647,14 @@ int user_duplicate(pcb_t *new, pcb_t *old)
// create the initial VM hierarchy
pde_t *pdir = vm_mkuvm();
- if (pdir == NULL) {
+ if( pdir == NULL ) {
return E_NO_MEMORY;
}
new->pdir = pdir;
// Next, add a USER_PDE page table that's a duplicate of the
// current process' page table
- if (!vm_uvmdup(new->pdir, old->pdir)) {
+ if( !vm_uvmdup(old->pdir,new->pdir) ) {
// check for memory leak?
return E_NO_MEMORY;
}
@@ -800,23 +669,26 @@ int user_duplicate(pcb_t *new, pcb_t *old)
// modified to loop over the larger space.
// pointer to the PMT for the user
- pte_t *pt = (pte_t *)(pdir[USER_PDE]);
- assert(pt != NULL);
+ pte_t *pt = (pte_t *) (pdir[USER_PDE]);
+ assert( pt != NULL );
- for (int i = 0; i < N_PTE; ++i) {
+ for( int i = 0; i < N_PTE; ++i ) {
// get the current entry from the PMT
pte_t entry = *pt;
// if this entry is present,
- if (IS_PRESENT(entry)) {
+ if( IS_PRESENT(entry) ) {
+
// duplicate the frame pointed to by this PTE
- void *tmp = vm_pagedup((void *)PTE_ADDR(entry));
+ void *tmp = vm_pagedup( (void *) PTE_ADDR(entry) );
// replace the old frame number with the new one
- *pt = (pte_t)(((uint32_t)tmp) | PERMS(entry));
+ *pt = (pte_t) (((uint32_t)tmp) | PERMS(entry) );
} else {
+
*pt = 0;
+
}
++pt;
}
@@ -833,74 +705,60 @@ int user_duplicate(pcb_t *new, pcb_t *old)
** @param ptab A pointer to the program table entry to be loaded
** @param pcb The PCB for the program being loaded
** @param args The argument vector for the program
-** @param sys Is the argument vector from kernel code?
**
** @return the status of the load attempt
*/
-int user_load(prog_t *ptab, pcb_t *pcb, const char **args, bool_t sys)
-{
- // NULL pointers are bad!
- assert1(ptab != NULL);
- assert1(pcb != NULL);
- assert1(args != NULL);
+int user_load( prog_t *ptab, pcb_t *pcb, const char **args ) {
-#if TRACING_USER
- cio_printf("Uload: prog '%s' pcb %08x args %08x\n",
- ptab->name[0] ? ptab->name : "?", (uint32_t)pcb, (uint32_t)args);
-#endif
+ // NULL pointers are bad!
+ assert1( ptab != NULL );
+ assert1( pcb != NULL );
+ assert1( args != NULL );
// locate the ELF binary
- elfhdr_t *hdr = (elfhdr_t *)((uint32_t)user_header + ptab->offset);
+ elfhdr_t *hdr = (elfhdr_t *) ((uint32_t)user_header + ptab->offset);
#if TRACING_ELF
- cio_printf("Load: ptab %08x: '%s', off %08x, size %08x, flags %08x\n",
- (uint32_t)ptab, ptab->name, ptab->offset, ptab->size,
- ptab->flags);
- cio_printf(" args %08x:", (uint32_t)args);
- if (sys) {
- for (int i = 0; args[i] != NULL; ++i) {
- cio_printf(" [%d] %s", i, args[i]);
- }
- } else {
- char **kv_args = vm_uva2kva(pcb->pdir, args);
- for (int i = 0; kv_args[i] != NULL; ++i) {
- cio_printf(" [%d] %s", i,
- (char *)vm_uva2kva(pcb->pdir, kv_args[i]));
- }
+ cio_printf( "Load: ptab %08x: '%s', off %08x, size %08x, flags %08x\n",
+ (uint32_t) ptab, ptab->name, ptab->offset, ptab->size,
+ ptab->flags );
+ cio_printf( " args %08x:", (uint32_t) args );
+ for( int i = 0; args[i] != NULL; ++i ) {
+ cio_printf( " [%d] %s", i, args[i] );
}
- cio_printf("\n pcb %08x (pid %u)\n", (uint32_t)pcb, pcb->pid);
- dump_fhdr(hdr);
+ cio_printf( "\n pcb %08x (pid %u)\n", (uint32_t) pcb, pcb->pid );
+ dump_fhdr( hdr );
#endif
// verify the ELF header
- if (hdr->e_ident.f.magic != ELF_MAGIC) {
+ if( hdr->e_ident.f.magic != ELF_MAGIC ) {
return E_BAD_PARAM;
}
// allocate a page directory
pcb->pdir = vm_mkuvm();
- if (pcb->pdir == NULL) {
+ if( pcb->pdir == NULL ) {
return E_NO_MEMORY;
}
// read all the program headers
- int stat = read_phdrs(hdr, pcb);
- if (stat != SUCCESS) {
- cio_printf("Uload: read_phdrs('%s') returned %d\n", ptab->name, stat);
- PANIC(0, "User_load: phdr read failed");
+ int stat = read_phdrs( hdr, pcb );
+ if( stat != SUCCESS ) {
+ // TODO figure out a better way to deal with this
+ PANIC( 0, "user_load: phdr read failed" );
}
// next, set up the runtime stack - just like setting up loadable
// sections, except nothing to copy
- stat =
- vm_add(pcb->pdir, true, false, (void *)USER_STACK, SZ_USTACK, NULL, 0);
- if (stat != SUCCESS) {
- cio_printf("Uload: vm_add('%s') stack returned %d\n", ptab->name, stat);
- PANIC(0, "user_load: vm_add stack failed");
+ stat = vm_add( pcb->pdir, true, false, (void *) USER_STACK,
+ SZ_USTACK, NULL, 0 );
+ if( stat != SUCCESS ) {
+ // TODO yadda yadda...
+ PANIC( 0, "user_load: vm_add failed" );
}
// set up the command-line arguments
- pcb->context = stack_setup(pcb, hdr->e_entry, args, sys);
+ pcb->context = stack_setup( pcb, hdr->e_entry, args );
return SUCCESS;
}
@@ -913,17 +771,13 @@ int user_load(prog_t *ptab, pcb_t *pcb, const char **args, bool_t sys)
**
** @param pcb The PCB of the program to be unloaded
*/
-void user_cleanup(pcb_t *pcb)
-{
-#if TRACING_USER
- cio_printf("Uclean: %08x\n", (uint32_t)pcb);
-#endif
-
- if (pcb == NULL) {
+void user_cleanup( pcb_t *pcb ) {
+
+ if( pcb == NULL ) {
// should this be an error?
return;
}
- vm_free(pcb->pdir);
+ vm_free( pcb->pdir );
pcb->pdir = NULL;
}
diff --git a/kernel/old/vm.c b/kernel/old/vm.c
index 814ff12..749bed3 100644
--- a/kernel/old/vm.c
+++ b/kernel/old/vm.c
@@ -6,7 +6,7 @@
** @brief Kernel VM support
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
@@ -37,244 +37,70 @@ pde_t *kpdir;
** @param vector Interrupt vector number
** @param code Error code pushed onto the stack
*/
-static void vm_isr(int vector, int code)
-{
+static void vm_isr( int vector, int code ) {
+
// get whatever information we can from the fault
pfec_t fault;
- fault.u = (uint32_t)code;
+ fault.u = (uint32_t) code;
uint32_t addr = r_cr2();
// report what we found
- sprint(b256,
- "** page fault @ 0x%08x %cP %c %cM %cRSV %c %cPK %cSS %cHLAT %cSGZ",
- addr, fault.s.p ? ' ' : '!', fault.s.w ? 'W' : 'R',
- fault.s.us ? 'U' : 'S', fault.s.rsvd ? ' ' : '!',
- fault.s.id ? 'I' : 'D', fault.s.pk ? ' ' : '!',
- fault.s.ss ? ' ' : '!', fault.s.hlat ? ' ' : '!',
- fault.s.sgz ? ' ' : '!');
+ sprint( b256,
+ "** page fault @ 0x%08x %cP %c %cM %cRSV %c %cPK %cSS %cHLAT %cSGZ",
+ addr,
+ fault.s.p ? ' ' : '!',
+ fault.s.w ? 'W' : 'R',
+ fault.s.us ? 'U' : 'S',
+ fault.s.rsvd ? ' ' : '!',
+ fault.s.id ? 'I' : 'D',
+ fault.s.pk ? ' ' : '!',
+ fault.s.ss ? ' ' : '!',
+ fault.s.hlat ? ' ' : '!',
+ fault.s.sgz ? ' ' : '!'
+ );
// and give up
- PANIC(0, b256);
+ PANIC( 0, b256 );
}
/**
-** Name: ptcount
-**
-** Count the number of each type of entry in a page table.
-** Returns a 32-bit result containing two 16-bit counts:
+** Name: uva2kva
**
-** Upper half Lower half
-** PDIR: # of 4MB entries # of 'present' entries
-** PMT: zero # of 'present' entries
-**
-** The number of "not present" can be calculated from these.
+** Convert a user VA into a kernel address. Works for all addresses -
+** if the address is a page address, the PERMS(va) value will be 0;
+** otherwise, it is the offset into the page.
**
-** @param pt Pointer to the page table
-** @param dir Is it a page directory (vs. a page table)?
+** @param pdir Pointer to the page directory to examine
+** @param va Virtual address to check
*/
ATTR_UNUSED
-static uint32_t ptcount(pte_t *ptr, bool_t dir)
-{
- uint16_t n_np = 0, n_p = 0, n_lg = 0;
-
- for (int i = 0; i < N_PTE; ++i) {
- pde_t entry = *ptr++;
- if (!IS_PRESENT(entry)) {
- ++n_np;
- continue;
- }
- if (dir && IS_LARGE(entry)) {
- ++n_lg;
- } else {
- ++n_p;
- }
- }
-
- // n_lg will be 0 for PMTs
- return (n_lg << 16) | n_p;
-}
-
-// decode a PDE
-static void pde_prt(uint32_t level, uint32_t i, uint32_t entry, bool_t all)
-{
- if (!IS_PRESENT(entry) && !all) {
- return;
- }
-
- // indent
- for (int n = 0; n <= level; ++n)
- cio_puts(" ");
-
- // line header
- cio_printf("[%03x] %08x", i, entry);
+static void *uva2kva( pde_t *pdir, void *va ) {
- // perms
- if (IS_LARGE(entry)) { // PS is 1
- if ((entry & PDE_PAT) != 0)
- cio_puts(" PAT");
- if ((entry & PDE_G) != 0)
- cio_puts(" G");
- cio_puts(" PS");
- if ((entry & PDE_D) != 0)
- cio_puts(" D");
+ // find the PMT entry for this address
+ pte_t *pte = vm_getpte( pdir, va, false );
+ if( pte == NULL ) {
+ return NULL;
}
- if ((entry & PDE_A) != 0)
- cio_puts(" A");
- if ((entry & PDE_PCD) != 0)
- cio_puts(" CD");
- if ((entry & PDE_PWT) != 0)
- cio_puts(" WT");
- if ((entry & PDE_US) != 0)
- cio_puts(" U");
- if ((entry & PDE_RW) != 0)
- cio_puts(" W");
- // frame address
- cio_printf(" P --> %s %08x\n", IS_LARGE(entry) ? "Pg" : "PT",
- PDE_ADDR(entry));
-}
+ // get the entry
+ pte_t entry = *pte;
-// decode a PTE
-static void pte_prt(uint32_t level, uint32_t i, uint32_t entry, bool_t all)
-{
- if (!IS_PRESENT(entry) && !all) {
- return;
+ // is this a valid address for the user?
+ if( IS_PRESENT(entry) ) {
+ return NULL;
}
- // indent
- for (int n = 0; n <= level; ++n)
- cio_puts(" ");
-
- // line header
- cio_printf("[%03x] %08x", i, entry);
-
- // perms
- if ((entry & PTE_G) != 0)
- cio_puts(" G");
- if ((entry & PTE_PAT) != 0)
- cio_puts(" PAT");
- if ((entry & PTE_D) != 0)
- cio_puts(" D");
- if ((entry & PTE_A) != 0)
- cio_puts(" A");
- if ((entry & PTE_PCD) != 0)
- cio_puts(" CD");
- if ((entry & PTE_PWT) != 0)
- cio_puts(" WT");
- if ((entry & PTE_US) != 0)
- cio_puts(" U");
- if ((entry & PTE_RW) != 0)
- cio_puts(" W");
-
- cio_printf(" P --> Pg %08x\n", PTE_ADDR(entry));
-}
-
-/**
-** Name: ptdump
-**
-** Recursive helper for table hierarchy dump.
-**
-** @param level Current hierarchy level
-** @param pt Page table to display
-** @param dir Is it a page directory (vs. a page table)?
-** @param mode How to display the entries
-*/
-ATTR_UNUSED
-static void ptdump(uint_t level, void *pt, bool_t dir, enum vmmode_e mode)
-{
- pte_t *ptr = (pte_t *)pt;
-
- // indent two spaces per level
- for (int n = 0; n < level; ++n)
- cio_puts(" ");
-
- cio_printf("%s at 0x%08x:", dir ? "PDir" : "PTbl", (uint32_t)pt);
- uint32_t nums = ptcount(ptr, dir);
- if (dir) {
- cio_printf(" 4MB=%u", (nums >> 16));
+ // is this a system-only page?
+ if( IS_SYSTEM(entry) ) {
+ return NULL;
}
- cio_printf(" P=%u !P=%u\n", nums & 0xffff,
- N_PTE - ((nums >> 16) + (nums & 0xffff)));
- for (uint32_t i = 0; i < (uint32_t)N_PTE; ++i) {
- pte_t entry = *ptr++;
+ // get the physical address
+ uint32_t frame = PTE_ADDR(*pte) | PERMS(va);
- // only process this entry if it's not empty
- if (entry) {
- if (dir) {
- // this is a PDIR entry; could be either a 4MB
- // page, or a PMT pointer
- if (mode > Simple) {
- pde_prt(level, i, entry, false);
- if (!IS_LARGE(entry) && mode > OneLevel) {
- ptdump(level + 1, (void *)P2V(PTE_ADDR(entry)), false,
- mode);
- }
- }
- } else {
- // just a PMT entry
- if (mode > Simple) {
- pte_prt(level, i, entry, false);
- }
- }
- }
- }
+ return (void *) P2V(frame);
}
-/**
-** Name: pmt_dump
-**
-** Dump the non-zero entries of a page table or directory
-**
-** @param pt The page table
-** @param dir Is this a page directory?
-** @param start First entry to process
-** @param num Number of entries to process
-*/
-ATTR_UNUSED
-static void pmt_dump(pte_t *pt, bool_t dir, uint32_t start, uint32_t num)
-{
- cio_printf("\n\nP%c dump", dir ? 'D' : 'T');
- cio_printf(" of %08x", (uint32_t)pt);
- cio_printf(" [%03x] through [%03x]\n", start, start + num - 1);
-
- uint_t n = 0;
- uint_t z = 0;
-
- for (uint_t i = 0; i < num; ++i) {
- pte_t entry = pt[start + i];
- // four entries per line
- if (n && ((n & 0x3) == 0)) {
- cio_putchar('\n');
- }
- if (IS_PRESENT(entry)) {
- cio_printf(" %03x", start + i);
- if (IS_LARGE(entry)) {
- cio_printf(" 8 %05x", GET_4MFRAME(entry) << 10);
- } else {
- cio_printf(" 4 %05x", GET_4KFRAME(entry));
- }
- ++n;
- } else {
- ++z;
- }
- // pause after every four lines of output
- if (n && ((n & 0xf) == 0)) {
- delay(DELAY_2_SEC);
- }
- }
-
- // partial line?
- if ((n & 0x3) != 0) {
- cio_putchar('\n');
- }
-
- if (z > 0) {
- cio_printf(" %u entries were !P\n", z);
- }
-
- delay(DELAY_2_SEC);
-}
/*
** PUBLIC FUNCTIONS
@@ -285,83 +111,21 @@ static void pmt_dump(pte_t *pt, bool_t dir, uint32_t start, uint32_t num)
**
** Description: Initialize the VM module
*/
-void vm_init(void)
-{
+void vm_init( void ) {
+
#if TRACING_INIT
- cio_puts(" VM");
+ cio_puts( " VM" );
#endif
// set up the kernel's 4K-page directory
kpdir = vm_mkkvm();
- assert(kpdir != NULL);
-
-#if TRACING_VM
- cio_printf("vm_init: kpdir %08x, adding user pages\n", kpdir);
-#endif
-
- // add the entries for the user address space
- for (uint32_t addr = 0; addr < NUM_4MB; addr += SZ_PAGE) {
- int stat = vm_map(kpdir, (void *)addr, addr, SZ_PAGE, PTE_US | PTE_RW);
- if (stat != SUCCESS) {
- cio_printf("vm_init, map %08x->%08x failed, status %d\n", addr,
- addr, stat);
- PANIC(0, "vm_init user range map failed");
- }
-#if TRACING_VM
- cio_putchar('.');
-#endif
- }
-#if TRACING_VM
- cio_puts(" done\n");
-#endif
+ assert( kpdir != NULL );
// switch to it
vm_set_kvm();
-#if TRACING_VM
- cio_puts("vm_init: running on new kpdir\n");
-#endif
-
// install the page fault handler
- install_isr(VEC_PAGE_FAULT, vm_isr);
-}
-
-/**
-** Name: vm_uva2kva
-**
-** Convert a user VA into a kernel address. Works for all addresses -
-** if the address is a page address, the low-order nine bits will be
-** zeroes; otherwise, they are the offset into the page, which is
-** unchanged between the address spaces.
-**
-** @param pdir Pointer to the page directory to examine
-** @param va Virtual address to check
-*/
-void *vm_uva2kva(pde_t *pdir, void *va)
-{
- // find the PMT entry for this address
- pte_t *pte = vm_getpte(pdir, va, false);
- if (pte == NULL) {
- return NULL;
- }
-
- // get the entry
- pte_t entry = *pte;
-
- // is this a valid address for the user?
- if (!IS_PRESENT(entry)) {
- return NULL;
- }
-
- // is this a system-only page?
- if (IS_SYSTEM(entry)) {
- return NULL;
- }
-
- // get the physical address
- uint32_t frame = PTE_ADDR(*pte) | PERMS(va);
-
- return (void *)P2V(frame);
+ install_isr( VEC_PAGE_FAULT, vm_isr );
}
/**
@@ -373,11 +137,10 @@ void *vm_uva2kva(pde_t *pdir, void *va)
**
** @return a pointer to the new, duplicate page, or NULL
*/
-void *vm_pagedup(void *old)
-{
- void *new = (void *)km_page_alloc();
- if (new != NULL) {
- blkmov(new, old, SZ_PAGE);
+void *vm_pagedup( void *old ) {
+ void *new = (void *) km_page_alloc();
+ if( new != NULL ) {
+ blkmov( new, old, SZ_PAGE );
}
return new;
}
@@ -387,54 +150,58 @@ void *vm_pagedup(void *old)
**
** Duplicate a page directory entry
**
-** @param entry The entry to be duplicated
+** @param dst Pointer to where the duplicate should go
+** @param curr Pointer to the entry to be duplicated
**
-** @return the new entry, or -1 on error
+** @return true on success, else false
*/
-pde_t vm_pdedup(pde_t entry)
-{
+bool_t vm_pdedup( pde_t *dst, pde_t *curr ) {
+
+ assert1( curr != NULL );
+ assert1( dst != NULL );
+
#if TRACING_VM
- cio_printf("vm_pdedup curr %08x\n", (uint32_t)entry);
+ cio_printf( "vm_pdedup dst %08x curr %08x\n",
+ (uint32_t) dst, (uint32_t) curr );
#endif
+ pde_t entry = *curr;
// simplest case
- if (!IS_PRESENT(entry)) {
- return 0;
- }
-
- // is this a large page?
- if (IS_LARGE(entry)) {
- // just copy it
- return entry;
+ if( !IS_PRESENT(entry) ) {
+ *dst = 0;
+ return true;
}
- // OK, we have a 4KB entry; allocate a page table for it
- pte_t *tblva = (pte_t *)km_page_alloc();
- if (tblva == NULL) {
- return (uint32_t)-1;
+ // OK, we have an entry; allocate a page table for it
+ pte_t *newtbl = (pte_t *) km_page_alloc();
+ if( newtbl == NULL ) {
+ return false;
}
- // make sure the entries are all initially 'not present'
- memclr(tblva, SZ_PAGE);
+ // we could clear the new table, but we'll be assigning to
+ // each entry anyway, so we'll save the execution time
- // VA of the page table for this directory entry
- pte_t *old = (pte_t *)P2V(PDE_ADDR(entry));
+ // address of the page table for this directory entry
+ pte_t *old = (pte_t *) PDE_ADDR(entry);
- // pointer to the first PTE in the new table (already a VA)
- pte_t *new = tblva;
+ // pointer to the first PTE in the new table
+ pte_t *new = newtbl;
- for (int i = 0; i < N_PTE; ++i) {
- // only need to copy 'present' entries
- if (IS_PRESENT(*old)) {
+ for( int i = 0 ; i < N_PTE; ++i ) {
+ if( !IS_PRESENT(*old) ) {
+ *new = 0;
+ } else {
*new = *old;
}
++old;
++new;
}
- // replace the page table address
- // (PA of page table, lower 12 bits from '*curr')
- return (pde_t)(V2P(PTE_ADDR(tblva)) | PERMS(entry));
+ // replace the page table address
+ // upper 22 bits from 'newtbl', lower 12 from '*curr'
+ *dst = (pde_t) ( PTE_ADDR(newtbl) | PERMS(entry) );
+
+ return true;
}
/**
@@ -452,37 +219,38 @@ pde_t vm_pdedup(pde_t entry)
** @return A pointer to the page table entry for this VA, or NULL if
** there isn't one and we're not allocating
*/
-pte_t *vm_getpte(pde_t *pdir, const void *va, bool_t alloc)
-{
- pte_t *ptbl;
+pte_t *vm_getpte( pde_t *pdir, const void *va, bool_t alloc ) {
+ pte_t *ptab;
// sanity check
- assert1(pdir != NULL);
+ assert1( pdir != NULL );
// get the PDIR entry for this virtual address
- pde_t *pde_ptr = &pdir[PDIX(va)];
+ pde_t *pde = &pdir[ PDIX(va) ];
// is it already set up?
- if (IS_PRESENT(*pde_ptr)) {
+ if( IS_PRESENT(*pde) ) {
+
// yes!
- ptbl = (pte_t *)P2V(PTE_ADDR(*pde_ptr));
+ ptab = (pte_t*)P2V(PTE_ADDR(*pde));
} else {
+
// no - should we create it?
- if (!alloc) {
+ if( !alloc ) {
// nope, so just return
return NULL;
}
// yes - try to allocate a page table
- ptbl = (pte_t *)km_page_alloc();
- if (ptbl == NULL) {
- WARNING("can't allocate page table");
+ ptab = (pte_t *) km_page_alloc();
+ if( ptab == NULL ) {
+ WARNING( "can't allocate page table" );
return NULL;
}
// who knows what was left in this page....
- memclr(ptbl, SZ_PAGE);
+ memclr( ptab, SZ_PAGE );
// add this to the page directory
//
@@ -491,54 +259,46 @@ pte_t *vm_getpte(pde_t *pdir, const void *va, bool_t alloc)
// entries, if necessary.
//
// NOTE: the allocator is serving us virtual page addresses,
- // so we must convert them to physical addresses for the
- // table entries
- *pde_ptr = V2P(ptbl) | PDE_P | PDE_RW | PDE_US;
+ // so we must convert them to physical addresses
+ *pde = ((uint32_t) V2P(ptab)) | PDE_P | PDE_RW;
}
- // finally, return a pointer to the entry in the page table for this VA
- return &ptbl[PTIX(va)];
+ // finally, return a pointer to the entry in the
+ // page table for this VA
+ return &ptab[ PTIX(va) ];
}
// Set up kernel part of a page table.
-pde_t *vm_mkkvm(void)
+pde_t *vm_mkkvm( void )
{
mapping_t *k;
// allocate the page directory
pde_t *pdir = km_page_alloc();
- if (pdir == NULL) {
+ if( pdir == NULL ) {
return NULL;
}
-#if 0 && TRACING_VM
- cio_puts( "\nEntering vm_mkkvm\n" );
- pmt_dump( pdir, true, 0, N_PDE );
-#endif
// clear it out to disable all the entries
- memclr(pdir, SZ_PAGE);
+ memclr( pdir, SZ_PAGE );
- if (P2V(PHYS_TOP) > DEV_BASE) {
- cio_printf("PHYS_TOP (%08x -> %08x) > DEV_BASE(%08x)\n", PHYS_TOP,
- P2V(PHYS_TOP), DEV_BASE);
- PANIC(0, "PHYS_TOP too large");
+ if( P2V(PHYS_TOP) > DEV_BASE ) {
+ cio_printf( "PHYS_TOP (%08x -> %08x) > DEV_BASE(%08x)\n",
+ PHYS_TOP, P2V(PHYS_TOP), DEV_BASE );
+ PANIC( 0, "PHYS_TOP too large" );
}
// map in all the page ranges
k = kmap;
- for (int i = 0; i < n_kmap; ++i, ++k) {
- int stat = vm_map(pdir, ((void *)k->va_start), k->pa_start,
- k->pa_end - k->pa_start, k->perm);
- if (stat != SUCCESS) {
- vm_free(pdir);
+ for( int i = 0; i < n_kmap; ++i, ++k ) {
+ int stat = vm_map( pdir, ((void *)k->va_start),
+ k->pa_end - k->pa_start,
+ k->pa_start, k->perm );
+ if( stat != SUCCESS ) {
+ vm_free( pdir );
return 0;
}
}
-#if 0 && TRACING_VM
- cio_puts( "\nvm_mkkvm() final PD:\n" );
- pmt_dump( pdir, true, 0, 16 );
- pmt_dump( pdir, true, 0x200, 16 );
-#endif
return pdir;
}
@@ -549,37 +309,32 @@ pde_t *vm_mkkvm(void)
**
** @return a pointer to the new page directory, or NULL
*/
-pde_t *vm_mkuvm(void)
-{
+pde_t *vm_mkuvm( void ) {
+
// allocate the directory
- pde_t *new = (pde_t *)km_page_alloc();
- if (new == NULL) {
+ pde_t *new = (pde_t *) km_page_alloc();
+ if( new == NULL ) {
return NULL;
}
- // iterate through the 'system' portions of the kernel
- // page directory
- int i = PDIX(KERN_BASE);
- pde_t *curr = &kpdir[i];
- pde_t *dst = &new[i];
- while (i < N_PDE) {
- if (*curr != 0) {
+ // iterate through the kernel page directory
+ pde_t *curr = kpdir;
+ pde_t *dst = new;
+ for( int i = 0; i < N_PDE; ++i ) {
+
+ if( *curr != 0 ) {
// found an active one - duplicate it
- pde_t entry = vm_pdedup(*curr);
- if (entry == (uint32_t)-1) {
+ if( !vm_pdedup(dst,curr) ) {
return NULL;
}
- *dst = entry;
- } else {
- *dst = 0;
}
++curr;
++dst;
- ++i;
}
return new;
+
}
/**
@@ -587,15 +342,8 @@ pde_t *vm_mkuvm(void)
**
** Switch the page table register to the kernel's page directory.
*/
-void vm_set_kvm(void)
-{
-#if TRACING_VM
- cio_puts("Entering vm_set_kvm()\n");
-#endif
- w_cr3(V2P(kpdir)); // switch to the kernel page table
-#if TRACING_VM
- cio_puts("Exiting vm_set_kvm()\n");
-#endif
+void vm_set_kvm( void ) {
+ w_cr3( V2P(kpdir) ); // switch to the kernel page table
}
/**
@@ -605,18 +353,11 @@ void vm_set_kvm(void)
**
** @param p PCB of the process we're switching to
*/
-void vm_set_uvm(pcb_t *p)
-{
-#if TRACING_VM
- cio_puts("Entering vm_set_uvm()\n");
-#endif
- assert(p != NULL);
- assert(p->pdir != NULL);
+void vm_set_uvm( pcb_t *p ) {
+ assert( p != NULL );
+ assert( p->pdir != NULL );
- w_cr3(V2P(p->pdir)); // switch to process's address space
-#if TRACING_VM
- cio_puts("Entering vm_set_uvm()\n");
-#endif
+ w_cr3( V2P(p->pdir) ); // switch to process's address space
}
/**
@@ -635,35 +376,36 @@ void vm_set_uvm(pcb_t *p)
**
** @return status of the allocation attempt
*/
-int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
- char *data, uint32_t bytes)
-{
+int vm_add( pde_t *pdir, bool_t wr, bool_t sys,
+ void *va, uint32_t size, char *data, uint32_t bytes ) {
+
// how many pages do we need?
- uint32_t npages = ((size & MOD4K_BITS) ? PGUP(size) : size) >> MOD4K_SHIFT;
+ uint_t npages = ((size & MOD4K_BITS) ? PGUP(size) : size) >> MOD4K_SHIFT;
// permission set for the PTEs
- uint32_t entrybase = PTE_P;
- if (wr) {
+ uint_t entrybase = PTE_P;
+ if( wr ) {
entrybase |= PTE_RW;
}
- if (!sys) {
+ if( sys ) {
entrybase |= PTE_US;
}
#if TRACING_VM
- cio_printf("vm_add: pdir %08x, %s, va %08x size %u (%u pgs)\n",
- (uint32_t)pdir, wr ? "W" : "!W", (uint32_t)va, size, npages);
- cio_printf(" from %08x, %u bytes, perms %08x\n", (uint32_t)data,
- bytes, entrybase);
+ cio_printf( "vm_add: pdir %08x, %s, va %08x (%u, %u pgs)\n",
+ (uint32_t) pdir, wr ? "W" : "!W", (uint32_t) va, size );
+ cio_printf( " from %08x, %u bytes, perms %08x\n",
+ (uint32_t) data, bytes, entrybase );
#endif
// iterate through the pages
- for (int i = 0; i < npages; ++i) {
+ for( int i = 0; i < npages; ++i ) {
+
// figure out where this page will go in the hierarchy
- pte_t *pte = vm_getpte(pdir, va, true);
- if (pte == NULL) {
- // if i > 0, this isn't the first frame - is
+ pte_t *pte = vm_getpte( pdir, va, true );
+ if( pte == NULL ) {
+ // TODO if i > 0, this isn't the first frame - is
// there anything to do about other frames?
// POSSIBLE MEMORY LEAK?
return E_NO_MEMORY;
@@ -671,27 +413,27 @@ int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
// allocate the frame
void *page = km_page_alloc();
- if (page == NULL) {
- // same question here
+ if( page == NULL ) {
+ // TODO same question here
return E_NO_MEMORY;
}
// clear it all out
- memclr(page, SZ_PAGE);
+ memclr( page, SZ_PAGE );
// create the PTE for this frame
- uint32_t entry = (uint32_t)(V2P(PTE_ADDR(page)) | entrybase);
+ uint32_t entry = (uint32_t) (PTE_ADDR(page) | entrybase);
*pte = entry;
// copy data if we need to
- if (data != NULL && bytes > 0) {
+ if( data != NULL && bytes > 0 ) {
// how much to copy
- uint32_t num = bytes > SZ_PAGE ? SZ_PAGE : bytes;
+ uint_t num = bytes > SZ_PAGE ? SZ_PAGE : bytes;
// do it!
- memmove((void *)page, (void *)data, num);
+ memcpy( (void *)page, (void *)data, num );
// adjust all the pointers
- data += num; // where to continue
- bytes -= num; // what's left to copy
+ data += num; // where to continue
+ bytes -= num; // what's left to copy
}
// bump the virtual address
@@ -699,6 +441,7 @@ int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
}
return SUCCESS;
+
}
/**
@@ -711,43 +454,36 @@ int vm_add(pde_t *pdir, bool_t wr, bool_t sys, void *va, uint32_t size,
**
** @param pdir Pointer to the page directory
*/
-void vm_free(pde_t *pdir)
-{
-#if TRACING_VM
- cio_printf("vm_free(%08x)\n", (uint32_t)pdir);
-#endif
+void vm_free( pde_t *pdir ) {
// do we have anything to do?
- if (pdir == NULL) {
+ if( pdir == NULL ) {
return;
}
// iterate through the page directory entries, freeing the
// PMTS and the frames they point to
pde_t *curr = pdir;
- int nf = 0;
- int nt = 0;
+ for( int i = 0; i < N_PDE; ++i ) {
- for (int i = 0; i < N_PDE; ++i) {
// the entry itself
pde_t entry = *curr;
// does this entry point to anything useful?
- if (IS_PRESENT(entry)) {
+ if( IS_PRESENT(entry) ) {
+
// yes - large pages make us unhappy
- assert(!IS_LARGE(entry));
+ assert( !IS_LARGE(entry) );
// get the PMT pointer
- pte_t *pmt = (pte_t *)P2V(PTE_ADDR(entry));
+ pte_t *pmt = (pte_t *) PTE_ADDR(entry);
// walk the PMT
- for (int j = 0; j < N_PTE; ++j) {
- pte_t tmp = *pmt;
+ for( int j = 0; j < N_PTE; ++j ) {
// does this entry point to a frame?
- if (IS_PRESENT(tmp)) {
+ if( IS_PRESENT(*pmt) ) {
// yes - free the frame
- km_page_free((void *)P2V(PTE_ADDR(tmp)));
- ++nf;
+ km_page_free( (void *) PTE_ADDR(*pmt) );
// mark it so we don't get surprised
*pmt = 0;
}
@@ -755,8 +491,7 @@ void vm_free(pde_t *pdir)
++pmt;
}
// now, free the PMT itself
- km_page_free((void *)P2V(PDE_ADDR(entry)));
- ++nt;
+ km_page_free( (void *) PDE_ADDR(entry) );
*curr = 0;
}
@@ -765,12 +500,7 @@ void vm_free(pde_t *pdir)
}
// finally, free the PDIR itself
- km_page_free((void *)pdir);
- ++nt;
-
-#if TRACING_VM
- cio_printf("vm_free: %d pages, %d tables\n", nf, nt);
-#endif
+ km_page_free( (void *) pdir );
}
/*
@@ -782,74 +512,47 @@ void vm_free(pde_t *pdir)
**
** @param pdir Page directory for this address space
** @param va The starting virtual address
-** @param pa The starting physical address
** @param size Length of the range to be mapped
+** @param pa The starting physical address
** @param perm Permission bits for the PTEs
**
** @return the status of the mapping attempt
*/
-int vm_map(pde_t *pdir, void *va, uint32_t pa, uint32_t size, int perm)
-{
+int vm_map( pde_t *pdir, void *va, uint_t size, uint_t pa, int perm ) {
+
// round the VA down to its page boundary
- char *addr = (char *)PGDOWN((uint32_t)va);
+ char *addr = (char*)PGDOWN((uint_t)va);
// round the end of the range down to its page boundary
- char *last = (char *)PGDOWN(((uint32_t)va) + size - 1);
+ char *last = (char*)PGDOWN(((uint_t)va) + size - 1);
-#if TRACING_VM
- cio_printf("vm_map pdir %08x va %08x pa %08x size %08x perm %03x\n",
- (uint32_t)pdir, (uint32_t)va, pa, size, perm);
-#endif
+ while( addr < last ) {
- while (addr <= last) {
// get a pointer to the PTE for the current VA
- pte_t *pte = vm_getpte(pdir, addr, true);
- if (pte == NULL) {
+ pte_t *pte = vm_getpte( pdir, addr, true );
+ if( pte == NULL ) {
// couldn't find it
return E_NO_PTE;
}
-#if 0 && TRACING_VM
- cio_printf( " addr %08x pa %08x last %08x pte %08x *pte %08x\n",
- (uint32_t) addr, pa, (uint32_t) last, (uint32_t) pte, *pte
- );
-#endif
-
- // create the new entry for the page table
- pde_t newpte = pa | perm | PTE_P;
// if this entry has already been mapped, we're in trouble
- if (IS_PRESENT(*pte)) {
- if (*pte != newpte) {
-#if TRACING_VM
- cio_printf(
- "vm_map: va %08x pa %08x pte %08x *pte %08x entry %08x\n",
- (uint32_t)va, pa, (uint32_t)pte, (uint32_t)*pte, newpte);
- cio_printf(" addr %08x PDIX 0x%x PTIX 0x%x\n", (uint32_t)addr,
- PDIX(addr), PTIX(addr));
-
- // dump the directory
- pmt_dump(pdir, true, PDIX(addr), 4);
+ if( IS_PRESENT(*pte) ) {
+ cio_printf( "vm_map(%08x,%08x,%u,%08x,%03x)\n",
+ (uint32_t) pdir, (uint32_t) va, size, pa, perm );
+ cio_printf( " addr %08x last %08x pte %08x *pte %08x\n",
+ (uint32_t) addr, (uint32_t) last,
+ (uint32_t) pte, *pte );
- // find the relevant PDE entry
- uint32_t ix = PDIX(va);
- pde_t entry = pdir[ix];
- if (!IS_LARGE(entry)) {
- // round the PMT index down
- uint32_t ix2 = PTIX(va) & MOD4_MASK;
- // dump the PMT for the relevant directory entry
- pmt_dump((void *)P2V(PDE_ADDR(entry)), false, ix2, 4);
- }
-#endif
- PANIC(0, "mapping an already-mapped address");
- }
+ PANIC( 0, "mapping an already-mapped address" );
}
// ok, set the PTE as requested
- *pte = newpte;
+ *pte = pa | perm | PTE_P;
// nope - move to the next page
addr += SZ_PAGE;
pa += SZ_PAGE;
+
}
return SUCCESS;
}
@@ -866,48 +569,48 @@ int vm_map(pde_t *pdir, void *va, uint32_t pa, uint32_t size, int perm)
** now have two sets of page tables that refer to the same physical
** frames in memory.
**
-** @param new New page directory
** @param old Existing page directory
+** @param new New page directory
**
** @return status of the duplication attempt
*/
-int vm_uvmdup(pde_t *new, pde_t *old)
-{
- if (old == NULL || new == NULL) {
+int vm_uvmdup( pde_t *old, pde_t *new ) {
+
+ if( old == NULL || new == NULL ) {
return E_BAD_PARAM;
}
-#if TRACING_VM
- cio_printf("vmdup: old %08x new %08x\n", (uint32_t)old, (uint32_t)new);
-#endif
-
// we only want to deal with the "user" half of the address space
- for (int i = 0; i < (N_PDE >> 1); ++i) {
+ for( int i = 0; i < (N_PDE >> 1); ++i ) {
+
// the entry to copy
pde_t entry = *old;
// is this entry in use?
- if (IS_PRESENT(entry)) {
+ if( IS_PRESENT(entry) ) {
+
// yes. if it points to a 4MB page, we just copy it;
// otherwise, we must duplicate the next level PMT
- if (!IS_LARGE(entry)) {
+ if( !IS_LARGE(entry) ) {
+
// it's a 4KB page, so we need to duplicate the PMT
- pte_t *newpt =
- (pte_t *)vm_pagedup((void *)P2V(PTE_ADDR(entry)));
- if (newpt == NULL) {
+ pte_t *newpt = (pte_t *) vm_pagedup( (void *)PTE_ADDR(entry) );
+ if( newpt == NULL ) {
return E_NO_MEMORY;
}
uint32_t perms = PERMS(entry);
// create the new PDE entry by replacing the frame #
- entry = ((uint32_t)V2P(PTE_ADDR(newpt))) | perms;
+ entry = ((uint32_t) newpt) | perms;
}
} else {
+
// not present, so create an empty entry
entry = 0;
+
}
// send it on its way
@@ -920,26 +623,3 @@ int vm_uvmdup(pde_t *new, pde_t *old)
return SUCCESS;
}
-
-/**
-** Name: vm_print
-**
-** Print out a paging hierarchy.
-**
-** @param pt Page table to display
-** @param dir Is it a page directory (vs. a page table)?
-** @param mode How to display the entries
-*/
-void vm_print(void *pt, bool_t dir, enum vmmode_e mode)
-{
- cio_puts("\nVM hierarchy");
- if (pt == NULL) {
- cio_puts(" (NULL pointer)\n");
- return;
- }
-
- cio_printf(", starting at 0x%08x (%s):\n", (uint32_t)pt,
- dir ? "PDIR" : "PMT");
-
- ptdump(1, pt, dir, mode);
-}
diff --git a/kernel/old/vmtables.c b/kernel/old/vmtables.c
index 113fd8b..a50315d 100644
--- a/kernel/old/vmtables.c
+++ b/kernel/old/vmtables.c
@@ -11,7 +11,7 @@
** 4MB of main memory.
*/
-#define KERNEL_SRC
+#define KERNEL_SRC
#include <common.h>
@@ -37,167 +37,146 @@ extern char _data[];
// identity-map 4MB virtual address #n to physical 4MB address #n
// used for addresses 0 to 2GB
-#define L(n) [n] = (pde_t)((TO_4MFRAME((n))) | (PDE_P | PDE_RW | PDE_PS))
+#define L(n) [n] = (pde_t) ( (TO_4MFRAME((n))) | (PDE_P|PDE_RW|PDE_PS) )
// ditto, but adds 512 (0x200) to the index
// used for addresses 2GB to 4GB
-#define M(n) \
- [n | 0x200] = (pde_t)((TO_4MFRAME((n))) | (PDE_P | PDE_RW | PDE_PS))
+#define M(n) [n|0x200] = (pde_t) ( (TO_4MFRAME((n))) | (PDE_P|PDE_RW|PDE_PS) )
ATTR_ALIGNED(SZ_PAGE)
const pde_t firstpdir[N_PDE] = {
// Map VA range [0, 2GB] to PA range [0, 2GB]
- L(0x000), L(0x001), L(0x002), L(0x003), L(0x004), L(0x005), L(0x006),
- L(0x007), L(0x008), L(0x009), L(0x00a), L(0x00b), L(0x00c), L(0x00d),
- L(0x00e), L(0x00f), L(0x010), L(0x011), L(0x012), L(0x013), L(0x014),
- L(0x015), L(0x016), L(0x017), L(0x018), L(0x019), L(0x01a), L(0x01b),
- L(0x01c), L(0x01d), L(0x01e), L(0x01f), L(0x020), L(0x021), L(0x022),
- L(0x023), L(0x024), L(0x025), L(0x026), L(0x027), L(0x028), L(0x029),
- L(0x02a), L(0x02b), L(0x02c), L(0x02d), L(0x02e), L(0x02f), L(0x030),
- L(0x031), L(0x032), L(0x033), L(0x034), L(0x035), L(0x036), L(0x037),
- L(0x038), L(0x039), L(0x03a), L(0x03b), L(0x03c), L(0x03d), L(0x03e),
- L(0x03f), L(0x040), L(0x041), L(0x042), L(0x043), L(0x044), L(0x045),
- L(0x046), L(0x047), L(0x048), L(0x049), L(0x04a), L(0x04b), L(0x04c),
- L(0x04d), L(0x04e), L(0x04f), L(0x050), L(0x051), L(0x052), L(0x053),
- L(0x054), L(0x055), L(0x056), L(0x057), L(0x058), L(0x059), L(0x05a),
- L(0x05b), L(0x05c), L(0x05d), L(0x05e), L(0x05f), L(0x060), L(0x061),
- L(0x062), L(0x063), L(0x064), L(0x065), L(0x066), L(0x067), L(0x068),
- L(0x069), L(0x06a), L(0x06b), L(0x06c), L(0x06d), L(0x06e), L(0x06f),
- L(0x070), L(0x071), L(0x072), L(0x073), L(0x074), L(0x075), L(0x076),
- L(0x077), L(0x078), L(0x079), L(0x07a), L(0x07b), L(0x07c), L(0x07d),
- L(0x07e), L(0x07f), L(0x080), L(0x081), L(0x082), L(0x083), L(0x084),
- L(0x085), L(0x086), L(0x087), L(0x088), L(0x089), L(0x08a), L(0x08b),
- L(0x08c), L(0x08d), L(0x08e), L(0x08f), L(0x090), L(0x091), L(0x092),
- L(0x093), L(0x094), L(0x095), L(0x096), L(0x097), L(0x098), L(0x099),
- L(0x09a), L(0x09b), L(0x09c), L(0x09d), L(0x09e), L(0x09f), L(0x0a0),
- L(0x0a1), L(0x0a2), L(0x0a3), L(0x0a4), L(0x0a5), L(0x0a6), L(0x0a7),
- L(0x0a8), L(0x0a9), L(0x0aa), L(0x0ab), L(0x0ac), L(0x0ad), L(0x0ae),
- L(0x0af), L(0x0b0), L(0x0b1), L(0x0b2), L(0x0b3), L(0x0b4), L(0x0b5),
- L(0x0b6), L(0x0b7), L(0x0b8), L(0x0b9), L(0x0ba), L(0x0bb), L(0x0bc),
- L(0x0bd), L(0x0be), L(0x0bf), L(0x0c0), L(0x0c1), L(0x0c2), L(0x0c3),
- L(0x0c4), L(0x0c5), L(0x0c6), L(0x0c7), L(0x0c8), L(0x0c9), L(0x0ca),
- L(0x0cb), L(0x0cc), L(0x0cd), L(0x0ce), L(0x0cf), L(0x0d0), L(0x0d1),
- L(0x0d2), L(0x0d3), L(0x0d4), L(0x0d5), L(0x0d6), L(0x0d7), L(0x0d8),
- L(0x0d9), L(0x0da), L(0x0db), L(0x0dc), L(0x0dd), L(0x0de), L(0x0df),
- L(0x0e0), L(0x0e1), L(0x0e2), L(0x0e3), L(0x0e4), L(0x0e5), L(0x0e6),
- L(0x0e7), L(0x0e8), L(0x0e9), L(0x0ea), L(0x0eb), L(0x0ec), L(0x0ed),
- L(0x0ee), L(0x0ef), L(0x0f0), L(0x0f1), L(0x0f2), L(0x0f3), L(0x0f4),
- L(0x0f5), L(0x0f6), L(0x0f7), L(0x0f8), L(0x0f9), L(0x0fa), L(0x0fb),
- L(0x0fc), L(0x0fd), L(0x0fe), L(0x0ff), L(0x100), L(0x101), L(0x102),
- L(0x103), L(0x104), L(0x105), L(0x106), L(0x107), L(0x108), L(0x109),
- L(0x10a), L(0x10b), L(0x10c), L(0x10d), L(0x10e), L(0x10f), L(0x110),
- L(0x111), L(0x112), L(0x113), L(0x114), L(0x115), L(0x116), L(0x117),
- L(0x118), L(0x119), L(0x11a), L(0x11b), L(0x11c), L(0x11d), L(0x11e),
- L(0x11f), L(0x120), L(0x121), L(0x122), L(0x123), L(0x124), L(0x125),
- L(0x126), L(0x127), L(0x128), L(0x129), L(0x12a), L(0x12b), L(0x12c),
- L(0x12d), L(0x12e), L(0x12f), L(0x130), L(0x131), L(0x132), L(0x133),
- L(0x134), L(0x135), L(0x136), L(0x137), L(0x138), L(0x139), L(0x13a),
- L(0x13b), L(0x13c), L(0x13d), L(0x13e), L(0x13f), L(0x140), L(0x141),
- L(0x142), L(0x143), L(0x144), L(0x145), L(0x146), L(0x147), L(0x148),
- L(0x149), L(0x14a), L(0x14b), L(0x14c), L(0x14d), L(0x14e), L(0x14f),
- L(0x150), L(0x151), L(0x152), L(0x153), L(0x154), L(0x155), L(0x156),
- L(0x157), L(0x158), L(0x159), L(0x15a), L(0x15b), L(0x15c), L(0x15d),
- L(0x15e), L(0x15f), L(0x160), L(0x161), L(0x162), L(0x163), L(0x164),
- L(0x165), L(0x166), L(0x167), L(0x168), L(0x169), L(0x16a), L(0x16b),
- L(0x16c), L(0x16d), L(0x16e), L(0x16f), L(0x170), L(0x171), L(0x172),
- L(0x173), L(0x174), L(0x175), L(0x176), L(0x177), L(0x178), L(0x179),
- L(0x17a), L(0x17b), L(0x17c), L(0x17d), L(0x17e), L(0x17f), L(0x180),
- L(0x181), L(0x182), L(0x183), L(0x184), L(0x185), L(0x186), L(0x187),
- L(0x188), L(0x189), L(0x18a), L(0x18b), L(0x18c), L(0x18d), L(0x18e),
- L(0x18f), L(0x190), L(0x191), L(0x192), L(0x193), L(0x194), L(0x195),
- L(0x196), L(0x197), L(0x198), L(0x199), L(0x19a), L(0x19b), L(0x19c),
- L(0x19d), L(0x19e), L(0x19f), L(0x1a0), L(0x1a1), L(0x1a2), L(0x1a3),
- L(0x1a4), L(0x1a5), L(0x1a6), L(0x1a7), L(0x1a8), L(0x1a9), L(0x1aa),
- L(0x1ab), L(0x1ac), L(0x1ad), L(0x1ae), L(0x1af), L(0x1b0), L(0x1b1),
- L(0x1b2), L(0x1b3), L(0x1b4), L(0x1b5), L(0x1b6), L(0x1b7), L(0x1b8),
- L(0x1b9), L(0x1ba), L(0x1bb), L(0x1bc), L(0x1bd), L(0x1be), L(0x1bf),
- L(0x1c0), L(0x1c1), L(0x1c2), L(0x1c3), L(0x1c4), L(0x1c5), L(0x1c6),
- L(0x1c7), L(0x1c8), L(0x1c9), L(0x1ca), L(0x1cb), L(0x1cc), L(0x1cd),
- L(0x1ce), L(0x1cf), L(0x1d0), L(0x1d1), L(0x1d2), L(0x1d3), L(0x1d4),
- L(0x1d5), L(0x1d6), L(0x1d7), L(0x1d8), L(0x1d9), L(0x1da), L(0x1db),
- L(0x1dc), L(0x1dd), L(0x1de), L(0x1df), L(0x1e0), L(0x1e1), L(0x1e2),
- L(0x1e3), L(0x1e4), L(0x1e5), L(0x1e6), L(0x1e7), L(0x1e8), L(0x1e9),
- L(0x1ea), L(0x1eb), L(0x1ec), L(0x1ed), L(0x1ee), L(0x1ef), L(0x1f0),
- L(0x1f1), L(0x1f2), L(0x1f3), L(0x1f4), L(0x1f5), L(0x1f6), L(0x1f7),
- L(0x1f8), L(0x1f9), L(0x1fa), L(0x1fb), L(0x1fc), L(0x1fd), L(0x1fe),
- L(0x1ff),
+L(0x000), L(0x001), L(0x002), L(0x003), L(0x004), L(0x005), L(0x006), L(0x007),
+L(0x008), L(0x009), L(0x00a), L(0x00b), L(0x00c), L(0x00d), L(0x00e), L(0x00f),
+L(0x010), L(0x011), L(0x012), L(0x013), L(0x014), L(0x015), L(0x016), L(0x017),
+L(0x018), L(0x019), L(0x01a), L(0x01b), L(0x01c), L(0x01d), L(0x01e), L(0x01f),
+L(0x020), L(0x021), L(0x022), L(0x023), L(0x024), L(0x025), L(0x026), L(0x027),
+L(0x028), L(0x029), L(0x02a), L(0x02b), L(0x02c), L(0x02d), L(0x02e), L(0x02f),
+L(0x030), L(0x031), L(0x032), L(0x033), L(0x034), L(0x035), L(0x036), L(0x037),
+L(0x038), L(0x039), L(0x03a), L(0x03b), L(0x03c), L(0x03d), L(0x03e), L(0x03f),
+L(0x040), L(0x041), L(0x042), L(0x043), L(0x044), L(0x045), L(0x046), L(0x047),
+L(0x048), L(0x049), L(0x04a), L(0x04b), L(0x04c), L(0x04d), L(0x04e), L(0x04f),
+L(0x050), L(0x051), L(0x052), L(0x053), L(0x054), L(0x055), L(0x056), L(0x057),
+L(0x058), L(0x059), L(0x05a), L(0x05b), L(0x05c), L(0x05d), L(0x05e), L(0x05f),
+L(0x060), L(0x061), L(0x062), L(0x063), L(0x064), L(0x065), L(0x066), L(0x067),
+L(0x068), L(0x069), L(0x06a), L(0x06b), L(0x06c), L(0x06d), L(0x06e), L(0x06f),
+L(0x070), L(0x071), L(0x072), L(0x073), L(0x074), L(0x075), L(0x076), L(0x077),
+L(0x078), L(0x079), L(0x07a), L(0x07b), L(0x07c), L(0x07d), L(0x07e), L(0x07f),
+L(0x080), L(0x081), L(0x082), L(0x083), L(0x084), L(0x085), L(0x086), L(0x087),
+L(0x088), L(0x089), L(0x08a), L(0x08b), L(0x08c), L(0x08d), L(0x08e), L(0x08f),
+L(0x090), L(0x091), L(0x092), L(0x093), L(0x094), L(0x095), L(0x096), L(0x097),
+L(0x098), L(0x099), L(0x09a), L(0x09b), L(0x09c), L(0x09d), L(0x09e), L(0x09f),
+L(0x0a0), L(0x0a1), L(0x0a2), L(0x0a3), L(0x0a4), L(0x0a5), L(0x0a6), L(0x0a7),
+L(0x0a8), L(0x0a9), L(0x0aa), L(0x0ab), L(0x0ac), L(0x0ad), L(0x0ae), L(0x0af),
+L(0x0b0), L(0x0b1), L(0x0b2), L(0x0b3), L(0x0b4), L(0x0b5), L(0x0b6), L(0x0b7),
+L(0x0b8), L(0x0b9), L(0x0ba), L(0x0bb), L(0x0bc), L(0x0bd), L(0x0be), L(0x0bf),
+L(0x0c0), L(0x0c1), L(0x0c2), L(0x0c3), L(0x0c4), L(0x0c5), L(0x0c6), L(0x0c7),
+L(0x0c8), L(0x0c9), L(0x0ca), L(0x0cb), L(0x0cc), L(0x0cd), L(0x0ce), L(0x0cf),
+L(0x0d0), L(0x0d1), L(0x0d2), L(0x0d3), L(0x0d4), L(0x0d5), L(0x0d6), L(0x0d7),
+L(0x0d8), L(0x0d9), L(0x0da), L(0x0db), L(0x0dc), L(0x0dd), L(0x0de), L(0x0df),
+L(0x0e0), L(0x0e1), L(0x0e2), L(0x0e3), L(0x0e4), L(0x0e5), L(0x0e6), L(0x0e7),
+L(0x0e8), L(0x0e9), L(0x0ea), L(0x0eb), L(0x0ec), L(0x0ed), L(0x0ee), L(0x0ef),
+L(0x0f0), L(0x0f1), L(0x0f2), L(0x0f3), L(0x0f4), L(0x0f5), L(0x0f6), L(0x0f7),
+L(0x0f8), L(0x0f9), L(0x0fa), L(0x0fb), L(0x0fc), L(0x0fd), L(0x0fe), L(0x0ff),
+L(0x100), L(0x101), L(0x102), L(0x103), L(0x104), L(0x105), L(0x106), L(0x107),
+L(0x108), L(0x109), L(0x10a), L(0x10b), L(0x10c), L(0x10d), L(0x10e), L(0x10f),
+L(0x110), L(0x111), L(0x112), L(0x113), L(0x114), L(0x115), L(0x116), L(0x117),
+L(0x118), L(0x119), L(0x11a), L(0x11b), L(0x11c), L(0x11d), L(0x11e), L(0x11f),
+L(0x120), L(0x121), L(0x122), L(0x123), L(0x124), L(0x125), L(0x126), L(0x127),
+L(0x128), L(0x129), L(0x12a), L(0x12b), L(0x12c), L(0x12d), L(0x12e), L(0x12f),
+L(0x130), L(0x131), L(0x132), L(0x133), L(0x134), L(0x135), L(0x136), L(0x137),
+L(0x138), L(0x139), L(0x13a), L(0x13b), L(0x13c), L(0x13d), L(0x13e), L(0x13f),
+L(0x140), L(0x141), L(0x142), L(0x143), L(0x144), L(0x145), L(0x146), L(0x147),
+L(0x148), L(0x149), L(0x14a), L(0x14b), L(0x14c), L(0x14d), L(0x14e), L(0x14f),
+L(0x150), L(0x151), L(0x152), L(0x153), L(0x154), L(0x155), L(0x156), L(0x157),
+L(0x158), L(0x159), L(0x15a), L(0x15b), L(0x15c), L(0x15d), L(0x15e), L(0x15f),
+L(0x160), L(0x161), L(0x162), L(0x163), L(0x164), L(0x165), L(0x166), L(0x167),
+L(0x168), L(0x169), L(0x16a), L(0x16b), L(0x16c), L(0x16d), L(0x16e), L(0x16f),
+L(0x170), L(0x171), L(0x172), L(0x173), L(0x174), L(0x175), L(0x176), L(0x177),
+L(0x178), L(0x179), L(0x17a), L(0x17b), L(0x17c), L(0x17d), L(0x17e), L(0x17f),
+L(0x180), L(0x181), L(0x182), L(0x183), L(0x184), L(0x185), L(0x186), L(0x187),
+L(0x188), L(0x189), L(0x18a), L(0x18b), L(0x18c), L(0x18d), L(0x18e), L(0x18f),
+L(0x190), L(0x191), L(0x192), L(0x193), L(0x194), L(0x195), L(0x196), L(0x197),
+L(0x198), L(0x199), L(0x19a), L(0x19b), L(0x19c), L(0x19d), L(0x19e), L(0x19f),
+L(0x1a0), L(0x1a1), L(0x1a2), L(0x1a3), L(0x1a4), L(0x1a5), L(0x1a6), L(0x1a7),
+L(0x1a8), L(0x1a9), L(0x1aa), L(0x1ab), L(0x1ac), L(0x1ad), L(0x1ae), L(0x1af),
+L(0x1b0), L(0x1b1), L(0x1b2), L(0x1b3), L(0x1b4), L(0x1b5), L(0x1b6), L(0x1b7),
+L(0x1b8), L(0x1b9), L(0x1ba), L(0x1bb), L(0x1bc), L(0x1bd), L(0x1be), L(0x1bf),
+L(0x1c0), L(0x1c1), L(0x1c2), L(0x1c3), L(0x1c4), L(0x1c5), L(0x1c6), L(0x1c7),
+L(0x1c8), L(0x1c9), L(0x1ca), L(0x1cb), L(0x1cc), L(0x1cd), L(0x1ce), L(0x1cf),
+L(0x1d0), L(0x1d1), L(0x1d2), L(0x1d3), L(0x1d4), L(0x1d5), L(0x1d6), L(0x1d7),
+L(0x1d8), L(0x1d9), L(0x1da), L(0x1db), L(0x1dc), L(0x1dd), L(0x1de), L(0x1df),
+L(0x1e0), L(0x1e1), L(0x1e2), L(0x1e3), L(0x1e4), L(0x1e5), L(0x1e6), L(0x1e7),
+L(0x1e8), L(0x1e9), L(0x1ea), L(0x1eb), L(0x1ec), L(0x1ed), L(0x1ee), L(0x1ef),
+L(0x1f0), L(0x1f1), L(0x1f2), L(0x1f3), L(0x1f4), L(0x1f5), L(0x1f6), L(0x1f7),
+L(0x1f8), L(0x1f9), L(0x1fa), L(0x1fb), L(0x1fc), L(0x1fd), L(0x1fe), L(0x1ff),
// Map VA range [2GB, 4GB] to PA range [0, 2MB]
- M(0x000), M(0x001), M(0x002), M(0x003), M(0x004), M(0x005), M(0x006),
- M(0x007), M(0x008), M(0x009), M(0x00a), M(0x00b), M(0x00c), M(0x00d),
- M(0x00e), M(0x00f), M(0x010), M(0x011), M(0x012), M(0x013), M(0x014),
- M(0x015), M(0x016), M(0x017), M(0x018), M(0x019), M(0x01a), M(0x01b),
- M(0x01c), M(0x01d), M(0x01e), M(0x01f), M(0x020), M(0x021), M(0x022),
- M(0x023), M(0x024), M(0x025), M(0x026), M(0x027), M(0x028), M(0x029),
- M(0x02a), M(0x02b), M(0x02c), M(0x02d), M(0x02e), M(0x02f), M(0x030),
- M(0x031), M(0x032), M(0x033), M(0x034), M(0x035), M(0x036), M(0x037),
- M(0x038), M(0x039), M(0x03a), M(0x03b), M(0x03c), M(0x03d), M(0x03e),
- M(0x03f), M(0x040), M(0x041), M(0x042), M(0x043), M(0x044), M(0x045),
- M(0x046), M(0x047), M(0x048), M(0x049), M(0x04a), M(0x04b), M(0x04c),
- M(0x04d), M(0x04e), M(0x04f), M(0x050), M(0x051), M(0x052), M(0x053),
- M(0x054), M(0x055), M(0x056), M(0x057), M(0x058), M(0x059), M(0x05a),
- M(0x05b), M(0x05c), M(0x05d), M(0x05e), M(0x05f), M(0x060), M(0x061),
- M(0x062), M(0x063), M(0x064), M(0x065), M(0x066), M(0x067), M(0x068),
- M(0x069), M(0x06a), M(0x06b), M(0x06c), M(0x06d), M(0x06e), M(0x06f),
- M(0x070), M(0x071), M(0x072), M(0x073), M(0x074), M(0x075), M(0x076),
- M(0x077), M(0x078), M(0x079), M(0x07a), M(0x07b), M(0x07c), M(0x07d),
- M(0x07e), M(0x07f), M(0x080), M(0x081), M(0x082), M(0x083), M(0x084),
- M(0x085), M(0x086), M(0x087), M(0x088), M(0x089), M(0x08a), M(0x08b),
- M(0x08c), M(0x08d), M(0x08e), M(0x08f), M(0x090), M(0x091), M(0x092),
- M(0x093), M(0x094), M(0x095), M(0x096), M(0x097), M(0x098), M(0x099),
- M(0x09a), M(0x09b), M(0x09c), M(0x09d), M(0x09e), M(0x09f), M(0x0a0),
- M(0x0a1), M(0x0a2), M(0x0a3), M(0x0a4), M(0x0a5), M(0x0a6), M(0x0a7),
- M(0x0a8), M(0x0a9), M(0x0aa), M(0x0ab), M(0x0ac), M(0x0ad), M(0x0ae),
- M(0x0af), M(0x0b0), M(0x0b1), M(0x0b2), M(0x0b3), M(0x0b4), M(0x0b5),
- M(0x0b6), M(0x0b7), M(0x0b8), M(0x0b9), M(0x0ba), M(0x0bb), M(0x0bc),
- M(0x0bd), M(0x0be), M(0x0bf), M(0x0c0), M(0x0c1), M(0x0c2), M(0x0c3),
- M(0x0c4), M(0x0c5), M(0x0c6), M(0x0c7), M(0x0c8), M(0x0c9), M(0x0ca),
- M(0x0cb), M(0x0cc), M(0x0cd), M(0x0ce), M(0x0cf), M(0x0d0), M(0x0d1),
- M(0x0d2), M(0x0d3), M(0x0d4), M(0x0d5), M(0x0d6), M(0x0d7), M(0x0d8),
- M(0x0d9), M(0x0da), M(0x0db), M(0x0dc), M(0x0dd), M(0x0de), M(0x0df),
- M(0x0e0), M(0x0e1), M(0x0e2), M(0x0e3), M(0x0e4), M(0x0e5), M(0x0e6),
- M(0x0e7), M(0x0e8), M(0x0e9), M(0x0ea), M(0x0eb), M(0x0ec), M(0x0ed),
- M(0x0ee), M(0x0ef), M(0x0f0), M(0x0f1), M(0x0f2), M(0x0f3), M(0x0f4),
- M(0x0f5), M(0x0f6), M(0x0f7), M(0x0f8), M(0x0f9), M(0x0fa), M(0x0fb),
- M(0x0fc), M(0x0fd), M(0x0fe), M(0x0ff), M(0x100), M(0x101), M(0x102),
- M(0x103), M(0x104), M(0x105), M(0x106), M(0x107), M(0x108), M(0x109),
- M(0x10a), M(0x10b), M(0x10c), M(0x10d), M(0x10e), M(0x10f), M(0x110),
- M(0x111), M(0x112), M(0x113), M(0x114), M(0x115), M(0x116), M(0x117),
- M(0x118), M(0x119), M(0x11a), M(0x11b), M(0x11c), M(0x11d), M(0x11e),
- M(0x11f), M(0x120), M(0x121), M(0x122), M(0x123), M(0x124), M(0x125),
- M(0x126), M(0x127), M(0x128), M(0x129), M(0x12a), M(0x12b), M(0x12c),
- M(0x12d), M(0x12e), M(0x12f), M(0x130), M(0x131), M(0x132), M(0x133),
- M(0x134), M(0x135), M(0x136), M(0x137), M(0x138), M(0x139), M(0x13a),
- M(0x13b), M(0x13c), M(0x13d), M(0x13e), M(0x13f), M(0x140), M(0x141),
- M(0x142), M(0x143), M(0x144), M(0x145), M(0x146), M(0x147), M(0x148),
- M(0x149), M(0x14a), M(0x14b), M(0x14c), M(0x14d), M(0x14e), M(0x14f),
- M(0x150), M(0x151), M(0x152), M(0x153), M(0x154), M(0x155), M(0x156),
- M(0x157), M(0x158), M(0x159), M(0x15a), M(0x15b), M(0x15c), M(0x15d),
- M(0x15e), M(0x15f), M(0x160), M(0x161), M(0x162), M(0x163), M(0x164),
- M(0x165), M(0x166), M(0x167), M(0x168), M(0x169), M(0x16a), M(0x16b),
- M(0x16c), M(0x16d), M(0x16e), M(0x16f), M(0x170), M(0x171), M(0x172),
- M(0x173), M(0x174), M(0x175), M(0x176), M(0x177), M(0x178), M(0x179),
- M(0x17a), M(0x17b), M(0x17c), M(0x17d), M(0x17e), M(0x17f), M(0x180),
- M(0x181), M(0x182), M(0x183), M(0x184), M(0x185), M(0x186), M(0x187),
- M(0x188), M(0x189), M(0x18a), M(0x18b), M(0x18c), M(0x18d), M(0x18e),
- M(0x18f), M(0x190), M(0x191), M(0x192), M(0x193), M(0x194), M(0x195),
- M(0x196), M(0x197), M(0x198), M(0x199), M(0x19a), M(0x19b), M(0x19c),
- M(0x19d), M(0x19e), M(0x19f), M(0x1a0), M(0x1a1), M(0x1a2), M(0x1a3),
- M(0x1a4), M(0x1a5), M(0x1a6), M(0x1a7), M(0x1a8), M(0x1a9), M(0x1aa),
- M(0x1ab), M(0x1ac), M(0x1ad), M(0x1ae), M(0x1af), M(0x1b0), M(0x1b1),
- M(0x1b2), M(0x1b3), M(0x1b4), M(0x1b5), M(0x1b6), M(0x1b7), M(0x1b8),
- M(0x1b9), M(0x1ba), M(0x1bb), M(0x1bc), M(0x1bd), M(0x1be), M(0x1bf),
- M(0x1c0), M(0x1c1), M(0x1c2), M(0x1c3), M(0x1c4), M(0x1c5), M(0x1c6),
- M(0x1c7), M(0x1c8), M(0x1c9), M(0x1ca), M(0x1cb), M(0x1cc), M(0x1cd),
- M(0x1ce), M(0x1cf), M(0x1d0), M(0x1d1), M(0x1d2), M(0x1d3), M(0x1d4),
- M(0x1d5), M(0x1d6), M(0x1d7), M(0x1d8), M(0x1d9), M(0x1da), M(0x1db),
- M(0x1dc), M(0x1dd), M(0x1de), M(0x1df), M(0x1e0), M(0x1e1), M(0x1e2),
- M(0x1e3), M(0x1e4), M(0x1e5), M(0x1e6), M(0x1e7), M(0x1e8), M(0x1e9),
- M(0x1ea), M(0x1eb), M(0x1ec), M(0x1ed), M(0x1ee), M(0x1ef), M(0x1f0),
- M(0x1f1), M(0x1f2), M(0x1f3), M(0x1f4), M(0x1f5), M(0x1f6), M(0x1f7),
- M(0x1f8), M(0x1f9), M(0x1fa), M(0x1fb), M(0x1fc), M(0x1fd), M(0x1fe),
- M(0x1ff)
+M(0x000), M(0x001), M(0x002), M(0x003), M(0x004), M(0x005), M(0x006), M(0x007),
+M(0x008), M(0x009), M(0x00a), M(0x00b), M(0x00c), M(0x00d), M(0x00e), M(0x00f),
+M(0x010), M(0x011), M(0x012), M(0x013), M(0x014), M(0x015), M(0x016), M(0x017),
+M(0x018), M(0x019), M(0x01a), M(0x01b), M(0x01c), M(0x01d), M(0x01e), M(0x01f),
+M(0x020), M(0x021), M(0x022), M(0x023), M(0x024), M(0x025), M(0x026), M(0x027),
+M(0x028), M(0x029), M(0x02a), M(0x02b), M(0x02c), M(0x02d), M(0x02e), M(0x02f),
+M(0x030), M(0x031), M(0x032), M(0x033), M(0x034), M(0x035), M(0x036), M(0x037),
+M(0x038), M(0x039), M(0x03a), M(0x03b), M(0x03c), M(0x03d), M(0x03e), M(0x03f),
+M(0x040), M(0x041), M(0x042), M(0x043), M(0x044), M(0x045), M(0x046), M(0x047),
+M(0x048), M(0x049), M(0x04a), M(0x04b), M(0x04c), M(0x04d), M(0x04e), M(0x04f),
+M(0x050), M(0x051), M(0x052), M(0x053), M(0x054), M(0x055), M(0x056), M(0x057),
+M(0x058), M(0x059), M(0x05a), M(0x05b), M(0x05c), M(0x05d), M(0x05e), M(0x05f),
+M(0x060), M(0x061), M(0x062), M(0x063), M(0x064), M(0x065), M(0x066), M(0x067),
+M(0x068), M(0x069), M(0x06a), M(0x06b), M(0x06c), M(0x06d), M(0x06e), M(0x06f),
+M(0x070), M(0x071), M(0x072), M(0x073), M(0x074), M(0x075), M(0x076), M(0x077),
+M(0x078), M(0x079), M(0x07a), M(0x07b), M(0x07c), M(0x07d), M(0x07e), M(0x07f),
+M(0x080), M(0x081), M(0x082), M(0x083), M(0x084), M(0x085), M(0x086), M(0x087),
+M(0x088), M(0x089), M(0x08a), M(0x08b), M(0x08c), M(0x08d), M(0x08e), M(0x08f),
+M(0x090), M(0x091), M(0x092), M(0x093), M(0x094), M(0x095), M(0x096), M(0x097),
+M(0x098), M(0x099), M(0x09a), M(0x09b), M(0x09c), M(0x09d), M(0x09e), M(0x09f),
+M(0x0a0), M(0x0a1), M(0x0a2), M(0x0a3), M(0x0a4), M(0x0a5), M(0x0a6), M(0x0a7),
+M(0x0a8), M(0x0a9), M(0x0aa), M(0x0ab), M(0x0ac), M(0x0ad), M(0x0ae), M(0x0af),
+M(0x0b0), M(0x0b1), M(0x0b2), M(0x0b3), M(0x0b4), M(0x0b5), M(0x0b6), M(0x0b7),
+M(0x0b8), M(0x0b9), M(0x0ba), M(0x0bb), M(0x0bc), M(0x0bd), M(0x0be), M(0x0bf),
+M(0x0c0), M(0x0c1), M(0x0c2), M(0x0c3), M(0x0c4), M(0x0c5), M(0x0c6), M(0x0c7),
+M(0x0c8), M(0x0c9), M(0x0ca), M(0x0cb), M(0x0cc), M(0x0cd), M(0x0ce), M(0x0cf),
+M(0x0d0), M(0x0d1), M(0x0d2), M(0x0d3), M(0x0d4), M(0x0d5), M(0x0d6), M(0x0d7),
+M(0x0d8), M(0x0d9), M(0x0da), M(0x0db), M(0x0dc), M(0x0dd), M(0x0de), M(0x0df),
+M(0x0e0), M(0x0e1), M(0x0e2), M(0x0e3), M(0x0e4), M(0x0e5), M(0x0e6), M(0x0e7),
+M(0x0e8), M(0x0e9), M(0x0ea), M(0x0eb), M(0x0ec), M(0x0ed), M(0x0ee), M(0x0ef),
+M(0x0f0), M(0x0f1), M(0x0f2), M(0x0f3), M(0x0f4), M(0x0f5), M(0x0f6), M(0x0f7),
+M(0x0f8), M(0x0f9), M(0x0fa), M(0x0fb), M(0x0fc), M(0x0fd), M(0x0fe), M(0x0ff),
+M(0x100), M(0x101), M(0x102), M(0x103), M(0x104), M(0x105), M(0x106), M(0x107),
+M(0x108), M(0x109), M(0x10a), M(0x10b), M(0x10c), M(0x10d), M(0x10e), M(0x10f),
+M(0x110), M(0x111), M(0x112), M(0x113), M(0x114), M(0x115), M(0x116), M(0x117),
+M(0x118), M(0x119), M(0x11a), M(0x11b), M(0x11c), M(0x11d), M(0x11e), M(0x11f),
+M(0x120), M(0x121), M(0x122), M(0x123), M(0x124), M(0x125), M(0x126), M(0x127),
+M(0x128), M(0x129), M(0x12a), M(0x12b), M(0x12c), M(0x12d), M(0x12e), M(0x12f),
+M(0x130), M(0x131), M(0x132), M(0x133), M(0x134), M(0x135), M(0x136), M(0x137),
+M(0x138), M(0x139), M(0x13a), M(0x13b), M(0x13c), M(0x13d), M(0x13e), M(0x13f),
+M(0x140), M(0x141), M(0x142), M(0x143), M(0x144), M(0x145), M(0x146), M(0x147),
+M(0x148), M(0x149), M(0x14a), M(0x14b), M(0x14c), M(0x14d), M(0x14e), M(0x14f),
+M(0x150), M(0x151), M(0x152), M(0x153), M(0x154), M(0x155), M(0x156), M(0x157),
+M(0x158), M(0x159), M(0x15a), M(0x15b), M(0x15c), M(0x15d), M(0x15e), M(0x15f),
+M(0x160), M(0x161), M(0x162), M(0x163), M(0x164), M(0x165), M(0x166), M(0x167),
+M(0x168), M(0x169), M(0x16a), M(0x16b), M(0x16c), M(0x16d), M(0x16e), M(0x16f),
+M(0x170), M(0x171), M(0x172), M(0x173), M(0x174), M(0x175), M(0x176), M(0x177),
+M(0x178), M(0x179), M(0x17a), M(0x17b), M(0x17c), M(0x17d), M(0x17e), M(0x17f),
+M(0x180), M(0x181), M(0x182), M(0x183), M(0x184), M(0x185), M(0x186), M(0x187),
+M(0x188), M(0x189), M(0x18a), M(0x18b), M(0x18c), M(0x18d), M(0x18e), M(0x18f),
+M(0x190), M(0x191), M(0x192), M(0x193), M(0x194), M(0x195), M(0x196), M(0x197),
+M(0x198), M(0x199), M(0x19a), M(0x19b), M(0x19c), M(0x19d), M(0x19e), M(0x19f),
+M(0x1a0), M(0x1a1), M(0x1a2), M(0x1a3), M(0x1a4), M(0x1a5), M(0x1a6), M(0x1a7),
+M(0x1a8), M(0x1a9), M(0x1aa), M(0x1ab), M(0x1ac), M(0x1ad), M(0x1ae), M(0x1af),
+M(0x1b0), M(0x1b1), M(0x1b2), M(0x1b3), M(0x1b4), M(0x1b5), M(0x1b6), M(0x1b7),
+M(0x1b8), M(0x1b9), M(0x1ba), M(0x1bb), M(0x1bc), M(0x1bd), M(0x1be), M(0x1bf),
+M(0x1c0), M(0x1c1), M(0x1c2), M(0x1c3), M(0x1c4), M(0x1c5), M(0x1c6), M(0x1c7),
+M(0x1c8), M(0x1c9), M(0x1ca), M(0x1cb), M(0x1cc), M(0x1cd), M(0x1ce), M(0x1cf),
+M(0x1d0), M(0x1d1), M(0x1d2), M(0x1d3), M(0x1d4), M(0x1d5), M(0x1d6), M(0x1d7),
+M(0x1d8), M(0x1d9), M(0x1da), M(0x1db), M(0x1dc), M(0x1dd), M(0x1de), M(0x1df),
+M(0x1e0), M(0x1e1), M(0x1e2), M(0x1e3), M(0x1e4), M(0x1e5), M(0x1e6), M(0x1e7),
+M(0x1e8), M(0x1e9), M(0x1ea), M(0x1eb), M(0x1ec), M(0x1ed), M(0x1ee), M(0x1ef),
+M(0x1f0), M(0x1f1), M(0x1f2), M(0x1f3), M(0x1f4), M(0x1f5), M(0x1f6), M(0x1f7),
+M(0x1f8), M(0x1f9), M(0x1fa), M(0x1fb), M(0x1fc), M(0x1fd), M(0x1fe), M(0x1ff)
};
#ifdef MAKE_IDENTITY_MAP
@@ -212,170 +191,148 @@ const pde_t firstpdir[N_PDE] = {
*/
// identity-map 4KB page #n
-#define S(n) [n] = (pte_t)((TO_4KFRAME((n))) | (PTE_P | PTE_RW))
+#define S(n) [n] = (pte_t) ( (TO_4KFRAME((n))) | (PTE_P|PTE_RW) )
const pte_t id_map[N_PTE] = {
- S(0x000), S(0x001), S(0x002), S(0x003), S(0x004), S(0x005), S(0x006),
- S(0x007), S(0x008), S(0x009), S(0x00a), S(0x00b), S(0x00c), S(0x00d),
- S(0x00e), S(0x00f), S(0x010), S(0x011), S(0x012), S(0x013), S(0x014),
- S(0x015), S(0x016), S(0x017), S(0x018), S(0x019), S(0x01a), S(0x01b),
- S(0x01c), S(0x01d), S(0x01e), S(0x01f), S(0x020), S(0x021), S(0x022),
- S(0x023), S(0x024), S(0x025), S(0x026), S(0x027), S(0x028), S(0x029),
- S(0x02a), S(0x02b), S(0x02c), S(0x02d), S(0x02e), S(0x02f), S(0x030),
- S(0x031), S(0x032), S(0x033), S(0x034), S(0x035), S(0x036), S(0x037),
- S(0x038), S(0x039), S(0x03a), S(0x03b), S(0x03c), S(0x03d), S(0x03e),
- S(0x03f), S(0x040), S(0x041), S(0x042), S(0x043), S(0x044), S(0x045),
- S(0x046), S(0x047), S(0x048), S(0x049), S(0x04a), S(0x04b), S(0x04c),
- S(0x04d), S(0x04e), S(0x04f), S(0x050), S(0x051), S(0x052), S(0x053),
- S(0x054), S(0x055), S(0x056), S(0x057), S(0x058), S(0x059), S(0x05a),
- S(0x05b), S(0x05c), S(0x05d), S(0x05e), S(0x05f), S(0x060), S(0x061),
- S(0x062), S(0x063), S(0x064), S(0x065), S(0x066), S(0x067), S(0x068),
- S(0x069), S(0x06a), S(0x06b), S(0x06c), S(0x06d), S(0x06e), S(0x06f),
- S(0x070), S(0x071), S(0x072), S(0x073), S(0x074), S(0x075), S(0x076),
- S(0x077), S(0x078), S(0x079), S(0x07a), S(0x07b), S(0x07c), S(0x07d),
- S(0x07e), S(0x07f), S(0x080), S(0x081), S(0x082), S(0x083), S(0x084),
- S(0x085), S(0x086), S(0x087), S(0x088), S(0x089), S(0x08a), S(0x08b),
- S(0x08c), S(0x08d), S(0x08e), S(0x08f), S(0x090), S(0x091), S(0x092),
- S(0x093), S(0x094), S(0x095), S(0x096), S(0x097), S(0x098), S(0x099),
- S(0x09a), S(0x09b), S(0x09c), S(0x09d), S(0x09e), S(0x09f), S(0x0a0),
- S(0x0a1), S(0x0a2), S(0x0a3), S(0x0a4), S(0x0a5), S(0x0a6), S(0x0a7),
- S(0x0a8), S(0x0a9), S(0x0aa), S(0x0ab), S(0x0ac), S(0x0ad), S(0x0ae),
- S(0x0af), S(0x0b0), S(0x0b1), S(0x0b2), S(0x0b3), S(0x0b4), S(0x0b5),
- S(0x0b6), S(0x0b7), S(0x0b8), S(0x0b9), S(0x0ba), S(0x0bb), S(0x0bc),
- S(0x0bd), S(0x0be), S(0x0bf), S(0x0c0), S(0x0c1), S(0x0c2), S(0x0c3),
- S(0x0c4), S(0x0c5), S(0x0c6), S(0x0c7), S(0x0c8), S(0x0c9), S(0x0ca),
- S(0x0cb), S(0x0cc), S(0x0cd), S(0x0ce), S(0x0cf), S(0x0d0), S(0x0d1),
- S(0x0d2), S(0x0d3), S(0x0d4), S(0x0d5), S(0x0d6), S(0x0d7), S(0x0d8),
- S(0x0d9), S(0x0da), S(0x0db), S(0x0dc), S(0x0dd), S(0x0de), S(0x0df),
- S(0x0e0), S(0x0e1), S(0x0e2), S(0x0e3), S(0x0e4), S(0x0e5), S(0x0e6),
- S(0x0e7), S(0x0e8), S(0x0e9), S(0x0ea), S(0x0eb), S(0x0ec), S(0x0ed),
- S(0x0ee), S(0x0ef), S(0x0f0), S(0x0f1), S(0x0f2), S(0x0f3), S(0x0f4),
- S(0x0f5), S(0x0f6), S(0x0f7), S(0x0f8), S(0x0f9), S(0x0fa), S(0x0fb),
- S(0x0fc), S(0x0fd), S(0x0fe), S(0x0ff), S(0x100), S(0x101), S(0x102),
- S(0x103), S(0x104), S(0x105), S(0x106), S(0x107), S(0x108), S(0x109),
- S(0x10a), S(0x10b), S(0x10c), S(0x10d), S(0x10e), S(0x10f), S(0x110),
- S(0x111), S(0x112), S(0x113), S(0x114), S(0x115), S(0x116), S(0x117),
- S(0x118), S(0x119), S(0x11a), S(0x11b), S(0x11c), S(0x11d), S(0x11e),
- S(0x11f), S(0x120), S(0x121), S(0x122), S(0x123), S(0x124), S(0x125),
- S(0x126), S(0x127), S(0x128), S(0x129), S(0x12a), S(0x12b), S(0x12c),
- S(0x12d), S(0x12e), S(0x12f), S(0x130), S(0x131), S(0x132), S(0x133),
- S(0x134), S(0x135), S(0x136), S(0x137), S(0x138), S(0x139), S(0x13a),
- S(0x13b), S(0x13c), S(0x13d), S(0x13e), S(0x13f), S(0x140), S(0x141),
- S(0x142), S(0x143), S(0x144), S(0x145), S(0x146), S(0x147), S(0x148),
- S(0x149), S(0x14a), S(0x14b), S(0x14c), S(0x14d), S(0x14e), S(0x14f),
- S(0x150), S(0x151), S(0x152), S(0x153), S(0x154), S(0x155), S(0x156),
- S(0x157), S(0x158), S(0x159), S(0x15a), S(0x15b), S(0x15c), S(0x15d),
- S(0x15e), S(0x15f), S(0x160), S(0x161), S(0x162), S(0x163), S(0x164),
- S(0x165), S(0x166), S(0x167), S(0x168), S(0x169), S(0x16a), S(0x16b),
- S(0x16c), S(0x16d), S(0x16e), S(0x16f), S(0x170), S(0x171), S(0x172),
- S(0x173), S(0x174), S(0x175), S(0x176), S(0x177), S(0x178), S(0x179),
- S(0x17a), S(0x17b), S(0x17c), S(0x17d), S(0x17e), S(0x17f), S(0x180),
- S(0x181), S(0x182), S(0x183), S(0x184), S(0x185), S(0x186), S(0x187),
- S(0x188), S(0x189), S(0x18a), S(0x18b), S(0x18c), S(0x18d), S(0x18e),
- S(0x18f), S(0x190), S(0x191), S(0x192), S(0x193), S(0x194), S(0x195),
- S(0x196), S(0x197), S(0x198), S(0x199), S(0x19a), S(0x19b), S(0x19c),
- S(0x19d), S(0x19e), S(0x19f), S(0x1a0), S(0x1a1), S(0x1a2), S(0x1a3),
- S(0x1a4), S(0x1a5), S(0x1a6), S(0x1a7), S(0x1a8), S(0x1a9), S(0x1aa),
- S(0x1ab), S(0x1ac), S(0x1ad), S(0x1ae), S(0x1af), S(0x1b0), S(0x1b1),
- S(0x1b2), S(0x1b3), S(0x1b4), S(0x1b5), S(0x1b6), S(0x1b7), S(0x1b8),
- S(0x1b9), S(0x1ba), S(0x1bb), S(0x1bc), S(0x1bd), S(0x1be), S(0x1bf),
- S(0x1c0), S(0x1c1), S(0x1c2), S(0x1c3), S(0x1c4), S(0x1c5), S(0x1c6),
- S(0x1c7), S(0x1c8), S(0x1c9), S(0x1ca), S(0x1cb), S(0x1cc), S(0x1cd),
- S(0x1ce), S(0x1cf), S(0x1d0), S(0x1d1), S(0x1d2), S(0x1d3), S(0x1d4),
- S(0x1d5), S(0x1d6), S(0x1d7), S(0x1d8), S(0x1d9), S(0x1da), S(0x1db),
- S(0x1dc), S(0x1dd), S(0x1de), S(0x1df), S(0x1e0), S(0x1e1), S(0x1e2),
- S(0x1e3), S(0x1e4), S(0x1e5), S(0x1e6), S(0x1e7), S(0x1e8), S(0x1e9),
- S(0x1ea), S(0x1eb), S(0x1ec), S(0x1ed), S(0x1ee), S(0x1ef), S(0x1f0),
- S(0x1f1), S(0x1f2), S(0x1f3), S(0x1f4), S(0x1f5), S(0x1f6), S(0x1f7),
- S(0x1f8), S(0x1f9), S(0x1fa), S(0x1fb), S(0x1fc), S(0x1fd), S(0x1fe),
- S(0x1ff), S(0x200), S(0x201), S(0x202), S(0x203), S(0x204), S(0x205),
- S(0x206), S(0x207), S(0x208), S(0x209), S(0x20a), S(0x20b), S(0x20c),
- S(0x20d), S(0x20e), S(0x20f), S(0x210), S(0x211), S(0x212), S(0x213),
- S(0x214), S(0x215), S(0x216), S(0x217), S(0x218), S(0x219), S(0x21a),
- S(0x21b), S(0x21c), S(0x21d), S(0x21e), S(0x21f), S(0x220), S(0x221),
- S(0x222), S(0x223), S(0x224), S(0x225), S(0x226), S(0x227), S(0x228),
- S(0x229), S(0x22a), S(0x22b), S(0x22c), S(0x22d), S(0x22e), S(0x22f),
- S(0x230), S(0x231), S(0x232), S(0x233), S(0x234), S(0x235), S(0x236),
- S(0x237), S(0x238), S(0x239), S(0x23a), S(0x23b), S(0x23c), S(0x23d),
- S(0x23e), S(0x23f), S(0x240), S(0x241), S(0x242), S(0x243), S(0x244),
- S(0x245), S(0x246), S(0x247), S(0x248), S(0x249), S(0x24a), S(0x24b),
- S(0x24c), S(0x24d), S(0x24e), S(0x24f), S(0x250), S(0x251), S(0x252),
- S(0x253), S(0x254), S(0x255), S(0x256), S(0x257), S(0x258), S(0x259),
- S(0x25a), S(0x25b), S(0x25c), S(0x25d), S(0x25e), S(0x25f), S(0x260),
- S(0x261), S(0x262), S(0x263), S(0x264), S(0x265), S(0x266), S(0x267),
- S(0x268), S(0x269), S(0x26a), S(0x26b), S(0x26c), S(0x26d), S(0x26e),
- S(0x26f), S(0x270), S(0x271), S(0x272), S(0x273), S(0x274), S(0x275),
- S(0x276), S(0x277), S(0x278), S(0x279), S(0x27a), S(0x27b), S(0x27c),
- S(0x27d), S(0x27e), S(0x27f), S(0x280), S(0x281), S(0x282), S(0x283),
- S(0x284), S(0x285), S(0x286), S(0x287), S(0x288), S(0x289), S(0x28a),
- S(0x28b), S(0x28c), S(0x28d), S(0x28e), S(0x28f), S(0x290), S(0x291),
- S(0x292), S(0x293), S(0x294), S(0x295), S(0x296), S(0x297), S(0x298),
- S(0x299), S(0x29a), S(0x29b), S(0x29c), S(0x29d), S(0x29e), S(0x29f),
- S(0x2a0), S(0x2a1), S(0x2a2), S(0x2a3), S(0x2a4), S(0x2a5), S(0x2a6),
- S(0x2a7), S(0x2a8), S(0x2a9), S(0x2aa), S(0x2ab), S(0x2ac), S(0x2ad),
- S(0x2ae), S(0x2af), S(0x2b0), S(0x2b1), S(0x2b2), S(0x2b3), S(0x2b4),
- S(0x2b5), S(0x2b6), S(0x2b7), S(0x2b8), S(0x2b9), S(0x2ba), S(0x2bb),
- S(0x2bc), S(0x2bd), S(0x2be), S(0x2bf), S(0x2c0), S(0x2c1), S(0x2c2),
- S(0x2c3), S(0x2c4), S(0x2c5), S(0x2c6), S(0x2c7), S(0x2c8), S(0x2c9),
- S(0x2ca), S(0x2cb), S(0x2cc), S(0x2cd), S(0x2ce), S(0x2cf), S(0x2d0),
- S(0x2d1), S(0x2d2), S(0x2d3), S(0x2d4), S(0x2d5), S(0x2d6), S(0x2d7),
- S(0x2d8), S(0x2d9), S(0x2da), S(0x2db), S(0x2dc), S(0x2dd), S(0x2de),
- S(0x2df), S(0x2e0), S(0x2e1), S(0x2e2), S(0x2e3), S(0x2e4), S(0x2e5),
- S(0x2e6), S(0x2e7), S(0x2e8), S(0x2e9), S(0x2ea), S(0x2eb), S(0x2ec),
- S(0x2ed), S(0x2ee), S(0x2ef), S(0x2f0), S(0x2f1), S(0x2f2), S(0x2f3),
- S(0x2f4), S(0x2f5), S(0x2f6), S(0x2f7), S(0x2f8), S(0x2f9), S(0x2fa),
- S(0x2fb), S(0x2fc), S(0x2fd), S(0x2fe), S(0x2ff), S(0x300), S(0x301),
- S(0x302), S(0x303), S(0x304), S(0x305), S(0x306), S(0x307), S(0x308),
- S(0x309), S(0x30a), S(0x30b), S(0x30c), S(0x30d), S(0x30e), S(0x30f),
- S(0x310), S(0x311), S(0x312), S(0x313), S(0x314), S(0x315), S(0x316),
- S(0x317), S(0x318), S(0x319), S(0x31a), S(0x31b), S(0x31c), S(0x31d),
- S(0x31e), S(0x31f), S(0x320), S(0x321), S(0x322), S(0x323), S(0x324),
- S(0x325), S(0x326), S(0x327), S(0x328), S(0x329), S(0x32a), S(0x32b),
- S(0x32c), S(0x32d), S(0x32e), S(0x32f), S(0x330), S(0x331), S(0x332),
- S(0x333), S(0x334), S(0x335), S(0x336), S(0x337), S(0x338), S(0x339),
- S(0x33a), S(0x33b), S(0x33c), S(0x33d), S(0x33e), S(0x33f), S(0x340),
- S(0x341), S(0x342), S(0x343), S(0x344), S(0x345), S(0x346), S(0x347),
- S(0x348), S(0x349), S(0x34a), S(0x34b), S(0x34c), S(0x34d), S(0x34e),
- S(0x34f), S(0x350), S(0x351), S(0x352), S(0x353), S(0x354), S(0x355),
- S(0x356), S(0x357), S(0x358), S(0x359), S(0x35a), S(0x35b), S(0x35c),
- S(0x35d), S(0x35e), S(0x35f), S(0x360), S(0x361), S(0x362), S(0x363),
- S(0x364), S(0x365), S(0x366), S(0x367), S(0x368), S(0x369), S(0x36a),
- S(0x36b), S(0x36c), S(0x36d), S(0x36e), S(0x36f), S(0x370), S(0x371),
- S(0x372), S(0x373), S(0x374), S(0x375), S(0x376), S(0x377), S(0x378),
- S(0x379), S(0x37a), S(0x37b), S(0x37c), S(0x37d), S(0x37e), S(0x37f),
- S(0x380), S(0x381), S(0x382), S(0x383), S(0x384), S(0x385), S(0x386),
- S(0x387), S(0x388), S(0x389), S(0x38a), S(0x38b), S(0x38c), S(0x38d),
- S(0x38e), S(0x38f), S(0x390), S(0x391), S(0x392), S(0x393), S(0x394),
- S(0x395), S(0x396), S(0x397), S(0x398), S(0x399), S(0x39a), S(0x39b),
- S(0x39c), S(0x39d), S(0x39e), S(0x39f), S(0x3a0), S(0x3a1), S(0x3a2),
- S(0x3a3), S(0x3a4), S(0x3a5), S(0x3a6), S(0x3a7), S(0x3a8), S(0x3a9),
- S(0x3aa), S(0x3ab), S(0x3ac), S(0x3ad), S(0x3ae), S(0x3af), S(0x3b0),
- S(0x3b1), S(0x3b2), S(0x3b3), S(0x3b4), S(0x3b5), S(0x3b6), S(0x3b7),
- S(0x3b8), S(0x3b9), S(0x3ba), S(0x3bb), S(0x3bc), S(0x3bd), S(0x3be),
- S(0x3bf), S(0x3c0), S(0x3c1), S(0x3c2), S(0x3c3), S(0x3c4), S(0x3c5),
- S(0x3c6), S(0x3c7), S(0x3c8), S(0x3c9), S(0x3ca), S(0x3cb), S(0x3cc),
- S(0x3cd), S(0x3ce), S(0x3cf), S(0x3d0), S(0x3d1), S(0x3d2), S(0x3d3),
- S(0x3d4), S(0x3d5), S(0x3d6), S(0x3d7), S(0x3d8), S(0x3d9), S(0x3da),
- S(0x3db), S(0x3dc), S(0x3dd), S(0x3de), S(0x3df), S(0x3e0), S(0x3e1),
- S(0x3e2), S(0x3e3), S(0x3e4), S(0x3e5), S(0x3e6), S(0x3e7), S(0x3e8),
- S(0x3e9), S(0x3ea), S(0x3eb), S(0x3ec), S(0x3ed), S(0x3ee), S(0x3ef),
- S(0x3f0), S(0x3f1), S(0x3f2), S(0x3f3), S(0x3f4), S(0x3f5), S(0x3f6),
- S(0x3f7), S(0x3f8), S(0x3f9), S(0x3fa), S(0x3fb), S(0x3fc), S(0x3fd),
- S(0x3fe), S(0x3ff)
+S(0x000), S(0x001), S(0x002), S(0x003), S(0x004), S(0x005), S(0x006), S(0x007),
+S(0x008), S(0x009), S(0x00a), S(0x00b), S(0x00c), S(0x00d), S(0x00e), S(0x00f),
+S(0x010), S(0x011), S(0x012), S(0x013), S(0x014), S(0x015), S(0x016), S(0x017),
+S(0x018), S(0x019), S(0x01a), S(0x01b), S(0x01c), S(0x01d), S(0x01e), S(0x01f),
+S(0x020), S(0x021), S(0x022), S(0x023), S(0x024), S(0x025), S(0x026), S(0x027),
+S(0x028), S(0x029), S(0x02a), S(0x02b), S(0x02c), S(0x02d), S(0x02e), S(0x02f),
+S(0x030), S(0x031), S(0x032), S(0x033), S(0x034), S(0x035), S(0x036), S(0x037),
+S(0x038), S(0x039), S(0x03a), S(0x03b), S(0x03c), S(0x03d), S(0x03e), S(0x03f),
+S(0x040), S(0x041), S(0x042), S(0x043), S(0x044), S(0x045), S(0x046), S(0x047),
+S(0x048), S(0x049), S(0x04a), S(0x04b), S(0x04c), S(0x04d), S(0x04e), S(0x04f),
+S(0x050), S(0x051), S(0x052), S(0x053), S(0x054), S(0x055), S(0x056), S(0x057),
+S(0x058), S(0x059), S(0x05a), S(0x05b), S(0x05c), S(0x05d), S(0x05e), S(0x05f),
+S(0x060), S(0x061), S(0x062), S(0x063), S(0x064), S(0x065), S(0x066), S(0x067),
+S(0x068), S(0x069), S(0x06a), S(0x06b), S(0x06c), S(0x06d), S(0x06e), S(0x06f),
+S(0x070), S(0x071), S(0x072), S(0x073), S(0x074), S(0x075), S(0x076), S(0x077),
+S(0x078), S(0x079), S(0x07a), S(0x07b), S(0x07c), S(0x07d), S(0x07e), S(0x07f),
+S(0x080), S(0x081), S(0x082), S(0x083), S(0x084), S(0x085), S(0x086), S(0x087),
+S(0x088), S(0x089), S(0x08a), S(0x08b), S(0x08c), S(0x08d), S(0x08e), S(0x08f),
+S(0x090), S(0x091), S(0x092), S(0x093), S(0x094), S(0x095), S(0x096), S(0x097),
+S(0x098), S(0x099), S(0x09a), S(0x09b), S(0x09c), S(0x09d), S(0x09e), S(0x09f),
+S(0x0a0), S(0x0a1), S(0x0a2), S(0x0a3), S(0x0a4), S(0x0a5), S(0x0a6), S(0x0a7),
+S(0x0a8), S(0x0a9), S(0x0aa), S(0x0ab), S(0x0ac), S(0x0ad), S(0x0ae), S(0x0af),
+S(0x0b0), S(0x0b1), S(0x0b2), S(0x0b3), S(0x0b4), S(0x0b5), S(0x0b6), S(0x0b7),
+S(0x0b8), S(0x0b9), S(0x0ba), S(0x0bb), S(0x0bc), S(0x0bd), S(0x0be), S(0x0bf),
+S(0x0c0), S(0x0c1), S(0x0c2), S(0x0c3), S(0x0c4), S(0x0c5), S(0x0c6), S(0x0c7),
+S(0x0c8), S(0x0c9), S(0x0ca), S(0x0cb), S(0x0cc), S(0x0cd), S(0x0ce), S(0x0cf),
+S(0x0d0), S(0x0d1), S(0x0d2), S(0x0d3), S(0x0d4), S(0x0d5), S(0x0d6), S(0x0d7),
+S(0x0d8), S(0x0d9), S(0x0da), S(0x0db), S(0x0dc), S(0x0dd), S(0x0de), S(0x0df),
+S(0x0e0), S(0x0e1), S(0x0e2), S(0x0e3), S(0x0e4), S(0x0e5), S(0x0e6), S(0x0e7),
+S(0x0e8), S(0x0e9), S(0x0ea), S(0x0eb), S(0x0ec), S(0x0ed), S(0x0ee), S(0x0ef),
+S(0x0f0), S(0x0f1), S(0x0f2), S(0x0f3), S(0x0f4), S(0x0f5), S(0x0f6), S(0x0f7),
+S(0x0f8), S(0x0f9), S(0x0fa), S(0x0fb), S(0x0fc), S(0x0fd), S(0x0fe), S(0x0ff),
+S(0x100), S(0x101), S(0x102), S(0x103), S(0x104), S(0x105), S(0x106), S(0x107),
+S(0x108), S(0x109), S(0x10a), S(0x10b), S(0x10c), S(0x10d), S(0x10e), S(0x10f),
+S(0x110), S(0x111), S(0x112), S(0x113), S(0x114), S(0x115), S(0x116), S(0x117),
+S(0x118), S(0x119), S(0x11a), S(0x11b), S(0x11c), S(0x11d), S(0x11e), S(0x11f),
+S(0x120), S(0x121), S(0x122), S(0x123), S(0x124), S(0x125), S(0x126), S(0x127),
+S(0x128), S(0x129), S(0x12a), S(0x12b), S(0x12c), S(0x12d), S(0x12e), S(0x12f),
+S(0x130), S(0x131), S(0x132), S(0x133), S(0x134), S(0x135), S(0x136), S(0x137),
+S(0x138), S(0x139), S(0x13a), S(0x13b), S(0x13c), S(0x13d), S(0x13e), S(0x13f),
+S(0x140), S(0x141), S(0x142), S(0x143), S(0x144), S(0x145), S(0x146), S(0x147),
+S(0x148), S(0x149), S(0x14a), S(0x14b), S(0x14c), S(0x14d), S(0x14e), S(0x14f),
+S(0x150), S(0x151), S(0x152), S(0x153), S(0x154), S(0x155), S(0x156), S(0x157),
+S(0x158), S(0x159), S(0x15a), S(0x15b), S(0x15c), S(0x15d), S(0x15e), S(0x15f),
+S(0x160), S(0x161), S(0x162), S(0x163), S(0x164), S(0x165), S(0x166), S(0x167),
+S(0x168), S(0x169), S(0x16a), S(0x16b), S(0x16c), S(0x16d), S(0x16e), S(0x16f),
+S(0x170), S(0x171), S(0x172), S(0x173), S(0x174), S(0x175), S(0x176), S(0x177),
+S(0x178), S(0x179), S(0x17a), S(0x17b), S(0x17c), S(0x17d), S(0x17e), S(0x17f),
+S(0x180), S(0x181), S(0x182), S(0x183), S(0x184), S(0x185), S(0x186), S(0x187),
+S(0x188), S(0x189), S(0x18a), S(0x18b), S(0x18c), S(0x18d), S(0x18e), S(0x18f),
+S(0x190), S(0x191), S(0x192), S(0x193), S(0x194), S(0x195), S(0x196), S(0x197),
+S(0x198), S(0x199), S(0x19a), S(0x19b), S(0x19c), S(0x19d), S(0x19e), S(0x19f),
+S(0x1a0), S(0x1a1), S(0x1a2), S(0x1a3), S(0x1a4), S(0x1a5), S(0x1a6), S(0x1a7),
+S(0x1a8), S(0x1a9), S(0x1aa), S(0x1ab), S(0x1ac), S(0x1ad), S(0x1ae), S(0x1af),
+S(0x1b0), S(0x1b1), S(0x1b2), S(0x1b3), S(0x1b4), S(0x1b5), S(0x1b6), S(0x1b7),
+S(0x1b8), S(0x1b9), S(0x1ba), S(0x1bb), S(0x1bc), S(0x1bd), S(0x1be), S(0x1bf),
+S(0x1c0), S(0x1c1), S(0x1c2), S(0x1c3), S(0x1c4), S(0x1c5), S(0x1c6), S(0x1c7),
+S(0x1c8), S(0x1c9), S(0x1ca), S(0x1cb), S(0x1cc), S(0x1cd), S(0x1ce), S(0x1cf),
+S(0x1d0), S(0x1d1), S(0x1d2), S(0x1d3), S(0x1d4), S(0x1d5), S(0x1d6), S(0x1d7),
+S(0x1d8), S(0x1d9), S(0x1da), S(0x1db), S(0x1dc), S(0x1dd), S(0x1de), S(0x1df),
+S(0x1e0), S(0x1e1), S(0x1e2), S(0x1e3), S(0x1e4), S(0x1e5), S(0x1e6), S(0x1e7),
+S(0x1e8), S(0x1e9), S(0x1ea), S(0x1eb), S(0x1ec), S(0x1ed), S(0x1ee), S(0x1ef),
+S(0x1f0), S(0x1f1), S(0x1f2), S(0x1f3), S(0x1f4), S(0x1f5), S(0x1f6), S(0x1f7),
+S(0x1f8), S(0x1f9), S(0x1fa), S(0x1fb), S(0x1fc), S(0x1fd), S(0x1fe), S(0x1ff),
+S(0x200), S(0x201), S(0x202), S(0x203), S(0x204), S(0x205), S(0x206), S(0x207),
+S(0x208), S(0x209), S(0x20a), S(0x20b), S(0x20c), S(0x20d), S(0x20e), S(0x20f),
+S(0x210), S(0x211), S(0x212), S(0x213), S(0x214), S(0x215), S(0x216), S(0x217),
+S(0x218), S(0x219), S(0x21a), S(0x21b), S(0x21c), S(0x21d), S(0x21e), S(0x21f),
+S(0x220), S(0x221), S(0x222), S(0x223), S(0x224), S(0x225), S(0x226), S(0x227),
+S(0x228), S(0x229), S(0x22a), S(0x22b), S(0x22c), S(0x22d), S(0x22e), S(0x22f),
+S(0x230), S(0x231), S(0x232), S(0x233), S(0x234), S(0x235), S(0x236), S(0x237),
+S(0x238), S(0x239), S(0x23a), S(0x23b), S(0x23c), S(0x23d), S(0x23e), S(0x23f),
+S(0x240), S(0x241), S(0x242), S(0x243), S(0x244), S(0x245), S(0x246), S(0x247),
+S(0x248), S(0x249), S(0x24a), S(0x24b), S(0x24c), S(0x24d), S(0x24e), S(0x24f),
+S(0x250), S(0x251), S(0x252), S(0x253), S(0x254), S(0x255), S(0x256), S(0x257),
+S(0x258), S(0x259), S(0x25a), S(0x25b), S(0x25c), S(0x25d), S(0x25e), S(0x25f),
+S(0x260), S(0x261), S(0x262), S(0x263), S(0x264), S(0x265), S(0x266), S(0x267),
+S(0x268), S(0x269), S(0x26a), S(0x26b), S(0x26c), S(0x26d), S(0x26e), S(0x26f),
+S(0x270), S(0x271), S(0x272), S(0x273), S(0x274), S(0x275), S(0x276), S(0x277),
+S(0x278), S(0x279), S(0x27a), S(0x27b), S(0x27c), S(0x27d), S(0x27e), S(0x27f),
+S(0x280), S(0x281), S(0x282), S(0x283), S(0x284), S(0x285), S(0x286), S(0x287),
+S(0x288), S(0x289), S(0x28a), S(0x28b), S(0x28c), S(0x28d), S(0x28e), S(0x28f),
+S(0x290), S(0x291), S(0x292), S(0x293), S(0x294), S(0x295), S(0x296), S(0x297),
+S(0x298), S(0x299), S(0x29a), S(0x29b), S(0x29c), S(0x29d), S(0x29e), S(0x29f),
+S(0x2a0), S(0x2a1), S(0x2a2), S(0x2a3), S(0x2a4), S(0x2a5), S(0x2a6), S(0x2a7),
+S(0x2a8), S(0x2a9), S(0x2aa), S(0x2ab), S(0x2ac), S(0x2ad), S(0x2ae), S(0x2af),
+S(0x2b0), S(0x2b1), S(0x2b2), S(0x2b3), S(0x2b4), S(0x2b5), S(0x2b6), S(0x2b7),
+S(0x2b8), S(0x2b9), S(0x2ba), S(0x2bb), S(0x2bc), S(0x2bd), S(0x2be), S(0x2bf),
+S(0x2c0), S(0x2c1), S(0x2c2), S(0x2c3), S(0x2c4), S(0x2c5), S(0x2c6), S(0x2c7),
+S(0x2c8), S(0x2c9), S(0x2ca), S(0x2cb), S(0x2cc), S(0x2cd), S(0x2ce), S(0x2cf),
+S(0x2d0), S(0x2d1), S(0x2d2), S(0x2d3), S(0x2d4), S(0x2d5), S(0x2d6), S(0x2d7),
+S(0x2d8), S(0x2d9), S(0x2da), S(0x2db), S(0x2dc), S(0x2dd), S(0x2de), S(0x2df),
+S(0x2e0), S(0x2e1), S(0x2e2), S(0x2e3), S(0x2e4), S(0x2e5), S(0x2e6), S(0x2e7),
+S(0x2e8), S(0x2e9), S(0x2ea), S(0x2eb), S(0x2ec), S(0x2ed), S(0x2ee), S(0x2ef),
+S(0x2f0), S(0x2f1), S(0x2f2), S(0x2f3), S(0x2f4), S(0x2f5), S(0x2f6), S(0x2f7),
+S(0x2f8), S(0x2f9), S(0x2fa), S(0x2fb), S(0x2fc), S(0x2fd), S(0x2fe), S(0x2ff),
+S(0x300), S(0x301), S(0x302), S(0x303), S(0x304), S(0x305), S(0x306), S(0x307),
+S(0x308), S(0x309), S(0x30a), S(0x30b), S(0x30c), S(0x30d), S(0x30e), S(0x30f),
+S(0x310), S(0x311), S(0x312), S(0x313), S(0x314), S(0x315), S(0x316), S(0x317),
+S(0x318), S(0x319), S(0x31a), S(0x31b), S(0x31c), S(0x31d), S(0x31e), S(0x31f),
+S(0x320), S(0x321), S(0x322), S(0x323), S(0x324), S(0x325), S(0x326), S(0x327),
+S(0x328), S(0x329), S(0x32a), S(0x32b), S(0x32c), S(0x32d), S(0x32e), S(0x32f),
+S(0x330), S(0x331), S(0x332), S(0x333), S(0x334), S(0x335), S(0x336), S(0x337),
+S(0x338), S(0x339), S(0x33a), S(0x33b), S(0x33c), S(0x33d), S(0x33e), S(0x33f),
+S(0x340), S(0x341), S(0x342), S(0x343), S(0x344), S(0x345), S(0x346), S(0x347),
+S(0x348), S(0x349), S(0x34a), S(0x34b), S(0x34c), S(0x34d), S(0x34e), S(0x34f),
+S(0x350), S(0x351), S(0x352), S(0x353), S(0x354), S(0x355), S(0x356), S(0x357),
+S(0x358), S(0x359), S(0x35a), S(0x35b), S(0x35c), S(0x35d), S(0x35e), S(0x35f),
+S(0x360), S(0x361), S(0x362), S(0x363), S(0x364), S(0x365), S(0x366), S(0x367),
+S(0x368), S(0x369), S(0x36a), S(0x36b), S(0x36c), S(0x36d), S(0x36e), S(0x36f),
+S(0x370), S(0x371), S(0x372), S(0x373), S(0x374), S(0x375), S(0x376), S(0x377),
+S(0x378), S(0x379), S(0x37a), S(0x37b), S(0x37c), S(0x37d), S(0x37e), S(0x37f),
+S(0x380), S(0x381), S(0x382), S(0x383), S(0x384), S(0x385), S(0x386), S(0x387),
+S(0x388), S(0x389), S(0x38a), S(0x38b), S(0x38c), S(0x38d), S(0x38e), S(0x38f),
+S(0x390), S(0x391), S(0x392), S(0x393), S(0x394), S(0x395), S(0x396), S(0x397),
+S(0x398), S(0x399), S(0x39a), S(0x39b), S(0x39c), S(0x39d), S(0x39e), S(0x39f),
+S(0x3a0), S(0x3a1), S(0x3a2), S(0x3a3), S(0x3a4), S(0x3a5), S(0x3a6), S(0x3a7),
+S(0x3a8), S(0x3a9), S(0x3aa), S(0x3ab), S(0x3ac), S(0x3ad), S(0x3ae), S(0x3af),
+S(0x3b0), S(0x3b1), S(0x3b2), S(0x3b3), S(0x3b4), S(0x3b5), S(0x3b6), S(0x3b7),
+S(0x3b8), S(0x3b9), S(0x3ba), S(0x3bb), S(0x3bc), S(0x3bd), S(0x3be), S(0x3bf),
+S(0x3c0), S(0x3c1), S(0x3c2), S(0x3c3), S(0x3c4), S(0x3c5), S(0x3c6), S(0x3c7),
+S(0x3c8), S(0x3c9), S(0x3ca), S(0x3cb), S(0x3cc), S(0x3cd), S(0x3ce), S(0x3cf),
+S(0x3d0), S(0x3d1), S(0x3d2), S(0x3d3), S(0x3d4), S(0x3d5), S(0x3d6), S(0x3d7),
+S(0x3d8), S(0x3d9), S(0x3da), S(0x3db), S(0x3dc), S(0x3dd), S(0x3de), S(0x3df),
+S(0x3e0), S(0x3e1), S(0x3e2), S(0x3e3), S(0x3e4), S(0x3e5), S(0x3e6), S(0x3e7),
+S(0x3e8), S(0x3e9), S(0x3ea), S(0x3eb), S(0x3ec), S(0x3ed), S(0x3ee), S(0x3ef),
+S(0x3f0), S(0x3f1), S(0x3f2), S(0x3f3), S(0x3f4), S(0x3f5), S(0x3f6), S(0x3f7),
+S(0x3f8), S(0x3f9), S(0x3fa), S(0x3fb), S(0x3fc), S(0x3fd), S(0x3fe), S(0x3ff)
};
-#endif /* MAKE_IDENTITY_MAP */
-
-extern char _end[];
+#endif /* MAKE_IDENTITY_MAP */
/*
** Kernel address mappings, present in every page table
*/
const mapping_t kmap[] = {
// va pa_start pa_end perms
- { KERN_BASE, 0, EXT_BASE, PDE_RW },
- { KERN_VLINK, KERN_PLINK, V2P(_data), PDE_RW },
- // { (uint32_t) _data, V2P(_data), V2P(_end), PDE_RW },
- { (uint32_t)_data, V2P(_data), PHYS_TOP, PDE_RW }
- // { DEV_BASE, DEV_BASE, 0, PDE_RW }
+ { KERN_BASE, 0, EXT_BASE, PDE_RW },
+ { KERN_VLINK, KERN_PLINK, V2P(_data), 0 },
+ { (uint32_t) _data, V2P(_data), KERN_BASE, PDE_RW },
+ { DEV_BASE, DEV_BASE, 0, PDE_RW }
};
const uint_t n_kmap = sizeof(kmap) / sizeof(kmap[0]);