0,0 → 1,1417 |
|
tmp_page_tab equ 0x01000000 |
|
align 4 |
proc mem_test |
mov eax, cr0 |
or eax, 0x60000000 ;disable caching |
mov cr0, eax |
wbinvd ;invalidate cache |
|
xor edi, edi |
mov ebx, 'TEST' |
@@: |
add edi, 0x400000 |
xchg ebx, dword [edi] |
cmp dword [edi], 'TEST' |
xchg ebx, dword [edi] |
je @b |
|
and eax, 0x21 |
mov cr0, eax |
mov eax, edi |
ret |
endp |
|
align 4 |
proc init_memEx |
xor eax, eax |
mov edi, sys_pgdir |
mov ecx, 2048 |
rep stosd |
|
bt [cpu_caps], CAPS_PSE |
jnc .no_PSE |
|
mov ebx, cr4 |
or ebx, CR4_PSE |
mov eax, PG_LARGE+PG_SW |
bt [cpu_caps], CAPS_PGE |
jnc @F |
or eax, PG_GLOBAL |
or ebx, CR4_PGE |
@@: |
mov dword [sys_pgdir], eax |
add eax, 0x00400000 |
mov dword [sys_pgdir+4], eax |
add eax, 0x00400000 |
mov dword [sys_pgdir+8], eax |
add eax, 0x00400000 |
mov dword [sys_pgdir+12], eax |
|
mov dword [sys_pgdir+0x600], sys_master_tab+PG_SW |
mov dword [sys_master_tab+0x600], sys_master_tab+PG_SW |
|
mov cr4, ebx |
|
mov ecx, [pg_data.kernel_tables] |
sub ecx, 4 |
mov eax, tmp_page_tab+PG_SW |
mov edi, sys_pgdir+16 |
mov esi, sys_master_tab+16 |
|
jmp .map_kernel_tabs |
.no_PSE: |
mov eax, PG_SW |
mov esi, tmp_page_tab |
mov ecx, 4096/4 ;0x0 - 0x00FFFFFF |
.map_low: |
mov [esi], eax |
add eax, 0x1000 |
mov [esi+4], eax |
add eax, 0x1000 |
mov [esi+8], eax |
add eax, 0x1000 |
mov [esi+12], eax |
add eax, 0x1000 |
add esi, 16 |
dec ecx |
jnz .map_low ;ÿäðî |
|
mov ecx, [pg_data.kernel_tables] |
mov eax, tmp_page_tab+PG_SW |
mov edi, sys_pgdir |
mov esi, sys_master_tab |
|
.map_kernel_tabs: |
|
mov [edi], eax |
mov [esi], eax |
add eax, 0x1000 |
add edi, 4 |
add esi, 4 |
dec ecx |
jnz .map_kernel_tabs |
|
mov edi, tmp_page_tab |
bt [cpu_caps], CAPS_PSE |
jc @F |
add edi, 4096*4 ;skip low kernel memory |
@@: |
mov ecx, [pg_data.kernel_tables] |
sub ecx, 4 |
shl ecx, 10 |
xor eax, eax |
cld |
rep stosd |
|
mov dword [sys_pgdir+0x600], sys_master_tab+PG_SW |
mov dword [sys_master_tab+0x600], sys_master_tab+PG_SW |
ret |
endp |
|
;align 4 |
;proc init_mem |
; |
; xor eax, eax |
; mov edi, sys_pgdir |
; mov ecx, 2048 |
; rep stosd |
; |
; bt [cpu_caps], CAPS_PSE |
; jc .use_PSE |
; |
; mov eax, PG_SW |
; mov esi, tmp_page_tab |
; mov ecx, 4096/4 ;0x0 - 0x00FFFFFF |
; |
;.map_low: |
; mov [esi], eax |
; add eax, 0x1000 |
; mov [esi+4], eax |
; add eax, 0x1000 |
; mov [esi+8], eax |
; add eax, 0x1000 |
; mov [esi+12], eax |
; add eax, 0x1000 |
; add esi, 16 |
; dec ecx |
; jnz .map_low ;ÿäðî |
|
; mov eax, tmp_page_tab+PG_SW |
; mov ecx, 4 |
; xor ebx, ebx |
|
;.map_page_tables: |
; mov [sys_pgdir+ebx], eax |
; mov [sys_master_tab+ebx], eax |
; add eax, 0x1000 |
; add ebx, 4 |
; dec ecx |
; jnz .map_page_tables |
|
; mov dword [sys_pgdir+0x600], sys_master_tab+PG_SW |
; mov dword [sys_master_tab+0x600], sys_master_tab+PG_SW |
|
; ret |
|
;.use_PSE: |
; mov ebx, cr4 |
; or ebx, CR4_PSE |
; mov eax, PG_LARGE+PG_SW |
; bt [cpu_caps], CAPS_PGE |
; jnc @F |
; or eax, PG_GLOBAL |
; or ebx, CR4_PGE |
;@@: |
; mov dword [sys_pgdir], eax |
; add eax, 0x00400000 |
; mov dword [sys_pgdir+4], eax |
; add eax, 0x00400000 |
; mov dword [sys_pgdir+8], eax |
; add eax, 0x00400000 |
; mov dword [sys_pgdir+12], eax |
; |
; mov dword [sys_pgdir+0x600], sys_master_tab+PG_SW |
; mov dword [sys_master_tab+0x600], sys_master_tab+PG_SW |
|
; mov cr4, ebx |
; ret |
;endp |
|
align 4 |
proc init_page_map |
mov edi, sys_pgmap |
mov ecx, 512/4 |
xor eax,eax |
cld |
rep stosd |
|
not eax |
mov ecx, [pg_data.pagemap_size] |
sub ecx, 512 |
shr ecx, 2 |
rep stosd |
|
mov edi, sys_pgmap+512 |
mov edx, [pg_data.pages_count] |
mov ecx, [pg_data.kernel_tables] |
bt [cpu_caps], CAPS_PSE |
jnc @f |
sub ecx, 4 |
@@: |
sub edx, 4096 |
sub edx, ecx |
mov [pg_data.pages_free], edx |
|
xor eax, eax |
mov ebx, ecx |
shr ecx, 5 |
rep stosd |
|
not eax |
mov ecx, ebx |
and ecx, 31 |
shl eax, cl |
stosd |
|
mov [page_start], sys_pgmap+512 |
mov ebx, sys_pgmap |
add ebx, [pg_data.pagemap_size] |
mov [page_end], ebx |
|
mov [pg_data.pg_mutex], 0 |
|
ret |
endp |
|
;align 4 |
;proc init_pg_mem |
; |
; mov edi, sys_pgmap |
; mov ecx, 512/4 |
; xor eax,eax |
; cld |
; rep stosd |
; |
; not eax |
; mov ecx, [pg_data.pagemap_size] |
; sub ecx, 512 |
; shr ecx, 2 |
; rep stosd |
; |
; shl eax, PAGES_USED |
; mov [sys_pgmap+512], eax |
; |
; mov [page_start], sys_pgmap+512 |
; mov ebx, sys_pgmap |
; add ebx, [pg_data.pagemap_size] |
; mov [page_end], ebx |
; mov eax, [pg_data.pages_count] |
; sub eax, 4096+PAGES_USED |
; mov [pg_data.pages_free], eax |
; |
; mov [pg_data.pages_faults], 0 |
; |
; mov edi, OS_BASE+0x01000000 |
; mov esi, [pg_data.kernel_tables] |
; sub esi, 4 |
; ja @f |
; mov esi, 1 |
;@@: |
; call alloc_page |
; stdcall map_page_table, sys_pgdir, edi, eax |
; add edi, 0x00400000 |
; dec esi |
; jnz @B |
; |
; mov ecx, [pg_data.kernel_tables] |
; sub ecx, 4 |
; shl ecx, 10 |
; mov edi, OS_BASE+0x01000000 |
; shr edi, 10 |
; add edi, pages_tab |
; xor eax, eax |
; cld |
; rep stosd |
; |
; mov eax, cr3 |
; mov cr3, eax |
; |
; mov [pg_data.pg_mutex], 0 |
; ret |
;endp |
|
align 4 |
proc alloc_page |
|
pushfd |
cli |
mov ebx, [page_start] |
mov ecx, [page_end] |
.l1: |
bsf eax,[ebx]; |
jnz .found |
add ebx,4 |
cmp ebx, ecx |
jb .l1 |
popfd |
xor eax,eax |
ret |
.found: |
btr [ebx], eax |
mov [page_start],ebx |
sub ebx, sys_pgmap |
shl ebx, 3 |
add eax,ebx |
shl eax, 12 |
dec [pg_data.pages_free] |
popfd |
ret |
endp |
|
align 4 |
proc alloc_pages stdcall, count:dword |
pushfd |
cli |
mov eax, [count] |
add eax, 7 |
shr eax, 3 |
mov [count], eax |
cmp eax, [pg_data.pages_free] |
ja .fail |
|
mov ecx, [page_start] |
mov ebx, [page_end] |
.find: |
mov edx, [count] |
mov edi, ecx |
|
.match: |
cmp byte [ecx], 0xFF |
jne .next |
dec edx |
jz .ok |
inc ecx |
cmp ecx,ebx |
jb .match |
.fail: xor eax, eax |
popfd |
ret |
.next: |
inc ecx |
cmp ecx, ebx |
jb .find |
popfd |
xor eax, eax |
ret |
.ok: |
sub ecx, edi |
inc ecx |
mov esi, edi |
xor eax, eax |
rep stosb |
sub esi, sys_pgmap |
shl esi, 3+12 |
mov eax, esi |
mov ebx, [count] |
shl ebx, 3 |
sub [pg_data.pages_free], ebx |
popfd |
ret |
endp |
|
align 4 |
proc map_page stdcall,lin_addr:dword,phis_addr:dword,flags:dword |
mov eax, [phis_addr] |
and eax, not 0xFFF |
or eax, [flags] |
mov ebx, [lin_addr] |
shr ebx, 12 |
mov [pages_tab+ebx*4], eax |
mov eax, [lin_addr] |
invlpg [eax] |
ret |
endp |
|
align 4 |
proc free_page |
;arg: eax page address |
pushfd |
cli |
inc [pg_data.pages_free] |
shr eax, 12 ;page index |
mov ebx, sys_pgmap |
bts [ebx], eax ;that's all! |
shr eax, 3 |
and eax, not 3 ;dword offset from page_map |
add eax, ebx |
cmp [page_start], eax |
ja @f |
popfd |
ret |
@@: |
mov [page_start], eax |
popfd |
ret |
endp |
|
align 4 |
proc map_page_table stdcall,page_dir:dword, lin_addr:dword, phis_addr:dword |
mov ebx, [lin_addr] |
shr ebx, 22 |
mov eax, [phis_addr] |
and eax, not 0xFFF |
or eax, PG_UW ;+PG_NOCACHE |
mov ecx, [page_dir] |
mov dword [ecx+ebx*4], eax |
mov dword [master_tab+ebx*4], eax |
mov eax, [lin_addr] |
shr eax, 10 |
add eax, pages_tab |
invlpg [eax] |
ret |
endp |
|
align 4 |
proc init_LFB |
|
cmp dword [LFBAddress], -1 |
jne @f |
|
stdcall kernel_alloc, 0x280000 |
mov [LFBAddress], eax |
ret |
@@: |
test [SCR_MODE],word 0100000000000000b |
jz @f |
call map_LFB |
@@: |
ret |
endp |
|
align 4 |
proc map_LFB |
locals |
pg_count dd ? |
endl |
|
mov edi, [LFBSize] |
mov esi, [LFBAddress] |
shr edi, 12 |
mov [pg_count], edi |
shr edi, 10 |
|
bt [cpu_caps], CAPS_PSE |
jnc .map_page_tables |
mov ebx, esi |
or esi, PG_LARGE+PG_UW |
shr ebx, 20 |
mov ecx, ebx |
@@: |
mov [sys_pgdir+ebx], esi |
add ebx, 4 |
add esi, 0x00400000 |
dec edi |
jnz @B |
|
or dword [sys_pgdir+ecx], PG_GLOBAL |
mov eax, cr3 ;flush TLB |
mov cr3, eax |
ret |
|
.map_page_tables: |
|
@@: |
call alloc_page |
stdcall map_page_table,sys_pgdir, esi, eax |
add esi, 0x00400000 |
dec edi |
jnz @B |
|
mov eax, [LFBAddress] |
mov esi, eax |
shr esi, 10 |
add esi, pages_tab |
or eax, PG_UW |
mov ecx, [pg_count] |
shr ecx, 2 |
.map: |
mov [esi], eax |
add eax, 0x1000 |
mov [esi+4], eax |
add eax, 0x1000 |
mov [esi+8], eax |
add eax, 0x1000 |
mov [esi+12], eax |
add eax, 0x1000 |
add esi, 16 |
sub ecx, 1 |
jnz .map |
|
mov eax, cr3 ;flush TLB |
mov cr3, eax |
|
ret |
endp |
|
align 4 |
proc new_mem_resize stdcall, new_size:dword |
|
stdcall wait_mutex, pg_data.pg_mutex |
|
mov edi, [new_size] |
add edi,4095 |
and edi,not 4095 |
mov [new_size], edi |
|
mov edx,[CURRENT_TASK] |
shl edx,8 |
mov esi, [PROC_BASE+0x8c+edx] |
add esi, 4095 |
and esi, not 4095 |
|
cmp edi, esi |
jae .expand |
|
shr edi, 12 |
shr esi, 12 |
@@: |
mov eax, [pages_tab+0x00181000+edi*4] |
test eax, 1 |
jz .next |
mov dword [pages_tab+0x00181000+edi*4], 2 |
mov ebx, edi |
shl ebx, 12 |
invlpg [ebx+std_application_base_address] |
call free_page |
|
.next: add edi, 1 |
cmp edi, esi |
jb @B |
|
.update_size: |
|
mov ebx, [new_size] |
mov [PROC_BASE+0x8c+edx],ebx |
|
;search threads and update |
;application memory size infomation |
mov ecx,[PROC_BASE+0xb8+edx] |
mov eax,2 |
|
.search_threads: |
;eax = current slot |
;ebx = new memory size |
;ecx = page directory |
cmp eax,[TASK_COUNT] |
jg .search_threads_end |
mov edx,eax |
shl edx,5 |
cmp word [CURRENT_TASK+edx+0xa],9 ;if slot empty? |
jz .search_threads_next |
shl edx,3 |
cmp [PROC_BASE+edx+0xb8],ecx ;if it is our thread? |
jnz .search_threads_next |
mov [PROC_BASE+edx+0x8c],ebx ;update memory size |
.search_threads_next: |
inc eax |
jmp .search_threads |
.search_threads_end: |
xor eax, eax |
dec [pg_data.pg_mutex] |
ret |
|
.expand: |
add edi, new_app_base |
add esi, new_app_base |
|
push esi |
push edi |
|
add edi, 0x3FFFFF |
and edi, not(0x3FFFFF) |
add esi, 0x3FFFFF |
and esi, not(0x3FFFFF) |
|
cmp esi, edi |
jae .grow |
|
xchg esi, edi |
|
mov eax, cr3 |
stdcall map_page,[tmp_task_pdir],eax,dword PG_SW+PG_NOCACHE |
|
@@: |
call alloc_page |
test eax, eax |
jz .exit |
|
stdcall map_page_table,[tmp_task_pdir], edi, eax |
|
push edi |
shr edi, 10 |
add edi, pages_tab |
mov ecx, 1024 |
xor eax, eax |
cld |
rep stosd |
pop edi |
|
add edi, 0x00400000 |
cmp edi, esi |
jb @B |
|
stdcall map_page,[tmp_task_pdir],dword 0,dword PG_UNMAP |
.grow: |
pop edi |
pop esi |
@@: |
call alloc_page |
test eax, eax |
jz .exit |
stdcall map_page,esi,eax,dword PG_UW |
|
push edi |
mov edi, esi |
xor eax, eax |
mov ecx, 1024 |
cld |
rep stosd |
pop edi |
|
add esi, 0x1000 |
cmp esi, edi |
jna @B |
|
jmp .update_size |
.exit: |
xor eax, eax |
inc eax |
dec [pg_data.pg_mutex] |
ret |
endp |
|
align 4 |
proc get_pg_addr stdcall, lin_addr:dword |
mov ebx, [lin_addr] |
shr ebx, 12 |
mov eax, [pages_tab+ebx*4] |
and eax, 0xFFFFF000 |
ret |
endp |
|
align 16 |
proc page_fault_handler |
pushad |
|
mov ebp, esp |
mov eax, cr2 |
sub esp, 4 |
mov [esp], eax |
push ds |
|
mov ax, 0x10 |
mov ds, ax |
|
; mov edx, 0x400 ;bocsh |
; mov al,0xff ;bocsh |
; out dx, al ;bocsh |
; nop ;bocsh fix |
|
|
mov ebx, [ebp-4] |
|
cmp ebx, 0xe0000000 |
jae .lfb_addr |
|
cmp ebx, 0x60400000 |
jae .user_space |
|
cmp ebx, 0x60000000 |
jae .tab_space |
|
jmp .kernel_space |
|
.user_space: |
inc [pg_data.pages_faults] |
|
shr ebx, 12 |
mov eax, [pages_tab+ebx*4] |
|
shr ebx, 10 |
mov edx, [master_tab+ebx*4] |
|
test eax, 2 |
jz .exit |
|
call alloc_page |
and eax, eax |
jz .exit |
|
stdcall map_page,[ebp-4],eax,dword PG_UW |
|
mov esi, [ebp-4] |
and esi, 0xFFFFF000 |
mov ecx, 1024 |
xor eax, eax |
@@: |
mov [esi], eax |
add esi, 4 |
dec ecx |
jnz @B |
.exit: |
pop ds |
mov esp, ebp |
popad |
add esp, 4 |
iretd |
|
.kernel_space: |
shr ebx, 12 |
mov eax, [pages_tab+ebx*4] |
shr ebx, 10 |
mov eax, [master_tab+ebx*4] |
|
pop ds |
mov esp, ebp |
popad |
add esp, 4 |
iretd |
|
.old_addr: |
shr ebx, 12 |
; mov eax, [pages_tab+ebx*4] |
shr ebx, 10 |
mov eax, [master_tab+ebx*4] |
|
pop ds |
mov esp, ebp |
popad |
add esp, 4 |
iretd |
|
.lfb_addr: |
shr ebx, 22 |
;mov ecx, [sys_page_dir] |
mov eax, [master_tab+ebx*4] |
|
pop ds |
mov esp, ebp |
popad |
add esp, 4 |
iretd |
|
.tab_space: |
shr ebx, 12 |
; mov eax, [pages_tab+ebx*4] |
shr ebx, 10 |
;mov ecx, [sys_page_dir] |
mov eax, [master_tab+ebx*4] |
|
pop ds |
mov esp, ebp |
popad |
add esp, 4 |
iretd |
endp |
|
align 4 |
proc map_mem stdcall, lin_addr:dword,pdir:dword,\ |
ofs:dword,buf_size:dword |
mov eax, [buf_size] |
test eax, eax |
jz .exit |
|
mov eax, [pdir] |
and eax, 0xFFFFF000 |
|
stdcall map_page,[ipc_pdir],eax,dword PG_UW |
mov ebx, [ofs] |
shr ebx, 22 |
mov esi, [ipc_pdir] |
mov edi, [ipc_ptab] |
mov eax, [esi+ebx*4] |
and eax, 0xFFFFF000 |
test eax, eax |
jz .exit |
stdcall map_page,edi,eax,dword PG_UW |
; inc ebx |
; add edi, 0x1000 |
; mov eax, [esi+ebx*4] |
; test eax, eax |
; jz @f |
; and eax, 0xFFFFF000 |
; stdcall map_page, edi, eax |
|
@@: mov edi, [lin_addr] |
and edi, 0xFFFFF000 |
mov ecx, [buf_size] |
add ecx, 4095 |
shr ecx, 12 |
inc ecx |
|
mov edx, [ofs] |
shr edx, 12 |
and edx, 0x3FF |
mov esi, [ipc_ptab] |
|
.map: mov eax, [esi+edx*4] |
and eax, 0xFFFFF000 |
test eax, eax |
jz .exit |
stdcall map_page,edi,eax,dword PG_UW |
add edi, 0x1000 |
inc edx |
dec ecx |
jnz .map |
|
.exit: |
ret |
endp |
|
align 4 |
proc map_memEx stdcall, lin_addr:dword,pdir:dword,\ |
ofs:dword,buf_size:dword |
mov eax, [buf_size] |
test eax, eax |
jz .exit |
|
mov eax, [pdir] |
and eax, 0xFFFFF000 |
|
stdcall map_page,[proc_mem_pdir],eax,dword PG_UW |
mov ebx, [ofs] |
shr ebx, 22 |
mov esi, [proc_mem_pdir] |
mov edi, [proc_mem_tab] |
mov eax, [esi+ebx*4] |
and eax, 0xFFFFF000 |
test eax, eax |
jz .exit |
stdcall map_page,edi,eax,dword PG_UW |
|
@@: mov edi, [lin_addr] |
and edi, 0xFFFFF000 |
mov ecx, [buf_size] |
add ecx, 4095 |
shr ecx, 12 |
inc ecx |
|
mov edx, [ofs] |
shr edx, 12 |
and edx, 0x3FF |
mov esi, [proc_mem_tab] |
|
.map: mov eax, [esi+edx*4] |
; and eax, 0xFFFFF000 |
; test eax, eax |
; jz .exit |
stdcall map_page,edi,eax,dword PG_UW |
add edi, 0x1000 |
inc edx |
dec ecx |
jnz .map |
.exit: |
ret |
endp |
|
|
|
|
sys_IPC: |
;input: |
; eax=1 - set ipc buffer area |
; ebx=address of buffer |
; ecx=size of buffer |
; eax=2 - send message |
; ebx=PID |
; ecx=address of message |
; edx=size of message |
|
cmp eax,1 |
jne @f |
call set_ipc_buff |
mov [esp+36], eax |
ret |
|
@@: |
cmp eax, 2 |
jne @f |
stdcall sys_ipc_send, ebx, ecx, edx |
mov [esp+36], eax |
ret |
|
@@: |
xor eax, eax |
not eax |
mov [esp+36], eax |
ret |
|
align 4 |
proc set_ipc_buff |
|
mov eax,[CURRENT_TASK] |
shl eax,8 |
add eax, PROC_BASE |
pushf |
cli |
mov [eax+0xA0],ebx ;set fields in extended information area |
mov [eax+0xA4],ecx |
|
add ebx, new_app_base |
add ecx, ebx |
add ecx, 4095 |
and ecx, not 4095 |
|
.touch: mov eax, [ebx] |
add ebx, 0x1000 |
cmp ebx, ecx |
jna .touch |
|
popf |
xor eax, eax |
ret |
endp |
|
proc sys_ipc_send stdcall, PID:dword, msg_addr:dword, msg_size:dword |
locals |
dst_slot dd ? |
dst_offset dd ? |
buf_size dd ? |
endl |
|
pushf |
cli |
|
mov eax, [PID] |
call pid_to_slot |
test eax,eax |
jz .no_pid |
|
mov [dst_slot], eax |
shl eax,8 |
mov edi,[eax+PROC_BASE+0xa0] ;is ipc area defined? |
test edi,edi |
jz .no_ipc_area |
|
mov ebx, edi |
add edi, new_app_base |
and ebx, 0xFFF |
mov [dst_offset], ebx |
|
mov esi, [eax+PROC_BASE+0xa4] |
mov [buf_size], esi |
|
stdcall map_mem, [ipc_tmp], [PROC_BASE+eax+0xB8],\ |
edi, esi |
|
mov edi, [dst_offset] |
add edi, [ipc_tmp] |
cmp dword [edi], 0 |
jnz .ipc_blocked ;if dword [buffer]<>0 - ipc blocked now |
mov ebx, dword [edi+4] |
mov edx, ebx |
add ebx, 8 |
add ebx, [msg_size] |
cmp ebx, [buf_size] |
ja .buffer_overflow ;esi<0 - not enough memory in buffer |
mov dword [edi+4], ebx |
mov eax,[TASK_BASE] |
mov eax, [eax+0x04] ;eax - our PID |
mov edi, [dst_offset] |
add edi, [ipc_tmp] |
add edi, edx |
mov [edi], eax |
mov ecx, [msg_size] |
|
mov [edi+4], ecx |
add edi, 8 |
mov esi, [msg_addr] |
add esi, new_app_base |
cld |
rep movsb |
|
mov ebx, [ipc_tmp] |
mov edx, ebx |
shr ebx, 12 |
xor eax, eax |
mov [pages_tab+ebx*4], eax |
invlpg [edx] |
|
mov ebx, [ipc_pdir] |
mov edx, ebx |
shr ebx, 12 |
xor eax, eax |
mov [pages_tab+ebx*4], eax |
invlpg [edx] |
|
mov ebx, [ipc_ptab] |
mov edx, ebx |
shr ebx, 12 |
xor eax, eax |
mov [pages_tab+ebx*4], eax |
invlpg [edx] |
|
mov eax, [dst_slot] |
shl eax, 8 |
or [eax+PROC_BASE+0xA8],dword 0x40 |
cmp dword [check_idle_semaphore],20 |
jge .ipc_no_cis |
|
mov dword [check_idle_semaphore],5 |
.ipc_no_cis: |
popf |
xor eax, eax |
ret |
.no_pid: |
popf |
mov eax, 4 |
ret |
.no_ipc_area: |
popf |
xor eax, eax |
inc eax |
ret |
.ipc_blocked: |
popf |
mov eax, 2 |
ret |
.buffer_overflow: |
popf |
mov eax, 3 |
ret |
endp |
|
align 4 |
proc get_mem_info stdcall, val:dword |
|
mov esi, [val] |
|
mov eax, [pg_data.pages_count] |
mov [esi], eax |
mov ebx, [pg_data.pages_free] |
mov [esi+4], ebx |
mov ecx, [pg_data.pages_faults] |
mov [esi+8], ecx |
|
ret |
endp |
|
align 4 |
new_services: |
|
cmp eax,4 |
jle sys_sheduler |
|
cmp eax, 10 |
jb .fail |
ja @f |
|
add ebx, new_app_base |
stdcall get_mem_info, ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 11 |
ja @f |
|
stdcall init_heap, ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 12 |
ja @f |
|
stdcall user_alloc, ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 13 |
ja @f |
|
stdcall user_free, ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 14 |
ja @f |
add ebx,new_app_base |
stdcall get_notify, ebx |
ret |
@@: |
cmp eax, 15 |
ja @f |
mov ecx, [CURRENT_TASK] |
shl ecx, 8 |
mov eax, [ecx+PROC_BASE+APPDATA.fpu_handler] |
mov [ecx+PROC_BASE+APPDATA.fpu_handler], ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 16 |
ja @f |
|
add ebx, new_app_base |
stdcall get_service, ebx |
mov [esp+36], eax |
ret |
@@: |
cmp eax, 17 |
ja @f |
stdcall srv_handlerEx, ebx |
mov [esp+36], eax |
ret |
|
@@: |
.fail: |
xor eax, eax |
mov [esp+36], eax |
ret |
|
|
align 4 |
proc strncmp stdcall, str1:dword, str2:dword, count:dword |
|
mov ecx,[count] |
jecxz .end |
|
mov ebx,ecx |
|
mov edi,[str1] |
mov esi,edi |
xor eax,eax |
repne scasb |
neg ecx ; cx = count - strlen |
add ecx,ebx ; strlen + count - strlen |
|
.okay: |
mov edi,esi |
mov esi,[str2] |
repe cmpsb |
mov al,[esi-1] |
xor ecx,ecx |
|
cmp al,[edi-1] |
ja .str2_big |
je .end |
|
.str1_big: |
sub ecx,2 |
|
.str2_big: |
not ecx |
.end: |
mov eax,ecx |
ret |
endp |
|
align 4 |
proc fpu_save |
clts |
mov ebx, [fpu_owner] |
shl ebx, 8 |
mov eax, [ebx+PROC_BASE+0x10] |
mov ebx, [CURRENT_TASK] |
mov [fpu_owner], ebx |
|
bt [cpu_caps], CAPS_FXSR |
jnc .no_SSE |
|
fxsave [eax] |
ret |
.no_SSE: |
fnsave [eax] |
ret |
endp |
|
align 4 |
proc fpu_restore |
mov ebx, [CURRENT_TASK] |
shl ebx, 8 |
mov eax, [ebx+PROC_BASE+0x10] |
bt [cpu_caps], CAPS_FXSR |
jnc .no_SSE |
|
fxrstor [eax] |
ret |
.no_SSE: |
frstor [eax] |
ret |
endp |
|
align 4 |
proc test_cpu |
locals |
cpu_type dd 0 |
cpu_id dd 0 |
cpu_Intel dd 0 |
cpu_AMD dd 0 |
endl |
|
mov [cpu_type], 0 |
|
pushfd |
pop eax |
mov ecx, eax |
xor eax, 0x40000 |
push eax |
popfd |
pushfd |
pop eax |
xor eax, ecx |
mov [cpu_type], CPU_386 |
jz .end_cpu |
push ecx |
popfd |
|
mov [cpu_type], CPU_486 |
mov eax, ecx |
xor eax, 0x200000 |
push eax |
popfd |
pushfd |
pop eax |
xor eax, ecx |
je .end_cpu |
mov [cpu_id], 1 |
|
xor eax, eax |
cpuid |
mov [cpu_vendor], ebx |
mov [cpu_vendor+4], edx |
mov [cpu_vendor+8], ecx |
cmp ebx, dword [intel_str] |
jne .check_AMD |
cmp edx, dword [intel_str+4] |
jne .check_AMD |
cmp ecx, dword [intel_str+8] |
jne .check_AMD |
mov [cpu_Intel], 1 |
cmp eax, 1 |
jl .end_cpuid |
mov eax, 1 |
cpuid |
mov [cpu_sign], eax |
mov [cpu_info], ebx |
mov [cpu_caps], edx |
mov [cpu_caps+4],ecx |
|
shr eax, 8 |
and eax, 0x0f |
mov [cpu_type], eax |
ret |
|
.end_cpuid: |
mov eax, [cpu_type] |
ret |
|
.check_AMD: |
cmp ebx, dword [AMD_str] |
jne .end_cpu |
cmp edx, dword [AMD_str+4] |
jne .end_cpu |
cmp ecx, dword [AMD_str+8] |
jne .end_cpu |
mov [cpu_AMD], 1 |
cmp eax, 1 |
jl .end_cpuid |
mov eax, 1 |
cpuid |
mov [cpu_sign], eax |
mov [cpu_info], ebx |
mov [cpu_caps], edx |
mov [cpu_caps+4],ecx |
shr eax, 8 |
and eax, 0x0f |
mov [cpu_type], eax |
.end_cpu: |
mov eax, [cpu_type] |
ret |
endp |
|
MEM_WB equ 6 ;write-back memory |
MEM_WC equ 1 ;write combined memory |
MEM_UC equ 0 ;uncached memory |
|
align 4 |
proc init_mtrr |
|
cmp [0x2f0000+0x901c],byte 2 |
je .exit |
|
mov eax, cr0 |
or eax, 0x60000000 ;disable caching |
mov cr0, eax |
wbinvd ;invalidate cache |
|
mov ecx, 0x2FF |
rdmsr ; |
push eax |
|
xor edx, edx |
xor eax, eax |
mov ecx, 0x2FF |
wrmsr ;disable all MTRR |
|
stdcall set_mtrr, dword 0,dword 0,[MEM_AMOUNT],MEM_WB |
stdcall set_mtrr, dword 1,[LFBAddress],[LFBSize],MEM_WC |
xor edx, edx |
xor eax, eax |
mov ecx, 0x204 |
mov ebx, 6 |
@@: |
wrmsr ;disable unused MTRR |
inc ecx |
wrmsr |
inc ecx |
dec ebx |
jnz @b |
|
wbinvd ;again invalidate |
|
pop eax |
or eax, 0x800 ;set default memtype to UC |
and al, 0xF0 |
mov ecx, 0x2FF |
wrmsr ;and enable MTRR |
|
mov eax, cr0 |
and eax, not 0x60000000 |
mov cr0, eax ; enable caching |
.exit: |
ret |
endp |
|
align 4 |
proc set_mtrr stdcall, reg:dword,base:dword,size:dword,mem_type:dword |
|
xor edx, edx |
mov eax, [base] |
or eax, [mem_type] |
mov ecx, [reg] |
lea ecx, [0x200+ecx*2] |
wrmsr |
|
mov ebx, [size] |
dec ebx |
mov eax, 0xFFFFFFFF |
mov edx, 0x0000000F |
sub eax, ebx |
sbb edx, 0 |
or eax, 0x800 |
inc ecx |
wrmsr |
ret |
endp |
|
|
iglobal |
align 4 |
intel_str db "GenuineIntel",0 |
AMD_str db "AuthenticAMD",0 |
endg |
|
uglobal |
align 16 |
irq_tab rd 16 |
|
|
MEM_FreeSpace rd 1 |
|
ipc_tmp rd 1 |
ipc_pdir rd 1 |
ipc_ptab rd 1 |
|
proc_mem_map rd 1 |
proc_mem_pdir rd 1 |
proc_mem_tab rd 1 |
|
tmp_task_pdir rd 1 |
tmp_task_ptab rd 1 |
tmp_task_data rd 1 |
|
current_pdir rd 1 |
|
fpu_data rd 1 |
fdd_buff rd 1 |
|
;;CPUID information |
|
cpu_vendor rd 3 |
cpu_sign rd 1 |
cpu_info rd 1 |
|
endg |
|
uglobal |
align 16 |
dll_tab rb 32*32 |
srv_tab rb 32*32 |
dll_map rd 1 |
srv_map rd 1 |
|
mem_used_list rd 1 |
mem_block_list rd 64 |
mem_block_map rb 512 |
mem_block_arr rd 1 |
mem_block_start rd 1 |
mem_block_end rd 1 |
mem_block_mask rd 2 |
|
page_start rd 1 |
page_end rd 1 |
sys_page_map rd 1 |
app_load rd 1 |
endg |
|
|
; push eax |
; push edx |
; mov edx, 0x400 ;bocsh |
; mov al,0xff ;bocsh |
; out dx, al ;bocsh |
; nop ;bocsh fix |
; pop edx |
; pop eax |
|