From 4711c901345620176e1fe66e2432ce2ce5771aee Mon Sep 17 00:00:00 2001 From: hinus Date: Thu, 10 Jun 2021 12:34:13 +0800 Subject: [PATCH] Title: Initialize console. Issue: https://gitee.com/hinus/linux_kernel_011/issues/I3V30D Description: Initialize console and print video type to right-upper corner of console. --- include/linux/tty.h | 7 ++++ kernel/Makefile | 7 +++- kernel/chr_drv/Makefile | 20 +++++++++++ kernel/chr_drv/console.c | 74 ++++++++++++++++++++++++++++++++++++++++ kernel/chr_drv/tty_io.c | 6 ++++ kernel/head.S | 4 --- kernel/main.c | 8 ++++- 7 files changed, 120 insertions(+), 6 deletions(-) create mode 100644 include/linux/tty.h create mode 100644 kernel/chr_drv/Makefile create mode 100644 kernel/chr_drv/console.c create mode 100644 kernel/chr_drv/tty_io.c diff --git a/include/linux/tty.h b/include/linux/tty.h new file mode 100644 index 0000000..542afc7 --- /dev/null +++ b/include/linux/tty.h @@ -0,0 +1,7 @@ +#ifndef _TTY_H +#define _TTY_H + +void con_init(); +void tty_init(); + +#endif diff --git a/kernel/Makefile b/kernel/Makefile index 2f1973f..0c8dcf1 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -2,7 +2,7 @@ GCC := gcc CCFLAG := -I../include -nostdinc -Wall -fomit-frame-pointer -c -m32 LDFLAG := -Ttext 0x0 -s --oformat binary -m elf_i386 INCDIR := ../include -OBJS := head.o main.o sched.o +OBJS := head.o main.o sched.o chr_drv/chr_drv.a system: $(OBJS) $(LD) $(LDFLAG) -e startup_32 -o $@ $^ @@ -16,7 +16,12 @@ main.o : main.c sched.o : sched.c $(GCC) $(CCFLAG) -o $@ $< +chr_drv/chr_drv.a: chr_drv/*.c + cd chr_drv; make chr_drv.a; cd .. + + clean : rm *.o rm system + cd chr_drv; make clean; cd .. diff --git a/kernel/chr_drv/Makefile b/kernel/chr_drv/Makefile new file mode 100644 index 0000000..afb3e4e --- /dev/null +++ b/kernel/chr_drv/Makefile @@ -0,0 +1,20 @@ +AR := ar +LD := ld +GCC := gcc +CCFLAG := -m32 -I../../include -nostdinc -Wall -fomit-frame-pointer -c +OBJS := tty_io.o console.o + +tty_io.o : tty_io.c + $(GCC) $(CCFLAG) -o $@ $< + +console.o : console.c + $(GCC) $(CCFLAG) -o $@ $< + +chr_drv.a : $(OBJS) + $(AR) rcs $@ $^ + sync + +clean : + rm *.o + rm chr_drv.a + diff --git a/kernel/chr_drv/console.c b/kernel/chr_drv/console.c new file mode 100644 index 0000000..5cbd4f2 --- /dev/null +++ b/kernel/chr_drv/console.c @@ -0,0 +1,74 @@ +#include + +#define ORIG_VIDEO_PAGE (*(unsigned short *)0x90004) +#define ORIG_VIDEO_MODE ((*(unsigned short *)0x90006) & 0xff) +#define ORIG_VIDEO_COLS (((*(unsigned short *)0x90006) & 0xff00) >> 8) +#define ORIG_VIDEO_LINES ((*(unsigned short *)0x9000e) & 0xff) +#define ORIG_VIDEO_EGA_AX (*(unsigned short *)0x90008) +#define ORIG_VIDEO_EGA_BX (*(unsigned short *)0x9000a) +#define ORIG_VIDEO_EGA_CX (*(unsigned short *)0x9000c) + +#define VIDEO_TYPE_MDA 0x10 /* Monochrome Text Display */ +#define VIDEO_TYPE_CGA 0x11 /* CGA Display */ +#define VIDEO_TYPE_EGAM 0x20 /* EGA/VGA in Monochrome Mode */ +#define VIDEO_TYPE_EGAC 0x21 /* EGA/VGA in Color Mode */ + +static unsigned char video_type; /* Type of display being used */ +static unsigned long video_num_columns; /* Number of text columns */ +static unsigned long video_num_lines; /* Number of test lines */ +static unsigned long video_mem_base; /* Base of video memory */ +static unsigned long video_mem_term; /* End of video memory */ +static unsigned long video_size_row; /* Bytes per row */ +static unsigned char video_page; /* Initial video page */ +static unsigned short video_port_reg; /* Video register select port */ +static unsigned short video_port_val; /* Video register value port */ + +void con_init() { + char * display_desc = "????"; + char * display_ptr; + + video_num_columns = ORIG_VIDEO_COLS; + video_size_row = video_num_columns * 2; + video_num_lines = ORIG_VIDEO_LINES; + video_page = ORIG_VIDEO_PAGE; + + /* Is this a monochrome display? */ + if (ORIG_VIDEO_MODE == 7) { + video_mem_base = 0xb0000; + video_port_reg = 0x3b4; + video_port_val = 0x3b5; + if ((ORIG_VIDEO_EGA_BX & 0xff) != 0x10) { + video_type = VIDEO_TYPE_EGAM; + video_mem_term = 0xb8000; + display_desc = "EGAm"; + } + else { + video_type = VIDEO_TYPE_MDA; + video_mem_term = 0xb2000; + display_desc = "*MDA"; + } + } + else { /* color display */ + video_mem_base = 0xb8000; + video_port_reg = 0x3d4; + video_port_val = 0x3d5; + + if ((ORIG_VIDEO_EGA_BX & 0xff) != 0x10) { + video_type = VIDEO_TYPE_EGAC; + video_mem_term = 0xc0000; + display_desc = "EGAc"; + } + else { + video_type = VIDEO_TYPE_CGA; + video_mem_term = 0xba000; + display_desc = "*CGA"; + } + } + + display_ptr = ((char *)video_mem_base) + video_size_row - 8; + while (*display_desc) { + *display_ptr++ = *display_desc++; + *display_ptr++; + } +} + diff --git a/kernel/chr_drv/tty_io.c b/kernel/chr_drv/tty_io.c new file mode 100644 index 0000000..724ec13 --- /dev/null +++ b/kernel/chr_drv/tty_io.c @@ -0,0 +1,6 @@ +#include + +void tty_init() { + con_init(); +} + diff --git a/kernel/head.S b/kernel/head.S index 4f74b18..b0643b4 100644 --- a/kernel/head.S +++ b/kernel/head.S @@ -20,10 +20,6 @@ startup_32: movl $0x18, %eax movw %ax, %gs - movl $0x0, %edi - movb $0xf, %ah - movb $0x42, %al - movw %ax, %gs:(%edi) xorl %eax, %eax 1: diff --git a/kernel/main.c b/kernel/main.c index 014708a..2de940e 100644 --- a/kernel/main.c +++ b/kernel/main.c @@ -1,14 +1,20 @@ #define __LIBRARY__ +#include + void main(void) { + /* char* p1 = "hello world!\0"; short* p = (short*)0xb8000; while(*p1) { *p++ = 0xf00 | (*p1++); } + */ + + //__asm__("int $0x80\n\r"::); - __asm__("int $0x80\n\r"::); + tty_init(); __asm__ __volatile__( "loop:\n\r" -- Gitee