/tmp/sos-code-article7.5/drivers/zero.c (2005-04-27 20:17:13.000000000 +0200
) |
|
../sos-code-article7.5/drivers/zero.c (2005-06-06 20:47:20.000000000 +0200
) |
|
|
|
zero_resource | zero_resource |
= (struct zero_mapped_resource*) | = (struct zero_mapped_resource*) |
sos_umem_vmm_get_mapped_resource_of_vr(vr)->custom_data; | sos_umem_vmm_get_mapped_resource_of_vr(vr)->custom_data; |
| |
SOS_ASSERT_FATAL(zero_resource->ref_cnt > 0); | SOS_ASSERT_FATAL(zero_resource->ref_cnt > 0); |
zero_resource->ref_cnt --; | zero_resource->ref_cnt --; |
|
|
struct zero_mapped_page *zmp; | struct zero_mapped_page *zmp; |
list_collapse(zero_resource->list_mapped_pages, zmp) | list_collapse(zero_resource->list_mapped_pages, zmp) |
{ | { |
/* No need to free the underlying physical pages, since they | /* Unreference the underlying physical page */ |
should have been unmapped just before this unref is | sos_physmem_unref_physpage(zmp->ppage_paddr); |
called */ | |
} | } |
| |
|
|
SOS_PAGE_ALIGN_INF(uaddr), | SOS_PAGE_ALIGN_INF(uaddr), |
TRUE, | TRUE, |
vr_prot); | vr_prot); |
| |
return retval; | return retval; |
} | } |
} | } |
|
|
ppage_paddr = sos_physmem_ref_physpage_new(FALSE); | ppage_paddr = sos_physmem_ref_physpage_new(FALSE); |
if (! ppage_paddr) | if (! ppage_paddr) |
return -SOS_ENOMEM; | return -SOS_ENOMEM; |
| |
SOS_PAGE_ALIGN_INF(uaddr), | SOS_PAGE_ALIGN_INF(uaddr), |
TRUE, | TRUE, |
|
|
zmp->ppage_paddr = ppage_paddr; | zmp->ppage_paddr = ppage_paddr; |
| |
list_add_head(mr->list_mapped_pages, zmp); | list_add_head(mr->list_mapped_pages, zmp); |
| sos_physmem_ref_physpage_at(ppage_paddr); |
return SOS_OK; | return SOS_OK; |
} | } |
| |
| |
/tmp/sos-code-article7.5/extra/bootsect.S (2005-04-27 20:17:13.000000000 +0200
) |
|
../sos-code-article7.5/extra/bootsect.S (2005-06-06 20:47:22.000000000 +0200
) |
|
|
|
| |
/* | /* |
* @(#) $Id: bootsect.S,v 1.8 2004/11/20 16:00:11 d2 Exp $ | * @(#) $Id: bootsect.S,v 1.11 2005/04/28 21:55:35 d2 Exp $ |
* Auteurs : Thomas Petazzoni & Fabrice Gautier & Emmanuel Marty | * Auteurs : Thomas Petazzoni & Fabrice Gautier & Emmanuel Marty |
* Jerome Petazzoni & Bernard Cassagne & coffeeman | * Jerome Petazzoni & Bernard Cassagne & coffeeman |
* David Decotigny | * David Decotigny (SOS integration for kernel size detection) |
| * Christopher Goyet (RAM size determination through BIOS int 15H) |
*/ | */ |
| |
|
|
* valide | * valide |
* - Le bootsect verifie que le processeur est du type 386+ | * - Le bootsect verifie que le processeur est du type 386+ |
* - Il charge le noyau depuis la disquette en memoire a partir de | * - Il charge le noyau depuis la disquette en memoire a partir de |
* 0x1000 (LOAD_ADRESS). Le noyau peut au max tenir sur | * 0x1000 (LOAD_ADRESS). La place dispo est donc 0x9f000 - 0x1000 , soit |
* SECTORS_TO_LOAD secteurs | * 0x9E000, soit encore 1264 secteurs de 512 octets |
* - Il recopie le noyau (situe en LOAD_ADRESS) vers son adresse | * - Il recopie le noyau (situe en LOAD_ADRESS) vers son adresse |
* finale (FINAL_ADDRESS = 2Mo). La recopie se fait sur tout l'espace | * finale (FINAL_ADDRESS = 2Mo). La recopie se fait sur tout l'espace |
|
|
/* Pour que gas genere du 16bits, afin que ca marche en realm */ | /* Pour que gas genere du 16bits, afin que ca marche en realm */ |
.code16 | .code16 |
| |
#define SECTORS_TO_LOAD 128 /* 64 ko */ /* MAX=1264 */ | |
| |
* Parametres de la disquette. Comme c'est chiant de faire une | * Parametres de la disquette. Comme c'est chiant de faire une |
* procedure de detection auto, et que ca prend de la place, on fait | * procedure de detection auto, et que ca prend de la place, on fait |
|
|
copier le bootsecteur */ | copier le bootsecteur */ |
#define LOAD_ADRESS 0x01000 /* 1er chargement du systeme */ | #define LOAD_ADRESS 0x01000 /* 1er chargement du systeme */ |
#define LOAD_SEG (LOAD_ADRESS>>4) /* Segment du 1er chargement du */ | #define LOAD_SEG (LOAD_ADRESS>>4) /* Segment du 1er chargement du */ |
#define MAX_KERN_LEN COPY_ADRESS-LOAD_ADRESS /* Taille noyau maxi */ | #define MAX_KERN_LEN (COPY_ADRESS-LOAD_ADRESS) /* Taille noyau maxi */ |
| #define MAX_KERN_SECTS ((MAX_KERN_LEN + 511) / 512) /* Nbre de secteurs maxi */ |
/* IMPORTANT : Cette valeur DOIT etre identique a l'adresse presente | /* IMPORTANT : Cette valeur DOIT etre identique a l'adresse presente |
dans sos.lds ! */ | dans sos.lds ! */ |
|
|
/* Efface l'ecran */ | /* Efface l'ecran */ |
movb $0x0, %ah | movb $0x0, %ah |
movb $0x3, %al | movb $0x3, %al |
int $0x10 | int $0x10 |
| |
| /* Verifie que le noyau n'est pas trop gros a charger */ |
| cmpw $MAX_KERN_SECTS, (load_size) |
| jb sizeOk |
| movw $toobig, %si |
| call message |
| call halt |
| |
| sizeOk: |
| /* Recupere la taille de la RAM */ |
| mov $0xE801, %ax |
| int $0x15 |
| movw %ax, (memsize1) |
| movw %bx, (memsize2) |
/* Affiche les messages d'attente */ | /* Affiche les messages d'attente */ |
movw $loadkern, %si | movw $loadkern, %si |
|
|
movl %eax, %ss | movl %eax, %ss |
movl $(stack + BOOT_STACK_SIZE), %ebp | movl $(stack + BOOT_STACK_SIZE), %ebp |
movl %ebp, %esp | movl %ebp, %esp |
| |
| /* passe les arguments a sos */ |
| xor %eax, %eax |
| xor %ebx, %ebx |
| movw (COPY_ADRESS+(memsize2)), %ax /*eax = num de block de 64KB apres 16MB*/ |
| movw (COPY_ADRESS+(memsize1)), %bx /*ebx = num de block de 1KB entre 1MB et 16MB*/ |
| movl $0x40, %ecx /*ecx=64 */ |
| mul %ecx |
| add %ebx, %eax |
| pushl %eax /* valeur de addr */ |
| pushl $0x42244224 /* valeur de magic pour indiquer qu'on a pousse |
| la taille de la RAM sur la pile */ |
| pushl $0 /* normalement call fait un push eip, mais la on a un jmp*/ |
| |
/* Saut vers le noyau. La GDT est en place (flat mode), les | /* Saut vers le noyau. La GDT est en place (flat mode), les |
* selecteurs aussi, a20 est ouverte, et les interruptions sont | * selecteurs aussi, a20 est ouverte, et les interruptions sont |
|
|
| |
/* quelques messages */ | /* quelques messages */ |
| |
loadkern: .string "-= S O S =- : The Simple Operating System \r\n" | loadkern: .string "This is SOS\r\n" |
check: .string "Checking for a 386+ processor... " | toobig: .string "Image too big\r\n" |
| check: .string "Checking 386+ processor... " |
need386: .string " [FAILED]\r\n" | need386: .string " [FAILED]\r\n" |
diskerror: .string "Disk Error\r\n" | diskerror: .string "Disk Error\r\n" |
loading: .string "Loading... " | loading: .string "Loading... " |
haltmsg: .string "System Halted\r\n" | haltmsg: .string "System Halted\r\n" |
| |
| /* Variables pour stocker la taille de la RAM (int 0x15) */ |
| memsize1: .long 0 |
| memsize2: .long 0 |
| |
/*** Les code/données du boot secteur se terminent ICI. le marqueur de | /*** Les code/données du boot secteur se terminent ICI. le marqueur de |
* fin (aa55) est ajouté automatiquement par le script ld | * fin (aa55) est ajouté automatiquement par le script ld |
* sos_bsect.lds ***/ | * sos_bsect.lds ***/ |
| |
/tmp/sos-code-article7.5/INSTALL (2005-04-27 20:17:12.000000000 +0200
) |
|
../sos-code-article7.5/INSTALL (2005-06-06 20:47:17.000000000 +0200
) |
|
|
|
copy the file 'fd.img' to a floppy, and boot from it | copy the file 'fd.img' to a floppy, and boot from it |
| |
2nd method | 2nd method |
=> see extra/README to compile with the boot sector we provide (up to | => see extra/README to compile with the boot sector we provide, |
article 2 only), copy the file 'extra/sos_bsect.img' to a floppy, | copy the file 'extra/sos_bsect.img' to a floppy, and boot from |
and boot from it | it |
| |
Inside a PC emulator (x86 and non-x86 hosts) | Inside a PC emulator (x86 and non-x86 hosts) |
|
|
installed: 'apt-get install libsdl1.2-dev' on debian | installed: 'apt-get install libsdl1.2-dev' on debian |
testing/unstable). | testing/unstable). |
| |
| |
1/ Grub is installed on the host (x86 hosts only) | 1/ Grub is installed on the host (x86 hosts only) |
- - - - - - - - - - - - - - - - - - - - - - - - - | - - - - - - - - - - - - - - - - - - - - - - - - - |
| |
|
|
qemu: run 'qemu -fda fd.img' | qemu: run 'qemu -fda fd.img' |
If grub hangs while loading the kernel, please go to method 2/ | If grub hangs while loading the kernel, please go to method 2/ |
| |
| |
2/ Grub is not installed (all hosts) | 2/ Grub is not installed (all hosts) |
- - - - - - - - - - - - - - - - - - | - - - - - - - - - - - - - - - - - - |
| |
|
|
| |
qemu: run 'qemu -fda fd.img' | qemu: run 'qemu -fda fd.img' |
| |
3/ Bonus: boot with the bootsector we provide (all hosts, up to art. 2 ONLY !) | |
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | 3/ Bonus: boot with the bootsector we provide (all hosts) |
| - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
See extra/README to generate a floppy image with the boot sector we | See extra/README to generate a floppy image with the boot sector we |
provide, and: | provide, and: |
|
|
| |
qemu: run 'qemu -fda extra/sos_qemu.img' | qemu: run 'qemu -fda extra/sos_qemu.img' |
| |
NOTE: After article 2, this way of booting is not supported: please | NOTE: This technique assumes that INT 15H is supported by the |
use the method 2/ above. | machine's BIOS. This should be OK for the vast majority of targets |
| (bochs, qemu, recent machines), but we do not guarantee it. In case |
| of doubt, please use Grub. |
| |
NOTE : recommended versions of the tools | NOTE : recommended versions of the tools |
---------------------------------------- | ---------------------------------------- |
- OS : Linux 2.6.11.7-d2-1 i686 | - OS : Linux 2.6.11.7 i686 |
- gcc : gcc (GCC) 3.3.5 (Debian 1:3.3.5-8) | - gcc : gcc (GCC) 3.3.5 (Debian 1:3.3.5-12) |
- GNU make : GNU Make 3.80 | - GNU make : GNU Make 3.80 |
| |
| |
/tmp/sos-code-article7.5/Makefile (2005-04-27 20:17:12.000000000 +0200
) |
|
../sos-code-article7.5/Makefile (2005-06-06 20:47:16.000000000 +0200
) |
|
|
|
| |
CC=gcc | CC=gcc |
LD=ld | LD=ld |
| CP=cp |
| STRIP=strip |
CFLAGS = -Wall -nostdinc -ffreestanding -DKERNEL_SOS | CFLAGS = -Wall -nostdinc -ffreestanding -DKERNEL_SOS |
LIBGCC := $(shell $(CC) -print-libgcc-file-name) # To benefit from FP/64bits artihm. | LIBGCC = $(shell $(CC) -print-libgcc-file-name) # To benefit from FP/64bits artihm. |
OBJECTS = bootstrap/multiboot.o \ | OBJECTS = bootstrap/multiboot.o \ |
hwcore/idt.o hwcore/gdt.o \ | hwcore/idt.o hwcore/gdt.o \ |
hwcore/swintr.o hwcore/swintr_wrappers.o \ | hwcore/swintr.o hwcore/swintr_wrappers.o \ |
hwcore/exception.o hwcore/exception_wrappers.o \ | hwcore/exception.o hwcore/exception_wrappers.o \ |
hwcore/irq.o hwcore/irq_wrappers.o hwcore/i8259.o \ | hwcore/irq.o hwcore/irq_wrappers.o hwcore/i8259.o \ |
hwcore/paging.o \ | hwcore/paging.o \ |
hwcore/cpu_context.o hwcore/cpu_context_switch.o \ | hwcore/cpu_context.o hwcore/cpu_context_switch.o \ |
hwcore/mm_context.o \ | hwcore/mm_context.o \ |
|
|
userland/userprogs.kimg | userland/userprogs.kimg |
| |
KERNEL_OBJ = sos.elf | KERNEL_OBJ = sos.elf |
| KERNEL_LOAD = sos.gz |
MULTIBOOT_IMAGE = fd.img | MULTIBOOT_IMAGE = fd.img |
PWD := $(shell pwd) | PWD := $(shell pwd) |
| |
# Main target | # Main target |
all: $(MULTIBOOT_IMAGE) | all: $(MULTIBOOT_IMAGE) |
| |
$(MULTIBOOT_IMAGE): $(KERNEL_OBJ) | $(MULTIBOOT_IMAGE): $(KERNEL_LOAD) |
| |
| $(KERNEL_LOAD): $(KERNEL_OBJ) |
| $(CP) $< $<.strip && $(STRIP) -sx $<.strip |
| gzip < $<.strip > $@ |
| |
$(KERNEL_OBJ): $(OBJECTS) ./support/sos.lds | $(KERNEL_OBJ): $(OBJECTS) ./support/sos.lds |
$(LD) $(LDFLAGS) -T ./support/sos.lds -o $@ $(OBJECTS) $(LIBGCC) | $(LD) $(LDFLAGS) -T ./support/sos.lds -o $@ $(OBJECTS) $(LIBGCC) |
-nm -C $@ | cut -d ' ' -f 1,3 > sos.map | -nm -C $@ | cut -d ' ' -f 1,3 > sos.map |
|
|
| |
# Clean directory | # Clean directory |
clean: | clean: |
$(RM) *.img *.o mtoolsrc *~ menu.txt *.img *.elf *.bin *.map | $(RM) *.img *.o mtoolsrc *~ menu.txt *.img *.elf *.bin *.strip *.map |
$(RM) *.log *.out bochs* | $(RM) *.log *.out bochs* sos.gz |
$(RM) drivers/*.o drivers/*~ | $(RM) drivers/*.o drivers/*~ |
$(RM) hwcore/*.o hwcore/*~ | $(RM) hwcore/*.o hwcore/*~ |
| |
/tmp/sos-code-article7.5/README (2005-04-27 20:17:12.000000000 +0200
) |
|
../sos-code-article7.5/README (2005-06-06 20:47:18.000000000 +0200
) |
|
|
|
i586-gnu) is available. Can be tested on real i486/pentium | i586-gnu) is available. Can be tested on real i486/pentium |
hardware, or on any host that can run an i486/pentium PC emulator | hardware, or on any host that can run an i486/pentium PC emulator |
(bochs or qemu) | (bochs or qemu) |
- kernel loaded by grub, or by a sample bootsector (up to article 2 | - kernel loaded by grub or by a sample bootsector |
ONLY) | |
even inside the kernel: no identity-mapping of the physical memory | even inside the kernel: no identity-mapping of the physical memory |
inside the kernel (allows to move virtual mappings of kernel pages | inside the kernel (allows to move virtual mappings of kernel pages |
|
|
'all' and 'clean' | 'all' and 'clean' |
- bootstrap/ directory: code to load the kernel. Both the stuff | - bootstrap/ directory: code to load the kernel. Both the stuff |
needed for a multiboot-compliant loader (eg grub) AND a bootsector | needed for a multiboot-compliant loader (eg grub) AND a bootsector |
are provided. The bootsector may only be used up to article 2. | are provided. |
systemwide header files, a set of common useful C routines | systemwide header files, a set of common useful C routines |
("nano-klibc"), and kernel subsystems (kernel memory management, | ("nano-klibc"), and kernel subsystems (kernel memory management, |
| |
/tmp/sos-code-article7.5/sos/errno.h (2005-04-27 20:17:16.000000000 +0200
) |
|
../sos-code-article7.5/sos/errno.h (2005-06-06 20:47:34.000000000 +0200
) |
|
|
|
*/ | */ |
| |
/* Positive values of the error codes */ | /* Positive values of the error codes */ |
#define SOS_OK 0 /* No error */ | #define SOS_OK 0 /* No error */ |
#define SOS_EINVAL 1 /* Invalid argument */ | #define SOS_EINVAL 1 /* Invalid argument */ |
#define SOS_ENOSUP 2 /* Operation not supported */ | #define SOS_ENOSUP 2 /* Operation not supported */ |
#define SOS_ENOMEM 3 /* No available memory */ | #define SOS_ENOMEM 3 /* No available memory */ |
#define SOS_EBUSY 4 /* Object or device still in use */ | #define SOS_EBUSY 4 /* Object or device still in use */ |
#define SOS_EINTR 5 /* Wait/Sleep has been interrupted */ | #define SOS_EINTR 5 /* Wait/Sleep has been interrupted */ |
#define SOS_EPERM 6 /* Mutex/files ownership error */ | #define SOS_EPERM 6 /* Mutex/files ownership error */ |
#define SOS_EFAULT 7 /* Unresolved virtual memory fault */ | #define SOS_EFAULT 7 /* Unresolved virtual memory fault */ |
#define SOS_ENOENT 8 /* No such file or directory */ | #define SOS_ENOENT 8 /* No such file or directory */ |
#define SOS_EFATAL 255 /* Internal fatal error */ | #define SOS_EFATAL 255 /* Internal fatal error */ |
/* A negative value means that an error occured. For | /* A negative value means that an error occured. For |
* example -SOS_EINVAL means that the error was "invalid | * example -SOS_EINVAL means that the error was "invalid |
| |
/tmp/sos-code-article7.5/sos/main.c (2005-04-27 20:17:17.000000000 +0200
) |
|
../sos-code-article7.5/sos/main.c (2005-06-06 20:47:35.000000000 +0200
) |
|
|
|
USA. | USA. |
*/ | */ |
| |
| #include <sos/errno.h> |
| |
/* Include definitions of the multiboot standard */ | /* Include definitions of the multiboot standard */ |
#include <bootstrap/multiboot.h> | #include <bootstrap/multiboot.h> |
#include <hwcore/idt.h> | #include <hwcore/idt.h> |
|
|
} | } |
} | } |
| |
| |
static void clk_it(int intid) | static void clk_it(int intid) |
{ | { |
|
|
sos_process_unref(proc_init); | sos_process_unref(proc_init); |
return -SOS_ENOENT; | return -SOS_ENOENT; |
} | } |
| |
ustack = (SOS_PAGING_TOP_USER_ADDRESS - SOS_DEFAULT_USER_STACK_SIZE) + 1; | ustack = (SOS_PAGING_TOP_USER_ADDRESS - SOS_DEFAULT_USER_STACK_SIZE) + 1; |
retval = sos_dev_zero_map(as_init, &ustack, SOS_DEFAULT_USER_STACK_SIZE, | retval = sos_dev_zero_map(as_init, &ustack, SOS_DEFAULT_USER_STACK_SIZE, |
|
|
/* PRIVATE */ 0); | /* PRIVATE */ 0); |
if (SOS_OK != retval) | if (SOS_OK != retval) |
{ | { |
sos_bochs_printf("ici 2\n"); | |
return -SOS_ENOMEM; | return -SOS_ENOMEM; |
} | } |
|
|
SOS_SCHED_PRIO_TS_LOWEST); | SOS_SCHED_PRIO_TS_LOWEST); |
if (! new_thr) | if (! new_thr) |
{ | { |
sos_bochs_printf("ici 3\n"); | |
return -SOS_ENOMEM; | return -SOS_ENOMEM; |
} | } |
|
|
/* ====================================================================== | /* ====================================================================== |
* The C entry point of our operating system | * The C entry point of our operating system |
*/ | */ |
void sos_main(unsigned long magic, unsigned long addr) | void sos_main(unsigned long magic, unsigned long arg) |
unsigned i; | unsigned i; |
sos_paddr_t sos_kernel_core_base_paddr, sos_kernel_core_top_paddr; | sos_paddr_t sos_kernel_core_base_paddr, sos_kernel_core_top_paddr; |
struct sos_time tick_resolution; | struct sos_time tick_resolution; |
| |
/* Grub sends us a structure, called multiboot_info_t with a lot of | /* Size of RAM above 1MB. Might be undefined ! */ |
precious informations about the system, see the multiboot | unsigned long int upper_mem = 0; |
documentation for more information. */ | |
multiboot_info_t *mbi; | |
mbi = (multiboot_info_t *) addr; | |
/* Setup bochs and console, and clear the console */ | /* Setup bochs and console, and clear the console */ |
sos_bochs_setup(); | sos_bochs_setup(); |
|
|
| |
/* Greetings from SOS */ | /* Greetings from SOS */ |
if (magic == MULTIBOOT_BOOTLOADER_MAGIC) | if (magic == MULTIBOOT_BOOTLOADER_MAGIC) |
/* Loaded with Grub */ | { |
sos_x86_videomem_printf(1, 0, | /* Grub sends us a structure, called multiboot_info_t with a lot of |
SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, | precious informations about the system, see the multiboot |
"Welcome From GRUB to %s%c RAM is %dMB (upper mem = 0x%x kB)", | documentation for more information. */ |
"SOS article 7.5", ',', | multiboot_info_t *mbi = (multiboot_info_t *) arg; |
(unsigned)(mbi->mem_upper >> 10) + 1, | |
(unsigned)mbi->mem_upper); | /* Multiboot says: "The value returned for upper memory is |
| maximally the address of the first upper memory hole minus 1 |
| megabyte.". It also adds: "It is not guaranteed to be this |
| value." aka "YMMV" ;) */ |
| upper_mem = mbi->mem_upper; |
| sos_x86_videomem_printf(1, 0, |
| SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, |
| "Welcome From GRUB to %s%c RAM is %dMB (upper mem = 0x%x kB)", |
| "SOS article 7.5", ',', |
| (unsigned)(upper_mem >> 10) + 1, |
| (unsigned)upper_mem); |
| } |
| else if (magic == 0x42244224) |
| { |
| /* Loaded with SOS bootsect */ |
| upper_mem = arg; |
| sos_x86_videomem_printf(1, 0, |
| SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, |
| "Welcome to %s%c RAM is %dMB (upper mem = 0x%x kB)", |
| "SOS article 7.5", ',', |
| (unsigned)(upper_mem >> 10) + 1, |
| (unsigned)upper_mem); |
| } |
/* Not loaded with grub */ | /* Not loaded with grub, not from an enhanced bootsect */ |
SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, | SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, |
"Welcome to SOS article 7.5"); | "Welcome to SOS article 7.5"); |
|
|
tick_resolution = (struct sos_time) { .sec=0, .nanosec=10000000UL }; | tick_resolution = (struct sos_time) { .sec=0, .nanosec=10000000UL }; |
sos_time_subsysem_setup(& tick_resolution); | sos_time_subsysem_setup(& tick_resolution); |
| |
/* We need a multiboot-compliant boot loader to get the size of the RAM */ | /* We need to know the RAM size */ |
if (magic != MULTIBOOT_BOOTLOADER_MAGIC) | if (upper_mem == 0) |
sos_x86_videomem_putstring(20, 0, | sos_x86_videomem_putstring(20, 0, |
SOS_X86_VIDEO_FG_LTRED | SOS_X86_VIDEO_FG_LTRED |
| SOS_X86_VIDEO_BG_BLUE | | SOS_X86_VIDEO_BG_BLUE |
| SOS_X86_VIDEO_FG_BLINKING, | | SOS_X86_VIDEO_FG_BLINKING, |
"I'm not loaded with Grub !"); | "I don't know RAM size ! Load me with Grub..."); |
for (;;) | for (;;) |
continue; | continue; |
|
|
* Setup physical memory management | * Setup physical memory management |
*/ | */ |
| |
/* Multiboot says: "The value returned for upper memory is maximally | SOS_ASSERT_FATAL(SOS_OK |
the address of the first upper memory hole minus 1 megabyte.". It | == sos_physmem_subsystem_setup((upper_mem<<10) + (1<<20), |
also adds: "It is not guaranteed to be this value." aka "YMMV" ;) */ | &sos_kernel_core_base_paddr, |
sos_physmem_subsystem_setup((mbi->mem_upper<<10) + (1<<20), | &sos_kernel_core_top_paddr)); |
& sos_kernel_core_base_paddr, | |
& sos_kernel_core_top_paddr); | |
/* | /* |
* Switch to paged-memory mode | * Switch to paged-memory mode |
|
|
interrupt call the scheduler */ | interrupt call the scheduler */ |
asm volatile ("sti\n"); | asm volatile ("sti\n"); |
| |
| |
/* Start the 'init' process, which in turns launches the other | /* Start the 'init' process, which in turns launches the other |
programs */ | programs */ |
start_init(); | start_init(); |
| |
* We can safely exit from this function now, for there is already | * We can safely exit from this function now, for there is already |
* an idle Kernel thread ready to make the CPU busy working... | * an idle Kernel thread ready to make the CPU busy working... |
| |
/tmp/sos-code-article7.5/sos/sched.c (2005-04-27 20:17:17.000000000 +0200
) |
|
../sos-code-article7.5/sos/sched.c (2005-06-06 20:47:38.000000000 +0200
) |
|
|
|
return SOS_OK; | return SOS_OK; |
| |
/* Reset the CPU time used in the quantuum */ | /* Reset the CPU time used in the quantuum */ |
memset(& thr->running.user_time_spent_in_slice, 0x0, sizeof(struct sos_time)); | memset(& thr->user_time_spent_in_slice, 0x0, sizeof(struct sos_time)); |
if (SOS_SCHED_PRIO_IS_RT(sos_thread_get_priority(thr))) | if (SOS_SCHED_PRIO_IS_RT(sos_thread_get_priority(thr))) |
{ | { |
|
|
/* Current (user) thread expired its time quantuum ? A kernel | /* Current (user) thread expired its time quantuum ? A kernel |
thread never expires because sos_sched_do_timer_tick() below | thread never expires because sos_sched_do_timer_tick() below |
won't update its user_time_spent_in_slice */ | won't update its user_time_spent_in_slice */ |
if (sos_time_cmp(& thr->running.user_time_spent_in_slice, | if (sos_time_cmp(& thr->user_time_spent_in_slice, |
return TRUE; | return TRUE; |
| |
|
|
if (thread_expired_its_quantuum(current_thread)) | if (thread_expired_its_quantuum(current_thread)) |
{ | { |
/* Reset the CPU time used in the quantuum */ | /* Reset the CPU time used in the quantuum */ |
memset(& current_thread->running.user_time_spent_in_slice, | memset(& current_thread->user_time_spent_in_slice, |
| |
do_yield = TRUE; | do_yield = TRUE; |
|
|
& tick_duration); | & tick_duration); |
| |
/* Update time spent is current timeslice ONLY for a user thread */ | /* Update time spent is current timeslice ONLY for a user thread */ |
sos_time_inc(& interrupted_thread->running.user_time_spent_in_slice, | sos_time_inc(& interrupted_thread->user_time_spent_in_slice, |
} | } |
else | else |
| |