feat(kernel): double linked list helper
This commit is contained in:
parent
cadddcbb13
commit
549c063b38
11 changed files with 504 additions and 77 deletions
|
@ -28,6 +28,7 @@ SRCS = kernel.asm \
|
||||||
pic.inc \
|
pic.inc \
|
||||||
idt.inc \
|
idt.inc \
|
||||||
heap.inc \
|
heap.inc \
|
||||||
|
queue.inc \
|
||||||
dev/console.inc \
|
dev/console.inc \
|
||||||
dev/at/pit.inc \
|
dev/at/pit.inc \
|
||||||
dev/at/cga.inc \
|
dev/at/cga.inc \
|
||||||
|
|
|
@ -2,6 +2,9 @@ KERNEL_VIRT_BASE = 0xC0000000
|
||||||
KERNEL_OFFSET = 0x100000
|
KERNEL_OFFSET = 0x100000
|
||||||
KBASE = KERNEL_VIRT_BASE + KERNEL_OFFSET
|
KBASE = KERNEL_VIRT_BASE + KERNEL_OFFSET
|
||||||
|
|
||||||
|
KERNEL_HEAP_BASE = KERNEL_VIRT_BASE + 0x800000
|
||||||
|
KERNEL_HEAP_SIZE = 260046848
|
||||||
|
|
||||||
PSIZE = 0x1000
|
PSIZE = 0x1000
|
||||||
|
|
||||||
STPDBOOT_MAGIC = 0x53545044
|
STPDBOOT_MAGIC = 0x53545044
|
||||||
|
@ -17,6 +20,7 @@ BUILD_DATE equ "@DATE@"
|
||||||
CR = 0x0D
|
CR = 0x0D
|
||||||
LF = 0x0A
|
LF = 0x0A
|
||||||
|
|
||||||
|
|
||||||
CONFIG_COMPAT_I386 = 0
|
CONFIG_COMPAT_I386 = 0
|
||||||
CONFIG_TRACE_PMM = 1
|
CONFIG_TRACE_PMM = 1
|
||||||
|
CONFIG_TRACE_VMEM = 1
|
||||||
|
CONFIG_TRACE_VMM = 1
|
||||||
|
|
|
@ -47,6 +47,7 @@ kmain:
|
||||||
call mm_bootstrap
|
call mm_bootstrap
|
||||||
|
|
||||||
call pmm_init
|
call pmm_init
|
||||||
|
call vmm_bootstrap
|
||||||
|
|
||||||
mov eax, 4
|
mov eax, 4
|
||||||
call pmm_alloc
|
call pmm_alloc
|
||||||
|
@ -111,6 +112,7 @@ kmain:
|
||||||
jmp .halt
|
jmp .halt
|
||||||
|
|
||||||
include 'klog.inc'
|
include 'klog.inc'
|
||||||
|
include 'queue.inc'
|
||||||
include 'dev/console.inc'
|
include 'dev/console.inc'
|
||||||
include 'dev/dev.inc'
|
include 'dev/dev.inc'
|
||||||
include 'mm/mm.inc'
|
include 'mm/mm.inc'
|
||||||
|
@ -132,7 +134,7 @@ kmain:
|
||||||
szMsgKernelAlive db "Kernel (", VERSION_FULL , ") is alive", 0
|
szMsgKernelAlive db "Kernel (", VERSION_FULL , ") is alive", 0
|
||||||
szMsgBuildDate db "Built ", BUILD_DATE, 0
|
szMsgBuildDate db "Built ", BUILD_DATE, 0
|
||||||
szErrorBootProtocol db "Error: wrong magic number", 0
|
szErrorBootProtocol db "Error: wrong magic number", 0
|
||||||
|
szKernelHeapStr db "KERNEL-HEAP", 0
|
||||||
;; Variable: stBootInfo
|
;; Variable: stBootInfo
|
||||||
;; <BootInfo>
|
;; <BootInfo>
|
||||||
stBootInfo BootInfo
|
stBootInfo BootInfo
|
||||||
|
|
|
@ -3,6 +3,7 @@ MM_KERNEL_PTE_BASE = 0xFFC00000
|
||||||
include '../sys/mmu.inc'
|
include '../sys/mmu.inc'
|
||||||
include 'bootstrap.inc'
|
include 'bootstrap.inc'
|
||||||
include 'pmm.inc'
|
include 'pmm.inc'
|
||||||
|
include 'vmem.inc'
|
||||||
include 'vmm.inc'
|
include 'vmm.inc'
|
||||||
|
|
||||||
mm_init:
|
mm_init:
|
||||||
|
|
9
kernel/mm/uvm/uvm.inc
Normal file
9
kernel/mm/uvm/uvm.inc
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
;; File: uvm.inc
|
||||||
|
|
||||||
|
include 'uvm_km.inc'
|
||||||
|
|
||||||
|
;; Function: uvm_init
|
||||||
|
;;
|
||||||
|
;; Sets up the UVM system
|
||||||
|
uvm_init:
|
||||||
|
ret
|
0
kernel/mm/uvm/uvm_km.inc
Normal file
0
kernel/mm/uvm/uvm_km.inc
Normal file
5
kernel/mm/uvm/uvm_map.inc
Normal file
5
kernel/mm/uvm/uvm_map.inc
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
;; File: uvm_map.inc
|
||||||
|
|
||||||
|
struc VmMap {
|
||||||
|
|
||||||
|
}
|
278
kernel/mm/vmem.inc
Normal file
278
kernel/mm/vmem.inc
Normal file
|
@ -0,0 +1,278 @@
|
||||||
|
;; File: vmem.inc
|
||||||
|
;;
|
||||||
|
;; General purpose resource allocator.
|
||||||
|
;; Based on <tinyvmem at https://github.com/rdmsr/tinyvmem> and on <Bonwick's paper at https://www.usenix.org/legacy/event/usenix01/full_papers/bonwick/bonwick.pdf>
|
||||||
|
|
||||||
|
;;; MARK: macros and structs
|
||||||
|
|
||||||
|
VM_BESTFIT = (1 shl 0)
|
||||||
|
VM_INSTANTFIT = (1 shl 1)
|
||||||
|
VM_NEXTFIT = (1 shl 2)
|
||||||
|
VM_SLEEP = (1 shl 3)
|
||||||
|
VM_NOSLEEP = (1 shl 4)
|
||||||
|
VM_BOOTSTRAP = (1 shl 5)
|
||||||
|
|
||||||
|
STATIC_SEG_COUNT = 64
|
||||||
|
|
||||||
|
FREELISTS_N = 4 * 8
|
||||||
|
HASHTABLE_N = 16
|
||||||
|
|
||||||
|
SEGMENT_ALLOCATED = 0
|
||||||
|
SEGMENT_FREE = 1
|
||||||
|
SEGMENT_SPAN = 2
|
||||||
|
|
||||||
|
macro GET_LIST reg, N {
|
||||||
|
bsr reg, reg
|
||||||
|
xor reg, 31
|
||||||
|
add reg, -N
|
||||||
|
sub reg, 1
|
||||||
|
}
|
||||||
|
|
||||||
|
struc VmSegment {
|
||||||
|
.type db ?
|
||||||
|
.imported db ?
|
||||||
|
.base dd ?
|
||||||
|
.size dd ?
|
||||||
|
|
||||||
|
.spanlist ListEntry
|
||||||
|
.seglist ListEntry
|
||||||
|
}
|
||||||
|
DEFN VmSegment
|
||||||
|
|
||||||
|
;; Struc: Vmem
|
||||||
|
struc Vmem {
|
||||||
|
.name db 16 dup(0)
|
||||||
|
.base dd ?
|
||||||
|
.size dd ?
|
||||||
|
.quantum dd ?
|
||||||
|
.alloc dd ?
|
||||||
|
.free dd ?
|
||||||
|
.source dd ?
|
||||||
|
.vmflag dd ?
|
||||||
|
|
||||||
|
.freelist dd FREELISTS_N dup(0)
|
||||||
|
.hashtable dd HASHTABLE_N dup(0)
|
||||||
|
.spanlist ListHead 0
|
||||||
|
}
|
||||||
|
DEFN Vmem
|
||||||
|
|
||||||
|
;;; MARK: private functions
|
||||||
|
|
||||||
|
;; Function: _murmur32
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Address
|
||||||
|
;;
|
||||||
|
;; Out:
|
||||||
|
;; EAX - Hash
|
||||||
|
;;
|
||||||
|
_murmur32:
|
||||||
|
; hash ← hash XOR (hash >> 16)
|
||||||
|
mov ecx, eax
|
||||||
|
shr ecx, 16
|
||||||
|
xor eax, ecx
|
||||||
|
; hash ← hash × 0x85ebca6b
|
||||||
|
mov ecx, 0x85ebca6b
|
||||||
|
mul ecx
|
||||||
|
; hash ← hash XOR (hash >> 13)
|
||||||
|
mov ecx, eax
|
||||||
|
shr ecx, 13
|
||||||
|
xor eax, ecx
|
||||||
|
; hash ← hash × 0xc2b2ae35
|
||||||
|
mov ecx, 0xc2b2ae35
|
||||||
|
mul ecx
|
||||||
|
; hash ← hash XOR (hash >> 16)
|
||||||
|
mov ecx, eax
|
||||||
|
shr ecx, 16
|
||||||
|
xor eax, ecx
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: _hash_table_addr
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Vmem
|
||||||
|
;; EDX - ADDR
|
||||||
|
__hash_table_addr:
|
||||||
|
push ebp
|
||||||
|
mov ebp, esp
|
||||||
|
push esi
|
||||||
|
|
||||||
|
mov esi, eax
|
||||||
|
mov eax, edx
|
||||||
|
call _murmur32
|
||||||
|
and eax, HASHTABLE_N-1 ; x % y (y is a power of two)
|
||||||
|
shl eax, 2
|
||||||
|
|
||||||
|
mov edx, esi
|
||||||
|
add edx, Vmem.hashtable
|
||||||
|
add edx, eax
|
||||||
|
mov eax, [edx]
|
||||||
|
|
||||||
|
pop esi
|
||||||
|
leave
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: _vmm_segfree
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Segment address
|
||||||
|
_vmm_segfree:
|
||||||
|
;mov ecx, eax
|
||||||
|
;add ecx, VmSegment.seglist.next
|
||||||
|
|
||||||
|
;mov edx, [pVmmFreeSegHead]
|
||||||
|
;or edx, edx
|
||||||
|
;jz @f
|
||||||
|
;mov [eax + VmSegment.seglist.next], edx
|
||||||
|
;mov [edx + VmSegment.seglist.prev], ecx
|
||||||
|
;@@:
|
||||||
|
; mov [pVmmFreeSegHead], eax
|
||||||
|
; mov [eax + VmSegment.seglist.prev], ecx
|
||||||
|
;
|
||||||
|
; inc [iVmmFreeSegCount]
|
||||||
|
ret
|
||||||
|
;
|
||||||
|
; ;; Function: _vmm_segalloc
|
||||||
|
;_vmm_segalloc:
|
||||||
|
; mov eax, [pVmmFreeSegHead]
|
||||||
|
; or eax, eax
|
||||||
|
; jz @f
|
||||||
|
;
|
||||||
|
; dec [iVmmFreeSegCount]
|
||||||
|
;@@:
|
||||||
|
; ret
|
||||||
|
|
||||||
|
|
||||||
|
;;; MARK: public functions
|
||||||
|
|
||||||
|
;; Function: vmem_create
|
||||||
|
;;
|
||||||
|
;; Creates a new <Vmem> arena whose initial span is [Base, Base + Size).
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to a <Vmem> object.
|
||||||
|
;; EDX - String.
|
||||||
|
;; ECX - Base.
|
||||||
|
;; ESP[4] - Size in bytes.
|
||||||
|
;; ESP[8] - Quantum.
|
||||||
|
;; ESP[12] - Alloc function.
|
||||||
|
;; ESP[16] - Free function.
|
||||||
|
;; ESP[20] - Source.
|
||||||
|
;; ESP[24] - Flags. (<VM_SLEEP> or <VM_NOSLEEP>)
|
||||||
|
vmem_create:
|
||||||
|
push ebp
|
||||||
|
mov ebp, esp
|
||||||
|
|
||||||
|
mov [eax + Vmem.base], ecx
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if CONFIG_TRACE_VMEM
|
||||||
|
push esi
|
||||||
|
push edi
|
||||||
|
push ebx
|
||||||
|
|
||||||
|
mov esi, eax
|
||||||
|
mov edi, edx
|
||||||
|
mov ebx, ecx
|
||||||
|
|
||||||
|
mov eax, esi
|
||||||
|
mov edx, edi
|
||||||
|
mov ecx, ebx
|
||||||
|
|
||||||
|
pop ebx
|
||||||
|
pop edi
|
||||||
|
pop esi
|
||||||
|
end if
|
||||||
|
|
||||||
|
leave
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_destroy
|
||||||
|
;;
|
||||||
|
;; Destroys an arena
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to a <Vmem> object.
|
||||||
|
vmem_destroy:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_alloc
|
||||||
|
;;
|
||||||
|
;; Allocates n-bytes from arena.
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to a <Vmem> object.
|
||||||
|
;; EDX - Size in bytes.
|
||||||
|
;; ECX - Flags
|
||||||
|
;;
|
||||||
|
;; Out:
|
||||||
|
;; EAX - Allocated address on succes, 0 on failure.
|
||||||
|
vmem_alloc:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_free
|
||||||
|
;;
|
||||||
|
;; Free n-bytes at address to arena
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to a <Vmem> object.
|
||||||
|
;; EDX - Address.
|
||||||
|
;; ECX - Size in bytes.
|
||||||
|
vmem_free:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_xalloc
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to a <Vmem> object.
|
||||||
|
;; EDX - Size in bytes.
|
||||||
|
;; ECX - Alignment boundary.
|
||||||
|
;; ESP[4] - Phase.
|
||||||
|
;; ESP[8] - Nocross.
|
||||||
|
;; ESP[12] - Min address.
|
||||||
|
;; ESP[16] - Max address.
|
||||||
|
;; ESP[20] - Flags. (<VM_BESTFIT>, <VM_INSTANTFIT>, <VM_NEXTFIT>, <VM_SLEEP>, <VM_NOSLEEP>)
|
||||||
|
;;
|
||||||
|
;; Out:
|
||||||
|
;; EAX - Allocated address on succes, 0 on failure.
|
||||||
|
vmem_xalloc:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_xfree
|
||||||
|
;;
|
||||||
|
;; Frees n-bytes at address.
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to <Vmem> object.
|
||||||
|
;; EDX - Address.
|
||||||
|
;; ECX - Size in bytes.
|
||||||
|
vmem_xfree:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: vmem_add
|
||||||
|
;;
|
||||||
|
;; Adds a span [Address, Address + Size) to an arena.
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to <Vmem> object.
|
||||||
|
;; EDX - Address.
|
||||||
|
;; ECX - Size in bytes.
|
||||||
|
;; ESP[4] - Flags. (<VM_SLEEP> or <VM_NOSLEEP>)
|
||||||
|
;;
|
||||||
|
;; Out:
|
||||||
|
;; EAX - Return Address on success, 0 on failure.
|
||||||
|
vmem_add:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;;; MARK: variables
|
||||||
|
|
||||||
|
aVmemStaticSegs db STATIC_SEG_COUNT*sizeof.VmSegment dup(0)
|
||||||
|
pVmemFreeSegHead dd 0
|
||||||
|
iVmemFreeSegCount dd 0
|
||||||
|
|
||||||
|
if CONFIG_TRACE_VMM
|
||||||
|
szTraceVmemCreate db "Trace(VMEM): Create %s [%x, %x)", 0
|
||||||
|
szTraceVmemAdd db "Trace(VMEM): %s: Add span [%x, %x)", 0
|
||||||
|
szTraceVmemDestroy db "Trace(VMEM): Destroy %s", 0
|
||||||
|
end if
|
|
@ -1,80 +1,82 @@
|
||||||
;; File: vm.inc
|
;; File: vm.inc
|
||||||
;; Based on <https://github.com/rdmsr/tinyvmem at tinyvm>
|
;; Based on <tinyvmem at https://github.com/rdmsr/tinyvmem> and on <Bonwick's paper at https://www.usenix.org/legacy/event/usenix01/full_papers/bonwick/bonwick.pdf>
|
||||||
|
|
||||||
VM_BESTFIT = (1 shl 0)
|
;; Function: vmm_init
|
||||||
VM_INSTANTFIT = (1 shl 1)
|
;;
|
||||||
VM_NEXTFIT = (1 shl 2)
|
;; Initializes a Vmem arena
|
||||||
VM_SLEEP = (1 shl 3)
|
|
||||||
VM_NOSLEEP = (1 shl 4)
|
|
||||||
VM_BOOTSTRAP = (1 shl 5)
|
|
||||||
|
|
||||||
FREELISTS_N = 4 * 8
|
|
||||||
HASHTABLE_N = 16
|
|
||||||
|
|
||||||
SEGMENT_ALLOCATED = 0
|
|
||||||
SEGMENT_FREE = 1
|
|
||||||
SEGMENT_SPAN = 2
|
|
||||||
|
|
||||||
struc VmSegment {
|
|
||||||
.type db ?
|
|
||||||
.imported db ?
|
|
||||||
.base dd ?
|
|
||||||
.size dd ?
|
|
||||||
}
|
|
||||||
|
|
||||||
struc VmObject {
|
|
||||||
.tmp dd ?
|
|
||||||
}
|
|
||||||
|
|
||||||
struc VmPager {
|
|
||||||
.tmp dd ?
|
|
||||||
}
|
|
||||||
|
|
||||||
struc Vmem {
|
|
||||||
.name db 32 dup(0)
|
|
||||||
.base dd ?
|
|
||||||
.size dd ?
|
|
||||||
.quantum dd ?
|
|
||||||
.alloc dd ?
|
|
||||||
.free dd ?
|
|
||||||
.source dd ?
|
|
||||||
.qcache_max dd ?
|
|
||||||
.vmflag dd ? ;; db ?
|
|
||||||
|
|
||||||
.segqueue dd ?
|
|
||||||
.freelist dd FREELISTS_N dup(0)
|
|
||||||
.hashtable dd HASHTABLE_N dup(0)
|
|
||||||
.spanlist dd ?
|
|
||||||
}
|
|
||||||
|
|
||||||
;; Subroutine: _murmur32
|
|
||||||
;;
|
;;
|
||||||
;; In:
|
;; In:
|
||||||
;; EAX - Address
|
;; EAX - Pointer to a Vmem dest
|
||||||
;;
|
;; EDX - Base address
|
||||||
;; Out:
|
;; ECX - Size
|
||||||
;; EAX - Hash
|
;; ESP[4] - Quantum
|
||||||
;;
|
;; ESP[8] - Pointer to alloc function
|
||||||
_murmur32:
|
;; ESP[12] - Pointer to free function
|
||||||
; hash ← hash XOR (hash >> 16)
|
;; ESP[16] - Poiter to Vmem source
|
||||||
mov ecx, eax
|
;; ESP[20] - qcache max
|
||||||
shr ecx, 16
|
;; ESP[24] - Flags
|
||||||
xor eax, ecx
|
vmm_init:
|
||||||
; hash ← hash × 0x85ebca6b
|
push ebp
|
||||||
mov ecx, 0x85ebca6b
|
mov ebp, esp
|
||||||
mul ecx
|
|
||||||
; hash ← hash XOR (hash >> 13)
|
push esi
|
||||||
mov ecx, eax
|
push edi
|
||||||
shr ecx, 13
|
|
||||||
xor eax, ecx
|
mov [eax + Vmem.base], edx
|
||||||
; hash ← hash × 0xc2b2ae35
|
mov [eax + Vmem.size], ecx
|
||||||
mov ecx, 0xc2b2ae35
|
|
||||||
mul ecx
|
; copy other param from the stack
|
||||||
; hash ← hash XOR (hash >> 16)
|
mov ecx, 28
|
||||||
mov ecx, eax
|
mov edx, esp
|
||||||
shr ecx, 16
|
add edx, 4
|
||||||
xor eax, ecx
|
mov esi, edx
|
||||||
|
mov edx, eax
|
||||||
|
add edx, Vmem.quantum
|
||||||
|
mov edi, edx
|
||||||
|
rep movsd
|
||||||
|
|
||||||
|
mov ecx, [eax + Vmem.size]
|
||||||
|
or ecx, ecx
|
||||||
|
jz @f
|
||||||
|
|
||||||
|
mov edx, [eax + Vmem.source]
|
||||||
|
or edx, edx
|
||||||
|
jnz @f
|
||||||
|
|
||||||
|
mov edx, [eax + Vmem.base]
|
||||||
|
|
||||||
|
; call vmm_add
|
||||||
|
add esp, 4
|
||||||
|
|
||||||
|
@@:
|
||||||
|
pop edi
|
||||||
|
pop esi
|
||||||
|
|
||||||
|
leave
|
||||||
ret
|
ret
|
||||||
|
|
||||||
vmem_init:
|
;; Function: vmm_bootstrap
|
||||||
|
;;
|
||||||
|
vmm_bootstrap:
|
||||||
|
push ebp
|
||||||
|
mov ebp, esp
|
||||||
|
|
||||||
|
push ebx
|
||||||
|
|
||||||
|
xor ebx, ebx
|
||||||
|
@@:
|
||||||
|
mov eax, aVmemStaticSegs
|
||||||
|
add eax, ebx
|
||||||
|
|
||||||
|
call _vmm_segfree
|
||||||
|
|
||||||
|
add ebx, sizeof.VmSegment
|
||||||
|
cmp ebx, STATIC_SEG_COUNT*sizeof.VmSegment
|
||||||
|
jl @b
|
||||||
|
|
||||||
|
pop ebx
|
||||||
|
|
||||||
|
leave
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
||||||
|
|
125
kernel/queue.inc
Normal file
125
kernel/queue.inc
Normal file
|
@ -0,0 +1,125 @@
|
||||||
|
;; File: queue.inc
|
||||||
|
|
||||||
|
;;; MARK: doubly linked lists
|
||||||
|
|
||||||
|
;; Group: List
|
||||||
|
;; Doubly linked lists
|
||||||
|
|
||||||
|
;; Struc: ListHead
|
||||||
|
struc ListHead initial {
|
||||||
|
.first dd initial
|
||||||
|
}
|
||||||
|
|
||||||
|
;; Struc: ListEntry
|
||||||
|
struc ListEntry {
|
||||||
|
.next dd ?
|
||||||
|
.prev dd ?
|
||||||
|
}
|
||||||
|
|
||||||
|
;; Function: list_insert_head
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Head (see <ListHead>)
|
||||||
|
;; EDX - Element (see <ListEntry>)
|
||||||
|
;;
|
||||||
|
list_insert_head:
|
||||||
|
mov ecx, [eax]
|
||||||
|
mov [edx], ecx
|
||||||
|
or ecx, ecx
|
||||||
|
jz @f
|
||||||
|
mov [ecx + 4], edx
|
||||||
|
@@:
|
||||||
|
mov [eax], edx
|
||||||
|
mov [edx + 4], edx
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: list_remove
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Element.
|
||||||
|
list_remove:
|
||||||
|
mov ecx, [eax + 4]
|
||||||
|
mov edx, [eax]
|
||||||
|
or edx, edx
|
||||||
|
jz @f
|
||||||
|
mov [edx + 4], ecx
|
||||||
|
@@:
|
||||||
|
mov [ecx], edx
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: list_map
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Pointer to <ListHead>
|
||||||
|
;; EDX - Function to apply
|
||||||
|
;;
|
||||||
|
list_map:
|
||||||
|
push ebp
|
||||||
|
mov ebp, esp
|
||||||
|
|
||||||
|
push esi
|
||||||
|
push edi
|
||||||
|
|
||||||
|
; save function pointer
|
||||||
|
mov esi, edx
|
||||||
|
|
||||||
|
; load first elem
|
||||||
|
mov edi, [eax]
|
||||||
|
@@:
|
||||||
|
or edi, edi
|
||||||
|
jz @f ; exit loop if element is null
|
||||||
|
|
||||||
|
mov eax, edi
|
||||||
|
call esi
|
||||||
|
|
||||||
|
mov edi, [edi] ; load next element
|
||||||
|
jmp @b
|
||||||
|
@@:
|
||||||
|
pop edi
|
||||||
|
pop esi
|
||||||
|
|
||||||
|
leave
|
||||||
|
ret
|
||||||
|
|
||||||
|
;;; MARK: doubly linked tail queues
|
||||||
|
|
||||||
|
;; Group: TailQ
|
||||||
|
;; doubly linked tail queues
|
||||||
|
|
||||||
|
;; Struc: TailQHead
|
||||||
|
struc TailQHead {
|
||||||
|
.first dd ?
|
||||||
|
.last dd $$
|
||||||
|
}
|
||||||
|
|
||||||
|
;; Struc: TailQEntry
|
||||||
|
struc TailQEntry {
|
||||||
|
.next dd ?
|
||||||
|
.prev dd ?
|
||||||
|
}
|
||||||
|
|
||||||
|
;; Function: tailq_insert_head
|
||||||
|
;;
|
||||||
|
;; In:
|
||||||
|
;; EAX - Head.
|
||||||
|
;; EDX - Element.
|
||||||
|
tailq_insert_head:
|
||||||
|
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: tailq_insert_after
|
||||||
|
;;
|
||||||
|
tailq_insert_after:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: tailq_insert_tail
|
||||||
|
tailq_insert_tail:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: tailq_remove
|
||||||
|
tailq_remove:
|
||||||
|
ret
|
||||||
|
|
||||||
|
;; Function: tailq_map
|
||||||
|
tailq_map:
|
||||||
|
ret
|
|
@ -1,7 +1,7 @@
|
||||||
;; File: cpu.inc
|
;; File: cpu.inc
|
||||||
|
|
||||||
|
|
||||||
;; Structure: tss
|
;; Struc: tss
|
||||||
;;
|
;;
|
||||||
;; > 31 23 15 7 0
|
;; > 31 23 15 7 0
|
||||||
;; > +----------|----------+----------|----------+
|
;; > +----------|----------+----------|----------+
|
||||||
|
@ -93,7 +93,7 @@ struc GDTGate {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
;; Structure: IDTGate
|
;; Struc: IDTGate
|
||||||
;; .offset_low - TODO
|
;; .offset_low - TODO
|
||||||
;; .selector - TODO
|
;; .selector - TODO
|
||||||
;; .zero - TODO
|
;; .zero - TODO
|
||||||
|
|
Loading…
Reference in a new issue