diff --git a/kernel/branches/Kolibri-acpi/blkdev/disk.inc b/kernel/branches/Kolibri-acpi/blkdev/disk.inc index 6b0983385d..9487920943 100644 --- a/kernel/branches/Kolibri-acpi/blkdev/disk.inc +++ b/kernel/branches/Kolibri-acpi/blkdev/disk.inc @@ -350,8 +350,10 @@ disk_add: inc eax cmp byte [ebx+eax-1], 0 jnz @b -; 2b. Call the heap manager. +; 2b. Call the heap manager. Note that it can change ebx. + push ebx call malloc + pop ebx ; 2c. Check the result. If allocation failed, go to 7. pop esi ; restore allocated pointer to DISK test eax, eax @@ -418,7 +420,7 @@ disk_del: push esi ; save used registers to be stdcall ; 1. Force media to be removed. If the media is already removed, the ; call does nothing. - mov esi, [esp+4+8] ; esi = handle of the disk + mov esi, [esp+4+4] ; esi = handle of the disk stdcall disk_media_changed, esi, 0 ; 2. Delete the structure from the global list. ; 2a. Acquire the mutex. @@ -975,15 +977,33 @@ virtual at ebp+8 .start dq ? .length dq ? end virtual -; Currently no file systems are supported, so just allocate the PARTITION +; When disk_add_partition is called, ebx contains a pointer to +; a two-sectors-sized buffer. This function saves ebx in the stack +; immediately before ebp. +virtual at ebp-4 +.buffer dd ? +end virtual +; 1. Read the bootsector to the buffer. + mov al, DISKFUNC.read + mov ebx, [.buffer] + add ebx, 512 + push 1 + stdcall disk_call_driver, ebx, dword [.start], dword [.start+4], esp +; 2. Run tests for all supported filesystems. If at least one test succeeded, +; go to 4. +; For tests: qword [ebp+8] = partition start, qword [ebp+10h] = partition +; length, [esp] = 0 if reading bootsector failed or 1 if succeeded, +; ebx points to the buffer for bootsector. + call fat_create_partition + test eax, eax + jnz .success +; 3. No file system has recognized the volume, so just allocate the PARTITION ; structure without extra fields. -; 1. Allocate and check result. push sizeof.PARTITION pop eax call malloc test eax, eax jz .nothing -; 2. Fill the common fields: copy .start and .length. mov edx, dword [.start] mov dword [eax+PARTITION.FirstSector], edx mov edx, dword [.start+4] @@ -992,8 +1012,12 @@ end virtual mov dword [eax+PARTITION.Length], edx mov edx, dword [.length+4] mov dword [eax+PARTITION.Length+4], edx + mov [eax+PARTITION.Disk], esi + and [eax+PARTITION.FSUserFunctions], 0 +.success: .nothing: -; 3. Return with eax = pointer to PARTITION or NULL. +; 4. Return with eax = pointer to PARTITION or NULL. + pop ecx ret ; This function is called from file_system_lfn. @@ -1061,6 +1085,7 @@ dyndisk_handler: ; 6. Now we are sure that the DISK structure is not going to die at least ; while we are working with it, so release the global mutex. call mutex_unlock + pop ecx ; pop from the stack saved value of esi ; 7. Acquire the mutex for media object. pop edi ; restore edi lea ecx, [ebx+DISK.MediaLock] @@ -1175,15 +1200,36 @@ fs_dyndisk: .main: cmp ecx, [edx+DISK.NumPartitions] jae .notfound - mov dword [esp+32], ERROR_UNKNOWN_FS + mov eax, [edx+DISK.Partitions] + mov eax, [eax+ecx*4] + mov edi, [eax+PARTITION.FSUserFunctions] + test edi, edi + jz .nofs + mov ecx, [ebx] + cmp [edi], ecx + jbe .unsupported + push edx + push ebp + mov ebp, eax + call dword [edi+4+ecx*4] + pop ebp + pop edx + mov dword [esp+32], eax + mov dword [esp+20], ebx .cleanup: mov esi, edx call disk_media_dereference call disk_dereference ret +.nofs: + mov dword [esp+32], ERROR_UNKNOWN_FS + jmp .cleanup .notfound: mov dword [esp+32], ERROR_FILE_NOT_FOUND jmp .cleanup +.unsupported: + mov dword [esp+32], ERROR_UNSUPPORTED_FS + jmp .cleanup .nomedia: test ecx, ecx jnz .notfound @@ -1192,7 +1238,6 @@ fs_dyndisk: ; if the driver does not support insert notifications and we are the only fs ; operation with this disk, issue the fake insert notification; if media is ; still not inserted, 'disk_media_changed' will detect this and do nothing -;;; push ebx lea ecx, [edx+DISK.MediaLock] call mutex_lock cmp [edx+DISK.MediaRefCount], 1 diff --git a/kernel/branches/Kolibri-acpi/blkdev/disk_cache.inc b/kernel/branches/Kolibri-acpi/blkdev/disk_cache.inc index 663e163688..c5651d9217 100644 --- a/kernel/branches/Kolibri-acpi/blkdev/disk_cache.inc +++ b/kernel/branches/Kolibri-acpi/blkdev/disk_cache.inc @@ -18,9 +18,11 @@ fs_read32_sys: ; this request should be processed by hd_read. cmp [ebp+PARTITION.Disk], 'old' jnz @f + add eax, dword [ebp+PARTITION.FirstSector] mov [hdd_appl_data], 0 call hd_read mov [hdd_appl_data], 1 ; restore to default state + mov eax, [hd_error] ret @@: ; In the normal case, save ecx, set ecx to SysCache and let the common part @@ -41,8 +43,11 @@ fs_read32_app: ; this request should be processed by hd_read. cmp [ebp+PARTITION.Disk], 'old' jnz @f + add eax, dword [ebp+PARTITION.FirstSector] mov [hdd_appl_data], 1 - jmp hd_read + call hd_read + mov eax, [hd_error] + ret @@: ; In the normal case, save ecx, set ecx to AppCache and let the common part ; do its work. @@ -63,7 +68,7 @@ fs_read32_common: ret @@: ; 2. Get the absolute sector on the disk. - push edx + push edx esi xor edx, edx add eax, dword [ebp+PARTITION.FirstSector] adc edx, dword [ebp+PARTITION.FirstSector+4] @@ -75,15 +80,16 @@ fs_read32_common: push edx ; startsector push eax ; startsector push ebx ; buffer + mov esi, [ebp+PARTITION.Disk] mov al, DISKFUNC.read call disk_call_driver pop ecx - pop edx + pop esi edx pop ecx ret .scancache: ; 4. Scan the cache. - push esi edi ecx ; scan cache + push edi ecx ; scan cache push edx eax virtual at esp .sector_lo dd ? @@ -183,9 +189,11 @@ fs_write32_sys: ; this request should be processed by hd_write. cmp [ebp+PARTITION.Disk], 'old' jnz @f + add eax, dword [ebp+PARTITION.FirstSector] mov [hdd_appl_data], 0 call hd_write mov [hdd_appl_data], 1 ; restore to default state + mov eax, [hd_error] ret @@: ; In the normal case, save ecx, set ecx to SysCache and let the common part @@ -206,8 +214,11 @@ fs_write32_app: ; this request should be processed by hd_write. cmp [ebp+PARTITION.Disk], 'old' jnz @f + add eax, dword [ebp+PARTITION.FirstSector] mov [hdd_appl_data], 1 - jmp hd_write + call hd_write + mov eax, [hd_error] + ret @@: ; In the normal case, save ecx, set ecx to AppCache and let the common part ; do its work. @@ -227,7 +238,7 @@ fs_write32_common: pop ecx ret @@: - push edx + push edx esi ; 2. Get the absolute sector on the disk. xor edx, edx add eax, dword [ebp+PARTITION.FirstSector] @@ -240,15 +251,16 @@ fs_write32_common: push edx ; startsector push eax ; startsector push ebx ; buffer + mov esi, [ebp+PARTITION.Disk] mov al, DISKFUNC.write call disk_call_driver pop ecx - pop edx + pop esi edx pop ecx ret .scancache: ; 4. Scan the cache. - push esi edi ecx ; scan cache + push edi ecx ; scan cache push edx eax virtual at esp .sector_lo dd ? @@ -348,7 +360,7 @@ find_empty_slot64: jb .found_slot ; it's empty or read dec ecx jnz .search_for_empty - call write_cache64 ; no empty slots found, write all + stdcall write_cache64, [ebp+PARTITION.Disk] ; no empty slots found, write all test eax, eax jne .found_slot_access_denied jmp .search_again ; and start again @@ -359,7 +371,7 @@ find_empty_slot64: ret ; This function is intended to replace the old 'write_cache' function. -proc write_cache64 uses ecx edx esi edi +proc write_cache64 uses ecx edx esi edi, disk:dword locals cache_chain_started dd ? cache_chain_size dd ? @@ -432,8 +444,7 @@ endl test eax, eax jnz .nothing .flush: - mov esi, [ebp] - mov esi, [esi+PARTITION.Disk] + mov esi, [disk] mov al, DISKFUNC.flush call disk_call_driver .nothing: @@ -590,3 +601,26 @@ disk_free_cache: stdcall kernel_free, eax .nothing: ret + +; This function flushes all modified data from both caches for the given DISK. +; esi = pointer to DISK +disk_sync: +; Compatibility hack: if PARTITION.Disk is 'old', there is no DISK structure, +; this request should be processed by write_cache. + cmp esi, 'old' + jnz @f + mov [hdd_appl_data], 0 + call write_cache + mov [hdd_appl_data], 1 + jmp write_cache +@@: +; The algorithm is straightforward. + push esi + push esi ; for second write_cache64 + push esi ; for first write_cache64 + add esi, DISK.SysCache + call write_cache64 + add esi, DISK.AppCache - DISK.SysCache + call write_cache64 + pop esi + ret diff --git a/kernel/branches/Kolibri-acpi/blkdev/hd_drv.inc b/kernel/branches/Kolibri-acpi/blkdev/hd_drv.inc index 9183011ce2..4dc0bffb49 100644 --- a/kernel/branches/Kolibri-acpi/blkdev/hd_drv.inc +++ b/kernel/branches/Kolibri-acpi/blkdev/hd_drv.inc @@ -945,3 +945,83 @@ int13_call: @@: ret ; \end{diamond} + +reserve_hd1: + + cli + cmp [hd1_status], 0 + je reserve_ok1 + + sti + call change_task + jmp reserve_hd1 + + reserve_ok1: + + push eax + mov eax, [CURRENT_TASK] + shl eax, 5 + mov eax, [eax+CURRENT_TASK+TASKDATA.pid] + mov [hd1_status], eax + pop eax + sti + ret +;******************************************** + +uglobal +hd_in_cache db ? +endg + +reserve_hd_channel: +; BIOS disk accesses are protected with common mutex hd1_status +; This must be modified when hd1_status will not be valid! + cmp [hdpos], 0x80 + jae .ret + cmp [hdbase], 0x1F0 + jne .IDE_Channel_2 +.IDE_Channel_1: + cli + cmp [IDE_Channel_1], 0 + je .reserve_ok_1 + sti + call change_task + jmp .IDE_Channel_1 +.IDE_Channel_2: + cli + cmp [IDE_Channel_2], 0 + je .reserve_ok_2 + sti + call change_task + jmp .IDE_Channel_2 +.reserve_ok_1: + mov [IDE_Channel_1], 1 + push eax + mov al, 1 + jmp @f +.reserve_ok_2: + mov [IDE_Channel_2], 1 + push eax + mov al, 3 +@@: + cmp [hdid], 1 + sbb al, -1 + mov [hd_in_cache], al + pop eax + sti +.ret: + ret + +free_hd_channel: +; see comment at reserve_hd_channel + cmp [hdpos], 0x80 + jae .ret + cmp [hdbase], 0x1F0 + jne .IDE_Channel_2 +.IDE_Channel_1: + mov [IDE_Channel_1], 0 +.ret: + ret +.IDE_Channel_2: + mov [IDE_Channel_2], 0 + ret +;******************************************** diff --git a/kernel/branches/Kolibri-acpi/blkdev/ide_cache.inc b/kernel/branches/Kolibri-acpi/blkdev/ide_cache.inc index 32157e2baa..5c7414a806 100644 --- a/kernel/branches/Kolibri-acpi/blkdev/ide_cache.inc +++ b/kernel/branches/Kolibri-acpi/blkdev/ide_cache.inc @@ -137,8 +137,6 @@ found_slot_access_denied: ;-------------------------------------------------------------------- align 4 clear_hd_cache: - mov [fat_in_cache], -1 - mov [fat_change], 0 ret ;-------------------------------------------------------------------- align 4 diff --git a/kernel/branches/Kolibri-acpi/boot/preboot.inc b/kernel/branches/Kolibri-acpi/boot/preboot.inc index 4c9a0cbd2e..b5bbf9baa6 100644 --- a/kernel/branches/Kolibri-acpi/boot/preboot.inc +++ b/kernel/branches/Kolibri-acpi/boot/preboot.inc @@ -38,5 +38,5 @@ end if ERROR: prebooting parameters must fit in first sector!!! end if -hdsysimage db 'KOLIBRI IMG' ; load from -image_save db 'KOLIBRI IMG' ; save to +hdsysimage db 'KOLIBRI.IMG',0 ; load from +image_save db 'KOLIBRI.IMG',0 ; save to diff --git a/kernel/branches/Kolibri-acpi/boot/rdload.inc b/kernel/branches/Kolibri-acpi/boot/rdload.inc index b1f15e8c55..ae6ec8ace9 100644 --- a/kernel/branches/Kolibri-acpi/boot/rdload.inc +++ b/kernel/branches/Kolibri-acpi/boot/rdload.inc @@ -89,13 +89,22 @@ $Revision$ mov [image_retrieved], 1 ret +iglobal +align 4 +read_image_fsinfo: + dd 0 ; function: read + dq 0 ; offset: zero + dd 1474560/512 ; size + dd RAMDISK ; buffer + db 0 + dd hdsysimage+OS_BASE+0x10000 +endg + read_image: - mov eax, hdsysimage+OS_BASE+0x10000 - mov ebx, 1474560/512 - mov ecx, RAMDISK - mov esi, 0 - mov edi, 12 - call file_read + mov ebx, read_image_fsinfo + pushad + call file_system_lfn + popad ret image_retrieved db 0 diff --git a/kernel/branches/Kolibri-acpi/const.inc b/kernel/branches/Kolibri-acpi/const.inc index 0b26c43b7a..f766cedd58 100644 --- a/kernel/branches/Kolibri-acpi/const.inc +++ b/kernel/branches/Kolibri-acpi/const.inc @@ -189,7 +189,6 @@ TASK_BASE equ (OS_BASE+0x0003010) TASK_DATA equ (OS_BASE+0x0003020) TASK_EVENT equ (OS_BASE+0x0003020) -d_width_calc_area equ (OS_BASE+0x0005000) mouseunder equ (OS_BASE+0x0006900) CDDataBuf equ (OS_BASE+0x0007000) FLOPPY_BUFF equ (OS_BASE+0x0008000) @@ -256,7 +255,7 @@ SYS_SHUTDOWN equ (OS_BASE+0x000FF00) TASK_ACTIVATE equ (OS_BASE+0x000FF01) REDRAW_BACKGROUND equ (OS_BASE+0x000FFF0) -BACKGROUND_CHANGED equ (OS_BASE+0x000FFF1) + BANK_RW equ (OS_BASE+0x000FFF2) MOUSE_BACKGROUND equ (OS_BASE+0x000FFF4) DONT_DRAW_MOUSE equ (OS_BASE+0x000FFF5) @@ -264,9 +263,6 @@ DONT_SWITCH equ (OS_BASE+0x000FFFF) TMP_STACK_TOP equ 0x006CC00 -FONT_II equ (OS_BASE+0x006DC00) -FONT_I equ (OS_BASE+0x006E600) - sys_pgdir equ (OS_BASE+0x006F000) DRIVE_DATA equ (OS_BASE+0x0070000) @@ -290,7 +286,11 @@ BgrAuxTable equ (OS_BASE+0x0298000) SB16Buffer equ (OS_BASE+0x02A0000) SB16_Status equ (OS_BASE+0x02B0000) -BUTTON_INFO equ (OS_BASE+0x02C0000) +BUTTON_INFO equ (OS_BASE+0x02B3FEE) + +BPSLine_calc_area equ (OS_BASE+0x02C4000) +d_width_calc_area equ (OS_BASE+0x02CA000) + RESERVED_PORTS equ (OS_BASE+0x02D0000) BOOT_VAR equ (OS_BASE+0x02E0000) diff --git a/kernel/branches/Kolibri-acpi/core/dll.inc b/kernel/branches/Kolibri-acpi/core/dll.inc index 6866d6810a..4396ea81db 100644 --- a/kernel/branches/Kolibri-acpi/core/dll.inc +++ b/kernel/branches/Kolibri-acpi/core/dll.inc @@ -437,10 +437,19 @@ proc load_file stdcall, file_name:dword jz .cleanup mov [file2], eax - pushfd - cli + + pushad + mov ecx, unpack_mutex + call mutex_lock + popad + stdcall unpack, [file], eax - popfd + + pushad + mov ecx, unpack_mutex + call mutex_unlock + popad + stdcall kernel_free, [file] mov eax, [file2] mov ebx, [file_size] @@ -470,6 +479,11 @@ proc load_file stdcall, file_name:dword ret endp +uglobal +align 4 +unpack_mutex MUTEX +endg + align 4 proc get_proc_ex stdcall, proc_name:dword, imports:dword diff --git a/kernel/branches/Kolibri-acpi/core/exports.inc b/kernel/branches/Kolibri-acpi/core/exports.inc index 6d8d4fb400..fc5af7e80b 100644 --- a/kernel/branches/Kolibri-acpi/core/exports.inc +++ b/kernel/branches/Kolibri-acpi/core/exports.inc @@ -72,6 +72,9 @@ iglobal szLoadFile db 'LoadFile',0 szSendEvent db 'SendEvent',0 szSetMouseData db 'SetMouseData',0 + szSetKeyboardData db 'SetKeyboardData',0 + szRegKeyboard db 'RegKeyboard',0 + szDelKeyboard db 'DelKeyboard',0 szSleep db 'Sleep',0 szGetTimerTicks db 'GetTimerTicks',0 @@ -154,6 +157,9 @@ kernel_export: dd szLoadFile , load_file ;retval eax, ebx dd szSendEvent , send_event ;see EVENT.inc for specification dd szSetMouseData , set_mouse_data ;stdcall + dd szSetKeyboardData , set_keyboard_data + dd szRegKeyboard , register_keyboard + dd szDelKeyboard , delete_keyboard dd szSleep , delay_ms dd szGetTimerTicks , get_timer_ticks diff --git a/kernel/branches/Kolibri-acpi/core/memory.inc b/kernel/branches/Kolibri-acpi/core/memory.inc index bacb4f99ff..9047fef7a3 100644 --- a/kernel/branches/Kolibri-acpi/core/memory.inc +++ b/kernel/branches/Kolibri-acpi/core/memory.inc @@ -442,72 +442,83 @@ endp align 4 proc new_mem_resize stdcall, new_size:dword - mov ecx, pg_data.mutex - call mutex_lock + push ebx + push esi + push edi + + mov edx, [current_slot] + cmp [edx+APPDATA.heap_base], 0 + jne .exit mov edi, [new_size] add edi, 4095 and edi, not 4095 mov [new_size], edi - mov edx, [current_slot] - cmp [edx+APPDATA.heap_base], 0 - jne .exit - mov esi, [edx+APPDATA.mem_size] add esi, 4095 and esi, not 4095 cmp edi, esi - jae .expand + ja .expand + je .exit + mov ebx, edi shr edi, 12 shr esi, 12 + + mov ecx, pg_data.mutex + call mutex_lock @@: mov eax, [app_page_tabs+edi*4] test eax, 1 jz .next - mov dword [app_page_tabs+edi*4], 2 - mov ebx, edi - shl ebx, 12 - push eax + + mov dword [app_page_tabs+edi*4], 0 invlpg [ebx] - pop eax call free_page .next: - add edi, 1 + inc edi + add ebx, 0x1000 cmp edi, esi jb @B -.update_size: - mov ebx, [new_size] - call update_mem_size - mov ecx, pg_data.mutex call mutex_unlock +.update_size: + mov edx, [current_slot] + mov ebx, [new_size] + call update_mem_size +.exit: + pop edi + pop esi + pop ebx xor eax, eax ret + .expand: - push esi - push edi + mov ecx, pg_data.mutex + call mutex_lock + + xchg esi, edi + + push esi ;new size + push edi ;old size add edi, 0x3FFFFF and edi, not(0x3FFFFF) add esi, 0x3FFFFF and esi, not(0x3FFFFF) - cmp esi, edi + cmp edi, esi jae .grow - - xchg esi, edi - -@@: + @@: call alloc_page test eax, eax - jz .exit_pop + jz .exit_fail stdcall map_page_table, edi, eax @@ -524,51 +535,38 @@ proc new_mem_resize stdcall, new_size:dword cmp edi, esi jb @B .grow: -;//- - pop edi - push edi - mov esi, [pg_data.pages_free] - sub esi, 1 - shr edi, 12 - cmp esi, edi - jle .out_of_memory -;//- - pop edi - pop esi -@@: - call alloc_page - test eax, eax - jz .exit - stdcall map_page, esi, eax, dword PG_UW + pop edi ;old size + pop ecx ;new size - push edi - mov edi, esi - xor eax, eax - mov ecx, 1024 - cld + shr edi, 10 + shr ecx, 10 + sub ecx, edi + shr ecx, 2 ;pages count + mov eax, 2 + + add edi, app_page_tabs rep stosd - pop edi - add esi, 0x1000 - cmp esi, edi - jb @B - - jmp .update_size -;//- -.exit_pop: -.out_of_memory: -;//- - pop edi - pop esi -.exit: mov ecx, pg_data.mutex call mutex_unlock + jmp .update_size + +.exit_fail: + mov ecx, pg_data.mutex + call mutex_unlock + + add esp, 8 + pop edi + pop esi + pop ebx xor eax, eax inc eax ret endp + +align 4 update_mem_size: ; in: edx = slot base ; ebx = new memory size @@ -1253,7 +1251,7 @@ f68: cmp ecx, OS_BASE jae .fail - cmp ebx, OS_BASE + cmp edx, OS_BASE jae .fail mov edi, edx @@ -1459,7 +1457,7 @@ proc set_mtrr stdcall, base:dword,size:dword,mem_type:dword mov ebx, [size] dec ebx mov eax, 0xFFFFFFFF - mov edx, 0x00000000 + mov edx, 0x0000000F sub eax, ebx sbb edx, 0 or eax, 0x800 diff --git a/kernel/branches/Kolibri-acpi/core/sys32.inc b/kernel/branches/Kolibri-acpi/core/sys32.inc index 5a06f23ba7..20ebfd1b7c 100644 --- a/kernel/branches/Kolibri-acpi/core/sys32.inc +++ b/kernel/branches/Kolibri-acpi/core/sys32.inc @@ -425,6 +425,17 @@ term9: add eax, 16 cmp eax, hotkey_list+256*16 jb .loop +; get process PID + mov eax, esi + shl eax, 5 + mov eax, [eax+CURRENT_TASK+TASKDATA.pid] +; compare current lock input with process PID + cmp eax, [PID_lock_input] + jne @f + + xor eax, eax + mov [PID_lock_input], eax +@@: ; remove hotkeys in buffer mov eax, hotkey_buffer .loop2: @@ -677,24 +688,22 @@ term9: ret restore .slot -iglobal -if lang eq ru - boot_sched_1 db 'Создание GDT TSS указателя',0 - boot_sched_2 db 'Создание IDT таблицы',0 -else - boot_sched_1 db 'Building gdt tss pointer',0 - boot_sched_2 db 'Building IDT table',0 -end if -endg +;iglobal +;if lang eq ru +; boot_sched_1 db 'Создание GDT TSS указателя',0 +; boot_sched_2 db 'Создание IDT таблицы',0 +;else +; boot_sched_1 db 'Building gdt tss pointer',0 +; boot_sched_2 db 'Building IDT table',0 +;end if +;endg -build_scheduler: +;build_scheduler: +; mov esi, boot_sched_1 +; call boot_log +; call build_process_gdt_tss_pointer - mov esi, boot_sched_1 - call boot_log - ; call build_process_gdt_tss_pointer - - ; mov esi,boot_sched_2 - ; call boot_log - - ret +; mov esi,boot_sched_2 +; call boot_log +; ret diff --git a/kernel/branches/Kolibri-acpi/core/syscall.inc b/kernel/branches/Kolibri-acpi/core/syscall.inc index 92f2b702f9..c0e064fd88 100644 --- a/kernel/branches/Kolibri-acpi/core/syscall.inc +++ b/kernel/branches/Kolibri-acpi/core/syscall.inc @@ -145,7 +145,7 @@ iglobal dd sys_settime ; 22-setting date,time,clock and alarm-clock dd sys_wait_event_timeout ; 23-TimeOutWaitForEvent dd syscall_cdaudio ; 24-PlayCdTrack,StopCd and GetCdPlaylist - dd undefined_syscall ; 25-reserved + dd syscall_putarea_backgr ; 25-Put Area to background dd sys_getsetup ; 26-GetMidiBase,GetKeymap,GetShiftKeymap,. dd undefined_syscall ; 27-reserved dd undefined_syscall ; 28-reserved @@ -154,7 +154,7 @@ iglobal dd undefined_syscall ; 31-reserved dd undefined_syscall ; 32-reserved dd undefined_syscall ; 33-reserved - dd undefined_syscall ; 34-reserved + dd syscall_getpixel_WinMap ; 34-GetPixel WinMap dd syscall_getpixel ; 35-GetPixel dd syscall_getarea ; 36-GetArea dd readmousepos ; 37-GetMousePosition_ScreenRelative,. diff --git a/kernel/branches/Kolibri-acpi/core/taskman.inc b/kernel/branches/Kolibri-acpi/core/taskman.inc index 3b29cf522e..18067e5970 100644 --- a/kernel/branches/Kolibri-acpi/core/taskman.inc +++ b/kernel/branches/Kolibri-acpi/core/taskman.inc @@ -72,6 +72,7 @@ proc fs_execute slot_base dd ? file_base dd ? file_size dd ? + handle dd ? ;temp. for default cursor handle for curr. thread ;app header data hdr_cmdline dd ? ;0x00 hdr_path dd ? ;0x04 @@ -83,6 +84,15 @@ proc fs_execute pushad + cmp [SCR_MODE], word 0x13 + jbe @f + pushad + stdcall set_cursor, [def_cursor_clock] + mov [handle], eax + mov [redrawmouse_unconditional], 1 + call __sys_draw_pointer + popad +@@: mov [flags], edx ; [ebp] pointer to filename @@ -113,7 +123,8 @@ proc fs_execute .bigfilename: popad mov eax, -ERROR_FILE_NOT_FOUND - ret + + jmp .final .namecopied: @@ -127,6 +138,7 @@ proc fs_execute @@: lea eax, [filename] stdcall load_file, eax + mov esi, -ERROR_FILE_NOT_FOUND test eax, eax jz .err_file @@ -175,7 +187,7 @@ proc fs_execute jnz @F lea esi, [filename] @@: - mov ecx, 8; 8 chars for name + mov ecx, 11 ; 11 chars for name! 8 - is old value! mov edi, [slot_base] .copy_process_name_loop: lodsb @@ -237,7 +249,9 @@ end if xor ebx, ebx mov [application_table_status], ebx;unlock application_table_status mutex mov eax, [process_number];set result - ret + + jmp .final + .failed: mov eax, [save_cr3] call set_cr3 @@ -248,6 +262,15 @@ end if xor eax, eax mov [application_table_status], eax mov eax, esi +.final: + cmp [SCR_MODE], word 0x13 + jbe @f + pushad + stdcall set_cursor, [handle] + mov [redrawmouse_unconditional], 1 + call __sys_draw_pointer + popad +@@: ret endp diff --git a/kernel/branches/Kolibri-acpi/data32.inc b/kernel/branches/Kolibri-acpi/data32.inc index 32de00569d..e0893c0769 100644 --- a/kernel/branches/Kolibri-acpi/data32.inc +++ b/kernel/branches/Kolibri-acpi/data32.inc @@ -49,11 +49,23 @@ keymap_alt: if lang eq ru - boot_fonts db 'Шрифты загружены',0 + boot_initirq db 'Инициализация IRQ',0 + boot_picinit db 'Инициализация PIC',0 + boot_v86machine db 'Инициализация системы V86 машины',0 + boot_inittimer db 'Инициализация системного таймера (IRQ0)',0 + boot_initapic db 'Попытка инициализации APIC',0 + boot_enableirq db 'Включить прерывания 2, 6, 13, 14, 15',0 + boot_enablint_ide db 'Разрешение прерываний в контроллере IDE',0 + boot_detectfloppy db 'Поиск floppy дисководов',0 + boot_detecthdcd db 'Поиск жестких дисков и ATAPI приводов',0 + boot_getcache db 'Получение памяти для кэша',0 + boot_detectpart db 'Поиск разделов на дисковых устройствах',0 + boot_init_sys db 'Инициализация системного каталога /sys',0 + boot_loadlibs db 'Загрузка библиотек (.obj)',0 boot_memdetect db 'Количество оперативной памяти',' ',' Мб',0 boot_tss db 'Установка TSSs',0 boot_cpuid db 'Чтение CPUIDs',0 - boot_devices db 'Поиск устройств',0 +; boot_devices db 'Поиск устройств',0 boot_timer db 'Установка таймера',0 boot_irqs db 'Переопределение IRQ',0 boot_setmouse db 'Установка мыши',0 @@ -69,15 +81,30 @@ if lang eq ru boot_pal_vga db 'Установка VGA 640x480 палитры',0 boot_failed db 'Загрузка первого приложения не удалась',0 boot_mtrr db 'Установка MTRR',0 + + boot_APIC_found db 'APIC включен', 0 + boot_APIC_nfound db 'APIC не найден', 0 if preboot_blogesc boot_tasking db 'Все готово для запуска, нажмитре ESC для старта',0 end if else - boot_fonts db 'Fonts loaded',0 + boot_initirq db 'Initialize IRQ',0 + boot_picinit db 'Initialize PIC',0 + boot_v86machine db 'Initialize system V86 machine',0 + boot_inittimer db 'Initialize system timer (IRQ0)',0 + boot_initapic db 'Try to initialize APIC',0 + boot_enableirq db 'Enable interrupts 2, 6, 13, 14, 15',0 + boot_enablint_ide db 'Enable interrupts in IDE controller',0 + boot_detectfloppy db 'Search floppy drives',0 + boot_detecthdcd db 'Search hard drives and ATAPI drives',0 + boot_getcache db 'Get memory for cache',0 + boot_detectpart db 'Search partitions on disk devices',0 + boot_init_sys db 'Initialize system directory /sys',0 + boot_loadlibs db 'Loading librares (.obj)',0 boot_memdetect db 'Determining amount of memory',0 boot_tss db 'Setting TSSs',0 boot_cpuid db 'Reading CPUIDs',0 - boot_devices db 'Detecting devices',0 +; boot_devices db 'Detecting devices',0 boot_setmouse db 'Setting mouse',0 boot_windefs db 'Setting window defaults',0 boot_bgr db 'Calculating background',0 @@ -90,14 +117,14 @@ else boot_pal_vga db 'Setting VGA 640x480 palette',0 boot_failed db 'Failed to start first app',0 boot_mtrr db 'Setting MTRR',0 + + boot_APIC_found db 'APIC enabled', 0 + boot_APIC_nfound db 'APIC not found', 0 if preboot_blogesc boot_tasking db 'All set - press ESC to start',0 end if end if - boot_APIC_found db 'APIC enabled', 0 - boot_APIC_nfound db 'APIC not found', 0 - ;new_process_loading db 'K : New Process - loading',13,10,0 ;new_process_running db 'K : New Process - done',13,10,0 start_not_enough_memory db 'K : New Process - not enough memory',13,10,0 @@ -135,9 +162,6 @@ else ud_user_message db 'Error: unsupported processor instruction',0 end if -char db '/sys/FONTS/CHAR.MT',0 -char2 db '/sys/FONTS/CHAR2.MT',0 - bootpath db '/KOLIBRI ' bootpath2 db 0 vmode db '/sys/drivers/VMODE.MDR',0 @@ -333,6 +357,7 @@ _WinMapAddress rd 1 _WinMapSize rd 1 def_cursor rd 1 +def_cursor_clock rd 1 current_cursor rd 1 hw_cursor rd 1 cur_saved_base rd 1 diff --git a/kernel/branches/Kolibri-acpi/detect/sear_par.inc b/kernel/branches/Kolibri-acpi/detect/sear_par.inc index 82fbe1783b..e21a9fb417 100644 --- a/kernel/branches/Kolibri-acpi/detect/sear_par.inc +++ b/kernel/branches/Kolibri-acpi/detect/sear_par.inc @@ -133,6 +133,10 @@ end_search_partitions_bd: loop start_search_partitions_bd jmp end_search_partitions +problem_partition db 0 ; used for partitions search + +include '../fs/part_set.inc' + partition_data_transfer: mov edi, [transfer_adress] mov esi, PARTITION_START ;start of file_system_data diff --git a/kernel/branches/Kolibri-acpi/docs/sysfuncr.txt b/kernel/branches/Kolibri-acpi/docs/sysfuncr.txt index ede434f591..53661f6087 100644 --- a/kernel/branches/Kolibri-acpi/docs/sysfuncr.txt +++ b/kernel/branches/Kolibri-acpi/docs/sysfuncr.txt @@ -197,16 +197,21 @@ Параметры: * eax = 4 - номер функции * ebx = [координата по оси x]*65536 + [координата по оси y] - * ecx = 0xX0RRGGBB, где + * ecx = 0xXYRRGGBB, где * RR, GG, BB задают цвет текста * X=ABnn (биты): * nn задает используемый шрифт: 0=системный моноширинный, 1=системный шрифт переменной ширины * A=0 - выводить esi символов, A=1 - выводить ASCIIZ-строку * B=1 - закрашивать фон цветом edi + * Y=Cnnn (биты): + * C=1 перенаправить вывод в область пользователя, задано в edi + * nnn - не используется в текущем виде, должно быть 0 (zero) * edx = указатель на начало строки * esi = для A=0 длина строки, должна быть не больше 255; для A=1 игнорируется + * edi = цвет для закраски фона, если B=1 + * edi = указатель на область пользователя, если C=1 Возвращаемое значение: * функция не возвращает значения Замечания: @@ -214,7 +219,12 @@ второй - из char2.mt. * Оба шрифта имеют высоту 9 пикселей, ширина моноширинного шрифта равна 6 пикселей. - + * C=1, глубина точки = 32 бита, область пользователя выглядит так: + dword Xsize + dword Ysize + остаток области = Xsize * Y size * 4 + * Нельзя одновременно использовать B=1 и C=1, поскольку в обоих + случаях использован регистр edi для разных целей. ====================================================================== ========================= Функция 5 - пауза. ========================= ====================================================================== @@ -330,7 +340,7 @@ в позиции ecx * +8: word: зарезервировано * +10 = +0xA: 11 байт: имя процесса - (имя соответствующего исполняемого файла в формате 8+3) + (имя запущенного файла - исполняемый файл без расширения) * +21 = +0x15: byte: зарезервировано, этот байт не изменяется * +22 = +0x16: dword: адрес процесса в памяти * +26 = +0x1A: dword: размер используемой памяти - 1 @@ -608,6 +618,39 @@ Возвращаемое значение: * eax = 1 при успехе, 0 при ошибке +====================================================================== +====================== Функция 15, подфункция 8 ====================== +=========== Получить координаты последней отрисовки фона. ============ +====================================================================== +Параметры: + * eax = 15 - номер функции + * ebx = 8 - номер подфункции +Возвращаемое значение: + * eax = [left]*65536 + [right] + * ebx = [top]*65536 + [bottom] +Замечания: + * (left,top) - координаты левого верхнего угла, + (right,bottom) - координаты правого нижнего. + * Для получения более достоверных сведений, необходимо вызвать + функцию сразу после получения события: + 5 = завершилась перерисовка фона рабочего стола + +====================================================================== +====================== Функция 15, подфункция 9 ====================== +=============== Перерисовать прямоугольную часть фона. =============== +====================================================================== +Параметры: + * eax = 15 - номер функции + * ebx = 9 - номер подфункции + * ecx = [left]*65536 + [right] + * edx = [top]*65536 + [bottom] +Возвращаемое значение: + * функция не возвращает значения +Замечания: + * (left,top) - координаты левого верхнего угла, + (right,bottom) - координаты правого нижнего. + * Если параметры установлены некорректно - фон не перерисовывается. + ====================================================================== ============= Функция 16 - сохранить рамдиск на дискету. ============= ====================================================================== @@ -1065,6 +1108,34 @@ dd 1675 * Восстановление окна с одновременной активизацией осуществляется подфункции 3 (принимающей номер слота). +====================================================================== +======= Функция 18, подфункция 23 - минимизировать все окна. ========= +====================================================================== +Параметры: + * eax = 18 - номер функции + * ebx = 23 - номер подфункции +Возвращаемое значение: + * eax = 0 - все окна были минимизированы до вызова функции + * eax = N - количество окон свернутых функцией +Замечания: + * Окна спец. потоков (имя начинается с символа @) не сворачиваются. + +====================================================================== +===== Функция 18, подфункция 24 - установить пределы отрисовки. ====== +====================================================================== +Параметры: + * eax = 18 - номер функции + * ebx = 24 - номер подфункции + * ecx = новый размер по X + * edx = новый размер по Y +Возвращаемое значение: + * функция не возвращает значения +Замечания: + * Функция не меняет физический размер видеорежима. Она предназначена + для нестандартных дисплеев, отображающих изображение частично. + * Размеры указываемые в функции не должны превышать размеры текущего + видеорежима, иначе функция ничего не изменит. + ====================================================================== ==================== Функция 20 - интерфейс MIDI. ==================== ====================================================================== @@ -1506,6 +1577,26 @@ dd 1675 * Функция поддерживается только для ATAPI-устройств (CD и DVD). * Примером использования функции является приложение CD_tray. +====================================================================== +========== Функция 25 - записать область на слой фона. =============== +====================================================================== +Параметры: + * eax = 25 - номер функции + * ebx = указатель на предварительно выделенную область памяти, + где размещено исходное изображение в формате BBGGRRTTBBGGRRTT... + * ecx = [размер по оси x]*65536 + [размер по оси y] + * edx = [координата по оси x]*65536 + [координата по оси y] +Возвращаемое значение: + * функция не возвращает значения +Замечания: + * Координаты области - это координаты верхнего левого угла + области относительно экрана. + * Размер изображения в байтах есть 4*xsize*ysize. + * TT - байт указатель прозрачности, в настоящее время: + от 1 до FF - непрозрачно, от 0 - прозрачно. + * Функция размещает изображение не на фоновое изображение (ф.15), + а напрямую в LFB. Опции ф.15 для ф. 25 не имеют смысла. + ====================================================================== ===== Функция 26, подфункция 1 - получить базовый порт MPU MIDI. ===== ====================================================================== @@ -1703,6 +1794,19 @@ dd 1675 * При создании процесса/потока текущая папка наследуется от родителя. +====================================================================== +========= Функция 34 - узнать кому принадлежит точка экрана. ========= +====================================================================== +Параметры: + * eax = 34 - номер функции + * ebx = x-координата (относительно экрана) + * ecx = y-координата (относительно экрана) + +Возвращаемое значение: + * eax = 0x000000XX - точка принадлежит слоту окна N + При некорректных значениях ebx и ecx функция возвращает 0 + * Функция берет значения из области [_WinMapAddress] + ====================================================================== ============ Функция 35 - прочитать цвет точки на экране. ============ ====================================================================== @@ -3241,7 +3345,7 @@ IPC * ebx = указатель на изображение * ecx = [размер по оси x]*65536 + [размер по оси y] * edx = [координата по оси x]*65536 + [координата по оси y] - * esi = число бит на пиксель, должно быть 1,2,4,8,15,16,24 или 32 + * esi = число бит на пиксель, должно быть 1,2,4,8,9,15,16,24 или 32 * edi = указатель на палитру (2 в степени esi цветов 0x00RRGGBB); игнорируется при esi > 8 * ebp = смещение данных каждой следующей строки изображения @@ -3265,6 +3369,9 @@ IPC соответствует первому пикселю. * Формат изображения с 8 битами на пиксель: каждый байт изображения рассматривается как индекс в палитре. + * Формат изображения с 9 битами на пиксель: каждый байт изображения + (8 бит) обозначает интенсивность серого для одного пикселя, т.о. + этот тип изображения идентичен 8 бит на пиксель без палитры. * Формат изображения с 15 битами на пиксель: цвет каждого пикселя кодируется как (в битовом представлении) 0RRRRRGGGGGBBBBB - по 5 пикселей на каждый цвет. @@ -3364,6 +3471,27 @@ IPC Если другое приложение определило эту же комбинацию, оно по-прежнему будет получать уведомления. +------------- Подфункция 6 - заблокировать обычный ввод. ------------- +Параметры: + * eax = 66 - номер функции + * ebx = 6 - номер подфункции +Возвращаемое значение: + * функция не возвращает значения +Замечания: + * Блокируется обычный ввод данных с клавиатуры для установленных + "горячих" клавиш + * Для эмуляции мыши через клавиатуру, приложение MOUSEMUL + +--------- Подфункция 7 - разблокировать обычный ввод. ---------------- +Параметры: + * eax = 66 - номер функции + * ebx = 7 - номер подфункции +Возвращаемое значение: + * функция не возвращает значения +Замечания: + * Разблокирование результатов ф. 66.6 + * Для эмуляции мыши через клавиатуру, приложение MOUSEMUL + ====================================================================== ============ Функция 67 - изменить положение/размеры окна. =========== ====================================================================== @@ -3616,6 +3744,21 @@ Architecture Software Developer's Manual, Volume 3, Appendix B); * Содержимое памяти вплоть до наименьшего из старого и нового размеров сохраняется. +====================================================================== +========= Функция 68, подфункция 21 - загрузить драйвер PE. ========== +====================================================================== +Параметры: + * eax = 68 - номер функции + * ebx = 21 - номер подфункции + * ecx = указатель на ASCIIZ-строку с именем драйвера + * edx = указатель на командную строку +Возвращаемое значение: + * eax = 0 - неудача + * иначе eax = хэндл драйвера +Замечания: + * Если драйвер ещё не загружен, он загружается; + если драйвер уже загружен, ничего не меняется. + ====================================================================== === Функция 68, подфункция 22 - открыть именованную область памяти. == ====================================================================== @@ -4464,10 +4607,7 @@ Architecture Software Developer's Manual, Volume 3, Appendix B); кнопки из буфера считаны функцией 17) * 4 = зарезервировано (в текущей реализации никогда не приходит даже при размаскировке функцией 40) - * 5 = перерисовывается фон рабочего стола (сбрасывается - автоматически после перерисовки, так что если во время перерисовки - фона программа не ждёт и не проверяет события, то этого события - она не заметит) + * 5 = завершилась перерисовка фона рабочего стола * 6 = событие от мыши (что-то случилось - нажатие на кнопку мыши или перемещение; сбрасывается при прочтении) * 7 = произошло событие IPC (смотри функцию 60 - Inter Process diff --git a/kernel/branches/Kolibri-acpi/docs/sysfuncs.txt b/kernel/branches/Kolibri-acpi/docs/sysfuncs.txt index 668c3f89e1..b44d810d8f 100644 --- a/kernel/branches/Kolibri-acpi/docs/sysfuncs.txt +++ b/kernel/branches/Kolibri-acpi/docs/sysfuncs.txt @@ -194,16 +194,22 @@ Remarks: Parameters: * eax = 4 - function number * ebx = [coordinate on axis x]*65536 + [coordinate on axis y] - * ecx = 0xX0RRGGBB, where + * ecx = 0xXYRRGGBB, where * RR, GG, BB specify text color * X=ABnn (bits): * nn specifies the used font: 0=system monospaced, 1=system font of variable width * A=0 - output esi characters, A=1 - output ASCIIZ-string * B=1 - fill background with the color edi + * Y = Cnnn + * C=1 redirect the output to the user area, specified in edi + * nnn - not used in the current, must be 0 (zero) * edx = pointer to the beginning of the string * esi = for A=0 length of the string, must not exceed 255; for A=1 is ignored + * edi = color to fill background, if B=1 + * edi = pointer to user area, for redirect, if C=1 + Returned value: * function does not return value Remarks: @@ -211,6 +217,12 @@ Remarks: second - from char2.mt. * Both fonts have height 9 pixels, width of the monospaced font is equal to 6 pixels. + * C=1, pixel depth = 32 bits, user area is as follows: + dword Xsize + dword Ysize + rest of the area = Xsize * Y size * 4 + * You can not use B = 1 and C = 1, at the same time. Since in both + cases, the register edi is used for different purposes. ====================================================================== ========================= Function 5 - delay. ======================== @@ -325,7 +337,7 @@ Returned value: position ecx * +8: word: reserved * +10 = +0xA: 11 bytes: name of the process - (name of corresponding executable file in the format 8+3) + (name of the started file - executable file without extension) * +21 = +0x15: byte: reserved, this byte is not changed * +22 = +0x16: dword: address of the process in memory * +26 = +0x1A: dword: size of used memory - 1 @@ -600,6 +612,39 @@ Parameters: Returned value: * eax = 1 - success, 0 - error +====================================================================== +===================== Function 15, subfunction 8 ===================== +============= Get coordinates of last draw the background ============ +====================================================================== +Parameters: + * eax = 15 - function number + * ebx = 8 - subfunction number +Returned value: + * eax = [left]*65536 + [right] + * ebx = [top]*65536 + [bottom] +Remarks: + * (left,top) are coordinates of the left upper corner, + (right,bottom) are coordinates of the right lower one. + * For receiving more reliable information, call the function + immediately after the event: + 5 = kernel finished redrawing of the desktop background + +====================================================================== +===================== Function 15, subfunction 9 ===================== +============= Redraws a rectangular part of the background =========== +====================================================================== +Parameters: + * eax = 15 - function number + * ebx = 9 - subfunction number + * ecx = [left]*65536 + [right] + * edx = [top]*65536 + [bottom] +Returned value: + * function does not return value +Remarks: + * (left,top) are coordinates of the left upper corner, + (right,bottom) are coordinates of the right lower one. + * If parameters are set incorrectly then background is not redrawn. + ====================================================================== =============== Function 16 - save ramdisk on a floppy. ============== ====================================================================== @@ -1063,6 +1108,36 @@ Remarks: * One can restore and activate window simultaneously with subfunction 3 (which requires slot number). +====================================================================== +======== Function 18, subfunction 23 - minimize all windows. ========== +====================================================================== +Parameters: + * eax = 18 - function number + * ebx = 23 - subfunction number +Returned value: + * eax = 0 - all windows have been minimized before a function call + * eax = N - number of windows minimized from function +Remarks: + * Window of special thread (name begin to symbol @) is not minimize. + +====================================================================== +======= Function 18, subfunction 24 - set limits of screen. ========== +====================================================================== +Parameters: + * eax = 18 - function number + * ebx = 24 - subfunction number + * ecx = new X size + * edx = new Y size +Returned value: + * function does not return value +Remarks: + * The function does not change the physical size of the video mode. + It is designed for non-standard displays which display the image + partially. + * The sizes specified in the function should not exceed the sizes + of the current video mode, otherwise the function will not change + anything. + ====================================================================== ==================== Function 20 - MIDI interface. =================== ====================================================================== @@ -1492,6 +1567,26 @@ Remarks: * The function is supported only for ATAPI devices (CD and DVD). * An example of usage of the function is the application CD_tray. +====================================================================== +======= Function 25 - put image area on the background layer. ======== +====================================================================== +Paramters: + * eax = 25 - function number + * ebx = pointer to the previously allocated memory area, + where placed the source images in a format BBGGRRTTBBGGRRTT... + * ecx = [size on axis x]*65536 + [size on axis y] + * edx = [coordinate on axis x]*65536 + [coordinate on axis y] +Returned value: + * function does not return value +Remarks: + * Coordinates of the image are coordinates of the upper left corner + of the image relative to the screen. + * Size of the image in bytes is 4*xsize*ysize + * TT - byte pointer of transparency, at current version: + 1 to FF - opaque, 0 - transparent. + * The function places the image directly to LFB. It is not for + background image f.15. Options f.15 to f.25 does not make sense. + ====================================================================== ======== Function 26, subfunction 1 - get MPU MIDI base port. ======== ====================================================================== @@ -1681,6 +1776,19 @@ Remarks: * At process/thread creation the current folder will be inherited from the parent. +====================================================================== +========= Function 34 - who owner the pixel on the screen. =========== +====================================================================== +Parameters: + * eax = 34 - function number + * ebx = x-coordinate (relative to the display) + * ecx = y-coordinate (relative to the display) + +Returned value: + * eax = 0x000000XX - owner of pixel the slot window N + If incorrect values ebx and ecx then function returns 0 + * The function takes the value from the area [_WinMapAddress] + ====================================================================== ======= Function 35 - read the color of a pixel on the screen. ======= ====================================================================== @@ -3221,7 +3329,7 @@ Parameters: * ebx = pointer to the image * ecx = [size on axis x]*65536 + [size on axis y] * edx = [coordinate on axis x]*65536 + [coordinate on axis y] - * esi = number of bits per pixel, must be 1,2,4,8,15,16,24 or 32 + * esi = number of bits per pixel, must be 1,2,4,8,9,15,16,24 or 32; * edi = pointer to palette (2 to the power esi colors 0x00RRGGBB); ignored when esi > 8 * ebp = offset of next row data relative to previous row data @@ -3242,6 +3350,9 @@ Remarks: corresponds to first pixel. * Format of image with 8 bits per pixel: each byte of image is index in the palette. + * Format of image with 9 bits per pixel: array of one byte values; + each byte (8 bit) represents the intensity of gray for one pixel; + this format is equal to 8bpp without palette. * Format of image with 15 bits per pixel: the color of each pixel is coded as (bit representation) 0RRRRRGGGGGBBBBB - 5 bits per each color. @@ -3340,6 +3451,26 @@ Remarks: If other application has defined the same combination, it will still receive notices. +--------------- Subfunction 6 - block the normal input. -------------- +Parameters: + * eax = 66 - function number + * ebx = 6 - subfunction number +Returned value: + * function does not return value +Remarks: + * Blocking the normal keyboard input for installed hotkeys + * To emulate a mouse via the keyboard, the application MOUSEMUL + +------------ Subfunction 7 - unlock the normal input. ---------------- +Parameters: + * eax = 66 - function number + * ebx = 7 - subfunction number +Returned value: + * function does not return value +Remarks: + * Unlocking the results of the f. 66.6 + * To emulate a mouse via the keyboard, the application MOUSEMUL + ====================================================================== ========= Function 67 - change position/sizes of the window. ========= ====================================================================== @@ -3595,6 +3726,21 @@ Remarks: * The contents of the block are unchanged up to the shorter of the new and old sizes. +====================================================================== +=========== Function 68, subfunction 21 - load driver PE. ============ +====================================================================== +Parameters: + * eax = 68 - function number + * ebx = 21 - subfunction number + * ecx = pointer to ASCIIZ-string with driver name + * edx = pointer to command line +Returned value: + * eax = 0 - failed + * otherwise eax = driver handle +Remarks: + * If the driver was not loaded yet, it is loaded; + if the driver was loaded yet, nothing happens. + ====================================================================== ======== Function 68, subfunction 22 - open named memory area. ======= ====================================================================== @@ -4430,9 +4576,7 @@ Codes of events: are read out by function 17) * 4 = reserved (in current implementation never comes even after unmasking by function 40) - * 5 = the desktop background is redrawed (is reset automatically - after redraw, so if in redraw time program does not wait and - does not check events, it will not remark this event) + * 5 = kernel finished redrawing of the desktop background * 6 = mouse event (something happened - button pressing or moving; is reset at reading) * 7 = IPC event (see function 60 - diff --git a/kernel/branches/Kolibri-acpi/drivers/imports.inc b/kernel/branches/Kolibri-acpi/drivers/imports.inc index 395bb09267..90d3ca51be 100644 --- a/kernel/branches/Kolibri-acpi/drivers/imports.inc +++ b/kernel/branches/Kolibri-acpi/drivers/imports.inc @@ -80,6 +80,9 @@ kernel_export \ LoadFile,\ SendEvent,\ SetMouseData,\ + SetKeyboardData,\ + RegKeyboard,\ + DelKeyboard,\ Sleep,\ GetTimerTicks,\ \ @@ -92,4 +95,8 @@ kernel_export \ \ LFBAddress,\ GetDisplay,\ - SetScreen + SetScreen,\ +\ + DiskAdd,\ + DiskMediaChanged,\ + DiskDel diff --git a/kernel/branches/Kolibri-acpi/drivers/infinity.asm b/kernel/branches/Kolibri-acpi/drivers/infinity.asm index 4a739b1e02..a0e1f85a71 100644 --- a/kernel/branches/Kolibri-acpi/drivers/infinity.asm +++ b/kernel/branches/Kolibri-acpi/drivers/infinity.asm @@ -348,11 +348,18 @@ align 4 cmp [edi+inp_size], 12 jne .fail - mov eax, [ebx] - mov ebx, [ebx+4] + mov eax, [ebx+4] + mov ebx, [ebx+8] + + pushfd + cli mov dword [edx+STREAM.time_base], eax mov dword [edx+STREAM.time_base+4], ebx xor eax, eax + mov dword [edx+STREAM.time_stamp], eax + mov dword [edx+STREAM.time_stamp+4], eax + popfd + ret align 4 diff --git a/kernel/branches/Kolibri-acpi/drivers/sb16/sb16.asm b/kernel/branches/Kolibri-acpi/drivers/sb16/sb16.asm index 0c520360c2..634b60c4fa 100644 --- a/kernel/branches/Kolibri-acpi/drivers/sb16/sb16.asm +++ b/kernel/branches/Kolibri-acpi/drivers/sb16/sb16.asm @@ -1,6 +1,6 @@ ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; ;; -;; Copyright (C) KolibriOS team 2004-2011. All rights reserved. ;; +;; Copyright (C) KolibriOS team 2004-2012. All rights reserved. ;; ;; Distributed under terms of the GNU General Public License ;; ;; ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; @@ -93,8 +93,8 @@ if DEBUG mov esi, msgErrAtchIRQ call SysMsgBoardStr - stdcall GetIntHandler, sb_irq_num - call SysMsgBoardNum +; stdcall GetIntHandler, sb_irq_num +; call SysMsgBoardNum jmp .stop @@: diff --git a/kernel/branches/Kolibri-acpi/fs/ext2.inc b/kernel/branches/Kolibri-acpi/fs/ext2.inc index 56ef3425a4..21f29ddd06 100644 --- a/kernel/branches/Kolibri-acpi/fs/ext2.inc +++ b/kernel/branches/Kolibri-acpi/fs/ext2.inc @@ -14,47 +14,35 @@ EXT2_BAD_INO = 1 EXT2_ROOT_INO = 2 EXT2_ACL_IDX_INO = 3 EXT2_ACL_DATA_INO = 4 -EXT2_BOOT_LOADER_INO= 5 +EXT2_BOOT_LOADER_INO = 5 EXT2_UNDEL_DIR_INO = 6 -;type inode +;╤Д╨╗╨░╨│╨╕, ╤Г╨║╨░╨╖╤Л╨▓╨░╨╡╨╝╤Л╨╣ ╨▓ inode ╤Д╨░╨╣╨╗╨░ EXT2_S_IFREG = 0x8000 EXT2_S_IFDIR = 0x4000 -;user inode right's -EXT2_S_IRUSR = 0x0100 -EXT2_S_IWUSR = 0x0080 -EXT2_S_IXUSR = 0x0040 -;group inode right's -EXT2_S_IRGRP = 0x0020 -EXT2_S_IWGRP = 0x0010 -EXT2_S_IXGRP = 0x0008 -;other inode right's -EXT2_S_IROTH = 0x0004 -EXT2_S_IWOTH = 0x0002 -EXT2_S_IXOTH = 0x0001 -EXT2_777_MODE = EXT2_S_IROTH or EXT2_S_IWOTH or EXT2_S_IXOTH or \ - EXT2_S_IRGRP or EXT2_S_IWGRP or EXT2_S_IXGRP or \ - EXT2_S_IRUSR or EXT2_S_IWUSR or EXT2_S_IXUSR +EXT2_S_IFMT = 0xF000 ;╨╝╨░╤Б╨║╨░ ╨┤╨╗╤П ╤В╨╕╨┐╨░ ╤Д╨░╨╣╨╗╨░ +;╤Д╨╗╨░╨│╨╕, ╤Г╨║╨░╨╖╤Л╨▓╨░╨╡╨╝╤Л╨╡ ╨▓ linked list ╤А╨╛╨┤╨╕╤В╨╡╨╗╤М╤Б╨║╨╛╨╣ ╨┐╨░╨┐╨║╨╕ EXT2_FT_REG_FILE = 1 ;╤Н╤В╨╛ ╤Д╨░╨╣╨╗, ╨╖╨░╨┐╨╕╤Б╤М ╨▓ ╤А╨╛╨┤╨╕╤В╨╡╨╗╤М╤Б╨║╨╛╨╝ ╨║╨░╤В╨░╨╗╨╛╨│╨╡ EXT2_FT_DIR = 2 ;╤Н╤В╨╛ ╨┐╨░╨┐╨║╨░ +;╤Д╨╗╨░╨│╨╕ ╨╕╤Б╨┐╨╛╨╗╤М╨╖╤Г╨╡╨╝╤Л╨╡ KolibriOS FS_FT_HIDDEN = 2 FS_FT_DIR = 0x10 ;╤Н╤В╨╛ ╨┐╨░╨┐╨║╨░ FS_FT_ASCII = 0 ;╨╕╨╝╤П ╨▓ ascii FS_FT_UNICODE = 1 ;╨╕╨╝╤П ╨▓ unicode -EXT2_FEATURE_INCOMPAT_FILETYPE = 0x0002 +EXT2_FEATURE_INCOMPAT_FILETYPE = 0x0002 ;╤В╨╕╨┐ ╤Д╨░╨╣╨╗╨░ ╨┤╨╛╨╗╨╢╨╡╨╜ ╤Г╨║╨░╨╖╤Л╨▓╨░╤В╤М╤Б╤П ╨▓ ╨┤╨╕╤А╨╡╨║╤В╨╛╤А╨╕╨╕ +EXT4_FEATURE_INCOMPAT_EXTENTS = 0x0040 ;╤Н╨║╤Б╤В╨╡╨╜╤В╤Л +EXT4_FEATURE_INCOMPAT_FLEX_BG = 0x0200 ;╨│╨╕╨▒╨║╨╕╨╡ ╨│╤А╤Г╨┐╨┐╤Л ╨▒╨╗╨╛╨║╨╛╨▓ +;╤А╨╡╨░╨╗╨╕╨╖╨╛╨▓╨░╨╜╨╜╤Л╨╡ ext[234] features +EXT4_FEATURE_INCOMPAT_SUPP = EXT2_FEATURE_INCOMPAT_FILETYPE \ + or EXT4_FEATURE_INCOMPAT_EXTENTS \ + or EXT4_FEATURE_INCOMPAT_FLEX_BG -uglobal - EXT2_files_in_folder dd ? ;╨▓╤Б╨╡╨│╨╛ ╤Д╨░╨╣╨╗╨╛╨▓ ╨▓ ╨┐╨░╨┐╨║╨╡ - EXT2_read_in_folder dd ? ;╤Б╨║╨╛╨╗╤М╨║╨╛ ╤Д╨░╨╣╨╗╨╛╨▓ "╤Б╤З╨╕╤В╨░╨╗╨╕" - EXT2_end_block dd ? ;╨║╨╛╨╜╨╡╤Ж ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ ╨┐╨░╨┐╨║╨╕ - EXT2_counter_blocks dd ? - EXT2_filename rb 256 - EXT2_parent_name rb 256 - EXT2_name_len dd ? -endg + +;╤Д╨╗╨░╨│╨╕, ╤Г╨║╨░╨╖╤Л╨▓╨░╨╡╨╝╤Л╨╡ ╨┤╨╗╤П inode ╨▓ i_flags +EXT2_EXTENTS_FL = 0x00080000 struct EXT2_INODE_STRUC i_mode dw ? @@ -86,12 +74,14 @@ struct EXT2_DIR_STRUC ends struct EXT2_BLOCK_GROUP_DESC - block_bitmap dd ? - inode_bitmap dd ? - inode_table dd ? - free_blocks_count dw ? - free_inodes_count dw ? - used_dirs_count dw ? + block_bitmap dd ? ;+0 + inode_bitmap dd ? ;+4 + inode_table dd ? ;+8 + free_blocks_count dw ? ;+12 + free_inodes_count dw ? ;+14 + used_dirs_count dw ? ;+16 + pad dw ? ;+18 + reserved rb 12;+20 ends struct EXT2_SB_STRUC @@ -132,7 +122,7 @@ struct EXT2_SB_STRUC algo_bitmap dd ? ;+200 prealloc_blocks db ? ;+204 preallock_dir_blocks db ? ;+205 - dw ? ;+206 alignment + reserved_gdt_blocks dw ? ;+206 journal_uuid rb 16 ;+208 journal_inum dd ? ;+224 journal_dev dd ? ;+228 @@ -142,6 +132,41 @@ struct EXT2_SB_STRUC rb 3 ;+253 reserved default_mount_options dd ? ;+256 first_meta_bg dd ? ;+260 + mkfs_time dd ? ;+264 + jnl_blocks rd 17 ;+268 + blocks_count_hi dd ? ;+336 + r_blocks_count_hi dd ? ;+340 + free_blocks_count_hi dd ? ;+344 + min_extra_isize dw ? ;+348 + want_extra_isize dw ? ;+350 + flags dd ? ;+352 + raid_stride dw ? ;+356 + mmp_interval dw ? ;+358 + mmp_block dq ? ;+360 + raid_stripe_width dd ? ;+368 + log_groups_per_flex db ? ;+372 +ends + +struct EXT4_EXTENT_HEADER ;╨╖╨░╨│╨╛╨╗╨╛╨▓╨╛╨║ ╨▒╨╗╨╛╨║╨░ ╤Н╨║╤Б╤В╨╡╨╜╤В╨╛╨▓/╨╕╨╜╨┤╨╡╨║╤Б╨╛╨▓ + eh_magic dw ? ;╨▓ ╤В╨╡╨║╤Г╤Й╨╡╨╣ ╤А╨╡╨░╨╗╨╕╨╖╨░╤Ж╨╕╨╕ ext4 ╨┤╨╛╨╗╨╢╨╜╨╛ ╨▒╤Л╤В╤М 0xF30A + eh_entries dw ? ;╨║╨╛╨╗╨╕╤З╨╡╤Б╤В╨▓╨╛ ╤Н╨║╤Б╤В╨╡╨╜╤В╨╛╨▓/╨╕╨╜╨┤╨╡╨║╤Б╨╛╨▓ ╨▓ ╨▒╨╗╨╛╨║╨╡ + eh_max dw ? ;max ╨║╨╛╨╗╨╕╤З╨╡╤Б╤В╨▓╨╛ (╨╕╤Б╨┐╨╛╨╗╤М╨╖╤Г╨╡╤В╤Б╤П ╨┐╤А╨╕ ╨╖╨░╨┐╨╕╤Б╨╕) + eh_depth dw ? ;╨│╨╗╤Г╨▒╨╕╨╜╨░ ╨┤╨╡╤А╨╡╨▓╨░ (0, ╨╡╤Б╨╗╨╕ ╤Н╤В╨╛ ╨▒╨╗╨╛╨║ ╤Н╨║╤Б╤В╨╡╨╜╤В╨╛╨▓) + eh_generation dd ? ;??? +ends + +struct EXT4_EXTENT ;╤Н╨║╤Б╤В╨╡╨╜╤В + ee_block dd ? ;╨╜╨╛╨╝╨╡╤А ext4 ╨▒╨╗╨╛╨║╨░ + ee_len dw ? ;╨┤╨╗╨╕╨╜╨░ ╤Н╨║╤Б╤В╨╡╨╜╤В╨░ + ee_start_hi dw ? ;╤Б╤В╨░╤А╤И╨╕╨╡ 16 ╨▒╨╕╤В 48-╨▒╨╕╤В╨╜╨╛╨│╨╛ ╨░╨┤╤А╨╡╤Б╨░ (╨┐╨╛╨║╨░ ╨╜╨╡ ╨╕╤Б╨┐╨╛╨╗╤М╨╖╤Г╤О╤В╤Б╤П ╨▓ KOS) + ee_start_lo dd ? ;╨╝╨╗╨░╨┤╤И╨╕╨╡ 32 ╨▒╨╕╤В╨░ 48-╨▒╨╕╤В╨╜╨╛╨│╨╛ ╨░╨┤╤А╨╡╤Б╨░ +ends + +struct EXT4_EXTENT_IDX ;╨╕╨╜╨┤╨╡╤Б - ╤Г╨║╨░╨╖╨░╤В╨╡╨╗╤М ╨╜╨░ ╨▒╨╗╨╛╨║ ╤Б ╤Н╨║╤Б╤В╨╡╨╜╤В╨░╨╝╨╕/╨╕╨╜╨┤╨╡╨║╤Б╨░╨╝╨╕ + ei_block dd ? ;╨╜╨╛╨╝╨╡╤А ext4 ╨▒╨╗╨╛╨║╨░ + ei_leaf_lo dd ? ;╨╝╨╗╨░╨┤╤И╨╕╨╡ 32 ╨▒╨╕╤В 48-╨▒╨╕╤В╨╜╨╛╨│╨╛ ╨░╨┤╤А╨╡╤Б╨░ + ei_leaf_hi dw ? ;╤Б╤В╨░╤А╤И╨╕╨╡ 16 ╨▒╨╕╤В 48-╨▒╨╕╤В╨╜╨╛╨│╨╛ ╨░╨┤╤А╨╡╤Б╨░ (╨┐╨╛╨║╨░ ╨╜╨╡ ╨╕╤Б╨┐╨╛╨╗╤М╨╖╤Г╤О╤В╤Б╤П ╨▓ KOS) + ei_unused dw ? ;╨╖╨░╤А╨╡╨╖╨╡╤А╨▓╨╕╤А╨╛╨▓╨░╨╜╨╛ ends ext2_test_superblock: @@ -152,16 +177,19 @@ ext2_test_superblock: add eax, 2 ;superblock start at 1024b call hd_read - cmp dword [ebx+24], 3 ;s_block_size 0,1,2,3 + cmp [ebx + EXT2_SB_STRUC.log_block_size], 3 ;0,1,2,3 ja .no - cmp word [ebx+56], 0xEF53 ;s_magic + cmp [ebx + EXT2_SB_STRUC.magic], 0xEF53 jne .no - cmp word [ebx+58], 1 ;s_state (EXT_VALID_FS=1) + cmp [ebx + EXT2_SB_STRUC.state], 1 ;EXT_VALID_FS=1 jne .no - mov eax, [ebx+96] + cmp [ebx + EXT2_SB_STRUC.inodes_per_group], 0 + je .no + + mov eax, [ebx + EXT2_SB_STRUC.feature_incompat] test eax, EXT2_FEATURE_INCOMPAT_FILETYPE jz .no - test eax, not EXT2_FEATURE_INCOMPAT_FILETYPE + test eax, not EXT4_FEATURE_INCOMPAT_SUPP jnz .no ; OK, this is correct EXT2 superblock @@ -192,7 +220,7 @@ ext2_setup: inc eax mov [ext2_data.groups_count], eax - mov ecx, [ebx+24] + mov ecx, [ebx + EXT2_SB_STRUC.log_block_size] inc ecx mov [ext2_data.log_block_size], ecx ; 1, 2, 3, 4 equ 1kb, 2kb, 4kb, 8kb @@ -218,13 +246,11 @@ ext2_setup: call kernel_alloc mov [ext2_data.ext2_temp_block], eax ; and for get_inode proc - movzx ebp, word [ebx+88] - mov ecx, [ebx+32] - mov edx, [ebx+40] + movzx ebp, word [ebx + EXT2_SB_STRUC.inode_size] + mov ecx, [ebx + EXT2_SB_STRUC.blocks_per_group] mov [ext2_data.inode_size], ebp mov [ext2_data.blocks_per_group], ecx - mov [ext2_data.inodes_per_group], edx push ebp ebp ebp ;3 kernel_alloc call kernel_alloc @@ -241,31 +267,130 @@ ext2_setup: jmp return_from_part_set ;================================================================== -;in: eax = i_block +;read ext2 block form FS to memory +;in: eax = i_block (address of block in ext2 terms) ; ebx = pointer to return memory +;out: eax - error code (0 = no_error) ext2_get_block: - push eax ebx ecx + push ebx ecx mov ecx, [ext2_data.log_block_size] shl eax, cl add eax, [PARTITION_START] mov ecx, [ext2_data.count_block_in_block] @@: call hd_read + cmp [hd_error], 0 + jnz .fail inc eax add ebx, 512 loop @B - pop ecx ebx eax + xor eax, eax + @@: + pop ecx ebx ret + .fail: + mov eax, ERROR_DEVICE + jmp @B + + ;=================================================================== -; in: ecx = ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨▓ inode (0..) +;╨┐╨╛╨╗╤Г╤З╨░╨╡╤В ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨╕╨╖ extent inode +;in: ecx = ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨┐╨╛ ╨┐╨╛╤А╤П╨┤╨║╤Г +; ebp = ╨░╨┤╤А╨╡╤Б extent header`╨░ +;out: ecx - ╨░╨┤╤А╨╡╤Б ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ ╨▓ ╤Б╨╗╤Г╤З╨░╨╡ ╤Г╤Б╨┐╨╡╤Е╨░ +; eax - ╨╜╨╛╨╝╨╡╤А ╨╛╤И╨╕╨▒╨║╨╕ (╨╡╤Б╨╗╨╕ ╤А╨░╨▓╨╜╨╛ 0, ╤В╨╛ ╨╛╤И╨╕╨▒╨║╨╕ ╨╜╨╡╤В) +ext4_block_recursive_search: + cmp word [ebp + EXT4_EXTENT_HEADER.eh_magic], 0xF30A ;EXT4_EXT_MAGIC + jne .fail + + movzx ebx, [ebp + EXT4_EXTENT_HEADER.eh_entries] + add ebp, sizeof.EXT4_EXTENT_HEADER + cmp word [ebp - sizeof.EXT4_EXTENT_HEADER + EXT4_EXTENT_HEADER.eh_depth], 0 + je .leaf_block ;╨╗╨╕╤Б╤В╨╛╨▓╨╛╨╣ ╨╗╨╕ ╤Н╤В╨╛ ╨▒╨╗╨╛╨║? + + ;╨╜╨╡ ╨╗╨╕╤Б╤В╨╛╨▓╨╛╨╣ ╨▒╨╗╨╛╨║, ╨░ ╨╕╨╜╨┤╨╡╨║╤Б╨╜╤Л╨╣ ; eax - ext4_extent_idx + test ebx, ebx + jz .fail ;╨┐╤Г╤Б╤В╨╛╨╣ ╨╕╨╜╨┤╨╡╨║╤Б╨╜╤Л╨╣ ╨▒╨╗╨╛╨║ -> ╨╛╤И╨╕╨▒╨║╨░ + + ;╤Ж╨╕╨║╨╗ ╨┐╨╛ ╨╕╨╜╨┤╨╡╨║╤Б╨░╨╝ ╤Н╨║╤Б╤В╨╡╨╜╤В╨╛╨▓ + @@: + cmp ebx, 1 ;╤Г ╨╕╨╜╨┤╨╡╨║╤Б╨╛╨▓ ╨╜╨╡ ╤Е╤А╨░╨╜╨╕╤В╤Б╤П ╨┤╨╗╨╕╨╜╨░, + je .end_search_index ;╨┐╨╛╤Н╤В╨╛╨╝╤Г, ╨╡╤Б╨╗╨╕ ╨╛╤Б╤В╨░╨╗╤Б╤П ╨┐╨╛╤Б╨╗╨╡╨┤╨╜╨╕╨╣ - ╤В╨╛ ╤Н╤В╨╛ ╨╜╤Г╨╢╨╜╤Л╨╣ + + cmp ecx, [ebp + EXT4_EXTENT_IDX.ei_block] + jb .fail + + cmp ecx, [ebp + sizeof.EXT4_EXTENT_IDX + EXT4_EXTENT_IDX.ei_block] ;╨▒╨╗╨╛╨║ ╤Б╨╗e╨┤╤Г╤О╤Й╨╡╨│╨╛ ╨╕╨╜╨┤╨╡╨║╤Б╨░ + jb .end_search_index ;╤Б╨╗╨╡╨┤╤Г╤О╤Й╨╕╨╣ ╨┤╨░╨╗╤М╤И╨╡ - ╨╖╨╜╨░╤З╨╕╤В ╤В╨╡╨║╤Г╤Й╨╕╨╣, ╤В╨╛ ╤З╤В╨╛ ╨╜╨░╨╝ ╨╜╤Г╨╢╨╡╨╜ + + add ebp, sizeof.EXT4_EXTENT_IDX + dec ebx + jmp @B + + .end_search_index: + ;ebp ╤Г╨║╨░╨╖╤Л╨▓╨░╨╡╤В ╨╜╨░ ╨╜╤Г╨╢╨╜╤Л╨╣ extent_idx, ╤Б╤З╨╕╤В╤Л╨▓╨░╨╡╨╝ ╤Б╨╗╨╡╨┤╤Г╤О╤Й╨╕╨╣ ╨▒╨╗╨╛╨║ + mov ebx, [ext2_data.ext2_temp_block] + mov eax, [ebp + EXT4_EXTENT_IDX.ei_leaf_lo] + call ext2_get_block + test eax, eax + jnz .fail + mov ebp, ebx + jmp ext4_block_recursive_search ;╤А╨╡╨║╤Г╤А╤Б╨╕╨▓╨╜╨╛ ╨┐╤А╤Л╨│╨░╨╡╨╝ ╨▓ ╨╜╨░╤З╨░╨╗╨╛ + + .leaf_block: ;╨╗╨╕╤Б╤В╨╛╨▓╨╛╨╣ ╨▒╨╗╨╛╨║ ebp - ext4_extent + ;╤Ж╨╕╨║╨╗ ╨┐╨╛ ╤Н╨║╤Б╤В╨╡╨╜╤В╨░╨╝ + @@: + test ebx, ebx + jz .fail ;╨╜╨╕ ╨╛╨┤╨╕╨╜ ╤Г╨╖╨╡╨╗ ╨╜╨╡ ╨┐╨╛╨┤╨╛╤И╨╡╨╗ - ╨╛╤И╨╕╨▒╨║╨░ + + mov edx, [ebp + EXT4_EXTENT.ee_block] + cmp ecx, edx + jb .fail ;╨╡╤Б╨╗╨╕ ╨╝╨╡╨╜╤М╤И╨╡, ╨╖╨╜╨░╤З╨╕╤В ╨╛╨╜ ╨▒╤Л╨╗ ╨▓ ╨┐╤А╨╡╨┤╤Л╨┤╤Г╤Й╨╕╤Е ╨▒╨╗╨╛╨║╨░╤Е -> ╨╛╤И╨╕╨▒╨║╨░ + + movzx edi, [ebp + EXT4_EXTENT.ee_len] + add edx, edi + cmp ecx, edx + jb .end_search_extent ;╨╜╨░╤И╨╗╨╕ ╨╜╤Г╨╢╨╜╤Л╨╣ ╨▒╨╗╨╛╨║ + + add ebp, sizeof.EXT4_EXTENT + dec ebx + jmp @B + + .end_search_extent: + mov edx, [ebp + EXT4_EXTENT.ee_start_lo] + sub ecx, [ebp + EXT4_EXTENT.ee_block] ;╤А╨░╨╖╨╜╨╕╤Ж╨░ ╨▓ ext4 ╨▒╨╗╨╛╨║╨░╤Е + add ecx, edx + xor eax, eax + ret + + .fail: + mov eax, ERROR_FS_FAIL + ret + +;=================================================================== +;╨┐╨╛╨╗╤Г╤З╨░╨╡╤В ╨░╨┤╤А╨╡╤Б ext2 ╨▒╨╗╨╛╨║╨░ ╨╕╨╖ inode ╤Б ╨╛╨┐╤А╨╡╨┤╨╡╨╗╨╜╨╜╤Л╨╝ ╨╜╨╛╨╝╨╡╤А╨╛╨╝ +;in: ecx = ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨▓ inode (0..) ; ebp = ╨░╨┤╤А╨╡╤Б inode -; out: ecx = ╨░╨┤╤А╨╡╤Б ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ +;out: ecx = ╨░╨┤╤А╨╡╤Б ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ +; eax - error code ext2_get_inode_block: + test [ebp + EXT2_INODE_STRUC.i_flags], EXT2_EXTENTS_FL + jz @F + + pushad + add ebp, EXT2_INODE_STRUC.i_block ;ebp - extent_header + call ext4_block_recursive_search + mov PUSHAD_ECX, ecx + mov PUSHAD_EAX, eax + popad + ret + + @@: cmp ecx, 12 ; 0..11 - direct block address jb .get_direct_block sub ecx, 12 - cmp ecx, [ext2_data.count_pointer_in_block] ; 12.. - indirect block + cmp ecx, [ext2_data.count_pointer_in_block] ; 12.. - indirect blocks jb .get_indirect_block sub ecx, [ext2_data.count_pointer_in_block] @@ -273,12 +398,14 @@ ext2_get_inode_block: jb .get_double_indirect_block sub ecx, [ext2_data.count_pointer_in_block_square] - ;.get_triple_indirect_block: - push eax edx ebx + ;triple indirect block + push edx ebx mov eax, [ebx + EXT2_INODE_STRUC.i_block + 14*4] mov ebx, [ext2_data.ext2_temp_block] call ext2_get_block + test eax, eax + jnz .fail xor edx, edx mov eax, ecx @@ -287,16 +414,20 @@ ext2_get_inode_block: ;eax - ╨╜╨╛╨╝╨╡╤А ╨▓ ╨┐╨╛╨╗╤Г╤З╨╡╨╜╨╜╨╛╨╝ ╨▒╨╗╨╛╨║╨╡ edx - ╨╜╨╛╨╝╨╡╤А ╨┤╨░╨╗╤М╤И╨╡ mov eax, [ebx + eax*4] call ext2_get_block + test eax, eax + jnz .fail mov eax, edx jmp @F .get_double_indirect_block: - push eax edx ebx + push edx ebx mov eax, [ebp + EXT2_INODE_STRUC.i_block + 13*4] mov ebx, [ext2_data.ext2_temp_block] call ext2_get_block + test eax, eax + jnz .fail mov eax, ecx @@: @@ -305,36 +436,45 @@ ext2_get_inode_block: mov eax, [ebx + eax*4] call ext2_get_block - mov ecx, [ebx + edx*4] + test eax, eax + jnz .fail - pop ebx edx eax + mov ecx, [ebx + edx*4] + .fail: + pop ebx edx ret .get_indirect_block: - push eax ebx + push ebx mov eax, [ebp + EXT2_INODE_STRUC.i_block + 12*4] mov ebx, [ext2_data.ext2_temp_block] call ext2_get_block + test eax, eax + jz @F ;╨╡╤Б╨╗╨╕ ╨╜╨╡ ╨▒╤Л╨╗╨╛ ╨╛╤И╨╕╨▒╨║╨╕ - mov ecx, [ebx + ecx*4] - pop ebx eax + mov ecx, [ebx + ecx*4] ;╨╖╨░╨╜╨╛╤Б╨╕╨╝ ╤А╨╡╨╖╤Г╨╗╤М╤В╨░╤В + @@: + pop ebx ret .get_direct_block: - mov ecx, dword [ebp + EXT2_INODE_STRUC.i_block + ecx*4] + mov ecx, [ebp + EXT2_INODE_STRUC.i_block + ecx*4] + xor eax, eax ret ;=================================================================== ;get content inode by num ;in: eax = inode_num ; ebx = address of inode content +;out: eax - error code ext2_get_inode: - pushad mov edi, ebx ;╤Б╨╛╤Е╤А╨░╨╜╨╕╨╝ ╨░╨┤╤А╨╡╤Б inode dec eax xor edx, edx - div [ext2_data.inodes_per_group] + + mov ecx, [ext2_data.sb] + div [ecx + EXT2_SB_STRUC.inodes_per_group] push edx ;locale num in group @@ -343,16 +483,16 @@ ext2_get_inode: ; ╨▓ eax - ╤Б╨╝╨╡╤Й╨╡╨╜╨╕╨╡ ╨│╤А╤Г╨┐╨┐╤Л ╤Б inode-╨╛╨╝ ╨╛╤В╨╜╨╛╤Б╨╕╤В╨╡╨╗╤М╨╜╨╛ ╨╜╨░╤З╨░╨╗╨░ ╨│╨╗╨╛╨▒╨░╨╗╤М╨╜╨╛╨╣ ╨┤╨╡╤Б╨║╤А╨╕╨┐╤В╨╛╤А╨╜╨╛╨╣ ╤В╨░╨▒╨╗╨╕╤Ж╤Л ; ╨╜╨░╨╣╨┤╨╡╨╝ ╨▒╨╗╨╛╨║ ╨▓ ╨║╨╛╤В╨╛╤А╨╛╨╝ ╨╛╨╜ ╨╜╨░╤Е╨╛╨┤╨╕╤В╤Б╤П - div [ext2_data.block_size] - mov ecx, [ext2_data.sb] add eax, [ecx + EXT2_SB_STRUC.first_data_block] inc eax mov ebx, [ext2_data.ext2_temp_block] call ext2_get_block + test eax, eax + jnz .fail add ebx, edx ; ╨╗╨╛╨║╨░╨╗╤М╨╜╤Л╨╣ ╨╜╨╛╨╝╨╡╤А ╨▓ ╨▒╨╗╨╛╨║╨╡ - mov eax, [ebx+8] ; ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ - ╨▓ ╤В╨╡╤А╨╝╨╕╨╜╨░╤Е ext2 + mov eax, [ebx + EXT2_BLOCK_GROUP_DESC.inode_table]; ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ - ╨▓ ╤В╨╡╤А╨╝╨╕╨╜╨░╤Е ext2 mov ecx, [ext2_data.log_block_size] shl eax, cl @@ -371,74 +511,18 @@ ext2_get_inode: add eax, esi ;╨╜╨░╤И╨╗╨╕ ╨░╨┤╤А╨╡╤Б ╨▒╨╗╨╛╨║╨░ ╨┤╨╗╤П ╤З╤В╨╡╨╜╨╕╤П mov ebx, [ext2_data.ext2_temp_block] call hd_read + cmp [hd_error], 0 + jnz .fail mov esi, edx ;╨┤╨╛╨▒╨░╨▓╨╕╨╝ "╨╛╤Б╤В╨░╤В╨╛╨║" add esi, ebx ;╨║ ╨░╨┤╤А╨╡╤Б╤Г - ; mov ecx, [ext2_data.inode_size] rep movsb ;╨║╨╛╨┐╨╕╤А╤Г╨╡╨╝ inode + xor eax, eax + .fail: + mov PUSHAD_EAX, eax popad ret -;---------------------------------------------------------------- -; in: esi -> children -; ebx -> pointer to dir block -; out: esi -> name without parent or not_changed -; ebx -> dir_rec of inode children or trash -ext2_test_block_by_name: - push eax ecx edx edi - - mov edx, ebx - add edx, [ext2_data.block_size] ;╨╖╨░╨┐╨╛╨╝╨╜╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨▒╨╗╨╛╨║╨░ - - .start_rec: - cmp [ebx + EXT2_DIR_STRUC.inode], 0 - jz .next_rec - - push esi - movzx ecx, [ebx + EXT2_DIR_STRUC.name_len] - mov edi, EXT2_filename - lea esi, [ebx + EXT2_DIR_STRUC.name] - - call utf8toansi_str - mov ecx, edi - sub ecx, EXT2_filename ;╨║╨╛╨╗-╨▓╨╛ ╨▒╨░╨╣╤В ╨▓ ╨┐╨╛╨╗╤Г╤З╨╕╨▓╤И╨╡╨╣╤Б╤П ╤Б╤В╤А╨╛╨║╨╡ - - mov edi, EXT2_filename - mov esi, [esp] - @@: - jecxz .test_find - dec ecx - - lodsb - call char_toupper - - mov ah, [edi] - inc edi - xchg al, ah - call char_toupper - cmp al, ah - je @B - @@: ;╨╜╨╡ ╨┐╨╛╨┤╨╛╤И╨╗╨╛ - pop esi - .next_rec: - movzx eax, [ebx + EXT2_DIR_STRUC.rec_len] - add ebx, eax ;╨║ ╤Б╨╗╨╡╨┤. ╨╖╨░╨┐╨╕╤Б╨╕ - cmp ebx, edx ;╨┐╤А╨╛╨▓╨╡╤А╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨╗╨╕ - jb .start_rec - jmp .ret - - .test_find: - cmp byte [esi], 0 - je .find ;╨╜╨░╤И╨╗╨╕ ╨║╨╛╨╜╨╡╤Ж - cmp byte [esi], '/' - jne @B - inc esi - .find: - pop eax ;╤Г╨┤╨░╨╗╤П╨╡╨╝ ╨╕╨╖ ╤Б╤В╨╡╨║╨░ ╤Б╨╛╤Е╤А╨░╨╜╨╡╨╜╨╛╨╡ ╨╖╨╜╨░╤З╨╡╨╜╨╕╨╡ - .ret: - pop edi edx ecx eax - ret - ;---------------------------------------------------------------- ; ; ext2_HdReadFolder - read disk folder @@ -456,120 +540,137 @@ ext2_test_block_by_name: ;-------------------------------------------------------------- ext2_HdReadFolder: cmp byte [esi], 0 - jz .doit + jz .root_folder - push ecx ebx - call ext2_find_lfn - jnc .doit2 - pop ebx - .not_found: - pop ecx - or ebx, -1 - mov eax, ERROR_FILE_NOT_FOUND - ret - - .doit: - mov ebp, [ext2_data.root_inode] - push ecx - jmp @F - .doit2: - pop ebx + push ebx ecx edx + call ext2_find_lfn ;╨▓╨╡╤А╨╜╨╡╤В ╨▓ ebp ╨░╨┤╤А╨╡╤Б inode + pop edx ecx ebx + test eax, eax + jnz .error_ret test [ebp + EXT2_INODE_STRUC.i_mode], EXT2_S_IFDIR - jz .not_found + jz .error_not_found + jmp @F + + .root_folder: + mov ebp, [ext2_data.root_inode] + test [ebp + EXT2_INODE_STRUC.i_mode], EXT2_S_IFDIR + jz .error_root + ;╨┐╤А╨╕╨┤╨╡╤В╤Б╤П ╨║╨╛╨┐╨╕╤А╨╛╨▓╨░╤В╤М inode + push ecx + mov esi, ebp + mov edi, [ext2_data.ext2_save_inode] + mov ecx, [ext2_data.inode_size] + shr ecx, 2 + mov ebp, edi + rep movsd + pop ecx @@: - xor eax, eax + cmp [ebp + EXT2_INODE_STRUC.i_blocks], 0 ;╨┐╨░╨┐╨║╨░ ╨┐╤Г╤Б╤В╨░ + je .error_empty_dir + + push edx ;╨░╨┤╤А╨╡╤Б ╤А╨╡╨╖╤Г╨╗╤М╤В╨░╤В╨░ [edi + 28] + push 0 ;╨║╨╛╨╜╨╡╤Ж ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ ╨┐╨░╨┐╨║╨╕ [edi + 24] + push ecx ;╤Б╨║╨╛╨╗╤М╨║╨╛ ╤Д╨░╨╣╨╗╨╛╨▓ ╨╜╤Г╨╢╨╜╨╛ ╨┐╤А╨╛╤З╨╕╤В╨░╤В╤М [edi + 20] + push dword [ebx] ;╨┐╨╡╤А╨▓╤Л╨╣ "╨╜╤Г╨╢╨╜╤Л╨╣" ╤Д╨░╨╣╨╗ [edi + 16] + push dword [ebx + 4];╤Д╨╗╨░╨│╨╕ [edi + 12] + push 0 ;[EXT2_read_in_folder] [edi + 8] + push 0 ;[EXT2_files_in_folder] [edi + 4] + push 0 ;╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨┐╨╛ ╨┐╨╛╤А╤П╨┤╨║╤Г [edi] + mov edi, edx mov ecx, 32/4 rep stosd ; fill header zero - pop edi ; edi = ╤З╨╕╤Б╨╗╨╛ ╨▒╨╗╨╛╨║╨╛╨▓ ╨┤╨╗╤П ╤З╤В╨╡╨╜╨╕╤П - push edx ebx - ;--------------------------------------------- final step - and [EXT2_read_in_folder], 0 - and [EXT2_files_in_folder], 0 + mov edi, esp ; edi - ╤Г╨║╨░╨╖╨░╤В╨╡╨╗╤М ╨╜╨░ ╨╗╨╛╨║╨░╨╗╤М╨╜╤Л╨╡ ╨┐╨╡╤А╨╡╨╝╨╡╨╜╨╜╤Л╨╡ + add edx, 32 ; edx = current mem for return - mov eax, [ebp + EXT2_INODE_STRUC.i_blocks] - mov [EXT2_counter_blocks], eax - - add edx, 32 ; (header pointer in stack) edx = current mem for return - xor esi, esi ; esi = ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨┐╨╛ ╨┐╨╛╤А╤П╨┤╨║╤Г - - .new_block_folder: ;reserved label - mov ecx, esi ; ╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ + xor ecx, ecx ; ╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨╜╨╛╨╝╨╡╤А ╨┐╨╡╤А╨▓╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ call ext2_get_inode_block + test eax, eax + jnz .error_get_block mov eax, ecx mov ebx, [ext2_data.ext2_save_block] call ext2_get_block ; ╨╕ ╤Б╤З╨╕╤В╤Л╨▓╨░╨╡╨╝ ╨▒╨╗╨╛╨║ ╤Б hdd + test eax, eax + jnz .error_get_block - mov eax, ebx ; eax = current dir record + mov esi, ebx ; esi = current dir record add ebx, [ext2_data.block_size] - mov [EXT2_end_block], ebx ; ╨╖╨░╨┐╨╛╨╝╨╜╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ + mov [edi + 24], ebx ; ╨╖╨░╨┐╨╛╨╝╨╜╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ - pop ecx - mov ecx, [ecx] ; ecx = first wanted (flags ommited) + mov ecx, [edi + 16] ; ecx = first wanted (flags ommited) .find_wanted_start: jecxz .find_wanted_end .find_wanted_cycle: - cmp [eax + EXT2_DIR_STRUC.inode], 0 ; if (inode = 0) => not used + cmp [esi + EXT2_DIR_STRUC.inode], 0 ; if (inode = 0) => not used jz @F - inc [EXT2_files_in_folder] + inc dword [edi + 4] ; EXT2_files_in_folder dec ecx @@: - movzx ebx, [eax+EXT2_DIR_STRUC.rec_len] + movzx ebx, [esi + EXT2_DIR_STRUC.rec_len] cmp ebx, 12 ; ╨╝╨╕╨╜╨╕╨╝╨░╨╗╤М╨╜╨░╤П ╨┤╨╗╨╕╨╜╨░ ╨╖╨░╨┐╨╕╤Б╨╕ - jb .end_error + jb .error_bad_len test ebx, 0x3 ; ╨┤╨╗╨╕╨╜╨░ ╨╖╨░╨┐╨╕╤Б╨╕ ╨┤╨╛╨╗╨╢╨╜╨░ ╨┤╨╡╨╗╨╕╤В╤М╤Б╤П ╨╜╨░ 4 - jnz .end_error + jnz .error_bad_len - add eax, ebx ; ╨║ ╤Б╨╗╨╡╨┤╤Г╤О╤Й╨╡╨╣ ╨╖╨░╨┐╨╕╤Б╨╕ - cmp eax, [EXT2_end_block] ; ╨┐╤А╨╛╨▓╨╡╤А╤П╨╡╨╝ "╨║╨╛╨╜╨╡╤Ж" + add esi, ebx ; ╨║ ╤Б╨╗╨╡╨┤╤Г╤О╤Й╨╡╨╣ ╨╖╨░╨┐╨╕╤Б╨╕ + cmp esi, [edi + 24] ; ╤Б╤А╨░╨▓╨╜╨╕╨▓╨░╨╡╨╝ ╤Б ╨║╨╛╨╜╤Ж╨╛╨╝ ╨▒╨╗╨╛╨║╨░ jb .find_wanted_start push .find_wanted_start - .end_block: ;╨▓╤Л╨╗╨╡╤В╨╕╨╗╨╕ ╨╕╨╖ ╤Ж╨╕╨║╨╗╨░ + .end_block: ;╨▓╤Л╨╗╨╡╤В╨╡╨╗╨╕ ╨╕╨╖ ╤Ж╨╕╨║╨╗╨░ mov ebx, [ext2_data.count_block_in_block] - sub [EXT2_counter_blocks], ebx - jbe .end_dir + sub [ebp + EXT2_INODE_STRUC.i_blocks], ebx ;╨▓╤Л╤З╨╕╤В╨░╨╡╨╝ ╨╜╨░╨┐╤А╤П╨╝╤Г╤О ╨╕╨╖ ╤Б╤В╤А╤Г╨║╤В╤Г╤А╤Л inode + jle .end_dir - inc esi ;╨┐╨╛╨╗╤Г╤З╨░╨╡╨╝ ╨╜╨╛╨▓╤Л╨╣ ╨▒╨╗╨╛╨║ + inc dword [edi] ;╨┐╨╛╨╗╤Г╤З╨░╨╡╨╝ ╨╜╨╛╨▓╤Л╨╣ ╨▒╨╗╨╛╨║ push ecx - mov ecx, esi + mov ecx, [edi] call ext2_get_inode_block + test eax, eax + jnz .error_get_block + mov eax, ecx mov ebx, [ext2_data.ext2_save_block] call ext2_get_block + test eax, eax + jnz .error_get_block + pop ecx - mov eax, ebx + mov esi, ebx add ebx, [ext2_data.block_size] - mov [EXT2_end_block], ebx + mov [edi + 24], ebx ;╨╖╨░╨┐╨╛╨╝╨╜╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨▒╨╗╨╛╨║╨░ ret ; ╨╛╨┐╤П╤В╤М ╨▓ ╤Ж╨╕╨║╨╗ .wanted_end: - loop .find_wanted_cycle ; ecx = -1 + loop .find_wanted_cycle ; ecx 0 => -1 ╨╜╤Г╨╢╨╜╨╛ ╨┐╨╛╤Б╤З╨╕╤В╨░╤В╤М ╤Б╨║╨╛╨╗╤М╨║╨╛ ╤Д╨░╨╣╨╗╨╛╨▓ + ;╨┤╨╛╤И╨╗╨╕ ╨┤╨╛ ╨┐╨╡╤А╨▓╨╛╨│╨╛ "╨╜╤Г╨╢╨╜╨╛╨│╨╛" ╤Д╨░╨╣╨╗╨░ .find_wanted_end: - mov ecx, edi + mov ecx, [edi + 20] .wanted_start: ; ╨╕╤Й╨╡╨╝ first_wanted+count jecxz .wanted_end - cmp [eax + EXT2_DIR_STRUC.inode], 0 ; if (inode = 0) => not used + cmp [esi + EXT2_DIR_STRUC.inode], 0 ; if (inode = 0) => not used jz .empty_rec - inc [EXT2_files_in_folder] - inc [EXT2_read_in_folder] + inc dword [edi + 8] + inc dword [edi + 4] - mov edi, edx - push eax ecx + push edi ecx + mov edi, edx ;╨╛╨▒╨╜╤Г╨╗╤П╨╡╨╝ ╨╝╨╡╤Б╤В╨╛ ╨┐╨╛╨┤ ╨╛╤З╨╡╤А╨╡╨╜╨╛╨╡ ╨╕╨╝╤П ╤Д╨░╨╣╨╗╨░/╨┐╨░╨┐╨║╨╕ xor eax, eax mov ecx, 40 / 4 rep stosd - pop ecx eax + pop ecx edi - push eax esi edx ;╨┐╨╛╨╗╤Г╤З╨╕╨╝ inode - mov eax, [eax + EXT2_DIR_STRUC.inode] + push esi edi edx + mov eax, [esi + EXT2_DIR_STRUC.inode] ;╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨┤╨╛╤З╨╡╤А╨╜╨╕╨╣ inode mov ebx, [ext2_data.ext2_temp_inode] call ext2_get_inode + test eax, eax + jnz .error_read_subinode lea edi, [edx + 8] @@ -599,23 +700,20 @@ ext2_HdReadFolder: stosd mov eax, [ebx + EXT2_INODE_STRUC.i_dir_acl] ;high size stosd - xor dword [edx], FS_FT_DIR + xor dword [edx], FS_FT_DIR ;╨┐╨╛╨╝╨╡╤З╨░╨╡╨╝, ╤З╤В╨╛ ╤Н╤В╨╛ ╤Д╨░╨╣╨╗(2 ╤А╨░╨╖╨░ xor) @@: - xor dword [edx], FS_FT_DIR - pop esi eax - - or dword [edx+4], FS_FT_ASCII ; symbol type in name + xor dword [edx], FS_FT_DIR ;╨┐╨╛╨╝╨╡╤З╨░╨╡╨╝, ╤З╤В╨╛ ╤Н╤В╨╛ ╤Д╨░╨╣╨╗ ;╤В╨╡╨┐╨╡╤А╤М ╤Б╨║╨╛╨┐╨╕╤А╤Г╨╡╨╝ ╨╕╨╝╤П, ╤Б╨║╨╛╨╜╨▓╨╡╤А╤В╨╕╤А╨╛╨▓╨░╨▓ ╨╕╨╖ UTF-8 ╨▓ CP866 - push eax ecx esi - movzx ecx, [eax + EXT2_DIR_STRUC.name_len] + push ecx ;edi ╨╕ esi ╤Г╨╢╨╡ ╤Б╨╛╤Е╤А╨░╨╜╨╡╨╜╤Л ╨▓ ╤Б╤В╨╡╨║╨╡ + movzx ecx, [esi + EXT2_DIR_STRUC.name_len] lea edi, [edx + 40] - lea esi, [eax + EXT2_DIR_STRUC.name] - call utf8toansi_str - pop esi ecx eax + lea esi, [esi + EXT2_DIR_STRUC.name] + call utf8_to_cp866 and byte [edi], 0 + pop ecx edi esi - cmp byte [edx + 40], '.' + cmp byte [edx + 40], '.' ; ╨▓ linux ╤Д╨░╨╣╨╗, ╨╜╨░╤З╨╕╨╜╨░╤О╤Й╨╕╨╣╤Б╤П ╤Б ╤В╨╛╤З╨║╨╕ - ╤Б╨║╤А╤Л╤В╤Л╨╣ jne @F or dword [edx], FS_FT_HIDDEN @@: @@ -623,38 +721,60 @@ ext2_HdReadFolder: add edx, 40 + 264 ; go to next record dec ecx ; ╨╡╤Б╨╗╨╕ ╨╖╨░╨┐╨╕╤Б╤М ╨┐╤Г╤Б╤В╨░╤П ecx ╨╜╨╡ ╨╜╨░╨┤╨╛ ╤Г╨╝╨╡╨╜╤М╤И╨░╤В╤М .empty_rec: - movzx ebx, [eax + EXT2_DIR_STRUC.rec_len] + movzx ebx, [esi + EXT2_DIR_STRUC.rec_len] cmp ebx, 12 ; ╨╝╨╕╨╜╨╕╨╝╨░╨╗╤М╨╜╨░╤П ╨┤╨╗╨╕╨╜╨░ ╨╖╨░╨┐╨╕╤Б╨╕ - jb .end_error + jb .error_bad_len test ebx, 0x3 ; ╨┤╨╗╨╕╨╜╨░ ╨╖╨░╨┐╨╕╤Б╨╕ ╨┤╨╛╨╗╨╢╨╜╨░ ╨┤╨╡╨╗╨╕╤В╤М╤Б╤П ╨╜╨░ 4 - jnz .end_error + jnz .error_bad_len - add eax, ebx - cmp eax, [EXT2_end_block] + add esi, ebx + cmp esi, [edi + 24] ;╨┤╨╛╤И╨╗╨╕ ╨╗╨╕ ╨┤╨╛ ╨║╨╛╨╜╤Ж╨░ ╨▒╨╗╨╛╨║╨░? jb .wanted_start - push .wanted_start ; ╨┤╨╛╤И╨╗╨╕ ╨┤╨╛ ╨║╨╛╨╜╤Ж╨░ ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ + push .wanted_start ; ╨┤╨╛╤И╨╗╨╕ jmp .end_block - .end_dir: - pop eax ; ╨╝╤Г╤Б╨╛╤А (╨░╨┤╤А╨╡╤Б ╨▓╨╛╨╖╨▓╤А╨░╤В╨░ ╨▓ ╤Ж╨╕╨║╨╗) - .end_error: - pop edx - mov ebx, [EXT2_read_in_folder] - mov ecx, [EXT2_files_in_folder] + .end_dir: ;╨║╨╛╨╜╨╡╤Ж ╨┐╨░╨┐╨║╨╕, ╨║╨╛╨│╨┤╨░ ╨╡╤Й╨╡ ╨╜╨╡ ╨┤╨╛╤И╨╗╨╕ ╨┤╨╛ ╨╜╤Г╨╢╨╜╨╛╨│╨╛ ╤Д╨░╨╣╨╗╨░ + mov edx, [edi + 28] ;╨░╨┤╤А╨╡╤Б ╤Б╤В╤А╤Г╨║╤В╤Г╤А╤Л ╤А╨╡╨╖╤Г╨╗╤М╤В╨░╤В╨░ + mov ebx, [edi + 8] ;EXT2_read_in_folder + mov ecx, [edi + 4] ;EXT2_files_in_folder mov dword [edx], 1 ;version - xor eax, eax - mov [edx+4], ebx - mov [edx+8], ecx + mov [edx + 4], ebx + mov [edx + 8], ecx + + lea esp, [edi + 32] + + xor eax, eax ;╨╖╨░╤А╨╡╨╖╨╡╤А╨▓╨╕╤А╨╛╨▓╨░╨╜╨╛: ╨╜╤Г╨╗╨╕ ╨▓ ╤В╨╡╨║╤Г╤Й╨╡╨╣ ╤А╨╡╨░╨╗╨╕╨╖╨░╤Ж╨╕╨╕ lea edi, [edx + 12] mov ecx, 20 / 4 rep stosd ret -;====================== end ext2_HdReadFolder -utf8toansi_str: -; convert UTF-8 string to ASCII-string (codepage 866) -; in: ecx=length source, esi->source, edi->buffer + + .error_bad_len: + mov eax, ERROR_FS_FAIL + .error_read_subinode: + .error_get_block: + lea esp, [edi + 32] + .error_ret: + or ebx, -1 + ret + + .error_empty_dir: ;inode ╨┐╨░╨┐╨║╨╕ ╨▒╨╡╨╖ ╨▒╨╗╨╛╨║╨╛╨▓ + .error_root: ;root - ╨╜╨╡ ╨┐╨░╨┐╨║╨░ + mov eax, ERROR_FS_FAIL + jmp .error_ret + + .error_not_found: ;╤Д╨░╨╣╨╗ ╨╜╨╡ ╨╜╨░╨╣╨┤╨╡╨╜ + mov eax, ERROR_FILE_NOT_FOUND + jmp .error_ret + +;============================================ +;convert UTF-8 string to ASCII-string (codepage 866) +;in: ecx = length source +; esi = source +; edi = buffer ; destroys: eax,esi,edi +utf8_to_cp866: jecxz .ret .start: lodsw @@ -712,7 +832,7 @@ utf8toansi_str: ; ; ret ebx = bytes read or 0xffffffff file not found ; eax = 0 ok read or other = errormsg -; + ;-------------------------------------------------------------- ext2_HdRead: cmp byte [esi], 0 @@ -724,27 +844,31 @@ ext2_HdRead: ret @@: - push ecx ebx + push ecx ebx edx call ext2_find_lfn - pop ebx ecx - jnc .doit - ;.not_found: + pop edx ebx ecx + test eax, eax + jz @F + or ebx, -1 mov eax, ERROR_FILE_NOT_FOUND ret - .doit: - test [ebp + EXT2_INODE_STRUC.i_mode], EXT2_S_IFREG - jz .this_is_nofile + @@: + mov ax, [ebp + EXT2_INODE_STRUC.i_mode] + and ax, EXT2_S_IFMT ;╨╛╤Б╤В╨░╨▓╨╗╤П╨╡╨╝ ╤В╨╛╨╗╤М╨║╨╛ ╤В╨╕╨┐ inode ╨▓ ax + cmp ax, EXT2_S_IFREG + jne .this_is_nofile - ;-----------------------------------------------------------------------------final step mov edi, edx ; edi = pointer to return mem - mov esi, ebx ; esi = pointer to first_wanted - ;///// ╤Б╤А╨░╨▓╨╜╨╕╨╝ ╤Е╨▓╨░╤В╨╕╤В ╨╗╨╕ ╨╜╨░╨╝ ╤Д╨░╨╣╨╗╨░ ╨╕╨╗╨╕ ╨╜╨╡╤В + test ebx, ebx + jz @F + mov esi, ebx ; esi = pointer to first_wanted mov ebx, [esi+4] mov eax, [esi] ; ebx : eax - ╤Б╤В╨░╤А╤В╨╛╨▓╤Л╨╣ ╨╜╨╛╨╝╨╡╤А ╨▒╨░╨╣╤В╨░ + ;///// ╤Б╤А╨░╨▓╨╜╨╕╨╝ ╤Е╨▓╨░╤В╨╕╤В ╨╗╨╕ ╨╜╨░╨╝ ╤Д╨░╨╣╨╗╨░ ╨╕╨╗╨╕ ╨╜╨╡╤В cmp [ebp + EXT2_INODE_STRUC.i_dir_acl], ebx ja .size_great jb .size_less @@ -756,6 +880,10 @@ ext2_HdRead: xor ebx, ebx mov eax, ERROR_END_OF_FILE ret + + @@: + xor ebx, ebx + xor eax, eax .size_great: add eax, ecx ;add to first_wanted ╨║╨╛╨╗-╨▓╨╛ ╨▒╨░╨╣╤В ╨┤╨╗╤П ╤З╤В╨╡╨╜╨╕╤П adc ebx, 0 @@ -764,35 +892,45 @@ ext2_HdRead: ja .size_great_great jb .size_great_less cmp [ebp + EXT2_INODE_STRUC.i_size], eax - jae .size_great_great ; ╨░ ╨╡╤Б╨╗╨╕ ╤А╨░╨▓╨╜╨╛, ╤В╨╛ ╨╜╨╡ ╨▓╨░╨╢╨╜╨╛ ╨║╤Г╨┤╨░ + jae .size_great_great .size_great_less: - or [EXT2_files_in_folder], 1 ;╤З╨╕╤В╨░╨╡╨╝ ╨┐╨╛ ╨│╤А╨░╨╜╨╕╤Ж╨╡ ╤А╨░╨╖╨╝╨╡╤А╨░ + push 1 +; or [EXT2_files_in_folder], 1 ;╤З╨╕╤В╨░╨╡╨╝ ╨┐╨╛ ╨│╤А╨░╨╜╨╕╤Ж╨╡ ╤А╨░╨╖╨╝╨╡╤А╨░ mov ecx, [ebp + EXT2_INODE_STRUC.i_size] - sub ecx, [esi] ;(╤А╨░╨╖╨╝╨╡╤А - ╤Б╤В╨░╤А╤В) + sub ecx, [esi] ;(╤А╨░╨╖╨╝╨╡╤А - ╤Б╤В╨░╤А╤В) = ╤Б╨║╨╛╨╗╤М╨║╨╛ ╤З╨╕╤В╨░╤В╤М jmp @F .size_great_great: - and [EXT2_files_in_folder], 0 ;╤З╨╕╤В╨░╨╡╨╝ ╤Б╤В╨╛╨╗╤М╨║╨╛ ╤Б╨║╨╛╨╗╤М╨║╨╛ ╨╖╨░╨┐╤А╨╛╤Б╨╕╨╗╨╕ + push 0 +; and [EXT2_files_in_folder], 0 ;╤З╨╕╤В╨░╨╡╨╝ ╤Б╤В╨╛╨╗╤М╨║╨╛ ╤Б╨║╨╛╨╗╤М╨║╨╛ ╨╖╨░╨┐╤А╨╛╤Б╨╕╨╗╨╕ @@: - push ecx ;save for return + ;╨╖╨┤╨╡╤Б╤М ╨╝╤Л ╤В╨╛╤З╨╜╨╛ ╨╖╨╜╨░╨╡╨╝ ╤Б╨║╨╛╨╗╤М╨║╨╛ ╨▒╨░╨╣╤В ╤З╨╕╤В╨░╤В╤М - ecx + ;edi - return memory + ;esi -> first wanted + + push ecx ;╨║╨╛╨╗╨╕╤З╨╡╤Б╤В╨▓╨╛ ╤Б╤З╨╕╤В╨░╨╜╨╜╤Л╤Е ╨▒╨░╨╣╤В test esi, esi jz .zero_start - ;╨┐╨╛╨║╨░ ╨┤╨╡╨╗╨░╨╡╨╝ ╨┐..╤Ж ╨║╤А╨╕╨▓╨╛ =) + ;╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨║╤Г╤Б╨╛╨║ ╨╕╨╖ ╨┐╨╡╤А╨▓╨╛╨│╨╛ ╨▒╨╗╨╛╨║╨░ mov edx, [esi+4] mov eax, [esi] div [ext2_data.block_size] - mov [EXT2_counter_blocks], eax ;╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨╖╨░╨┐╨╛╨╝╨╕╨╜╨░╨╡╨╝ + push eax ;╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨╖╨░╨┐╨╛╨╝╨╕╨╜╨░╨╡╨╝ push ecx mov ecx, eax call ext2_get_inode_block + test eax, eax + jnz .error_at_first_block mov ebx, [ext2_data.ext2_save_block] mov eax, ecx call ext2_get_block + test eax, eax + jnz .error_at_first_block pop ecx add ebx, edx @@ -807,12 +945,13 @@ ext2_HdRead: mov esi, ebx rep movsb ;╨║╤Г╤Б╨╛╨║ 1-╨│╨╛ ╨▒╨╗╨╛╨║╨░ - jmp @F + jmp .calc_blocks_count .zero_start: mov eax, ecx + push 0 ;╤Б╤З╨╡╤В╤З╨╕╨║ ╨▒╨╗╨╛╨║╨╛╨▓ ;╤В╨╡╨┐╨╡╤А╤М ╨▓ eax ╨║╨╛╨╗-╨▓╨╛ ╨╛╤Б╤В╨░╨▓╤И╨╕╤Е╤Б╤П ╨▒╨░╨╣╤В ╨┤╨╗╤П ╤З╤В╨╡╨╜╨╕╤П - @@: + .calc_blocks_count: mov ebx, edi ;╤З╤В╨╡╨╜╨╕╨╡ ╨▒╨╗╨╛╨║╨░ ╨┐╤А╤П╨╝ ╨▓ ->ebx xor edx, edx div [ext2_data.block_size] ;╨║╨╛╨╗-╨▓╨╛ ╨▒╨░╨╣╤В ╨▓ ╨┐╨╛╤Б╨╗╨╡╨┤╨╜╨╡╨╝ ╨▒╨╗╨╛╨║╨╡ (╨╛╤Б╤В╨░╤В╨╛╨║) ╨▓ edx @@ -820,12 +959,16 @@ ext2_HdRead: @@: test edi, edi jz .finish_block - inc [EXT2_counter_blocks] - mov ecx, [EXT2_counter_blocks] + inc dword [esp] + mov ecx, [esp] call ext2_get_inode_block + test eax, eax + jnz .error_at_read_cycle mov eax, ecx ;╨░ ebx ╤Г╨╢╨╡ ╨╖╨░╨▒╨╕╤В ╨╜╤Г╨╢╨╜╤Л╨╝ ╨╖╨╜╨░╤З╨╡╨╜╨╕╨╡╨╝ call ext2_get_block + test eax, eax + jnz .error_at_read_cycle add ebx, [ext2_data.block_size] dec edi @@ -835,23 +978,26 @@ ext2_HdRead: test edx, edx jz .end_read - mov ecx, [EXT2_counter_blocks] + pop ecx ;╤Б╤З╨╡╤В╤З╨╕╨║ ╨▒╨╗╨╛╨║╨╛╨▓ -> ecx inc ecx call ext2_get_inode_block + test eax, eax + jz .error_at_finish_block mov edi, ebx mov eax, ecx mov ebx, [ext2_data.ext2_save_block] call ext2_get_block + test eax, eax + jnz .error_at_finish_block mov ecx, edx - - .only_one_block: mov esi, ebx rep movsb ;╨║╤Г╤Б╨╛╨║ last ╨▒╨╗╨╛╨║╨░ .end_read: pop ebx - cmp [EXT2_files_in_folder], 0 + pop eax + test eax, eax jz @F mov eax, ERROR_END_OF_FILE @@ -859,85 +1005,189 @@ ext2_HdRead: @@: xor eax, eax ret + + .only_one_block: + mov esi, ebx + rep movsb ;╨║╤Г╤Б╨╛╨║ last ╨▒╨╗╨╛╨║╨░ + pop eax + jmp .end_read + + .error_at_first_block: + pop edx + .error_at_read_cycle: + pop ebx + .error_at_finish_block: + pop ecx edx + or ebx, -1 + ret + +;---------------------------------------------------------------- +; in: esi = file path +; ebx = pointer to dir block +; out: esi - name without parent or not_changed +; ebx - dir_rec of inode children +ext2_test_block_by_name: + sub esp, 256 ;EXT2_filename + mov edx, ebx + add edx, [ext2_data.block_size] ;╨╖╨░╨┐╨╛╨╝╨╜╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨▒╨╗╨╛╨║╨░ + + .start_rec: + cmp [ebx + EXT2_DIR_STRUC.inode], 0 + jz .next_rec + + mov edi, esp + push esi + movzx ecx, [ebx + EXT2_DIR_STRUC.name_len] + lea esi, [ebx + EXT2_DIR_STRUC.name] + call utf8_to_cp866 + + mov ecx, edi + lea edi, [esp + 4] + sub ecx, edi ;╨║╨╛╨╗-╨▓╨╛ ╨▒╨░╨╣╤В ╨▓ ╨┐╨╛╨╗╤Г╤З╨╕╨▓╤И╨╡╨╣╤Б╤П ╤Б╤В╤А╨╛╨║╨╡ + + mov esi, [esp] + @@: + jecxz .test_find + dec ecx + + lodsb + call char_toupper + + mov ah, [edi] + inc edi + xchg al, ah + call char_toupper + cmp al, ah + je @B + @@: ;╨╜╨╡ ╨┐╨╛╨┤╨╛╤И╨╗╨╛ + pop esi + .next_rec: + movzx eax, [ebx + EXT2_DIR_STRUC.rec_len] + add ebx, eax ;╨║ ╤Б╨╗╨╡╨┤. ╨╖╨░╨┐╨╕╤Б╨╕ + cmp ebx, edx ;╨┐╤А╨╛╨▓╨╡╤А╨╕╨╝ ╨║╨╛╨╜╨╡╤Ж ╨╗╨╕ + jb .start_rec + add esp, 256 + ret + + .test_find: + cmp byte [esi], 0 + je .ret ;╨╜╨░╤И╨╗╨╕ ╨║╨╛╨╜╨╡╤Ж + cmp byte [esi], '/' + jne @B + inc esi + .ret: + add esp, 256 + 4 + ret + ;======================== -;in : esi -> name not save: eax ebx ecx -;out: ebp -> inode cf=0 -; ebp -> trash cf=1 +;╨Ш╤Й╨╡╤В inode ╨┐╨╛ ╤Б╤В╤А╨╛╨║╨╡ ╨┐╤Г╤В╨╕ +;in: esi = name +;out: eax - error code +; ebp = inode +; dl - ╨┐╨╡╤А╨▓╤Л╨╣ ╨▒╨░╨╣╤В ╨╕╨╖ ╨╕╨╝╨╡╨╜╨╕ ╤Д╨░╨╣╨╗╨░/╨┐╨░╨┐╨║╨╕ ext2_find_lfn: mov ebp, [ext2_data.root_inode] - .next_folder: - or [EXT2_counter_blocks], -1 ;╤Б╤З╨╡╤В╤З╨╕╨║ ╨▒╨╗╨╛╨║╨╛╨▓ ╨┐╨░╨┐╨║╨╕ cur block of inode - mov eax, [ebp + EXT2_INODE_STRUC.i_blocks] ;╤Г╨▒╤Л╨▓╨░╤О╤Й╨╕╨╣ ╤Б╤З╨╡╤В╤З╨╕╨║ ╨▒╨╗╨╛╨║╨╛╨▓ - add eax, [ext2_data.count_block_in_block] - mov [EXT2_end_block], eax - .next_block_folder: - mov eax, [ext2_data.count_block_in_block] - sub [EXT2_end_block], eax - jz .not_found - inc [EXT2_counter_blocks] - mov ecx, [EXT2_counter_blocks] + cmp [ebp + EXT2_INODE_STRUC.i_blocks], 0 + je .error_empty_root + + .next_path_part: + push [ebp + EXT2_INODE_STRUC.i_blocks] + xor ecx, ecx + .folder_block_cycle: call ext2_get_inode_block + test eax, eax + jnz .error_get_inode_block mov eax, ecx mov ebx, [ext2_data.ext2_save_block] ;ebx = cur dir record call ext2_get_block + test eax, eax + jnz .error_get_block - mov eax, esi + push esi call ext2_test_block_by_name - cmp eax, esi ;╨╜╨░╤И╨╗╨╕ ╨╕╨╝╤П? - jz .next_block_folder + pop edi - cmp byte [esi], 0 + cmp edi, esi ;╨╜╨░╤И╨╗╨╕ ╨╕╨╝╤П? + je .next_folder_block ;╨╜╨╡ ╨╜╨░╤И╨╗╨╕ -> ╨║ ╤Б╨╗╨╡╨┤. ╨▒╨╗╨╛╨║╤Г + + cmp byte [esi], 0 ;╨┤╨╛╤И╨╗╨╕ ╨┤╨╛ "╨║╨╛╨╜╤Ж╨░" ╨┐╤Г╤В╨╕ -> ╨▓╨╛╨╖╨▓╨░╤А╨░╤Й╨░╨╡╨╝╤Б╤П jz .get_inode_ret - cmp [ebx + EXT2_DIR_STRUC.file_type], EXT2_FT_DIR - jne .not_found ;╨╜╨░╤И╨╗╨╕, ╨╜╨╛ ╤Н╤В╨╛ ╨╜╨╡ ╨┐╨░╨┐╨║╨░ + cmp [ebx + EXT2_DIR_STRUC.file_type], EXT2_FT_DIR ;╨╜╨░╤И╨╗╨╕, ╨╜╨╛ ╤Н╤В╨╛ ╨╜╨╡ ╨┐╨░╨┐╨║╨░ + jne .not_found + mov eax, [ebx + EXT2_DIR_STRUC.inode] mov ebx, [ext2_data.ext2_save_inode] ;╨▓╤Б╨╡ ╨╢╨╡ ╨┐╨░╨┐╨║╨░. call ext2_get_inode + test eax, eax + jnz .error_get_inode + pop ecx ;╨▓ ╤Б╤В╨╡╨║╨╡ ╨╗╨╡╨╢╨╕╤В ╨║╨╛╨╗-╨▓╨╛ ╨▒╨╗╨╛╨║╨╛╨▓ mov ebp, ebx - jmp .next_folder + jmp .next_path_part + + .next_folder_block: + ;╨║ ╤Б╨╗╨╡╨┤╤Г╤О╤Й╨╡╨╝╤Г ╨▒╨╗╨╛╨║╤Г ╨▓ ╤В╨╡╨║╤Г╤Й╨╡╨╣ ╨┐╨░╨┐╨║╨╡ + pop eax ;╤Б╤З╨╡╤В╤З╨╕╨║ ╨▒╨╗╨╛╨║╨╛╨▓ + sub eax, [ext2_data.count_block_in_block] + jle .not_found + + inc ecx + jmp .folder_block_cycle .not_found: - stc + pop ebx + mov eax, ERROR_FILE_NOT_FOUND ret + .get_inode_ret: - mov [EXT2_end_block], ebx ; ╤Б╨╛╤Е╤А╨░╨╜╤П╨╡╨╝ ╤Г╨║╨░╨╖╨░╤В╨╡╤В╤М ╨╜╨░ dir_rec + pop ecx ;╨▓ ╤Б╤В╨╡╨║╨╡ ╨╗╨╡╨╢╨╕╤В ╨║╨╛╨╗-╨▓╨╛ ╨▒╨╗╨╛╨║╨╛╨▓ + mov dl, [ebx + EXT2_DIR_STRUC.name] ;╨▓ dl - ╨┐╨╡╤А╨▓╤Л╨╣ ╤Б╨╕╨╝╨▓╨╛╨╗ () mov eax, [ebx + EXT2_DIR_STRUC.inode] mov ebx, [ext2_data.ext2_save_inode] call ext2_get_inode mov ebp, ebx - clc + xor eax, eax ret + .error_get_inode_block: + .error_get_block: + .error_get_inode: + pop ebx + .error_empty_root: + mov eax, ERROR_FS_FAIL + ret -;======================== - +;---------------------------------------------------------------- +;ext2_HdGetFileInfo - read file info from block device +; +;in: esi points to filename +; edx mem location to return data +;-------------------------------------------------------------- ext2_HdGetFileInfo: + xchg bx, bx cmp byte [esi], 0 - jz .doit + jz .is_root + push edx call ext2_find_lfn - jnc .doit2 - ;.not_found: - mov eax, ERROR_FILE_NOT_FOUND + mov ebx, edx + pop edx + test eax, eax + jz @F ret - .doit: + .is_root: + xor ebx, ebx ;root ╨╜╨╡ ╨╝╨╛╨╢╨╡╤В ╨▒╤Л╤В╤М ╤Б╨║╤А╤Л╤В╤Л╨╝ mov ebp, [ext2_data.root_inode] - mov ebx, .doit ;╨╜╨╡╨▓╨░╨╢╨╜╨╛ ╤З╤В╨╛ ╨╗╨╕╤И╤М ╨▒╤Л ╤Н╤В╨╛╨╝╤Г ╨░╨┤╤А╨╡╤Б╤Г ╨╜╨╡ '.' - jmp @F - .doit2: - mov ebx, [EXT2_end_block] - add ebx, EXT2_DIR_STRUC.name @@: xor eax, eax mov edi, edx mov ecx, 40/4 rep stosd ; fill zero - cmp byte [ebx], '.' - jnz @F + cmp bl, '.' + jne @F or dword [edx], FS_FT_HIDDEN @@: @@ -952,19 +1202,19 @@ ext2_HdGetFileInfo: xor dword [edx], FS_FT_DIR lea edi, [edx + 8] - mov eax, [ebx + EXT2_INODE_STRUC.i_ctime] + mov eax, [ebp + EXT2_INODE_STRUC.i_ctime] xor edx, edx add eax, 3054539008 adc edx, 2 call ntfs_datetime_to_bdfe.sec - mov eax, [ebx + EXT2_INODE_STRUC.i_atime] + mov eax, [ebp + EXT2_INODE_STRUC.i_atime] xor edx, edx add eax, 3054539008 adc edx, 2 call ntfs_datetime_to_bdfe.sec - mov eax, [ebx + EXT2_INODE_STRUC.i_mtime] + mov eax, [ebp + EXT2_INODE_STRUC.i_mtime] xor edx, edx add eax, 3054539008 adc edx, 2 @@ -982,337 +1232,3 @@ ext2_HdCreateFolder: xor ebx, ebx mov eax, ERROR_UNSUPPORTED_FS ret -;---------------------------------------------------------------- -; -; ext2_HdCreateFolder - create new folder -; -; esi points to filename -; -; ret eax = 0 ok read or other = errormsg -; -;-------------------------------------------------------------- - cmp byte [esi], 0 - jz .not_found - cmp byte [esi], '/' - jz .not_found - - mov ebx, esi ; save source pointer - xor edi, edi ; slah pointer - @@: - lodsb - cmp al, 0 - jz .zero - cmp al, '/' - jz .slash - jmp @B - - .slash: - lodsb - cmp al, 0 - jz .zero ; ╤Г╨▒╨╡╤А╨╡╨╝ ╤Б╨╗╨╡╤И ╨╕╨╖ ╨╕╨╝╨╡╨╜╨╕ - cmp al, '/' - jz .not_found - mov edi, esi ; edi -> next symbol after '/' - dec edi - jmp @B - - .zero: - dec esi - test edi, edi - jz .doit - - ;╤Б╨╗╨╡╤И ╨▒╤Л╨╗ - mov eax, esi - sub eax, edi - mov [EXT2_name_len], eax - - mov ecx, edi - sub ecx, ebx - dec ecx ;╨▓╤Л╨║╨╕╨╜╤Г╨╗╨╕ '/' ╨╕╨╖ ╨╕╨╝╨╡╨╜╨╕ ╤А╨╛╨╗╨╕╤В╨╡╨╗╤П - mov esi, ebx - mov edi, EXT2_parent_name - rep movsb - ; esi - pointer to last slash - - mov edx, esi - mov esi, EXT2_parent_name - call ext2_find_lfn - jnc .doit2 - .not_found: - or ebx, -1 - mov eax, ERROR_FILE_NOT_FOUND - ret - - .doit: - mov ebp, [ext2_data.root_inode] - mov edx, ebx ; ╨╕╨╝╤П ╤Б╨╛╨╖╨┤╨░╨▓╨░╨╡╨╝╨╛╨╣ ╨┐╨░╨┐╨║╨╕ - sub esi, ebx - mov [EXT2_name_len], esi - .doit2: - ;ebp -> parent_inode ebx->name_new_folder [EXT2_name_len]=length of name -; ╤Б╤В╤А╨░╤В╨╡╨│╨╕╤П ╨▓╤Л╨▒╨╛╤А╨░ ╨│╤А╤Г╨┐╨┐╤Л ╨┤╨╗╤П ╨╜╨╛╨▓╨╛╨│╨╛ inode: (╤В╨░╨║ ╨┤╨╡╨╗╨░╨╡╤В ╨╗╨╕╨╜╤Г╨║╤Б) -; 1) ╨Ш╤Й╨╡╨╝ ╨│╤А╤Г╨┐╨┐╤Г ╨▓ ╨║╨╛╤В╨╛╤А╨╛╨╣ ╨╝╨╡╨╜╤М╤И╨╡ ╨▓╤Б╨╡╨│╨╛ ╨┐╨░╨┐╨╛╨║ ╨╕ ╨▓ ╨╡╤Б╤В╤М ╤Б╨▓╨╛╨▒╨╛╨┤╨╜╨╛╨╡ ╨╝╨╡╤Б╤В╨╛ -; 2) ╨Х╤Б╨╗╨╕ ╤В╨░╨║╨░╤П ╨│╤А╤Г╨┐╨┐╨░ ╨╜╨╡ ╨╜╨░╤И╨╗╨░╤Б╤М, ╤В╨╛ ╨▒╨╡╤А╨╡╨╝ ╨│╤А╤Г╨┐╨┐╤Г ╨▓ ╨║╨╛╤В╨╛╤А╨╛╨╣ ╨▒╨╛╨╗╤М╤И╨╡ ╤Б╨▓╨╛╨▒╨╛╨┤╨╜╨╛╨│╨╛ ╨╝╨╡╤Б╤В╨░ - - - - - call ext2_balloc - jmp ext2_HdDelete - - push ebx - push ebp - - mov ecx, [ext2_data.sb] - cmp [ecx + EXT2_SB_STRUC.free_inodes_count], 0 ; ╨╡╤Б╤В╤М ╨╗╨╕ ╨╝╨╡╤Б╤В╨╛ ╨┤╨╗╤П inode - jz .no_space - mov eax, [ecx + EXT2_SB_STRUC.free_block_count] - sub eax, [ecx + EXT2_SB_STRUC.r_block_count] - cmp eax, 2 ; ╨╕ ╨║╨░╨║ ╨╝╨╕╨╜╨╕╨╝╤Г╨╝ ╨╜╨░ 2 ╨▒╨╗╨╛╨║╨░ - jb .no_space - - mov ecx, [ext2_data.groups_count] - mov esi, [ext2_data.global_desc_table] - mov edi, -1 ;╤Г╨║╨░╨╖╨░╤В╨╡╨╗╤М ╨╜╨░ ╨╗╤Г╤З╤И╤Г╤О ╨│╤А╤Г╨┐╨┐╤Г - mov edx, 0 - .find_group_dir: - jecxz .end_find_group_dir - movzx eax, [esi + EXT2_BLOCK_GROUP_DESC.free_inodes_count] - cmp eax, edx - jbe @F - cmp [esi + EXT2_BLOCK_GROUP_DESC.free_blocks_count], 0 - jz @F - mov edi, esi - movzx edx, [esi + EXT2_BLOCK_GROUP_DESC.free_inodes_count] - @@: - dec ecx - add esi, 32 ;╤А╨░╨╖╨╝╨╡╤А ╤Б╤В╤А╤Г╨║╤В╤Г╤А╤Л - jmp .find_group_dir - .end_find_group_dir: - cmp edx, 0 - jz .no_space - - ;╨╜╨░╤И╨╗╨╕ ╨│╤А╤Г╨┐╨┐╤Г, ╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨▒╨╕╤В╨╛╨▓╤Г╤О ╨║╨░╤А╤В╤Г inode-╨╛╨▓ (╨╜╨░╨╣╨┤╨╡╨╝ locale number) - mov eax, [edi + EXT2_BLOCK_GROUP_DESC.inode_bitmap] - mov ebx, [ext2_data.ext2_save_block] - call ext2_get_block - - ;╤В╨╡╨┐╨╡╤А╤М ╤Ж╨╕╨║╨╗ ╨┐╨╛ ╨▓╤Б╨╡╨╝ ╨▒╨╕╤В╨░╨╝ - mov esi, ebx - mov ecx, [ext2_data.inodes_per_group] - shr ecx, 5 ;╨┤╨╡╨╗╨╕╨╝ ╨╜╨░ 32 - mov ebp, ecx ; ╨▓╤Б╨╡╨│╨╛ ╤Б╨╛╤Е╤А╨░╨╜╨╕╨╝ ╨▓ ebp - or eax, -1 ; ╨╕╤Й╨╡╨╝ ╨┐╨╡╤А╨▓╤Л╨╣ ╤Б╨▓╨╛╨▒╨╛╨┤╨╜╤Л╨╣ inode (!= -1) - repne scasd - jnz .test_last_dword ;╨╜╨░╤И╨╗╨╕ ╨╕╨╗╨╕ ╨╜╨╡╤В - mov eax, [esi-4] - - sub ebp, ecx - dec ebp - shl ebp, 5 ; ╨│╨╗╨╛╨▒╨░╨╗╤М╨╜╤Л╨╣ ╨╜╨╛╨╝╨╡╤А ╨╗╨╛╨║╨░╨╗╤М╨╜╨╛╨│╨╛ ╨╜╨╛╨╝╨╡╤А╨░ - - mov ecx, 32 - @@: - test eax, 1 - jz @F - shr eax, 1 - loop @B - @@: - mov eax, 32 - sub eax, ecx - - add ebp, eax ; locale num of inode - - mov eax, [esi-4] - ;╤Г╤Б╤В╨░╨╜╨░╨▓╨╗╨╕╨▓╨░╨╡╨╝ ╨▓ eax ╨║╤А╨░╨╣╨╜╨╕╨╣ ╤Б╨┐╤А╨░╨▓╨░ ╨╜╤Г╨╗╨╡╨▓╨╛╨╣ ╨▒╨╕╤В ╨▓ 1 - mov ecx, eax - inc ecx - or eax, ecx ; x | (x+1) - mov [esi-4], eax - mov ebx, [ext2_data.ext2_save_block] - mov eax, [edi + EXT2_BLOCK_GROUP_DESC.inode_bitmap] - call ext2_set_block - ;╤Б╤З╨╕╤В╨░╨╡╨╝ ╤В╨░╨▒╨╗╨╕╤Ж╤Г inode - sub edi, [ext2_data.global_desc_table] - shr edi, 5 - - mov eax, edi - mul [ext2_data.inodes_per_group] - add eax, ebp - inc eax ; ╤В╨╡╨┐╨╡╤А╤М ╨▓ eax (ebp) ╨╜╨╛╨╝╨╡╤А inode-╨░ - mov ebp, eax - ;call ext2_get_inode_address - - mov ebx, [ext2_data.ext2_save_block] - call hd_read - add edx, ebx ; ╨▓ edx ╨░╨┤╤А╨╡╤Б ╨╜╤Г╨╢╨╜╨╛╨│╨╛ inode - - ;╨╖╨░╨▒╤М╨╡╨╝ 0 ╨┤╨╗╤П ╨╜╨░╤З╨░╨╗╨░ - mov edi, edx - mov ecx, [ext2_data.inode_size] - shr ecx, 2 - xor eax, eax - rep stosd - - mov edi, edx - mov eax, EXT2_S_IFDIR or EXT2_777_MODE - stosd ; i_mode - xor eax, eax - stosd ; i_uid - mov eax, [ext2_data.block_size] - stosd ; i_size - xor eax, eax - stosd ; i_atime - stosd ; i_ctime - stosd ; i_mtime - stosd ; i_dtime - stosd ; i_gid - inc eax - stosd ; i_links_count - mov eax, [ext2_data.count_block_in_block] - stosd ; i_blocks - - - - -.test_last_dword: - - xor ebx, ebx - mov eax, ERROR_UNSUPPORTED_FS - ret - - - - .no_space: - or ebx, -1 - mov eax, ERROR_DISK_FULL - ret - -;╨▓╤Л╨┤╨╡╨╗╤П╨╡╤В ╨╜╨╛╨▓╤Л╨╣ ╨▒╨╗╨╛╨║, ╨╡╤Б╨╗╨╕ ╤Н╤В╨╛ ╨╝╨╛╨╢╨╜╨╛ -;╨╕╨╜╨░╤З╨╡ ╨▓╨╛╨╖╨▓╤А╨░╤Й╨░╨╡╤В eax=0 -ext2_balloc: - mov ecx, [ext2_data.sb] - mov eax, [ecx + EXT2_SB_STRUC.free_block_count] - sub eax, [ecx + EXT2_SB_STRUC.r_block_count] - jbe .no_space - - mov ecx, [ext2_data.groups_count] - mov edi, [ext2_data.global_desc_table] - ;mov esi, -1 ;╤Г╨║╨░╨╖╨░╤В╨╡╨╗╤М ╨╜╨░ ╨╗╤Г╤З╤И╤Г╤О ╨│╤А╤Г╨┐╨┐╤Г - mov edx, 0 - .find_group: - jecxz .end_find_group - movzx eax, [edi + EXT2_BLOCK_GROUP_DESC.free_blocks_count] - cmp eax, edx - jbe @F - mov esi, edi - mov edx, eax - @@: - dec ecx - add edi, 32 ;╤А╨░╨╖╨╝╨╡╤А ╤Б╤В╤А╤Г╨║╤В╤Г╤А╤Л - jmp .find_group - .end_find_group: - cmp edx, 0 - jz .no_space - - ;╨╜╨░╤И╨╗╨╕ ╨│╤А╤Г╨┐╨┐╤Г, ╨┐╨╛╨╗╤Г╤З╨╕╨╝ ╨▒╨╕╤В╨╛╨▓╤Г╤О ╨║╨░╤А╤В╤Г block-╨╛╨▓ - mov eax, [esi + EXT2_BLOCK_GROUP_DESC.block_bitmap] - mov ebx, [ext2_data.ext2_save_block] - call ext2_get_block - - ;╤В╨╡╨┐╨╡╤А╤М ╤Ж╨╕╨║╨╗ ╨┐╨╛ ╨▓╤Б╨╡╨╝ ╨▒╨╕╤В╨░╨╝ - mov edi, ebx - mov ecx, [ext2_data.blocks_per_group] - shr ecx, 5 ;╨┤╨╡╨╗╨╕╨╝ ╨╜╨░ 32 - mov ebp, ecx ;╨▓╤Б╨╡╨│╨╛ ╤Б╨╛╤Е╤А╨░╨╜╨╕╨╝ ╨▓ ebp - or eax, -1 ;╨╕╤Й╨╡╨╝ ╨┐╨╡╤А╨▓╤Л╨╣ ╤Б╨▓╨╛╨▒╨╛╨┤╨╜╤Л╨╣ inode (!= -1) - repe scasd - jz .test_last_dword ;╨╜╨░╤И╨╗╨╕ ╨╕╨╗╨╕ ╨╜╨╡╤В - - mov eax, [edi-4] - sub ebp, ecx - dec ebp - shl ebp, 5 ; ebp = 32*(╨╜╨╛╨╝╨╡╤А div 32). ╨в╨╡╨┐╨╡╤А╤М ╨╜╨░╨╣╨┤╨╡╨╝ (╨╜╨╛╨╝╨╡╤А mod 32) - - mov ecx, 32 - @@: - test eax, 1 - jz @F - shr eax, 1 - loop @B - @@: - mov eax, 32 - sub eax, ecx - - add ebp, eax ; ebp = ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ ╨▓ ╨│╤А╤Г╨┐╨┐╨╡ - - mov eax, [edi-4] - mov ecx, eax - inc ecx - or eax, ecx ; x | (x+1) - ╤Г╤Б╤В╨░╨╜╨░╨▓╨╗╨╕╨▓╨░╨╡╤В ╨▓ 1 ╨║╤А╨░╨╣╨╜╨╕╨╣ ╤Б╨┐╤А╨░╨▓╨░ ╨╜╤Г╨╗╨╡╨▓╨╛╨╣ ╨▒╨╕╤В (block used) - mov [edi-4], eax - - mov ebx, [ext2_data.ext2_save_block] - mov eax, [esi + EXT2_BLOCK_GROUP_DESC.inode_bitmap] - ; call ext2_set_block ; ╨╕ ╨┐╨╕╤И╨╡╨╝ ╨╜╨░ hdd ╨╜╨╛╨▓╤Г╤О ╨▒╨╕╤В╨╛╨▓╤Г╤О ╨╝╨░╤Б╨║╤Г - - ;============== ╤В╤Г╤В ╨┐╨╛╨╗╤Г╤З╨░╨╡╨╝ ╨╜╨╛╨╝╨╡╤А ╨▒╨╗╨╛╨║╨░ - mov eax, [ext2_data.blocks_per_group] - sub esi, [ext2_data.global_desc_table] - shr esi, 5 ;esi - ╨╜╨╛╨╝╨╡╤А ╨│╤А╤Г╨┐╨┐╤Л - mul esi - add ebp, eax ;(╨╜╨╛╨╝╨╡╤А_╨│╤А╤Г╨┐╨┐╤Л) * (blocks_per_group) + ╨╗╨╛╨║╨░╨╗╤М╨╜╤Л╨╣ ╨╜╨╛╨╝╨╡╤А ╨▓ ╨│╤А╤Г╨┐╨┐╨╡ - mov eax, [ext2_data.sb] - add ebp, [eax + EXT2_SB_STRUC.first_data_block] - - ;╤В╨╡╨┐╨╡╤А╤М ╨┐╨╛╨┐╤А╨░╨▓╨╕╨╝ ╨│╨╗╨╛╨▒╨░╨╗╤М╨╜╤Г╤О ╨┤╨╡╤Б╨║╤А╨╕╨┐╤В╨╛╤А╨╜╤Г╤О ╤В╨░╨▒╨╗╨╕╤Ж╤Г ╨╕ ╤Б╤Г╨┐╨╡╤А╨▒╨╗╨╛╨║ - mov ebx, [ext2_data.sb] - dec [ebx + EXT2_SB_STRUC.free_block_count] - mov eax, 2 - add eax, [PARTITION_START] - call hd_write - mov eax, [ebx + EXT2_SB_STRUC.first_data_block] - inc eax - dec [esi + EXT2_BLOCK_GROUP_DESC.free_blocks_count];edi ╨▓╤Б╨╡ ╨╡╤Й╨╡ ╤Г╨║╨░╨╖╤Л╨▓╨░╨╡╤В ╨╜╨░ ╨│╤А╤Г╨┐╨┐╤Г ╨▓ ╨║╨╛╤В╨╛╤А╨╛╨╣ ╨╝╤Л ╨▓╤Л╨┤╨╡╨╗╨╕╨╗ ╨▒╨╗╨╛╨║ - call ext2_set_block - - mov eax, ebx - ret - - .test_last_dword: - lodsd - mov ecx, [ext2_data.blocks_per_group] - and ecx, not (32-1) ;╨╛╨▒╨╜╤Г╨╗╤П╨╡╨╝ ╨▓╤Б╨╡ ╨║╤А╨╛╨╝╨╡ ╨┐╨╛╤Б╨╗╨╡╨┤╨╜╨╕╤Е 5 ╨▒╨╕╤В - mov edx, ecx - mov ebx, 1 - @@: - jecxz .no_space - mov edx, ebx - or edx, eax ; ╤В╨╡╤Б╤В╨╕╤А╤Г╨╡╨╝ ╨╛╤З╨╡╤А╨╡╨┤╨╜╨╛╨╣ ╨▒╨╕╤В - shl ebx, 1 - jmp @B - @@: - sub edx, ecx - dec edx ;╨╜╨╛╨╝╨╡╤А ╨▓ ╨┐╨╛╤Б╨╗╨╡╨┤╨╜╨╡╨╝ ╨▒╨╗╨╛╨║╨╡ - - - .no_space: - xor eax, eax - ret - -;in: eax = i_block -; ebx = pointer to memory -ext2_set_block: - push eax ebx ecx - mov ecx, [ext2_data.log_block_size] - shl eax, cl - add eax, [PARTITION_START] - mov ecx, [ext2_data.count_block_in_block] - @@: - call hd_write - inc eax - add ebx, 512 - loop @B - pop ecx ebx eax - ret - diff --git a/kernel/branches/Kolibri-acpi/fs/fat12.inc b/kernel/branches/Kolibri-acpi/fs/fat12.inc index 16fb0fb25d..327e51ef55 100644 --- a/kernel/branches/Kolibri-acpi/fs/fat12.inc +++ b/kernel/branches/Kolibri-acpi/fs/fat12.inc @@ -634,31 +634,34 @@ fat_find_lfn: ; [esp+4] = next ; [esp+8] = first ; [esp+C]... - possibly parameters for first and next -; out: CF=1 - file not found +; out: CF=1 - file not found, eax=error code ; else CF=0, esi->next name component, edi->direntry pusha lea eax, [esp+0Ch+20h] call dword [eax-4] jc .reterr sub esp, 262*2 ; reserve place for LFN - mov ebp, esp push 0 ; for fat_get_name: read ASCII name .l1: + lea ebp, [esp+4] call fat_get_name jc .l2 call fat_compare_name jz .found .l2: + mov ebp, [esp+8+262*2+4] lea eax, [esp+0Ch+20h+262*2+4] call dword [eax-8] jnc .l1 add esp, 262*2+4 .reterr: + mov [esp+28], eax stc popa ret .found: add esp, 262*2+4 + mov ebp, [esp+8] ; if this is LFN entry, advance to true entry cmp byte [edi+11], 0xF jnz @f diff --git a/kernel/branches/Kolibri-acpi/fs/fat32.inc b/kernel/branches/Kolibri-acpi/fs/fat32.inc index ee44495631..45bed2750b 100644 --- a/kernel/branches/Kolibri-acpi/fs/fat32.inc +++ b/kernel/branches/Kolibri-acpi/fs/fat32.inc @@ -49,19 +49,6 @@ $Revision$ cache_max equ 1919 ; max. is 1919*512+0x610000=0x6ffe00 -ERROR_SUCCESS = 0 -ERROR_DISK_BASE = 1 -ERROR_UNSUPPORTED_FS = 2 -ERROR_UNKNOWN_FS = 3 -ERROR_PARTITION = 4 -ERROR_FILE_NOT_FOUND = 5 -ERROR_END_OF_FILE = 6 -ERROR_MEMORY_POINTER = 7 -ERROR_DISK_FULL = 8 -ERROR_FAT_TABLE = 9 -ERROR_ACCESS_DENIED = 10 -ERROR_DEVICE = 11 - PUSHAD_EAX equ [esp+28] PUSHAD_ECX equ [esp+24] PUSHAD_EDX equ [esp+20] @@ -70,144 +57,247 @@ PUSHAD_EBP equ [esp+8] PUSHAD_ESI equ [esp+4] PUSHAD_EDI equ [esp+0] +; Internal data for every FAT partition. +struct FAT +p PARTITION ; must be the first item +fs_type db ? +fat16_root db 0 ; flag for fat16 rootdir +fat_change db 0 ; 1=fat has changed + db ? ; alignment +Lock MUTEX ? ; currently operations with one partition + ; can not be executed in parallel since the + ; legacy code is not ready; this mutex guards + ; all operations +SECTORS_PER_FAT dd 0x1f3a +NUMBER_OF_FATS dd 0x2 +SECTORS_PER_CLUSTER dd 0x8 +BYTES_PER_SECTOR dd 0x200 ; Note: if BPS <> 512 need lots of changes +ROOT_CLUSTER dd 2 ; first rootdir cluster +FAT_START dd 0 ; start of fat table +ROOT_START dd 0 ; start of rootdir (only fat16) +ROOT_SECTORS dd 0 ; count of rootdir sectors (only fat16) +DATA_START dd 0 ; start of data area (=first cluster 2) +LAST_CLUSTER dd 0 ; last availabe cluster +ADR_FSINFO dd 0 ; used only by fat32 + +fatRESERVED dd 0x0FFFFFF6 +fatBAD dd 0x0FFFFFF7 +fatEND dd 0x0FFFFFF8 +fatMASK dd 0x0FFFFFFF + +fatStartScan dd 2 + +cluster_tmp dd 0 ; used by analyze_directory + ; and analyze_directory_to_write + +longname_sec1 dd 0 ; used by analyze_directory to save 2 previous +longname_sec2 dd 0 ; directory sectors for delete long filename + +fat_in_cache dd -1 + +fat_cache rb 512 +buffer rb 512 +fsinfo_buffer rb 512 +ends + uglobal align 4 partition_count dd 0 ; partitions found by set_FAT32_variables -longname_sec1 dd 0 ; used by analyze_directory to save 2 previous -longname_sec2 dd 0 ; directory sectors for delete long filename hd_error dd 0 ; set by wait_for_sector_buffer hd_setup dd 0 hd_wait_timeout dd 0 -cluster_tmp dd 0 ; used by analyze_directory - ; and analyze_directory_to_write - -file_size dd 0 ; used by file_read - cache_search_start dd 0 ; used by find_empty_slot endg -iglobal -fat_in_cache dd -1 -endg - uglobal align 4 -fat_cache: - times 512 db 0 Sector512: ; label for dev_hdcd.inc buffer: times 512 db 0 - fsinfo_buffer: - times 512 db 0 endg -uglobal - fat16_root db 0 ; flag for fat16 rootdir - fat_change db 0 ; 1=fat has changed +iglobal +align 4 +fat_user_functions: + dd (fat_user_functions_end - fat_user_functions - 4) / 4 + dd fat_Read + dd fat_ReadFolder + dd fat_Rewrite + dd fat_Write + dd fat_SetFileEnd + dd fat_GetFileInfo + dd fat_SetFileInfo + dd 0 + dd fat_Delete + dd fat_CreateFolder +fat_user_functions_end: endg -reserve_hd1: - - cli - cmp [hd1_status], 0 - je reserve_ok1 - - sti - call change_task - jmp reserve_hd1 - - reserve_ok1: - - push eax - mov eax, [CURRENT_TASK] - shl eax, 5 - mov eax, [eax+CURRENT_TASK+TASKDATA.pid] - mov [hd1_status], eax - pop eax - sti +; these labels are located before the main function to make +; most of jumps to these be short +fat_create_partition.free_return0: + push ebx + mov eax, ebp + call free + pop ebx + pop ebp +fat_create_partition.return0: + xor eax, eax ret -;******************************************** +fat_create_partition: +; bootsector must have been successfully read + cmp dword [esp+4], 1 + jnz .return0 +; bootsector signature must be correct + cmp word [ebx+0x1fe], 0xaa55 + jnz .return0 +; sectors per cluster must be nonzero + cmp byte [ebx+0xd], 0 + jz .return0 +; bytes per sector must be 0x200 + cmp word [ebx+0xb], 0x200 + jnz .return0 +; number of fats must be nonzero + cmp byte [ebx+0x10], 0 + jz .return0 +; The only reason to be invalid partition now is FAT12. Since the test for +; FAT size requires knowledge of some calculated values, which are also used +; in the normal operation, let's hope for the best and allocate data now; if +; it will prove wrong, just deallocate it. + push ebx + push sizeof.FAT + pop eax + call malloc + pop ebx + test eax, eax + jz .return0 + mov ecx, [ebp+8] + mov dword [eax+FAT.p.FirstSector], ecx + mov ecx, [ebp+12] + mov dword [eax+FAT.p.FirstSector+4], ecx + mov ecx, [ebp+16] + mov dword [eax+FAT.p.Length], ecx + mov ecx, [ebp+20] + mov dword [eax+FAT.p.Length+4], ecx + mov [eax+FAT.p.Disk], esi + mov [eax+FAT.p.FSUserFunctions], fat_user_functions + or [eax+FAT.fat_in_cache], -1 + mov [eax+FAT.fat_change], 0 + push ebp + mov ebp, eax -uglobal -hd_in_cache db ? -endg + lea ecx, [ebp+FAT.Lock] + call mutex_init -reserve_hd_channel: -; BIOS disk accesses are protected with common mutex hd1_status -; This must be modified when hd1_status will not be valid! - cmp [hdpos], 0x80 - jae .ret - cmp [hdbase], 0x1F0 - jne .IDE_Channel_2 -.IDE_Channel_1: - cli - cmp [IDE_Channel_1], 0 - je .reserve_ok_1 - sti - call change_task - jmp .IDE_Channel_1 -.IDE_Channel_2: - cli - cmp [IDE_Channel_2], 0 - je .reserve_ok_2 - sti - call change_task - jmp .IDE_Channel_2 -.reserve_ok_1: - mov [IDE_Channel_1], 1 - push eax - mov al, 1 - jmp @f -.reserve_ok_2: - mov [IDE_Channel_2], 1 - push eax - mov al, 3 + movzx eax, word [ebx+0xe] ; sectors reserved + mov [ebp+FAT.FAT_START], eax + + movzx eax, byte [ebx+0xd] ; sectors per cluster + mov [ebp+FAT.SECTORS_PER_CLUSTER], eax + + movzx ecx, word [ebx+0xb] ; bytes per sector + mov [ebp+FAT.BYTES_PER_SECTOR], ecx + + movzx eax, word [ebx+0x11] ; count of rootdir entries (=0 fat32) + shl eax, 5 ; mul 32 + dec ecx + add eax, ecx ; round up if not equal count + inc ecx ; bytes per sector + xor edx, edx + div ecx + mov [ebp+FAT.ROOT_SECTORS], eax ; count of rootdir sectors + + movzx eax, word [ebx+0x16] ; sectors per fat <65536 + test eax, eax + jnz @f + mov eax, [ebx+0x24] ; sectors per fat @@: - cmp [hdid], 1 - sbb al, -1 - cmp al, [hd_in_cache] + mov [ebp+FAT.SECTORS_PER_FAT], eax + + movzx eax, byte [ebx+0x10] ; number of fats + mov [ebp+FAT.NUMBER_OF_FATS], eax + imul eax, [ebp+FAT.SECTORS_PER_FAT] + add eax, [ebp+FAT.FAT_START] + mov [ebp+FAT.ROOT_START], eax ; rootdir = fat_start + fat_size * fat_count + add eax, [ebp+FAT.ROOT_SECTORS] ; rootdir sectors should be 0 on fat32 + mov [ebp+FAT.DATA_START], eax ; data area = rootdir + rootdir_size + + movzx eax, word [ebx+0x13] ; total sector count <65536 + test eax, eax + jnz @f + mov eax, [ebx+0x20] ; total sector count +@@: + mov dword [ebp+FAT.p.Length], eax + and dword [ebp+FAT.p.Length+4], 0 + sub eax, [ebp+FAT.DATA_START] ; eax = count of data sectors + xor edx, edx + div [ebp+FAT.SECTORS_PER_CLUSTER] + inc eax + mov [ebp+FAT.LAST_CLUSTER], eax + dec eax ; cluster count + mov [ebp+FAT.fatStartScan], 2 + + ; limits by Microsoft Hardware White Paper v1.03 + cmp eax, 4085 ; 0xff5 + jb .free_return0 ; fat12 not supported + cmp eax, 65525 ; 0xfff5 + jb .fat16 +.fat32: + mov eax, [ebx+0x2c] ; rootdir cluster + mov [ebp+FAT.ROOT_CLUSTER], eax + movzx eax, word [ebx+0x30] + mov [ebp+FAT.ADR_FSINFO], eax + push ebx + add ebx, 512 + call fs_read32_sys + test eax, eax + jnz @f + mov eax, [ebx+0x1ec] + cmp eax, -1 jz @f - mov [hd_in_cache], al - call clear_hd_cache + mov [ebp+FAT.fatStartScan], eax @@: - pop eax - sti -.ret: + pop ebx + mov [ebp+FAT.fatRESERVED], 0x0FFFFFF6 + mov [ebp+FAT.fatBAD], 0x0FFFFFF7 + mov [ebp+FAT.fatEND], 0x0FFFFFF8 + mov [ebp+FAT.fatMASK], 0x0FFFFFFF + mov al, 32 + mov [fs_type], al + mov [ebp+FAT.fs_type], al + mov eax, ebp + pop ebp ret - -free_hd_channel: -; see comment at reserve_hd_channel - cmp [hdpos], 0x80 - jae .ret - cmp [hdbase], 0x1F0 - jne .IDE_Channel_2 -.IDE_Channel_1: - mov [IDE_Channel_1], 0 -.ret: +.fat16: + and [ebp+FAT.ROOT_CLUSTER], 0 + mov [ebp+FAT.fatRESERVED], 0x0000FFF6 + mov [ebp+FAT.fatBAD], 0x0000FFF7 + mov [ebp+FAT.fatEND], 0x0000FFF8 + mov [ebp+FAT.fatMASK], 0x0000FFFF + mov al, 16 + mov [fs_type], al + mov [ebp+FAT.fs_type], al + mov eax, ebp + pop ebp ret -.IDE_Channel_2: - mov [IDE_Channel_2], 0 - ret -;******************************************** -problem_partition db 0 ; used for partitions search - -include 'part_set.inc' set_FAT: ;-------------------------------- ; input : EAX = cluster ; EDX = value to save +; EBP = pointer to FAT structure ; output : EDX = old value ;-------------------------------- +; out: CF set <=> error push eax ebx esi cmp eax, 2 jb sfc_error - cmp eax, [LAST_CLUSTER] + cmp eax, [ebp+FAT.LAST_CLUSTER] ja sfc_error - cmp [fs_type], 16 + cmp [ebp+FAT.fs_type], 16 je sfc_1 add eax, eax sfc_1: @@ -215,27 +305,26 @@ set_FAT: mov esi, 511 and esi, eax ; esi = position in fat sector shr eax, 9 ; eax = fat sector - add eax, [FAT_START] - mov ebx, fat_cache + add eax, [ebp+FAT.FAT_START] + lea ebx, [ebp+FAT.fat_cache] - cmp eax, [fat_in_cache]; is fat sector already in memory? + cmp eax, [ebp+FAT.fat_in_cache]; is fat sector already in memory? je sfc_in_cache ; yes - cmp [fat_change], 0 ; is fat changed? + cmp [ebp+FAT.fat_change], 0; is fat changed? je sfc_no_change ; no call write_fat_sector; yes. write it into disk - cmp [hd_error], 0 - jne sfc_error + jc sfc_error sfc_no_change: - mov [fat_in_cache], eax; save fat sector - call hd_read - cmp [hd_error], 0 + mov [ebp+FAT.fat_in_cache], eax; save fat sector + call fs_read32_sys + test eax, eax jne sfc_error sfc_in_cache: - cmp [fs_type], 16 + cmp [ebp+FAT.fs_type], 16 jne sfc_test32 sfc_set16: @@ -243,7 +332,7 @@ set_FAT: jmp sfc_write sfc_test32: - mov eax, [fatMASK] + mov eax, [ebp+FAT.fatMASK] sfc_set32: and edx, eax @@ -254,24 +343,29 @@ set_FAT: mov [ebx+esi], eax ; save new value sfc_write: - mov [fat_change], 1 ; fat has changed + mov [ebp+FAT.fat_change], 1; fat has changed sfc_nonzero: - and edx, [fatMASK] + and edx, [ebp+FAT.fatMASK] - sfc_error: + sfc_return: pop esi ebx eax ret + sfc_error: + stc + jmp sfc_return get_FAT: ;-------------------------------- ; input : EAX = cluster +; EBP = pointer to FAT structure ; output : EAX = next cluster ;-------------------------------- +; out: CF set <=> error push ebx esi - cmp [fs_type], 16 + cmp [ebp+FAT.fs_type], 16 je gfc_1 add eax, eax gfc_1: @@ -279,30 +373,32 @@ get_FAT: mov esi, 511 and esi, eax ; esi = position in fat sector shr eax, 9 ; eax = fat sector - add eax, [FAT_START] - mov ebx, fat_cache + add eax, [ebp+FAT.FAT_START] + lea ebx, [ebp+FAT.fat_cache] - cmp eax, [fat_in_cache]; is fat sector already in memory? + cmp eax, [ebp+FAT.fat_in_cache]; is fat sector already in memory? je gfc_in_cache - cmp [fat_change], 0 ; is fat changed? + cmp [ebp+FAT.fat_change], 0; is fat changed? je gfc_no_change ; no call write_fat_sector; yes. write it into disk - cmp [hd_error], 0 - jne hd_error_01 + jc hd_error_01 gfc_no_change: - mov [fat_in_cache], eax - call hd_read - cmp [hd_error], 0 + mov [ebp+FAT.fat_in_cache], eax + call fs_read32_sys + test eax, eax jne hd_error_01 gfc_in_cache: mov eax, [ebx+esi] - and eax, [fatMASK] - hd_error_01: + and eax, [ebp+FAT.fatMASK] + gfc_return: pop esi ebx ret + hd_error_01: + stc + jmp gfc_return get_free_FAT: @@ -312,14 +408,14 @@ get_free_FAT: ; Note : for more speed need to use fat_cache directly ;----------------------------------------------------------- push ecx - mov ecx, [LAST_CLUSTER]; counter for full disk + mov ecx, [ebp+FAT.LAST_CLUSTER]; counter for full disk sub ecx, 2 - mov eax, [fatStartScan] + mov eax, [ebp+FAT.fatStartScan] cmp eax, 2 jb gff_reset gff_test: - cmp eax, [LAST_CLUSTER]; if above last cluster start at cluster 2 + cmp eax, [ebp+FAT.LAST_CLUSTER]; if above last cluster start at cluster 2 jbe gff_in_range gff_reset: mov eax, 2 @@ -327,8 +423,7 @@ get_free_FAT: gff_in_range: push eax call get_FAT ; get cluster state - cmp [hd_error], 0 - jne gff_not_found_1 + jc gff_not_found_1 test eax, eax ; is it free? pop eax @@ -337,16 +432,18 @@ get_free_FAT: dec ecx ; is all checked? jns gff_test ; no - gff_not_found_1: - add esp, 4 gff_not_found: pop ecx ; yes. disk is full stc ret + gff_not_found_1: + pop eax + jmp gff_not_found + gff_found: lea ecx, [eax+1] - mov [fatStartScan], ecx + mov [ebp+FAT.fatStartScan], ecx pop ecx clc ret @@ -358,19 +455,21 @@ write_fat_sector: ;----------------------------------------------------------- push eax ebx ecx - mov [fat_change], 0 - mov eax, [fat_in_cache] + mov [ebp+FAT.fat_change], 0 + mov eax, [ebp+FAT.fat_in_cache] cmp eax, -1 jz write_fat_not_used - mov ebx, fat_cache - mov ecx, [NUMBER_OF_FATS] + lea ebx, [ebp+FAT.fat_cache] + mov ecx, [ebp+FAT.NUMBER_OF_FATS] write_next_fat: - call hd_write - cmp [hd_error], 0 - jne write_fat_not_used + push eax + call fs_write32_sys + test eax, eax + pop eax + jnz write_fat_not_used - add eax, [SECTORS_PER_FAT] + add eax, [ebp+FAT.SECTORS_PER_FAT] dec ecx jnz write_next_fat @@ -379,209 +478,7 @@ write_fat_sector: ret -analyze_directory: -;----------------------------------------------------------- -; input : EAX = first cluster of the directory -; EBX = pointer to filename -; output : IF CARRY=0 EAX = sector where th file is found -; EBX = pointer in buffer -; [buffer .. buffer+511] -; ECX,EDX,ESI,EDI not changed -; IF CARRY=1 filename not found -; Note : if cluster=0 it's changed to read rootdir -; save 2 previous directory sectors in longname_sec -;----------------------------------------------------------- - push ecx edx esi edi ebx; ebx = [esp+0] - mov [longname_sec1], 0 - mov [longname_sec2], 0 - adr_new_cluster: - mov [cluster_tmp], eax - mov [fat16_root], 0 - cmp eax, [LAST_CLUSTER] - ja adr_not_found ; too big cluster number, something is wrong - cmp eax, 2 - jnb adr_data_cluster - - mov eax, [ROOT_CLUSTER]; if cluster < 2 then read rootdir - cmp [fs_type], 16 - jne adr_data_cluster - mov eax, [ROOT_START] - mov edx, [ROOT_SECTORS] - mov [fat16_root], 1 ; flag for fat16 rootdir - jmp adr_new_sector - - adr_data_cluster: - sub eax, 2 - mov edx, [SECTORS_PER_CLUSTER] - imul eax, edx - add eax, [DATA_START] - - adr_new_sector: - mov ebx, buffer - call hd_read - cmp [hd_error], 0 - jne adr_not_found - - mov ecx, 512/32 ; count of dir entrys per sector = 16 - - adr_analyze: - mov edi, [ebx+11] ; file attribute - and edi, 0xf - cmp edi, 0xf - je adr_long_filename - test edi, 0x8 ; skip over volume label - jne adr_long_filename; Note: label can be same name as file/dir - - mov esi, [esp+0] ; filename need to be uppercase - mov edi, ebx - push ecx - mov ecx, 11 - cld - rep cmpsb ; compare 8+3 filename - pop ecx - je adr_found - - adr_long_filename: - add ebx, 32 ; position of next dir entry - dec ecx - jnz adr_analyze - - mov ecx, [longname_sec1]; save 2 previous directory sectors - mov [longname_sec1], eax; for delete long filename - mov [longname_sec2], ecx - inc eax ; next sector - dec edx - jne adr_new_sector - cmp [fat16_root], 1 ; end of fat16 rootdir - je adr_not_found - - adr_next_cluster: - mov eax, [cluster_tmp] - call get_FAT ; get next cluster - cmp [hd_error], 0 - jne adr_not_found - - cmp eax, 2 ; incorrect fat chain? - jb adr_not_found ; yes - cmp eax, [fatRESERVED]; is it end of directory? - jb adr_new_cluster ; no. analyse it - - adr_not_found: - pop edi edi esi edx ecx; first edi will remove ebx - stc ; file not found - ret - - adr_found: - pop edi edi esi edx ecx; first edi will remove ebx - clc ; file found - ret - - -get_data_cluster: -;----------------------------------------------------------- -; input : EAX = cluster -; EBX = pointer to buffer -; EDX = # blocks to read in buffer -; ESI = # blocks to skip over -; output : if CARRY=0 ok EBX/EDX/ESI updated -; if CARRY=1 cluster out of range -; Note : if cluster=0 it's changed to read rootdir -;----------------------------------------------------------- - push eax ecx - - mov [fat16_root], 0 - cmp eax, [LAST_CLUSTER] - ja gdc_error ; too big cluster number, something is wrong - cmp eax, 2 - jnb gdc_cluster - - mov eax, [ROOT_CLUSTER]; if cluster < 2 then read rootdir - cmp [fs_type], 16 - jne gdc_cluster - mov eax, [ROOT_START] - mov ecx, [ROOT_SECTORS]; Note: not cluster size - mov [fat16_root], 1 ; flag for fat16 rootdir - jmp gdc_read - - gdc_cluster: - sub eax, 2 - mov ecx, [SECTORS_PER_CLUSTER] - imul eax, ecx - add eax, [DATA_START] - - gdc_read: - test esi, esi ; first wanted block - je gdcl1 ; yes, skip count is 0 - dec esi - jmp gdcl2 - - gdcl1: - call hd_read - cmp [hd_error], 0 - jne gdc_error - - add ebx, 512 ; update pointer - dec edx - - gdcl2: - test edx, edx ; is all read? - je out_of_read - - inc eax ; next sector - dec ecx - jnz gdc_read - - out_of_read: - pop ecx eax - clc - ret - - gdc_error: - pop ecx eax - stc - ret - - -get_cluster_of_a_path: -;--------------------------------------------------------- -; input : EBX = pointer to a path string -; (example: the path "/files/data/document" become -; "files......data.......document...0" -; '.' = space char -; '0' = char(0) (ASCII=0) !!! ) -; output : if (CARRY=1) -> ERROR in the PATH -; if (CARRY=0) -> EAX=cluster -;--------------------------------------------------------- - push ebx edx - - mov eax, [ROOT_CLUSTER] - mov edx, ebx - -search_end_of_path: - cmp byte [edx], 0 - je found_end_of_path - - inc edx; '/' - mov ebx, edx - call analyze_directory - jc directory_not_found - - mov eax, [ebx+20-2] ; read the HIGH 16bit cluster field - mov ax, [ebx+26] ; read the LOW 16bit cluster field - and eax, [fatMASK] - add edx, 11 ; 8+3 (name+extension) - jmp search_end_of_path - -found_end_of_path: - pop edx ebx - clc ; no errors - ret - -directory_not_found: - pop edx ebx - stc ; errors occour - ret bcd2bin: @@ -676,25 +573,25 @@ add_disk_free_space: ;----------------------------------------------------- test ecx, ecx ; no change je add_dfs_no - cmp [fs_type], 32 ; free disk space only used by fat32 + cmp [ebp+FAT.fs_type], 32 ; free disk space only used by fat32 jne add_dfs_no push eax ebx - mov eax, [ADR_FSINFO] - mov ebx, fsinfo_buffer - call hd_read - cmp [hd_error], 0 - jne add_not_fs + mov eax, [ebp+FAT.ADR_FSINFO] + lea ebx, [ebp+FAT.fsinfo_buffer] + call fs_read32_sys + test eax, eax + jnz add_not_fs cmp dword [ebx+0x1fc], 0xaa550000; check sector id jne add_not_fs add [ebx+0x1e8], ecx - push [fatStartScan] + push [ebp+FAT.fatStartScan] pop dword [ebx+0x1ec] - call hd_write -; cmp [hd_error],0 -; jne add_not_fs + mov eax, [ebp+FAT.ADR_FSINFO] + call fs_write32_sys +; jc add_not_fs add_not_fs: pop ebx eax @@ -703,174 +600,6 @@ add_disk_free_space: ret -file_read: -;-------------------------------------------------------------------------- -; INPUT : user-register register-in-this meaning symbol-in-this -; -; EAX EDI system call to write / -; EBX EAX (PAR0) pointer to file-name PAR0 -; EDX ECX (PAR1) pointer to buffer PAR1 -; ECX EBX (PAR2) vt file blocks to read PAR2 -; ESI EDX (PAR3) pointer to path PAR3 -; EDI ESI vt first 512 block to read -; EDI if 0 - read root -; -; output : eax = 0 - ok -; 3 - unknown FS -; 5 - file not found -; 6 - end of file -; 9 - fat table corrupted -; 10 - access denied -; ebx = size of file/directory -;-------------------------------------------------------------------------- - cmp [fs_type], 16 - jz fat_ok_for_reading - cmp [fs_type], 32 - jz fat_ok_for_reading - xor ebx, ebx - mov eax, ERROR_UNKNOWN_FS - mov [hd1_status], ebx - ret - - fat_ok_for_reading: -; call reserve_hd1 - - pushad - - mov ebx, edx - call get_cluster_of_a_path - jc file_to_read_not_found - - test edi, edi ; read rootdir - jne no_read_root - - xor eax, eax - call get_dir_size ; return rootdir size - cmp [hd_error], 0 - jne file_access_denied - - mov [file_size], eax - mov eax, [ROOT_CLUSTER] - jmp file_read_start - - no_read_root: - mov ebx, PUSHAD_EAX ; file name - call analyze_directory - jc file_to_read_not_found - - mov eax, [ebx+28] ; file size - test byte [ebx+11], 0x10; is it directory? - jz read_set_size ; no - - mov eax, [ebx+20-2] ; FAT entry - mov ax, [ebx+26] - and eax, [fatMASK] - call get_dir_size - cmp [hd_error], 0 - jne file_access_denied - - read_set_size: - mov [file_size], eax - - mov eax, [ebx+20-2] ; FAT entry - mov ax, [ebx+26] - and eax, [fatMASK] - - file_read_start: - mov ebx, PUSHAD_ECX ; pointer to buffer - mov edx, PUSHAD_EBX ; file blocks to read - mov esi, PUSHAD_ESI ; first 512 block to read - - file_read_new_cluster: - call get_data_cluster - jc file_read_eof ; end of file or cluster out of range - - test edx, edx ; is all read? - je file_read_OK ; yes - - call get_FAT ; get next cluster - cmp [hd_error], 0 - jne file_access_denied - - cmp eax, [fatRESERVED]; end of file - jnb file_read_eof - cmp eax, 2 ; incorrect fat chain - jnb file_read_new_cluster - - popad - mov [hd1_status], 0 - mov ebx, [file_size] - mov eax, ERROR_FAT_TABLE - ret - - file_read_eof: - cmp [hd_error], 0 - jne file_access_denied - popad - mov [hd1_status], 0 - mov ebx, [file_size] - mov eax, ERROR_END_OF_FILE - ret - - file_read_OK: - popad - mov [hd1_status], 0 - mov ebx, [file_size] - xor eax, eax - ret - - file_to_read_not_found: - cmp [hd_error], 0 - jne file_access_denied - popad - mov [hd1_status], 0 - xor ebx, ebx - mov eax, ERROR_FILE_NOT_FOUND - ret - - file_access_denied: - popad - mov [hd1_status], 0 - xor ebx, ebx - mov eax, ERROR_ACCESS_DENIED - ret - -get_dir_size: -;----------------------------------------------------- -; input : eax = first cluster (0=rootdir) -; output : eax = directory size in bytes -;----------------------------------------------------- - push edx - xor edx, edx ; count of directory clusters - test eax, eax - jnz dir_size_next - - mov eax, [ROOT_SECTORS] - shl eax, 9 ; fat16 rootdir size in bytes - cmp [fs_type], 16 - je dir_size_ret - mov eax, [ROOT_CLUSTER] - - dir_size_next: - cmp eax, 2 ; incorrect fat chain - jb dir_size_end - cmp eax, [fatRESERVED]; end of directory - ja dir_size_end - call get_FAT ; get next cluster - cmp [hd_error], 0 - jne dir_size_ret - - inc edx - jmp dir_size_next - - dir_size_end: - imul eax, [SECTORS_PER_CLUSTER], 512; cluster size in bytes - imul eax, edx - - dir_size_ret: - pop edx - ret - clear_cluster_chain: ;----------------------------------------------------- @@ -880,17 +609,16 @@ clear_cluster_chain: xor ecx, ecx ; cluster count clean_new_chain: - cmp eax, [LAST_CLUSTER]; end of file + cmp eax, [ebp+FAT.LAST_CLUSTER]; end of file ja delete_OK cmp eax, 2 ; unfinished fat chain or zero length file jb delete_OK - cmp eax, [ROOT_CLUSTER]; don't remove root cluster + cmp eax, [ebp+FAT.ROOT_CLUSTER]; don't remove root cluster jz delete_OK xor edx, edx call set_FAT ; clear fat entry - cmp [hd_error], 0 - jne access_denied_01 + jc access_denied_01 inc ecx ; update cluster count mov eax, edx ; old cluster @@ -898,11 +626,13 @@ clear_cluster_chain: delete_OK: call add_disk_free_space; add clusters to free disk space + clc access_denied_01: pop edx ecx eax ret +if 0 get_hd_info: ;----------------------------------------------------------- ; output : eax = 0 - ok @@ -912,9 +642,9 @@ get_hd_info: ; ebx = total clusters on disk ; ecx = free clusters on disk ;----------------------------------------------------------- - cmp [fs_type], 16 + cmp [ebp+FAT.fs_type], 16 jz info_fat_ok - cmp [fs_type], 32 + cmp [ebp+FAT.fs_type], 32 jz info_fat_ok xor edx, edx xor ebx, ebx @@ -927,13 +657,12 @@ get_hd_info: xor ecx, ecx ; count of free clusters mov eax, 2 - mov ebx, [LAST_CLUSTER] + mov ebx, [ebp+FAT.LAST_CLUSTER] info_cluster: push eax call get_FAT ; get cluster info - cmp [hd_error], 0 - jne info_access_denied + jc info_access_denied test eax, eax ; is it free? jnz info_used ; no @@ -946,8 +675,7 @@ get_hd_info: jbe info_cluster ; no. test next cluster dec ebx ; cluster count - imul edx, [SECTORS_PER_CLUSTER], 512; cluster size in bytes - mov [hd1_status], 0 + imul edx, [ebp+FAT.SECTORS_PER_CLUSTER], 512; cluster size in bytes xor eax, eax ret @@ -958,29 +686,39 @@ get_hd_info: xor ecx, ecx mov eax, ERROR_ACCESS_DENIED ret +end if update_disk: ;----------------------------------------------------------- ; write changed fat and cache to disk ;----------------------------------------------------------- - cmp [fat_change], 0 ; is fat changed? + cmp [ebp+FAT.fat_change], 0 ; is fat changed? je upd_no_change call write_fat_sector - cmp [hd_error], 0 - jne update_disk_acces_denied + jc update_disk_acces_denied upd_no_change: - call write_cache + push esi + mov esi, [ebp+PARTITION.Disk] + call disk_sync + pop esi update_disk_acces_denied: ret +fat_lock: + lea ecx, [ebp+FAT.Lock] + jmp mutex_lock +fat_unlock: + lea ecx, [ebp+FAT.Lock] + jmp mutex_unlock ; \begin{diamond} hd_find_lfn: -; in: esi+ebp -> name -; out: CF=1 - file not found +; in: ebp -> FAT structure +; in: esi+[esp+4] -> name +; out: CF=1 - file not found, eax=error code ; else CF=0 and edi->direntry, eax=sector ; destroys eax push esi edi @@ -988,8 +726,8 @@ hd_find_lfn: push 0 push fat16_root_first push fat16_root_next - mov eax, [ROOT_CLUSTER] - cmp [fs_type], 32 + mov eax, [ebp+FAT.ROOT_CLUSTER] + cmp [ebp+FAT.fs_type], 32 jz .fat32 .loop: call fat_find_lfn @@ -1011,12 +749,13 @@ hd_find_lfn: add esp, 16 pop edi esi stc - ret + ret 4 .found: - test ebp, ebp + lea eax, [esp+4+24] + cmp dword [eax], 0 jz @f - mov esi, ebp - xor ebp, ebp + mov esi, [eax] + and dword [eax], 0 jmp .continue @@: lea eax, [esp+8] @@ -1026,16 +765,18 @@ hd_find_lfn: jmp .cmn .root: mov eax, [eax+4] - add eax, [ROOT_START] + add eax, [ebp+FAT.ROOT_START] .cmn: add esp, 20 ; CF=0 pop esi - ret + ret 4 ;---------------------------------------------------------------- ; ; fs_HdRead - LFN variant for reading hard disk ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ebx pointer to 64-bit number = first wanted byte, 0+ ; may be ebx=0 - start from first byte @@ -1059,42 +800,59 @@ fs_HdRead: mov eax, ERROR_UNKNOWN_FS ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_Read + pop ebp + ret + +;---------------------------------------------------------------- +; fat_Read - FAT16/32 implementation of reading a file +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_Read: + call fat_lock push edi cmp byte [esi], 0 jnz @f .noaccess: pop edi .noaccess_2: + call fat_unlock or ebx, -1 mov eax, ERROR_ACCESS_DENIED ret @@: - call hd_find_lfn + stdcall hd_find_lfn, [esp+4+4] jnc .found pop edi - cmp [hd_error], 0 - jne .noaccess_2 + push eax + call fat_unlock + pop eax or ebx, -1 - mov eax, ERROR_FILE_NOT_FOUND ret .found: test byte [edi+11], 0x10; do not allow read directories jnz .noaccess - test ebx, ebx - jz .l1 - cmp dword [ebx+4], 0 + cmp dword [ebx+8], 0 jz @f xor ebx, ebx .reteof: - mov eax, 6 + call fat_unlock + mov eax, ERROR_END_OF_FILE pop edi ret @@: - mov ebx, [ebx] -.l1: - push ecx edx + mov ecx, [ebx+12] ; size + mov edx, [ebx+16] ; pointer + mov ebx, [ebx+4] ; file offset + push edx push 0 mov eax, [edi+28] sub eax, ebx @@ -1109,16 +867,16 @@ fs_HdRead: ; now eax=cluster, ebx=position, ecx=count, edx=buffer for data .new_cluster: jecxz .new_sector - test eax, eax - jz .eof - cmp eax, [fatRESERVED] + cmp eax, 2 + jb .eof + cmp eax, [ebp+FAT.fatRESERVED] jae .eof - mov [cluster_tmp], eax + mov [ebp+FAT.cluster_tmp], eax dec eax dec eax - mov edi, [SECTORS_PER_CLUSTER] + mov edi, [ebp+FAT.SECTORS_PER_CLUSTER] imul eax, edi - add eax, [DATA_START] + add eax, [ebp+FAT.DATA_START] .new_sector: test ecx, ecx jz .done @@ -1129,11 +887,11 @@ fs_HdRead: cmp ecx, 512 jb .force_buf ; we may read directly to given buffer - push ebx + push eax ebx mov ebx, edx - call hd_read - pop ebx - cmp [hd_error], 0 + call fs_read32_app + test eax, eax + pop ebx eax jne .noaccess_1 add edx, 512 sub ecx, 512 @@ -1141,11 +899,11 @@ fs_HdRead: .force_buf: ; we must read sector to temporary buffer and then copy it to destination push eax ebx - mov ebx, buffer - call hd_read + lea ebx, [ebp+FAT.buffer] + call fs_read32_app + test eax, eax mov eax, ebx pop ebx - cmp [hd_error], 0 jne .noaccess_3 add eax, ebx push ecx @@ -1166,25 +924,25 @@ fs_HdRead: inc eax dec edi jnz .new_sector - mov eax, [cluster_tmp] + mov eax, [ebp+FAT.cluster_tmp] call get_FAT - cmp [hd_error], 0 - jne .noaccess_1 + jc .noaccess_1 jmp .new_cluster .noaccess_3: pop eax .noaccess_1: pop eax - push 11 + push ERROR_DEVICE .done: mov ebx, edx - pop eax edx ecx edi + call fat_unlock + pop eax edx edi sub ebx, edx ret .eof: mov ebx, edx - pop eax edx ecx + pop eax edx sub ebx, edx jmp .reteof @@ -1192,6 +950,8 @@ fs_HdRead: ; ; fs_HdReadFolder - LFN variant for reading hard disk folder ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ebx pointer to structure 32-bit number = first wanted block, 0+ ; & flags (bitfields) @@ -1204,33 +964,52 @@ fs_HdRead: ; ;-------------------------------------------------------------- fs_HdReadFolder: - cmp [fs_type], 1 - jz ntfs_HdReadFolder - cmp [fs_type], 2 - jz ext2_HdReadFolder cmp [fs_type], 16 jz @f cmp [fs_type], 32 jz @f + cmp [fs_type], 1 + jz ntfs_HdReadFolder + cmp [fs_type], 2 + jz ext2_HdReadFolder push ERROR_UNSUPPORTED_FS pop eax or ebx, -1 ret @@: - mov eax, [ROOT_CLUSTER] + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_ReadFolder + pop ebp + ret + +;---------------------------------------------------------------- +; fat_ReadFolder - FAT16/32 implementation of reading a folder +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_ReadFolder: + call fat_lock + mov eax, [ebp+FAT.ROOT_CLUSTER] push edi cmp byte [esi], 0 jz .doit - call hd_find_lfn + stdcall hd_find_lfn, [esp+4+4] jnc .found pop edi + push eax + call fat_unlock + pop eax or ebx, -1 - mov eax, ERROR_FILE_NOT_FOUND ret .found: test byte [edi+11], 0x10 ; do not allow read files jnz .found_dir pop edi + call fat_unlock or ebx, -1 mov eax, ERROR_ACCESS_DENIED ret @@ -1238,48 +1017,53 @@ fs_HdReadFolder: mov eax, [edi+20-2] mov ax, [edi+26] ; eax=cluster .doit: - push esi ecx - push ebp + push esi sub esp, 262*2 ; reserve space for LFN - mov ebp, esp - push dword [ebx+4] ; for fat_get_name: read ANSI/UNICODE name - mov ebx, [ebx] + push dword [ebx+8] ; for fat_get_name: read ANSI/UNICODE name + mov edx, [ebx+16] ; pointer to buffer ; init header - push eax ecx + push eax mov edi, edx mov ecx, 32/4 xor eax, eax rep stosd - pop ecx eax + pop eax mov byte [edx], 1 ; version mov esi, edi ; esi points to BDFE + mov ecx, [ebx+12] ; number of blocks to read + mov ebx, [ebx+4] ; index of the first block .new_cluster: - mov [cluster_tmp], eax + mov [ebp+FAT.cluster_tmp], eax test eax, eax jnz @f - cmp [fs_type], 32 + cmp [ebp+FAT.fs_type], 32 jz .notfound - mov eax, [ROOT_START] - push [ROOT_SECTORS] + mov eax, [ebp+FAT.ROOT_START] + push [ebp+FAT.ROOT_SECTORS] push ebx jmp .new_sector @@: dec eax dec eax - imul eax, [SECTORS_PER_CLUSTER] - push [SECTORS_PER_CLUSTER] - add eax, [DATA_START] + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + push [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] push ebx .new_sector: - mov ebx, buffer + lea ebx, [ebp+FAT.buffer] mov edi, ebx - call hd_read - cmp [hd_error], 0 + push eax + call fs_read32_sys + test eax, eax + pop eax jnz .notfound2 add ebx, 512 push eax .l1: + push ebp + lea ebp, [esp+20] call fat_get_name + pop ebp jc .l2 cmp byte [edi+11], 0xF jnz .do_bdfe @@ -1290,30 +1074,31 @@ fs_HdReadFolder: inc eax dec dword [esp+4] jnz @f - mov eax, [cluster_tmp] + mov eax, [ebp+FAT.cluster_tmp] test eax, eax jz .done call get_FAT - cmp [hd_error], 0 - jnz .notfound2 + jc .notfound2 cmp eax, 2 jb .done - cmp eax, [fatRESERVED] + cmp eax, [ebp+FAT.fatRESERVED] jae .done push eax - mov eax, [SECTORS_PER_CLUSTER] + mov eax, [ebp+FAT.SECTORS_PER_CLUSTER] mov [esp+8], eax pop eax - mov [cluster_tmp], eax + mov [ebp+FAT.cluster_tmp], eax dec eax dec eax - imul eax, [SECTORS_PER_CLUSTER] - add eax, [DATA_START] + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] @@: - mov ebx, buffer + lea ebx, [ebp+FAT.buffer] mov edi, ebx - call hd_read - cmp [hd_error], 0 + push eax + call fs_read32_sys + test eax, eax + pop eax jnz .notfound2 add ebx, 512 push eax @@ -1324,7 +1109,10 @@ fs_HdReadFolder: dec ecx js .l2 inc dword [edx+4] ; new file block copied + push ebp + lea ebp, [esp+20] call fat_entry_to_bdfe + pop ebp .l2: add edi, 0x20 cmp edi, ebx @@ -1333,18 +1121,17 @@ fs_HdReadFolder: inc eax dec dword [esp+4] jnz .new_sector - mov eax, [cluster_tmp] + mov eax, [ebp+FAT.cluster_tmp] test eax, eax jz .done call get_FAT - cmp [hd_error], 0 - jnz .notfound2 + jc .notfound2 cmp eax, 2 jb .done - cmp eax, [fatRESERVED] + cmp eax, [ebp+FAT.fatRESERVED] jae .done push eax - mov eax, [SECTORS_PER_CLUSTER] + mov eax, [ebp+FAT.SECTORS_PER_CLUSTER] mov [esp+8], eax pop eax pop ebx @@ -1354,54 +1141,67 @@ fs_HdReadFolder: add esp, 8 .notfound: add esp, 262*2+4 - pop ebp ecx esi edi - mov eax, ERROR_FILE_NOT_FOUND - or ebx, -1 + pop esi edi + mov ebx, [edx+4] + call fat_unlock + mov eax, ERROR_DEVICE ret .done: add esp, 262*2+4+8 - pop ebp mov ebx, [edx+4] xor eax, eax dec ecx js @f mov al, ERROR_END_OF_FILE @@: - pop ecx esi edi + push eax + call fat_unlock + pop eax + pop esi edi ret fat16_root_next: - cmp edi, buffer+0x200-0x20 + push ecx + lea ecx, [ebp+FAT.buffer+0x200-0x20] + cmp edi, ecx jae fat16_root_next_sector + pop ecx add edi, 0x20 ret ; CF=0 fat16_root_next_sector: ; read next sector - push [longname_sec2] - pop [longname_sec1] - push ecx + push [ebp+FAT.longname_sec2] + pop [ebp+FAT.longname_sec1] mov ecx, [eax+4] push ecx - add ecx, [ROOT_START] - mov [longname_sec2], ecx + add ecx, [ebp+FAT.ROOT_START] + mov [ebp+FAT.longname_sec2], ecx pop ecx inc ecx mov [eax+4], ecx - cmp ecx, [ROOT_SECTORS] + cmp ecx, [ebp+FAT.ROOT_SECTORS] pop ecx - jae fat16_root_first.readerr + jb fat16_root_first + mov eax, ERROR_FILE_NOT_FOUND + stc + ret fat16_root_first: mov eax, [eax+4] - add eax, [ROOT_START] + add eax, [ebp+FAT.ROOT_START] push ebx - mov edi, buffer + lea edi, [ebp+FAT.buffer] mov ebx, edi - call hd_read + call fs_read32_sys pop ebx - cmp [hd_error], 0 + test eax, eax jnz .readerr ret ; CF=0 .readerr: + mov eax, ERROR_DEVICE + stc + ret +.notfound: + mov eax, ERROR_FILE_NOT_FOUND stc ret fat16_root_begin_write: @@ -1412,14 +1212,17 @@ fat16_root_begin_write: fat16_root_end_write: pusha mov eax, [eax+4] - add eax, [ROOT_START] - mov ebx, buffer - call hd_write + add eax, [ebp+FAT.ROOT_START] + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys popa ret fat16_root_next_write: - cmp edi, buffer+0x200 + push ecx + lea ecx, [ebp+FAT.buffer+0x200] + cmp edi, ecx jae @f + pop ecx ret @@: call fat16_root_end_write @@ -1429,21 +1232,23 @@ fat16_root_extend_dir: ret fat_notroot_next: - cmp edi, buffer+0x200-0x20 + push ecx + lea ecx, [ebp+FAT.buffer+0x200-0x20] + cmp edi, ecx jae fat_notroot_next_sector + pop ecx add edi, 0x20 ret ; CF=0 fat_notroot_next_sector: - push [longname_sec2] - pop [longname_sec1] + push [ebp+FAT.longname_sec2] + pop [ebp+FAT.longname_sec1] push eax call fat_get_sector - mov [longname_sec2], eax + mov [ebp+FAT.longname_sec2], eax pop eax - push ecx mov ecx, [eax+4] inc ecx - cmp ecx, [SECTORS_PER_CLUSTER] + cmp ecx, [ebp+FAT.SECTORS_PER_CLUSTER] jae fat_notroot_next_cluster mov [eax+4], ecx jmp @f @@ -1453,9 +1258,10 @@ fat_notroot_next_cluster: call get_FAT mov ecx, eax pop eax - cmp [hd_error], 0 - jnz fat_notroot_next_err - cmp ecx, [fatRESERVED] + jc fat_notroot_first.deverr + cmp ecx, 2 + jb fat_notroot_next_err + cmp ecx, [ebp+FAT.fatRESERVED] jae fat_notroot_next_err mov [eax], ecx and dword [eax+4], 0 @@ -1464,16 +1270,22 @@ fat_notroot_next_cluster: fat_notroot_first: call fat_get_sector push ebx - mov edi, buffer + lea edi, [ebp+FAT.buffer] mov ebx, edi - call hd_read + call fs_read32_sys pop ebx - cmp [hd_error], 0 - jnz @f - ret ; CF=0 + test eax, eax + jz .ret ; CF=0 + push ecx +.deverr: + pop ecx + mov eax, ERROR_DEVICE + stc +.ret: + ret fat_notroot_next_err: pop ecx -@@: + mov eax, ERROR_FILE_NOT_FOUND stc ret fat_notroot_begin_write: @@ -1484,13 +1296,16 @@ fat_notroot_begin_write: fat_notroot_end_write: call fat_get_sector push ebx - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys pop ebx ret fat_notroot_next_write: - cmp edi, buffer+0x200 + push ecx + lea ecx, [ebp+FAT.buffer+0x200] + cmp edi, ecx jae @f + pop ecx ret @@: push eax @@ -1505,16 +1320,17 @@ fat_notroot_extend_dir: ret ; CF=1 .found: push edx - mov edx, [fatEND] + mov edx, [ebp+FAT.fatEND] call set_FAT + jc .writeerr mov edx, eax mov eax, [esp+4] mov eax, [eax] push edx call set_FAT pop edx - cmp [hd_error], 0 - jz @f + jnc @f +.writeerr: pop edx pop eax stc @@ -1525,7 +1341,7 @@ fat_notroot_extend_dir: call add_disk_free_space ; zero new cluster mov ecx, 512/4 - mov edi, buffer + lea edi, [ebp+FAT.buffer] push edi xor eax, eax rep stosd @@ -1539,12 +1355,14 @@ fat_notroot_extend_dir: dec eax dec eax push ebx ecx - mov ecx, [SECTORS_PER_CLUSTER] + mov ecx, [ebp+FAT.SECTORS_PER_CLUSTER] imul eax, ecx - add eax, [DATA_START] + add eax, [ebp+FAT.DATA_START] mov ebx, edi @@: - call hd_write + push eax + call fs_write32_sys + pop eax inc eax loop @b pop ecx ebx eax @@ -1556,8 +1374,8 @@ fat_get_sector: mov ecx, [eax] dec ecx dec ecx - imul ecx, [SECTORS_PER_CLUSTER] - add ecx, [DATA_START] + imul ecx, [ebp+FAT.SECTORS_PER_CLUSTER] + add ecx, [ebp+FAT.DATA_START] add ecx, [eax+4] mov eax, ecx pop ecx @@ -1567,6 +1385,8 @@ fat_get_sector: ; ; fs_HdRewrite - LFN variant for writing hard disk ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ebx ignored (reserved) ; ecx number of bytes to write, 0+ @@ -1576,15 +1396,6 @@ fat_get_sector: ; eax = 0 ok read or other = errormsg ; ;-------------------------------------------------------------- -fshrad: - mov eax, ERROR_ACCESS_DENIED - xor ebx, ebx - ret -fshrfs: - mov eax, ERROR_UNKNOWN_FS - xor ebx, ebx - ret - fs_HdCreateFolder: mov al, 1 jmp fs_HdRewrite.common @@ -1592,23 +1403,70 @@ fs_HdCreateFolder: fs_HdRewrite: xor eax, eax .common: + cmp [fs_type], 16 + jz @f + cmp [fs_type], 32 + jz @f cmp [fs_type], 1 jz ntfs_HdRewrite cmp [fs_type], 2 jz ext2_HdRewrite - cmp [fs_type], 16 - jz @f - cmp [fs_type], 32 - jnz fshrfs + mov eax, ERROR_UNKNOWN_FS + xor ebx, ebx + ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + test eax, eax + mov eax, fat_CreateFolder + jnz @f + mov eax, fat_Rewrite +@@: + call eax + pop ebp + ret + +fshrad: + call fat_unlock + mov eax, ERROR_ACCESS_DENIED + xor ebx, ebx + ret + +;---------------------------------------------------------------- +; fat_CreateFolder - FAT16/32 implementation of creating a folder +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_CreateFolder: + push 1 + jmp fat_Rewrite.common + +;---------------------------------------------------------------- +; fat_HdRewrite - FAT16/32 implementation of creating a new file +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_Rewrite: + push 0 +.common: + call fat_lock + pop eax cmp byte [esi], 0 jz fshrad + mov ecx, [ebx+12] + mov edx, [ebx+16] pushad xor edi, edi + mov edx, [esp+4+20h] push esi - test ebp, ebp + test edx, edx jz @f - mov esi, ebp + mov esi, edx @@: lodsb test al, al @@ -1621,30 +1479,29 @@ fs_HdRewrite: pop esi test edi, edi jnz .noroot - test ebp, ebp + test edx, edx jnz .hasebp - mov ebp, [ROOT_CLUSTER] - cmp [fs_type], 32 + mov edx, [ebp+FAT.ROOT_CLUSTER] + cmp [ebp+FAT.fs_type], 32 jz .pushnotroot + xor edx, edx + push edx push fat16_root_extend_dir push fat16_root_end_write push fat16_root_next_write push fat16_root_begin_write - xor ebp, ebp - push ebp - push ebp + push edx + push edx push fat16_root_first push fat16_root_next jmp .common1 .hasebp: mov eax, ERROR_ACCESS_DENIED - cmp byte [ebp], 0 + cmp byte [edx], 0 jz .ret1 - push ebp - xor ebp, ebp - call hd_find_lfn - pop esi - jc .notfound0 + stdcall hd_find_lfn, 0 + mov esi, [esp+4+20h] + jc .ret1 jmp .common0 .noroot: mov eax, ERROR_ACCESS_DENIED @@ -1653,7 +1510,7 @@ fs_HdRewrite: ; check existence mov byte [edi], 0 push edi - call hd_find_lfn + stdcall hd_find_lfn, [esp+4+24h] pop esi mov byte [esi], '/' jnc @f @@ -1661,6 +1518,7 @@ fs_HdRewrite: mov eax, ERROR_FILE_NOT_FOUND .ret1: mov [esp+28], eax + call fat_unlock popad xor ebx, ebx ret @@ -1670,18 +1528,19 @@ fs_HdRewrite: test byte [edi+11], 0x10 ; must be directory mov eax, ERROR_ACCESS_DENIED jz .ret1 - mov ebp, [edi+20-2] - mov bp, [edi+26] ; ebp=cluster + mov edx, [edi+20-2] + mov dx, [edi+26] ; ebp=cluster mov eax, ERROR_FAT_TABLE - cmp ebp, 2 + cmp edx, 2 jb .ret1 .pushnotroot: + push edx push fat_notroot_extend_dir push fat_notroot_end_write push fat_notroot_next_write push fat_notroot_begin_write push 0 - push ebp + push edx push fat_notroot_first push fat_notroot_next .common1: @@ -1692,7 +1551,8 @@ fs_HdRewrite: jz .exists_file ; found directory; if we are creating directory, return OK, ; if we are creating file, say "access denied" - add esp, 32 + add esp, 36 + call fat_unlock popad test al, al mov eax, ERROR_ACCESS_DENIED @@ -1704,9 +1564,10 @@ fs_HdRewrite: .exists_file: ; found file; if we are creating directory, return "access denied", ; if we are creating file, delete existing file and continue - cmp byte [esp+32+28], 0 + cmp byte [esp+36+28], 0 jz @f - add esp, 32 + add esp, 36 + call fat_unlock popad mov eax, ERROR_ACCESS_DENIED xor ebx, ebx @@ -1724,13 +1585,14 @@ fs_HdRewrite: test eax, eax jz .done1 @@: - cmp eax, [fatRESERVED] + cmp eax, [ebp+FAT.fatRESERVED] jae .done1 push edx xor edx, edx call set_FAT mov eax, edx pop edx + jc .done1 inc ecx jmp @b .done1: @@ -1746,7 +1608,8 @@ fs_HdRewrite: ; file is not found; generate short name call fat_name_is_legal jc @f - add esp, 32 + add esp, 36 + call fat_unlock popad mov eax, ERROR_FILE_NOT_FOUND xor ebx, ebx @@ -1759,7 +1622,8 @@ fs_HdRewrite: push esi edi ecx mov esi, edi lea eax, [esp+12+12+8] - mov [eax], ebp + mov edx, [eax+24] + mov [eax], edx and dword [eax+4], 0 call dword [eax-4] jc .found @@ -1781,7 +1645,8 @@ fs_HdRewrite: call fat_next_short_name jnc .test_short_name_loop .disk_full: - add esp, 12+32 + add esp, 12+36 + call fat_unlock popa mov eax, ERROR_DISK_FULL xor ebx, ebx @@ -1821,15 +1686,17 @@ fs_HdRewrite: xor ecx, ecx push eax lea eax, [esp+16+8+12+8] - mov [eax], ebp + mov edx, [eax+24] + mov [eax], edx and dword [eax+4], 0 call dword [eax-4] pop eax jnc .scan_dir .fsfrfe3: - add esp, 12+8+12+32 + add esp, 12+8+12+36 + call fat_unlock popad - mov eax, 11 + mov eax, ERROR_DEVICE xor ebx, ebx ret .scan_dir: @@ -1842,16 +1709,18 @@ fs_HdRewrite: push eax lea eax, [esp+16+8+12+8] call dword [eax-8] + mov edx, eax pop eax jnc .scan_dir - cmp [hd_error], 0 - jnz .fsfrfe3 + cmp edx, ERROR_DEVICE + jz .fsfrfe3 push eax lea eax, [esp+16+8+12+8] call dword [eax+20] ; extend directory pop eax jnc .scan_dir - add esp, 12+8+12+32 + add esp, 12+8+12+36 + call fat_unlock popad mov eax, ERROR_DISK_FULL xor ebx, ebx @@ -1870,8 +1739,23 @@ fs_HdRewrite: cmp ecx, eax jb .scan_cont ; found! -; calculate name checksum push esi ecx +; If creating a directory, allocate one data cluster now and fail immediately +; if this is impossible. This prevents from creating an invalid directory entry +; on a full disk. +; yup, the argument is quite non-intuitive... but what should I do if +; the entire function uses such arguments? BTW, it refers to al from pushad, +; which in turn is filled with 0 in fat_Rewrite and 1 in fat_CreateFolder. + cmp byte [esp+8+12+8+12+36+28], 0 + jz .no.preallocate.folder.data + call get_free_FAT + jnc @f + add esp, 8+12+8 + jmp .disk_full +@@: + mov [esp+8+12+8+12+36+20], eax ; store the cluster somewhere +.no.preallocate.folder.data: +; calculate name checksum mov esi, [esp+8+12] mov ecx, 11 xor eax, eax @@ -1941,30 +1825,34 @@ fs_HdRewrite: mov word [edi+20], cx ; high word of cluster mov word [edi+26], cx ; low word of cluster - to be filled mov dword [edi+28], ecx ; file size - to be filled - cmp byte [esp+32+28], cl + cmp byte [esp+36+28], cl jz .doit ; create directory mov byte [edi+11], 10h ; attributes: folder - mov edx, edi + mov esi, edi lea eax, [esp+8] call dword [eax+16] ; flush directory + mov eax, [esp+36+20] ; extract saved cluster + mov [esp+36+20], edi ; this is needed for calculating arg of add_disk_free_space! push ecx - mov ecx, [SECTORS_PER_CLUSTER] + mov ecx, [ebp+FAT.SECTORS_PER_CLUSTER] shl ecx, 9 - jmp .doit2 -.doit: - lea eax, [esp+8] - call dword [eax+16] ; flush directory - push ecx - mov ecx, [esp+4+32+24] -.doit2: push ecx push edi - mov esi, edx + jmp .doit2 +.doit: + mov esi, [esp+36+20] + lea eax, [esp+8] + call dword [eax+16] ; flush directory + push ecx + mov ecx, [esp+4+36+24] + push ecx + push edi test ecx, ecx jz .done call get_free_FAT jc .diskfull +.doit2: push eax mov [edi+26], ax shr eax, 16 @@ -1973,35 +1861,35 @@ fs_HdRewrite: call dword [eax+16] ; flush directory pop eax push edx - mov edx, [fatEND] + mov edx, [ebp+FAT.fatEND] call set_FAT pop edx .write_cluster: push eax dec eax dec eax - mov ebp, [SECTORS_PER_CLUSTER] - imul eax, ebp - add eax, [DATA_START] + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] + push [ebp+FAT.SECTORS_PER_CLUSTER] ; write data .write_sector: - cmp byte [esp+16+32+28], 0 + cmp byte [esp+20+36+28], 0 jnz .writedir mov ecx, 512 - cmp dword [esp+8], ecx + cmp dword [esp+12], ecx jb .writeshort ; we can write directly from given buffer mov ebx, esi add esi, ecx jmp .writecommon .writeshort: - mov ecx, [esp+8] + mov ecx, [esp+12] push ecx - mov edi, buffer + lea edi, [ebp+FAT.buffer] mov ebx, edi rep movsb .writedircont: - mov ecx, buffer+0x200 + lea ecx, [ebp+FAT.buffer+0x200] sub ecx, edi push eax xor eax, eax @@ -2009,21 +1897,24 @@ fs_HdRewrite: pop eax pop ecx .writecommon: - call hd_write - cmp [hd_error], 0 + push eax + call fs_write32_app + test eax, eax + pop eax jnz .writeerr inc eax - sub dword [esp+8], ecx + sub dword [esp+12], ecx jz .writedone - dec ebp + dec dword [esp] jnz .write_sector + pop eax ; allocate new cluster pop eax mov ecx, eax call get_free_FAT jc .diskfull push edx - mov edx, [fatEND] + mov edx, [ebp+FAT.fatEND] call set_FAT xchg eax, ecx mov edx, ecx @@ -2035,47 +1926,47 @@ fs_HdRewrite: mov eax, ERROR_DISK_FULL jmp .ret .writeerr: - pop eax + pop eax eax sub esi, ecx - mov eax, 11 + mov eax, ERROR_DEVICE jmp .ret .writedone: - pop eax + pop eax eax .done: xor eax, eax .ret: pop edi ecx - mov ebx, esi - sub ebx, edx - pop ebp - mov [esp+32+28], eax - lea eax, [esp+8] + sub esi, [esp+4+36+20] + mov [esp+4+36+28], eax + mov [esp+4+36+16], esi + lea eax, [esp+12] call dword [eax+8] - mov [edi+28], ebx + mov [edi+28], esi call dword [eax+16] - mov [esp+32+16], ebx - lea eax, [ebx+511] + mov [esp+36+16], ebx + lea eax, [esi+511] shr eax, 9 - mov ecx, [SECTORS_PER_CLUSTER] + mov ecx, [ebp+FAT.SECTORS_PER_CLUSTER] lea eax, [eax+ecx-1] xor edx, edx div ecx - mov ecx, ebp + pop ecx sub ecx, eax call add_disk_free_space - add esp, 32 + add esp, 36 call update_disk + call fat_unlock popad ret .writedir: push 512 - mov edi, buffer + lea edi, [ebp+FAT.buffer] mov ebx, edi - mov ecx, [SECTORS_PER_CLUSTER] + mov ecx, [ebp+FAT.SECTORS_PER_CLUSTER] shl ecx, 9 - cmp ecx, [esp+12] + cmp ecx, [esp+16] jnz .writedircont - dec dword [esp+16] + dec dword [esp+20] push esi mov ecx, 32/4 rep movsd @@ -2092,8 +1983,8 @@ fs_HdRewrite: mov dword [edi-32+4], ' ' mov dword [edi-32+8], ' ' mov byte [edi-32+11], 10h - mov ecx, [esp+20+8] - cmp ecx, [ROOT_CLUSTER] + mov ecx, [esp+20+36] + cmp ecx, [ebp+FAT.ROOT_CLUSTER] jnz @f xor ecx, ecx @@: @@ -2106,6 +1997,8 @@ fs_HdRewrite: ; ; fs_HdWrite - LFN variant for writing to hard disk ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ebx pointer to 64-bit number = first wanted byte, 0+ ; may be ebx=0 - start from first byte @@ -2116,7 +2009,7 @@ fs_HdRewrite: ; eax = 0 ok write or other = errormsg ; ;-------------------------------------------------------------- -fs_HdWrite.access_denied: +fat_Write.access_denied: push ERROR_ACCESS_DENIED fs_HdWrite.ret0: pop eax @@ -2124,57 +2017,66 @@ fs_HdWrite.ret0: ret fs_HdWrite.ret11: - push 11 + push ERROR_DEVICE jmp fs_HdWrite.ret0 fs_HdWrite: - cmp [fs_type], 1 - jz ntfs_HdWrite - cmp [fs_type], 2 - jz ext2_HdWrite cmp [fs_type], 16 jz @f cmp [fs_type], 32 jz @f + cmp [fs_type], 1 + jz ntfs_HdWrite + cmp [fs_type], 2 + jz ext2_HdWrite push ERROR_UNKNOWN_FS jmp .ret0 @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_Write + pop ebp + ret + +;---------------------------------------------------------------- +; fat_Write - FAT16/32 implementation of writing to file +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_Write: cmp byte [esi], 0 jz .access_denied - pushad - call hd_find_lfn - pushfd - cmp [hd_error], 0 - jz @f - popfd - popad - push 11 - jmp .ret0 -@@: - popfd + call fat_lock + push edi + stdcall hd_find_lfn, [esp+4+4] jnc .found - popad - push ERROR_FILE_NOT_FOUND - jmp .ret0 + pop edi + push eax + call fat_unlock + jmp fs_HdWrite.ret0 .found: ; FAT does not support files larger than 4GB - test ebx, ebx - jz .l1 - cmp dword [ebx+4], 0 + cmp dword [ebx+8], 0 jz @f .eof: - popad + pop edi push ERROR_END_OF_FILE - jmp .ret0 + call fat_unlock + jmp fs_HdWrite.ret0 @@: - mov ebx, [ebx] -.l1: + mov ecx, [ebx+12] + mov edx, [ebx+16] + mov ebx, [ebx+4] ; now edi points to direntry, ebx=start byte to write, ; ecx=number of bytes to write, edx=data pointer ; extend file if needed add ecx, ebx jc .eof ; FAT does not support files larger than 4GB + push edx push eax ; save directory sector push 0 ; return value=0 @@ -2196,11 +2098,12 @@ fs_HdWrite: ; First two cases are fatal errors, in third case we may write some data cmp al, ERROR_DISK_FULL jz .disk_full + call fat_unlock pop eax pop eax - mov [esp+4+28], eax - pop eax - popad + pop ecx + pop edx + pop edi xor ebx, ebx ret .disk_full: @@ -2208,36 +2111,42 @@ fs_HdWrite: mov ecx, [edi+28] cmp ecx, ebx ja .length_ok + push 0 .ret: + pop eax + sub edx, [esp+12] + mov ebx, edx ; ebx=number of written bytes call update_disk - cmp [hd_error], 0 + test eax, eax jz @f - mov byte [esp+4], 11 + mov byte [esp+4], ERROR_DEVICE @@: + call fat_unlock pop eax pop eax - mov [esp+4+28], eax ; eax=return value - pop eax - sub edx, [esp+20] - mov [esp+16], edx ; ebx=number of written bytes - popad + pop ecx + pop edx + pop edi ret .length_ok: mov esi, [edi+28] mov eax, [edi+20-2] mov ax, [edi+26] mov edi, eax ; edi=current cluster - xor ebp, ebp ; ebp=current sector in cluster + push 0 ; current sector in cluster ; save directory - mov eax, [esp+8] + mov eax, [esp+12] push ebx - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys pop ebx - cmp [hd_error], 0 + test eax, eax jz @f .device_err: - mov byte [esp+4], 11 + mov byte [esp+8], ERROR_DEVICE + jmp .ret +.fat_err: + mov byte [esp+8], ERROR_FAT_TABLE jmp .ret @@: @@ -2246,7 +2155,7 @@ fs_HdWrite: jz .ret .write_loop: ; skip unmodified sectors - cmp dword [esp], 0x200 + cmp dword [esp+4], 0x200 jb .modify sub ebx, 0x200 jae .skip @@ -2269,21 +2178,21 @@ fs_HdWrite: mov eax, edi dec eax dec eax - imul eax, [SECTORS_PER_CLUSTER] - add eax, [DATA_START] - add eax, ebp + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] + add eax, [esp+4] ; load sector if needed - cmp dword [esp+4], 0 ; we don't need to read uninitialized data + cmp dword [esp+8], 0 ; we don't need to read uninitialized data jz .noread cmp ecx, 0x200 ; we don't need to read sector if it is fully rewritten jz .noread cmp ecx, esi ; (same for the last sector) jz .noread - push ebx - mov ebx, buffer - call hd_read - pop ebx - cmp [hd_error], 0 + push eax ebx + lea ebx, [ebp+FAT.buffer] + call fs_read32_app + test eax, eax + pop ebx eax jz @f .device_err2: pop ecx @@ -2294,18 +2203,17 @@ fs_HdWrite: push eax ecx edi xor eax, eax mov ecx, 0x200 - sub ecx, [esp+4+12] + sub ecx, [esp+8+12] jbe @f - mov edi, buffer - add edi, [esp+4+12] + lea edi, [ebp+FAT.buffer] + add edi, [esp+8+12] rep stosb @@: ; zero uninitialized data in the last sector mov ecx, 0x200 sub ecx, esi jbe @f - mov edi, buffer - add edi, esi + lea edi, [ebp+FAT.buffer+esi] rep stosb @@: pop edi ecx @@ -2313,17 +2221,17 @@ fs_HdWrite: mov eax, edx neg ebx jecxz @f - add ebx, buffer+0x200 + lea ebx, [ebp+FAT.buffer+0x200+ebx] call memmove xor ebx, ebx @@: pop eax ; save sector push ebx - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_app pop ebx - cmp [hd_error], 0 + test eax, eax jnz .device_err2 add edx, ecx sub [esp], ecx @@ -2331,23 +2239,28 @@ fs_HdWrite: jz .ret .skip: ; next sector - inc ebp - cmp ebp, [SECTORS_PER_CLUSTER] + pop eax + inc eax + push eax + cmp eax, [ebp+FAT.SECTORS_PER_CLUSTER] jb @f - xor ebp, ebp + and dword [esp], 0 mov eax, edi call get_FAT mov edi, eax - cmp [hd_error], 0 - jnz .device_err + jc .device_err + cmp edi, 2 + jb .fat_err + cmp edi, [ebp+FAT.fatRESERVED] + jae .fat_err @@: sub esi, 0x200 jae @f xor esi, esi @@: - sub dword [esp], 0x200 + sub dword [esp+4], 0x200 jae @f - and dword [esp], 0 + and dword [esp+4], 0 @@: jmp .write_loop @@ -2358,11 +2271,11 @@ hd_extend_file.zero_size: ; extends file on hd to given size (new data area is undefined) ; in: edi->direntry, ecx=new size ; out: CF=0 => OK, eax=0 -; CF=1 => error, eax=code (ERROR_FAT_TABLE or ERROR_DISK_FULL or 11) +; CF=1 => error, eax=code (ERROR_FAT_TABLE or ERROR_DISK_FULL or ERROR_DEVICE) hd_extend_file: - push ebp - mov ebp, [SECTORS_PER_CLUSTER] - imul ebp, [BYTES_PER_SECTOR] + push esi + mov esi, [ebp+FAT.SECTORS_PER_CLUSTER] + imul esi, [ebp+FAT.BYTES_PER_SECTOR] push ecx ; find the last cluster of file mov eax, [edi+20-2] @@ -2370,16 +2283,15 @@ hd_extend_file: mov ecx, [edi+28] jecxz .zero_size .last_loop: - sub ecx, ebp + sub ecx, esi jbe .last_found call get_FAT - cmp [hd_error], 0 - jz @f + jnc @f .device_err: pop ecx .device_err2: - pop ebp - push 11 + pop esi + push ERROR_DEVICE .ret_err: pop eax stc @@ -2387,21 +2299,20 @@ hd_extend_file: @@: cmp eax, 2 jb .fat_err - cmp eax, [fatRESERVED] + cmp eax, [ebp+FAT.fatRESERVED] jb .last_loop .fat_err: - pop ecx ebp + pop ecx esi push ERROR_FAT_TABLE jmp .ret_err .last_found: push eax call get_FAT - cmp [hd_error], 0 - jz @f + jnc @f pop eax jmp .device_err @@: - cmp eax, [fatRESERVED] + cmp eax, [ebp+FAT.fatRESERVED] pop eax jb .fat_err ; set length to full number of clusters @@ -2418,7 +2329,7 @@ hd_extend_file: push eax call get_free_FAT jc .disk_full - mov edx, [fatEND] + mov edx, [ebp+FAT.fatEND] call set_FAT mov edx, eax pop eax @@ -2439,26 +2350,20 @@ hd_extend_file: call add_disk_free_space pop ecx mov eax, edx - cmp [hd_error], 0 - jnz .device_err3 - add [edi+28], ebp + add [edi+28], esi jmp .extend_loop .extend_done: mov [edi+28], ecx - pop edx ebp + pop edx esi xor eax, eax ; CF=0 ret .device_err3: pop edx jmp .device_err2 .disk_full: - pop eax edx ebp + pop eax edx esi push ERROR_DISK_FULL pop eax - cmp [hd_error], 0 - jz @f - mov al, 11 -@@: stc ret @@ -2466,6 +2371,8 @@ hd_extend_file: ; ; fs_HdSetFileEnd - set end of file on hard disk ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ebx points to 64-bit number = new file size ; ecx ignored (reserved) @@ -2475,70 +2382,78 @@ hd_extend_file: ; ;-------------------------------------------------------------- fs_HdSetFileEnd: - cmp [fs_type], 1 - jz ntfs_HdSetFileEnd - cmp [fs_type], 2 - jz ext2_HdSetFileEnd cmp [fs_type], 16 jz @f cmp [fs_type], 32 jz @f + cmp [fs_type], 1 + jz ntfs_HdSetFileEnd + cmp [fs_type], 2 + jz ext2_HdSetFileEnd push ERROR_UNKNOWN_FS -.ret: pop eax ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_SetFileEnd + pop ebp + ret + +;---------------------------------------------------------------- +; fat_SetFileEnd - FAT16/32 implementation of setting end-of-file +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_SetFileEnd: + call fat_lock + push edi cmp byte [esi], 0 jnz @f .access_denied: push ERROR_ACCESS_DENIED - jmp .ret -@@: - push edi - call hd_find_lfn - pushfd - cmp [hd_error], 0 - jz @f - popfd - push 11 - jmp .ret -@@: - popfd - jnc @f +.ret: + call fat_unlock + pop eax pop edi - push ERROR_FILE_NOT_FOUND + ret +@@: + stdcall hd_find_lfn, [esp+4+4] + jnc @f +.reteax: + push eax jmp .ret @@: ; must not be directory test byte [edi+11], 10h - jz @f - pop edi - jmp .access_denied -@@: + jnz .access_denied ; file size must not exceed 4 Gb - cmp dword [ebx+4], 0 + cmp dword [ebx+8], 0 jz @f - pop edi push ERROR_END_OF_FILE jmp .ret @@: push eax ; save directory sector ; set file modification date/time to current call fat_update_datetime - mov eax, [ebx] + mov eax, [ebx+4] cmp eax, [edi+28] jb .truncate ja .expand pop eax - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys pop edi - xor eax, eax - cmp [hd_error], 0 + test eax, eax jz @f - mov al, 11 + push ERROR_DEVICE + jmp .ret @@: - ret + push 0 + jmp .ret .expand: push ebx ebp ecx push dword [edi+28] ; save old size @@ -2550,71 +2465,81 @@ fs_HdSetFileEnd: jz .disk_full .pop_ret: call update_disk - pop eax ecx ebp ebx ecx edi edi - ret + pop eax ecx ecx ebp ebx ecx + jmp .reteax .expand_ok: .disk_full: ; save directory mov eax, [edi+28] xchg eax, [esp+20] - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys + test eax, eax mov eax, [edi+20-2] mov ax, [edi+26] mov edi, eax - cmp [hd_error], 0 jz @f .pop_ret11: - mov byte [esp], 11 + mov byte [esp], ERROR_DEVICE jmp .pop_ret @@: + test edi, edi + jz .pop_ret ; now zero new data - xor ebp, ebp -; edi=current cluster, ebp=sector in cluster -; [esp+20]=new size, [esp+4]=old size, [esp]=return code + push 0 +; edi=current cluster, [esp]=sector in cluster +; [esp+24]=new size, [esp+8]=old size, [esp+4]=return code .zero_loop: - sub dword [esp+4], 0x200 + cmp edi, 2 + jb .error_fat + cmp edi, [ebp+FAT.fatRESERVED] + jae .error_fat + sub dword [esp+8], 0x200 jae .next_cluster lea eax, [edi-2] - imul eax, [SECTORS_PER_CLUSTER] - add eax, [DATA_START] - add eax, ebp - cmp dword [esp+4], -0x200 + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] + add eax, [esp] + cmp dword [esp+8], -0x200 jz .noread - mov ebx, buffer - call hd_read - cmp [hd_error], 0 + push eax + lea ebx, [ebp+FAT.buffer] + call fs_read32_app + test eax, eax + pop eax jnz .err_next .noread: - mov ecx, [esp+4] + mov ecx, [esp+8] neg ecx push edi - mov edi, buffer+0x200 - add edi, [esp+8] + lea edi, [ebp+FAT.buffer+0x200] + add edi, [esp+12] push eax xor eax, eax - mov [esp+12], eax + mov [esp+16], eax rep stosb pop eax pop edi - call hd_write - cmp [hd_error], 0 + call fs_write32_app + test eax, eax jz .next_cluster .err_next: - mov byte [esp], 11 + mov byte [esp+4], ERROR_DEVICE .next_cluster: + pop eax sub dword [esp+20], 0x200 jbe .pop_ret - inc ebp - cmp ebp, [SECTORS_PER_CLUSTER] + inc eax + push eax + cmp eax, [ebp+FAT.SECTORS_PER_CLUSTER] jb .zero_loop - xor ebp, ebp + and dword [esp], 0 mov eax, edi call get_FAT mov edi, eax - cmp [hd_error], 0 - jnz .pop_ret11 - jmp .zero_loop + jnc .zero_loop + pop eax + jmp .pop_ret11 .truncate: mov [edi+28], eax push ecx @@ -2625,18 +2550,23 @@ fs_HdSetFileEnd: jz .zero_size ; find new last cluster @@: - mov eax, [SECTORS_PER_CLUSTER] + cmp ecx, 2 + jb .error_fat2 + cmp ecx, [ebp+FAT.fatRESERVED] + jae .error_fat2 + mov eax, [ebp+FAT.SECTORS_PER_CLUSTER] shl eax, 9 sub [esp], eax jbe @f mov eax, ecx call get_FAT mov ecx, eax - cmp [hd_error], 0 - jz @b + jnc @b .device_err3: pop eax ecx eax edi - push 11 + call update_disk + call fat_unlock + push ERROR_DEVICE pop eax ret @@: @@ -2645,12 +2575,11 @@ fs_HdSetFileEnd: ; terminate FAT chain push edx mov eax, ecx - mov edx, [fatEND] + mov edx, [ebp+FAT.fatEND] call set_FAT mov eax, edx pop edx - cmp [hd_error], 0 - jz @f + jnc @f .device_err4: pop ecx jmp .device_err3 @@ -2662,22 +2591,21 @@ fs_HdSetFileEnd: @@: ; delete FAT chain call clear_cluster_chain - cmp [hd_error], 0 - jnz .device_err4 + jc .device_err4 ; save directory mov eax, [esp+12] push ebx - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys pop ebx - cmp [hd_error], 0 + test eax, eax jnz .device_err4 ; zero last sector, ignore errors pop ecx pop eax dec ecx - imul ecx, [SECTORS_PER_CLUSTER] - add ecx, [DATA_START] + imul ecx, [ebp+FAT.SECTORS_PER_CLUSTER] + add ecx, [ebp+FAT.DATA_START] push eax sar eax, 9 add ecx, eax @@ -2686,135 +2614,198 @@ fs_HdSetFileEnd: jz .truncate_done push ebx eax mov eax, ecx - mov ebx, buffer - call hd_read + lea ebx, [ebp+FAT.buffer] + call fs_read32_app pop eax - lea edi, [buffer+eax] + lea edi, [ebp+FAT.buffer+eax] push ecx mov ecx, 0x200 sub ecx, eax xor eax, eax rep stosb pop eax - call hd_write + call fs_write32_app pop ebx .truncate_done: pop ecx eax edi call update_disk + call fat_unlock xor eax, eax - cmp [hd_error], 0 - jz @f - mov al, 11 -@@: + ret +.error_fat: + pop eax + mov byte [esp], ERROR_FAT_TABLE + jmp .pop_ret +.error_fat2: + pop eax ecx eax edi + call update_disk + call fat_unlock + push ERROR_FAT_TABLE + pop eax ret fs_HdGetFileInfo: + cmp [fs_type], 16 + jz @f + cmp [fs_type], 32 + jz @f cmp [fs_type], 1 jz ntfs_HdGetFileInfo cmp [fs_type], 2 jz ext2_HdGetFileInfo - cmp [fs_type], 16 - jz @f - cmp [fs_type], 32 - jz @f mov eax, ERROR_UNKNOWN_FS ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_GetFileInfo + pop ebp + ret + +;---------------------------------------------------------------- +; fat_GetFileInfo - FAT16/32 implementation of getting file info +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_GetFileInfo: cmp byte [esi], 0 jnz @f mov eax, 2 ret @@: push edi - call hd_find_lfn - pushfd - cmp [hd_error], 0 - jz @f - popfd + call fat_lock + stdcall hd_find_lfn, [esp+4+4] + jc .error + push ebp + xor ebp, ebp + mov esi, [ebx+16] + mov dword [esi+4], ebp + call fat_entry_to_bdfe2 + pop ebp + call fat_unlock + xor eax, eax + pop edi + ret +.error: + push eax + call fat_unlock + pop eax pop edi - mov eax, 11 ret -@@: - popfd - jmp fs_GetFileInfo_finish fs_HdSetFileInfo: + cmp [fs_type], 16 + jz @f + cmp [fs_type], 32 + jz @f cmp [fs_type], 1 jz ntfs_HdSetFileInfo cmp [fs_type], 2 jz ext2_HdSetFileInfo - cmp [fs_type], 16 - jz @f - cmp [fs_type], 32 - jz @f mov eax, ERROR_UNKNOWN_FS ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_SetFileInfo + pop ebp + ret + +;---------------------------------------------------------------- +; fat_SetFileInfo - FAT16/32 implementation of setting file info +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_SetFileInfo: cmp byte [esi], 0 jnz @f mov eax, 2 ret @@: push edi - call hd_find_lfn - pushfd - cmp [hd_error], 0 - jz @f - popfd - pop edi - mov eax, 11 - ret -@@: - popfd - jnc @f - pop edi - mov eax, ERROR_FILE_NOT_FOUND - ret -@@: + call fat_lock + stdcall hd_find_lfn, [esp+4+4] + jc .error push eax + mov edx, [ebx+16] call bdfe_to_fat_entry pop eax - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys call update_disk + call fat_unlock pop edi xor eax, eax ret +.error: + push eax + call fat_unlock + pop eax + pop edi + ret ;---------------------------------------------------------------- ; ; fs_HdDelete - delete file or empty folder from hard disk ; +; Obsolete, will be replaced with filesystem-specific functions. +; ; esi points to filename ; ; ret eax = 0 ok or other = errormsg ; ;-------------------------------------------------------------- fs_HdDelete: - cmp [fs_type], 1 - jz ntfs_HdDelete - cmp [fs_type], 2 - jz ext2_HdDelete cmp [fs_type], 16 jz @f cmp [fs_type], 32 jz @f + cmp [fs_type], 1 + jz ntfs_HdDelete + cmp [fs_type], 2 + jz ext2_HdDelete push ERROR_UNKNOWN_FS -.pop_ret: pop eax ret @@: + sub ebx, 4 + push ebp + mov ebp, [fs_dependent_data_start.partition] + call fat_Delete + pop ebp + ret + +;---------------------------------------------------------------- +; fat_Delete - FAT16/32 implementation of deleting a file/folder +; in: ebp = pointer to FAT structure +; in: esi+[esp+4] = name +; in: ebx = pointer to parameters from sysfunc 70 +; out: eax, ebx = return values for sysfunc 70 +;---------------------------------------------------------------- +fat_Delete: + call fat_lock cmp byte [esi], 0 jnz @f ; cannot delete root! .access_denied: push ERROR_ACCESS_DENIED - jmp .pop_ret +.pop_ret: + call fat_unlock + pop eax + xor ebx, ebx + ret @@: - and [longname_sec1], 0 - and [longname_sec2], 0 + and [ebp+FAT.longname_sec1], 0 + and [ebp+FAT.longname_sec2], 0 push edi - call hd_find_lfn + stdcall hd_find_lfn, [esp+4+4] jnc .found pop edi push ERROR_FILE_NOT_FOUND @@ -2828,16 +2819,17 @@ fs_HdDelete: jz .dodel ; we can delete only empty folders! pushad - mov ebp, [edi+20-2] - mov bp, [edi+26] + mov esi, [edi+20-2] + mov si, [edi+26] xor ecx, ecx - lea eax, [ebp-2] - imul eax, [SECTORS_PER_CLUSTER] - add eax, [DATA_START] - mov ebx, buffer - call hd_read - cmp [hd_error], 0 + lea eax, [esi-2] + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] + lea ebx, [ebp+FAT.buffer] + call fs_read32_sys + test eax, eax jnz .err1 + lea eax, [ebx+0x200] add ebx, 2*0x20 .checkempty: cmp byte [ebx], 0 @@ -2845,47 +2837,49 @@ fs_HdDelete: cmp byte [ebx], 0xE5 jnz .notempty add ebx, 0x20 - cmp ebx, buffer+0x200 + cmp ebx, eax jb .checkempty inc ecx - cmp ecx, [SECTORS_PER_CLUSTER] + cmp ecx, [ebp+FAT.SECTORS_PER_CLUSTER] jb @f - mov eax, ebp + mov eax, esi call get_FAT - cmp [hd_error], 0 - jnz .err1 - mov ebp, eax + jc .err1 + mov esi, eax xor ecx, ecx @@: - lea eax, [ebp-2] - imul eax, [SECTORS_PER_CLUSTER] - add eax, [DATA_START] + lea eax, [esi-2] + imul eax, [ebp+FAT.SECTORS_PER_CLUSTER] + add eax, [ebp+FAT.DATA_START] add eax, ecx - mov ebx, buffer - call hd_read - cmp [hd_error], 0 + lea ebx, [ebp+FAT.buffer] + call fs_read32_sys + test eax, eax + lea eax, [ebx+0x200] jz .checkempty .err1: popad .err2: pop edi - push 11 + call fat_unlock + push ERROR_DEVICE pop eax ret .notempty: popad .access_denied2: pop edi + call fat_unlock push ERROR_ACCESS_DENIED pop eax ret .empty: popad - push ebx - mov ebx, buffer - call hd_read - pop ebx - cmp [hd_error], 0 + push eax ebx + lea ebx, [ebp+FAT.buffer] + call fs_read32_sys + test eax, eax + pop ebx eax jnz .err2 .dodel: push eax @@ -2896,22 +2890,23 @@ fs_HdDelete: mov byte [edi], 0xE5 ; delete LFN (if present) .lfndel: - cmp edi, buffer + lea edx, [ebp+FAT.buffer] + cmp edi, edx ja @f - cmp [longname_sec2], 0 + cmp [ebp+FAT.longname_sec2], 0 jz .lfndone - push [longname_sec2] - push [longname_sec1] - pop [longname_sec2] - and [longname_sec1], 0 + push [ebp+FAT.longname_sec2] + push [ebp+FAT.longname_sec1] + pop [ebp+FAT.longname_sec2] + and [ebp+FAT.longname_sec1], 0 push ebx - mov ebx, buffer - call hd_write + mov ebx, edx + call fs_write32_sys mov eax, [esp+4] - call hd_read + call fs_read32_sys pop ebx pop eax - mov edi, buffer+0x200 + lea edi, [ebp+FAT.buffer+0x200] @@: sub edi, 0x20 cmp byte [edi], 0xE5 @@ -2922,19 +2917,16 @@ fs_HdDelete: jmp .lfndel .lfndone: push ebx - mov ebx, buffer - call hd_write + lea ebx, [ebp+FAT.buffer] + call fs_write32_sys pop ebx ; delete FAT chain pop eax call clear_cluster_chain call update_disk + call fat_unlock pop edi xor eax, eax - cmp [hd_error], 0 - jz @f - mov al, 11 -@@: ret ; \end{diamond} diff --git a/kernel/branches/Kolibri-acpi/fs/fs.inc b/kernel/branches/Kolibri-acpi/fs/fs.inc index d045a73e5f..b5325b6084 100644 --- a/kernel/branches/Kolibri-acpi/fs/fs.inc +++ b/kernel/branches/Kolibri-acpi/fs/fs.inc @@ -169,10 +169,6 @@ endg fs_info: ;start of code - Mihasik push eax - cmp [eax+21], byte 'h' - je fs_info_h - cmp [eax+21], byte 'H' - je fs_info_h cmp [eax+21], byte 'r' je fs_info_r cmp [eax+21], byte 'R' @@ -189,9 +185,6 @@ endg mov ebx, 2847 ;total clusters mov edx, 512 ;cluster size xor eax, eax ;always 0 - jmp fs_info1 - fs_info_h: ;if harddisk - call get_hd_info fs_info1: pop edi mov [esp+36], eax @@ -437,32 +430,6 @@ hd_err_return: jmp file_system_return @@: - cmp dword [esp+20], 0; READ - jne fs_noharddisk_read - - mov eax, [esp+0] ; /fname - lea edi, [eax+12] - mov byte [eax], 0 ; path to asciiz - inc eax ; filename start - - mov ebx, [esp+12] ; count to read - mov ecx, [esp+8] ; buffer - mov edx, [esp+4] - add edx, 12*2 ; dir start - sub edi, edx ; path length - mov esi, [esp+16] ; blocks to read - - call file_read - - mov edi, [esp+0] - mov byte [edi], '/' - - call free_hd_channel - and [hd1_status], 0 - jmp file_system_return - - fs_noharddisk_read: - call free_hd_channel and [hd1_status], 0 diff --git a/kernel/branches/Kolibri-acpi/fs/fs_lfn.inc b/kernel/branches/Kolibri-acpi/fs/fs_lfn.inc index a234f0206d..a03e062b52 100644 --- a/kernel/branches/Kolibri-acpi/fs/fs_lfn.inc +++ b/kernel/branches/Kolibri-acpi/fs/fs_lfn.inc @@ -7,6 +7,19 @@ $Revision$ +ERROR_SUCCESS = 0 +ERROR_DISK_BASE = 1 +ERROR_UNSUPPORTED_FS = 2 +ERROR_UNKNOWN_FS = 3 +ERROR_PARTITION = 4 +ERROR_FILE_NOT_FOUND = 5 +ERROR_END_OF_FILE = 6 +ERROR_MEMORY_POINTER = 7 +ERROR_DISK_FULL = 8 +ERROR_FAT_TABLE = 9 ;deprecated +ERROR_FS_FAIL = 9 +ERROR_ACCESS_DENIED = 10 +ERROR_DEVICE = 11 image_of_eax EQU esp+32 image_of_ebx EQU esp+20 diff --git a/kernel/branches/Kolibri-acpi/fs/part_set.inc b/kernel/branches/Kolibri-acpi/fs/part_set.inc index 61ac2ea82b..955ba5beb4 100644 --- a/kernel/branches/Kolibri-acpi/fs/part_set.inc +++ b/kernel/branches/Kolibri-acpi/fs/part_set.inc @@ -33,24 +33,8 @@ align 4 fs_dependent_data_start: ; FATxx data -SECTORS_PER_FAT dd 0x1f3a -NUMBER_OF_FATS dd 0x2 -SECTORS_PER_CLUSTER dd 0x8 -BYTES_PER_SECTOR dd 0x200 ; Note: if BPS <> 512 need lots of changes -ROOT_CLUSTER dd 2 ; first rootdir cluster -FAT_START dd 0 ; start of fat table -ROOT_START dd 0 ; start of rootdir (only fat16) -ROOT_SECTORS dd 0 ; count of rootdir sectors (only fat16) -DATA_START dd 0 ; start of data area (=first cluster 2) -LAST_CLUSTER dd 0 ; last availabe cluster -ADR_FSINFO dd 0 ; used only by fat32 - -fatRESERVED dd 0x0FFFFFF6 -fatBAD dd 0x0FFFFFF7 -fatEND dd 0x0FFFFFF8 -fatMASK dd 0x0FFFFFFF - -fatStartScan dd 2 +.partition dd ? + rb 80 fs_dependent_data_end: file_system_data_size = $ - PARTITION_START @@ -88,7 +72,6 @@ ext2_data: .block_size dd ? .count_block_in_block dd ? .blocks_per_group dd ? - .inodes_per_group dd ? .global_desc_table dd ? .root_inode dd ? ; pointer to root inode in memory .inode_size dd ? @@ -427,108 +410,27 @@ boot_read_ok: cmp [hd_error], 0 jnz problem_fat_dec_count - cmp word [ebx+0x1fe], 0xaa55; is it valid boot sector? - jnz problem_fat_dec_count - - movzx eax, word [ebx+0xe]; sectors reserved - add eax, [PARTITION_START] - mov [FAT_START], eax; fat_start = partition_start + reserved - - movzx eax, byte [ebx+0xd]; sectors per cluster + push 0 + mov eax, [PARTITION_END] + sub eax, [PARTITION_START] + inc eax + push eax + push 0 + push [PARTITION_START] + push ebp + push ebp + mov ebp, esp + mov esi, 'old' ; special value: there is no DISK structure + push 1 ; bootsector read successfully + call fat_create_partition + add esp, 4*7 test eax, eax jz problem_fat_dec_count - mov [SECTORS_PER_CLUSTER], eax - - movzx ecx, word [ebx+0xb]; bytes per sector - cmp ecx, 0x200 - jnz problem_fat_dec_count - mov [BYTES_PER_SECTOR], ecx - - movzx eax, word [ebx+0x11]; count of rootdir entries (=0 fat32) - mov edx, 32 - mul edx - dec ecx - add eax, ecx ; round up if not equal count - inc ecx ; bytes per sector - div ecx - mov [ROOT_SECTORS], eax; count of rootdir sectors - - movzx eax, word [ebx+0x16]; sectors per fat <65536 - test eax, eax - jnz fat16_fatsize - mov eax, [ebx+0x24] ; sectors per fat - fat16_fatsize: - mov [SECTORS_PER_FAT], eax - - movzx eax, byte [ebx+0x10]; number of fats - test eax, eax ; if 0 it's not fat partition - jz problem_fat_dec_count - mov [NUMBER_OF_FATS], eax - imul eax, [SECTORS_PER_FAT] - add eax, [FAT_START] - mov [ROOT_START], eax; rootdir = fat_start + fat_size * fat_count - add eax, [ROOT_SECTORS]; rootdir sectors should be 0 on fat32 - mov [DATA_START], eax; data area = rootdir + rootdir_size - - movzx eax, word [ebx+0x13]; total sector count <65536 - test eax, eax - jnz fat16_total - mov eax, [ebx+0x20] ; total sector count - fat16_total: - add eax, [PARTITION_START] - dec eax - mov [PARTITION_END], eax - inc eax - sub eax, [DATA_START]; eax = count of data sectors - xor edx, edx - div dword [SECTORS_PER_CLUSTER] - inc eax - mov [LAST_CLUSTER], eax - dec eax ; cluster count - mov [fatStartScan], 2 - - ; limits by Microsoft Hardware White Paper v1.03 - cmp eax, 4085 ; 0xff5 - jb problem_fat_dec_count; fat12 not supported - cmp eax, 65525 ; 0xfff5 - jb fat16_partition - -fat32_partition: - mov eax, [ebx+0x2c] ; rootdir cluster - mov [ROOT_CLUSTER], eax - movzx eax, word [ebx+0x30]; fs info sector - add eax, [PARTITION_START] - mov [ADR_FSINFO], eax - call hd_read - mov eax, [ebx+0x1ec] - cmp eax, -1 - jz @f - mov [fatStartScan], eax -@@: + mov [fs_dependent_data_start.partition], eax + mov al, [eax+FAT.fs_type] + mov [fs_type], al popad - - mov [fatRESERVED], 0x0FFFFFF6 - mov [fatBAD], 0x0FFFFFF7 - mov [fatEND], 0x0FFFFFF8 - mov [fatMASK], 0x0FFFFFFF - mov [fs_type], 32 ; Fat32 call free_hd_channel mov [hd1_status], 0 ; free ret - -fat16_partition: - xor eax, eax - mov [ROOT_CLUSTER], eax - - popad - - mov [fatRESERVED], 0x0000FFF6 - mov [fatBAD], 0x0000FFF7 - mov [fatEND], 0x0000FFF8 - mov [fatMASK], 0x0000FFFF - mov [fs_type], 16 ; Fat16 - call free_hd_channel - mov [hd1_status], 0 ; free - ret - diff --git a/kernel/branches/Kolibri-acpi/gui/event.inc b/kernel/branches/Kolibri-acpi/gui/event.inc index 393d47cfe1..97e458d40a 100644 --- a/kernel/branches/Kolibri-acpi/gui/event.inc +++ b/kernel/branches/Kolibri-acpi/gui/event.inc @@ -23,6 +23,7 @@ endg EV_SPACE = 512 FreeEvents = event_start-EVENT.fd ; "тшЁЄєры№э√щ" event, шёяюы№чє■Єё  Єюы№ъю яюы : ; FreeEvents.fd=event_start ш FreeEvents.bk=event_end +;----------------------------------------------------------------------------- align 4 init_events: ;; used from kernel.asm stdcall kernel_alloc, EV_SPACE*sizeof.EVENT @@ -32,7 +33,9 @@ init_events: ;; used from kernel.asm mov ecx, EV_SPACE ; current - in allocated space mov ebx, FreeEvents ; previos - эрўрыю ёяшёър push ebx ; юэю цх ш ъюэхЎ яюЄюь сєфхЄ - @@: +;-------------------------------------- +align 4 +@@: mov [ebx+EVENT.fd], eax mov [eax+EVENT.bk], ebx mov ebx, eax ; previos <- current @@ -41,14 +44,16 @@ init_events: ;; used from kernel.asm pop eax ; тюЄ юэю ъюэЎюь ш ёЄрыю mov [ebx+EVENT.fd], eax mov [eax+EVENT.bk], ebx +;-------------------------------------- +align 4 .fail: ret - +;----------------------------------------------------------------------------- EVENT_WATCHED equ 0x10000000 ;сшЄ 28 EVENT_SIGNALED equ 0x20000000 ;сшЄ 29 MANUAL_RESET equ 0x40000000 ;сшЄ 30 MANUAL_DESTROY equ 0x80000000 ;сшЄ 31 - +;----------------------------------------------------------------------------- align 4 create_event: ;; EXPORT use ;info: @@ -67,7 +72,8 @@ create_event: ;; EXPORT use mov edx, [edx+TASKDATA.pid] pushfd cli - +;-------------------------------------- +align 4 set_event: ;; INTERNAL use !!! don't use for Call ;info: ; ┴хЁхь эют√щ event шч FreeEvents, чряюыэ хь хую яюы , ъръ єърчрэю т ecx,edx,esi @@ -89,7 +95,9 @@ set_event: ;; INTERNAL use !!! don't use call init_events popad jz RemoveEventTo.break ; POPF+RET - @@: +;-------------------------------------- +align 4 +@@: mov eax, [eax+EVENT.fd] mov [eax+EVENT.magic], 'EVNT' mov [eax+EVENT.destroy], destroy_event.internal @@ -103,7 +111,8 @@ set_event: ;; INTERNAL use !!! don't use mov ecx, (sizeof.EVENT -EVENT.code)/4 cld rep movsd - +;-------------------------------------- +align 4 RemoveEventTo: ;; INTERNAL use !!! don't use for Call ;param: ; eax - єърчрЄхы№ эр event, ╩╬╥╬╨█╔ тёЄрты хь @@ -118,10 +127,12 @@ RemoveEventTo: ;; INTERNAL use !!! don't use xchg ecx, [eax+EVENT.fd] ; Self.fd=NewRight, ecx=OldRight mov [ebx+EVENT.fd], ecx ; OldLeft.fd=OldRight mov [ecx+EVENT.bk], ebx ; OldRight.bk=OldLeft +;-------------------------------------- +align 4 .break: popfd ret - +;----------------------------------------------------------------------------- align 4 NotDummyTest: ;; INTERNAL use (not returned for fail !!!) pop edi @@ -129,6 +140,8 @@ NotDummyTest: ;; INTERNAL use (not returned mov ebx, eax mov eax, [ebx+EVENT.pid] push edi +;-------------------------------------- +align 4 .small: ; ъЁштю ъръ-Єю... pop edi pushfd @@ -137,7 +150,7 @@ NotDummyTest: ;; INTERNAL use (not returned shl eax, 8 jz RemoveEventTo.break ; POPF+RET jmp edi ; °ЄрЄэ√щ тючтЁрЄ - +;----------------------------------------------------------------------------- align 4 raise_event: ;; EXPORT use ;info: @@ -158,19 +171,23 @@ raise_event: ;; EXPORT use mov ecx, (sizeof.EVENT -EVENT.code)/4 cld rep movsd - @@: +;-------------------------------------- +align 4 +@@: test byte[ebx+EVENT.state+3], EVENT_SIGNALED shr 24 jnz RemoveEventTo.break ; POPF+RET bt edx, 28 ;EVENT_WATCHED jnc @f test byte[ebx+EVENT.state+3], EVENT_WATCHED shr 24 jz RemoveEventTo.break ; POPF+RET - @@: +;-------------------------------------- +align 4 +@@: or byte[ebx+EVENT.state+3], EVENT_SIGNALED shr 24 add eax, SLOT_BASE+APP_EV_OFFSET xchg eax, ebx jmp RemoveEventTo - +;----------------------------------------------------------------------------- align 4 clear_event: ;; EXPORT use ;info: @@ -184,7 +201,7 @@ clear_event: ;; EXPORT use and byte[ebx+EVENT.state+3], not((EVENT_SIGNALED+EVENT_WATCHED)shr 24) xchg eax, ebx jmp RemoveEventTo - +;----------------------------------------------------------------------------- align 4 send_event: ;; EXPORT use ;info: @@ -207,7 +224,7 @@ send_event: ;; EXPORT use lea ebx, [eax+SLOT_BASE+APP_EV_OFFSET] mov ecx, EVENT_SIGNALED jmp set_event - +;----------------------------------------------------------------------------- align 4 DummyTest: ;; INTERNAL use (not returned for fail !!!) ;param: @@ -217,16 +234,21 @@ DummyTest: ;; INTERNAL use (not returned jne @f cmp [eax+EVENT.id], ebx je .ret - @@: +;-------------------------------------- +align 4 +@@: pop eax xor eax, eax +;-------------------------------------- +align 4 .ret: ret - - +;----------------------------------------------------------------------------- align 4 Wait_events: or ebx, -1; infinite timeout +;-------------------------------------- +align 4 Wait_events_ex: ;info: ; ╬цшфрэшх "рсёЄЁръЄэюую" ёюс√Єш  ўхЁхч яхЁхтюф ёыюЄр т 5-■ яючшЎш■. @@ -260,9 +282,11 @@ Wait_events_ex: mov [eax+TASKDATA.state], 5 call change_task mov eax, [esi+APPDATA.wait_param] - @@: +;-------------------------------------- +align 4 +@@: ret - +;----------------------------------------------------------------------------- align 4 wait_event: ;; EXPORT use ;info: @@ -281,7 +305,7 @@ wait_event: ;; EXPORT use mov edx, get_event_alone ; wait_test call Wait_events ; timeout ignored jmp wait_finish - +;----------------------------------------------------------------------------- align 4 get_event_ex: ;; f68:14 ;info: @@ -303,6 +327,8 @@ get_event_ex: ;; f68:14 cld rep movsd mov byte[edi-(sizeof.EVENT-EVENT.code)+2], cl;clear priority field +;-------------------------------------- +align 4 wait_finish: test byte[eax+EVENT.state+3], MANUAL_RESET shr 24 jnz get_event_queue.ret ; RET @@ -314,7 +340,7 @@ wait_finish: pushfd cli jmp RemoveEventTo - +;----------------------------------------------------------------------------- align 4 destroy_event: ;; EXPORT use ;info: @@ -326,6 +352,8 @@ destroy_event: ;; EXPORT use ; eax - рфЁхё юс·хъЄр EVENT (=0 => fail) ;scratched: ebx,ecx call DummyTest ; not returned for fail !!! +;-------------------------------------- +align 4 .internal: xor ecx, ecx ; clear common header pushfd @@ -336,7 +364,7 @@ destroy_event: ;; EXPORT use mov [eax+EVENT.id], ecx mov ebx, FreeEvents jmp RemoveEventTo - +;----------------------------------------------------------------------------- align 4 get_event_queue: ;info: @@ -353,9 +381,11 @@ get_event_queue: mov eax, [ebx+APPOBJ.bk] ; т√сшЁрхь ё ъюэЎр, яю яЁшэЎшяє FIFO cmp eax, ebx ; empty ??? je get_event_alone.ret0 +;-------------------------------------- +align 4 .ret: ret - +;----------------------------------------------------------------------------- align 4 get_event_alone: ;info: @@ -372,21 +402,27 @@ get_event_alone: test byte[eax+EVENT.state+3], EVENT_SIGNALED shr 24 jnz .ret or byte[eax+EVENT.state+3], EVENT_WATCHED shr 24 +;-------------------------------------- +align 4 .ret0: xor eax, eax; NO event!!! +;-------------------------------------- +align 4 .ret: ret - +;----------------------------------------------------------------------------- align 4 sys_sendwindowmsg: ;; f72 dec ebx jnz .ret ;subfunction==1 ? - ;pushfd ;р эрЇшур? + pushfd cli sub ecx, 2 je .sendkey dec ecx jnz .retf +;-------------------------------------- +align 4 .sendbtn: cmp byte[BTN_COUNT], 1 jae .result ;overflow @@ -394,18 +430,27 @@ sys_sendwindowmsg: ;; f72 shl edx, 8 mov [BTN_BUFF], edx jmp .result +;-------------------------------------- +align 4 .sendkey: movzx eax, byte[KEY_COUNT] cmp al, 120 jae .result ;overflow inc byte[KEY_COUNT] mov [KEY_COUNT+1+eax], dl +;-------------------------------------- +align 4 .result: setae byte[esp+32] ;ёўшЄрхь, ўЄю шёїюфэю: dword[esp+32]==72 -.retf: ;popfd +;-------------------------------------- +align 4 +.retf: + popfd +;-------------------------------------- +align 4 .ret: ret - +;----------------------------------------------------------------------------- align 4 sys_getevent: ;; f11 mov ebx, [current_slot];яюър ¤Єю тюяЁюё, ўхую ъєф√ ёєтрЄ№.......... @@ -415,16 +460,18 @@ sys_getevent: ;; f11 popfd mov [esp+32], eax ret - +;----------------------------------------------------------------------------- align 4 sys_waitforevent: ;; f10 or ebx, -1; infinite timeout +;-------------------------------------- +align 4 sys_wait_event_timeout: ;; f23 mov edx, get_event_for_app; wait_test call Wait_events_ex ; ebx - timeout mov [esp+32], eax ret - +;----------------------------------------------------------------------------- align 4 get_event_for_app: ;; used from f10,f11,f23 ;info: @@ -442,36 +489,52 @@ get_event_for_app: ;; used from f10,f11,f23 add edi, CURRENT_TASK ; edi is assumed as [TASK_BASE] mov ecx, [edi+TASKDATA.event_mask] and ecx, 0x7FFFFFFF +;-------------------------------------- +align 4 .loop: ; яюър эх шёўхЁярхь тёх сшЄ√ ьрёъш bsr eax, ecx ; эрїюфшь эхэєыхтющ сшЄ ьрёъш (31 -> 0) jz .no_events ; шёўхЁярыш тёх сшЄ√ ьрёъш, эю эшўхую эх эр°ыш ??? btr ecx, eax ; ёсЁрё√трхь яЁютхЁ хь√щ сшЄ ьрёъш ; яхЁхїюфшь эр юсЁрсюЄўшъ ¤Єюую (eax) сшЄр cmp eax, 9 - jae .loop ; eax=[9..31], ignored + jae .loop ; eax=[9..31], ignored (event 10...32) + cmp eax, 3 - je .loop ; eax=3, ignored - ja .FlagAutoReset ; eax=[4..8], retvals=eax+1 + je .loop ; eax=3, ignored (event 4) + + cmp eax, 4 + je .FlagAutoReset ; eax=4, retvals=eax+1 (event 5) + + cmp eax, 5 + je .mouse_check ; eax=5, retvals=eax+1 (event 6) + + ja .FlagAutoReset ; eax=[6..8], retvals=eax+1 (event 7...9) + cmp eax, 1 - jae .BtKy ; eax=[1,2], retvals=eax+1 + jae .BtKy ; eax=[1,2], retvals=eax+1 (event 2,3) +;-------------------------------------- +align 4 .WndRedraw: ; eax=0, retval WndRedraw=1 cmp [edi-twdw+WDATA.fl_redraw], al;al==0 jne .result jmp .loop - .no_events: +;-------------------------------------- +align 4 +.no_events: xor eax, eax ret - -.FlagAutoReset: ; retvals: BgrRedraw=5, Mouse=6, IPC=7, Stack=8, Debug=9 - cmp eax, 5; Mouse 5+1=6 - jne .no_mouse_check +;-------------------------------------- +align 4 +.mouse_check: ; Mouse 5+1=6 push eax mov eax, [TASK_BASE] mov eax, [eax + TASKDATA.event_mask] test eax, 0x80000000 ; bit 31: active/inactive filter f.40 jz @f pop eax - jmp .no_mouse_check + jmp .FlagAutoReset +;-------------------------------------- +align 4 @@: ; If the window is captured and moved by the user, then no mouse events!!! mov al, [mouse.active_sys_window.action] @@ -479,16 +542,24 @@ get_event_for_app: ;; used from f10,f11,f23 test al, al pop eax jnz .loop -.no_mouse_check: +;-------------------------------------- +align 4 +.FlagAutoReset: ; retvals: BgrRedraw=5, IPC=7, Stack=8, Debug=9 btr [ebx+APPDATA.event_mask], eax jnc .loop - .result: ; retval = eax+1 +;-------------------------------------- +align 4 +.result: ; retval = eax+1 inc eax ret - .BtKy: +;-------------------------------------- +align 4 +.BtKy: movzx edx, bh movzx edx, word[WIN_STACK+edx*2] je .Keys ; eax=1, retval Keys=2 +;-------------------------------------- +align 4 .Buttons: ; eax=2, retval Buttons=3 cmp byte[BTN_COUNT], 0 je .loop ; empty ??? @@ -501,14 +572,20 @@ get_event_for_app: ;; used from f10,f11,f23 mov [window_minimize], 1 dec byte[BTN_COUNT] jmp .loop +;-------------------------------------- +align 4 .Keys: ; eax==1 cmp edx, [TASK_COUNT] jne @f ; not Top ??? cmp [KEY_COUNT], al; al==1 jae .result ; not empty ??? - @@: +;-------------------------------------- +align 4 +@@: mov edx, hotkey_buffer - @@: +;-------------------------------------- +align 4 +@@: cmp [edx], bh ; bh - slot for testing je .result add edx, 8 @@ -516,3 +593,4 @@ get_event_for_app: ;; used from f10,f11,f23 jb @b jmp .loop ;end. +;----------------------------------------------------------------------------- \ No newline at end of file diff --git a/kernel/branches/Kolibri-acpi/gui/font.inc b/kernel/branches/Kolibri-acpi/gui/font.inc index 8eb5096632..dfddb7d008 100644 --- a/kernel/branches/Kolibri-acpi/gui/font.inc +++ b/kernel/branches/Kolibri-acpi/gui/font.inc @@ -16,15 +16,15 @@ dtext_asciiz_esi: ; for skins title out jmp dtext.1 ;------------------------------------------------------------------------------ align 4 -dtext: ; Text String Output (rw by Johnny_B[john@kolibrios.org]) - ; ebx x & y - ; ecx style ( 0xX0000000 ) & color ( 0x00RRGGBB ) - ; X = ABnnb: - ; nn = font - ; A = 0 <=> output esi characters; otherwise output ASCIIZ string - ; B = 1 <=> fill background with color eax - ; edx start of text - ; edi 1 force +dtext: +; ebx x & y +; ecx style ( 0xX0000000 ) & color ( 0x00RRGGBB ) +; X = ABnnb: +; nn = font +; A = 0 <=> output esi characters; otherwise output ASCIIZ string +; B = 1 <=> fill background with color eax +; edx start of text +; edi 1 force or user area for redirect push eax xor eax, eax ;-------------------------------------- @@ -36,14 +36,17 @@ align 4 xchg eax, ebx ; eax=x, ebx=y cmp esi, 255 jb .loop + mov esi, 255 ;-------------------------------------- align 4 .loop: test ecx, ecx js .test_asciiz + dec esi js .end + jmp @f ;-------------------------------------- align 4 @@ -53,6 +56,7 @@ align 4 cmp byte [esp+28], 1 jne @f + dec esi js .end ;-------------------------------------- @@ -63,6 +67,7 @@ align 4 movzx edx, byte [edx-1] test ecx, 0x10000000 jnz .font2 + mov esi, 9 lea ebp, [FONT_I+8*edx+edx] ;-------------------------------------- @@ -75,7 +80,17 @@ align 4 .pixloop1: shr dl, 1 jz .pixloop1end + jnc .nopix + + test ecx, 0x08000000 ; redirect the output to the user area + jz @f + + call draw_text_to_user_area + jmp .pixloop1cont +;-------------------------------------- +align 4 +@@: and ecx, 0xFBFFFFFF ;negate 0x04000000 save to mouseunder area ; call [putpixel] call __sys_putpixel @@ -85,8 +100,19 @@ align 4 .nopix: test ecx, 0x40000000 jz .pixloop1cont + push ecx mov ecx, [esp+4+20h+20h] + + test ecx, 0x08000000 ; redirect the output to the user area + jz @f + + call draw_text_to_user_area + pop ecx + jmp .pixloop1cont +;-------------------------------------- +align 4 +@@: and ecx, 0xFBFFFFFF ;negate 0x04000000 save to mouseunder area ; call [putpixel] call __sys_putpixel @@ -104,6 +130,7 @@ align 4 inc ebp dec esi jnz .symloop1 + popad add eax, 6 jmp .loop @@ -124,6 +151,15 @@ align 4 .pixloop2: shr dl, 1 jnc .nopix2 + + test ecx, 0x08000000 ; redirect the output to the user area + jz @f + + call draw_text_to_user_area + jmp .pixloop2cont +;-------------------------------------- +align 4 +@@: and ecx, 0xFBFFFFFF ;negate 0x04000000 save to mouseunder area ; call [putpixel] call __sys_putpixel @@ -133,8 +169,19 @@ align 4 .nopix2: test ecx, 0x40000000 jz .pixloop2cont + push ecx mov ecx, [esp+12+20h+20h] + + test ecx, 0x08000000 ; redirect the output to the user area + jz @f + + call draw_text_to_user_area + pop ecx + jmp .pixloop2cont +;-------------------------------------- +align 4 +@@: and ecx, 0xFBFFFFFF ;negate 0x04000000 save to mouseunder area ; call [putpixel] call __sys_putpixel @@ -145,12 +192,14 @@ align 4 inc eax dec esi jnz .pixloop2 + pop esi sub eax, esi inc ebx inc ebp dec dword [esp] jnz .symloop2 + pop eax add dword [esp+28], esi popad @@ -162,3 +211,29 @@ align 4 pop eax ret ;------------------------------------------------------------------------------ +; eax = x coordinate +; ebx = y coordinate +; ecx = ?? RR GG BB +; edi = user area +align 4 +draw_text_to_user_area: + pushad + imul ebx, [edi+0] + add eax, ebx + shl eax, 2 + add eax, edi + add eax, 8 + and ecx, 0xffffff + or ecx, 0xff000000 ; not transparent + mov [eax], ecx ; store pixel + popad + ret +;------------------------------------------------------------------------------ +align 4 +FONT_I: + file 'char.mt' +;------------------------------------------------------------------------------ +align 4 +FONT_II: + file 'char2.mt' +;------------------------------------------------------------------------------ \ No newline at end of file diff --git a/kernel/branches/Kolibri-acpi/gui/mouse.inc b/kernel/branches/Kolibri-acpi/gui/mouse.inc index 6b73a256ca..7977b4a80f 100644 --- a/kernel/branches/Kolibri-acpi/gui/mouse.inc +++ b/kernel/branches/Kolibri-acpi/gui/mouse.inc @@ -258,8 +258,8 @@ mouse._.left_button_press_handler: ;/////////////////////////////////////////// call .calculate_e_delta .call_window_handler: - mov eax, mouse.active_sys_window.old_box - call sys_window_start_moving_handler +; mov eax, mouse.active_sys_window.old_box +; call sys_window_start_moving_handler .exit: ret diff --git a/kernel/branches/Kolibri-acpi/gui/window.inc b/kernel/branches/Kolibri-acpi/gui/window.inc index 9d84a9c9b6..e1cf9c4f7d 100644 --- a/kernel/branches/Kolibri-acpi/gui/window.inc +++ b/kernel/branches/Kolibri-acpi/gui/window.inc @@ -1026,6 +1026,55 @@ align 4 ;------------------------------------------------------------------------------ align 4 ;------------------------------------------------------------------------------ +minimize_all_window: + push ebx ecx edx esi edi + pushfd + cli + xor edx, edx + mov eax, 2 ; we do not minimize the kernel thread N1 + mov ebx, [TASK_COUNT] +;-------------------------------------- +align 4 +.loop: + movzx edi, word[WIN_POS + eax * 2] + shl edi, 5 +; it is a unused slot? + cmp dword [edi+CURRENT_TASK+TASKDATA.state], 9 + je @f +; it is a hidden thread? + lea esi, [edi*8+SLOT_BASE+APPDATA.app_name] + cmp [esi], byte '@' + je @f +; is it already minimized? + test [edi + window_data+WDATA.fl_wstate], WSTATE_MINIMIZED + jnz @f +; no it's not, let's do that + or [edi + window_data+WDATA.fl_wstate], WSTATE_MINIMIZED + inc edx +;-------------------------------------- +align 4 +@@: + inc eax + cmp eax, ebx + jbe .loop +; If nothing has changed + test edx, edx + jz @f + + push edx + call syscall_display_settings._.calculate_whole_screen + call syscall_display_settings._.redraw_whole_screen + pop edx +;-------------------------------------- +align 4 +@@: + mov eax, edx + popfd + pop edi esi edx ecx ebx + ret +;------------------------------------------------------------------------------ +align 4 +;------------------------------------------------------------------------------ minimize_window: ;///////////////////////////////////////////////////////////// ;------------------------------------------------------------------------------ ;> eax = window number on screen @@ -1047,6 +1096,13 @@ minimize_window: ;///////////////////////////////////////////////////////////// ; no it's not, let's do that or [edi + WDATA.fl_wstate], WSTATE_MINIMIZED +; If the window width is 0, then the action is not needed. + cmp [edi + WDATA.box.width], dword 0 + je @f +; If the window height is 0, then the action is not needed. + cmp [edi + WDATA.box.height], dword 0 + je @f + mov eax, [edi + WDATA.box.left] mov [draw_limits.left], eax mov ecx, eax @@ -1057,11 +1113,20 @@ minimize_window: ;///////////////////////////////////////////////////////////// mov edx, ebx add edx, [edi + WDATA.box.height] mov [draw_limits.bottom], edx - call calculatescreen - xor esi, esi - xor eax, eax - call redrawscreen +; DEBUGF 1, "K : minimize_window\n" +; DEBUGF 1, "K : dl_left %x\n",[draw_limits.left] +; DEBUGF 1, "K : dl_right %x\n",[draw_limits.right] +; DEBUGF 1, "K : dl_top %x\n",[draw_limits.top] +; DEBUGF 1, "K : dl_bottom %x\n",[draw_limits.bottom] + call calculatescreen +; xor esi, esi +; xor eax, eax + mov eax, edi + call redrawscreen +;-------------------------------------- +align 4 +@@: pop esi edx ecx ebx eax ;-------------------------------------- align 4 @@ -1266,16 +1331,16 @@ align 4 ;------------------------------------------------------------------------------ align 4 ;------------------------------------------------------------------------------ -sys_window_start_moving_handler: ;///////////////////////////////////////////// +;sys_window_start_moving_handler: ;///////////////////////////////////////////// ;------------------------------------------------------------------------------ ;? ;------------------------------------------------------------------------------ ;> eax = old (original) window box ;> esi = process slot ;------------------------------------------------------------------------------ - mov edi, eax - call window._.draw_negative_box - ret +; mov edi, eax +; call window._.draw_negative_box +; ret ;------------------------------------------------------------------------------ align 4 ;------------------------------------------------------------------------------ @@ -1287,8 +1352,8 @@ sys_window_end_moving_handler: ;/////////////////////////////////////////////// ;> ebx = new (final) window box ;> esi = process slot ;------------------------------------------------------------------------------ - mov edi, ebx - call window._.end_moving__box +; mov edi, ebx +; call window._.end_moving__box mov edi, esi shl edi, 5 @@ -1351,45 +1416,17 @@ window._.invalidate_screen: ;////////////////////////////////////////////////// ; TODO: do we really need `draw_limits`? ; Yes, they are used by background drawing code. - mov ecx, [eax + BOX.left] - mov edx, [ebx + BOX.left] - cmp ecx, edx - jle @f - mov ecx, edx -;-------------------------------------- -align 4 -@@: + +; we need only to restore the background windows at the old place! + mov ecx, [ebx + BOX.left] mov [draw_limits.left], ecx - mov ecx, [eax + BOX.left] - add ecx, [eax + BOX.width] - add edx, [ebx + BOX.width] - cmp ecx, edx - jae @f - mov ecx, edx -;-------------------------------------- -align 4 -@@: + add ecx, [ebx + BOX.width] mov [draw_limits.right], ecx - mov ecx, [eax + BOX.top] - mov edx, [ebx + BOX.top] - cmp ecx, edx - jle @f - mov ecx, edx -;-------------------------------------- -align 4 -@@: + mov ecx, [ebx + BOX.top] mov [draw_limits.top], ecx - mov ecx, [eax + BOX.top] - add ecx, [eax + BOX.height] - add edx, [ebx + BOX.height] - cmp ecx, edx - jae @f - mov ecx, edx -;-------------------------------------- -align 4 -@@: + add ecx, [ebx + BOX.height] mov [draw_limits.bottom], ecx - ; recalculate screen buffer at old position +; recalculate screen buffer at old position push ebx mov edx, [eax + BOX.height] mov ecx, [eax + BOX.width] @@ -1399,7 +1436,7 @@ align 4 add edx, ebx call calculatescreen pop eax - ; recalculate screen buffer at new position +; recalculate screen buffer at new position mov edx, [eax + BOX.height] mov ecx, [eax + BOX.width] mov ebx, [eax + BOX.top] @@ -1578,7 +1615,10 @@ window._.sys_set_window: ;///////////////////////////////////////////////////// test [edi + WDATA.fl_wdrawn], 1 jnz .set_client_box or [edi + WDATA.fl_wdrawn], 1 - +; After first draw_window we need redraw mouse necessarily! +; Otherwise the user can see cursor specified by f.37.5 from another window. +; He will be really unhappy! He is terrible in rage - usually he throws stones! + mov [redrawmouse_unconditional], 1 ; NOTE: commented out since doesn't provide necessary functionality ; anyway, to be reworked ; mov eax, [timer_ticks] ; [0xfdf0] @@ -2344,17 +2384,17 @@ align 4 pop esi ebx eax ret ;------------------------------------------------------------------------------ -align 4 +;align 4 ;------------------------------------------------------------------------------ -window._.end_moving__box: ;////////////////////////////////////////////////// +;window._.end_moving__box: ;////////////////////////////////////////////////// ;------------------------------------------------------------------------------ ;? Draw positive box ;------------------------------------------------------------------------------ ;> edi = pointer to BOX struct ;------------------------------------------------------------------------------ - push eax ebx esi - xor esi, esi - jmp window._.draw_negative_box.1 +; push eax ebx esi +; xor esi, esi +; jmp window._.draw_negative_box.1 ;------------------------------------------------------------------------------ align 4 ;------------------------------------------------------------------------------ diff --git a/kernel/branches/Kolibri-acpi/hid/keyboard.inc b/kernel/branches/Kolibri-acpi/hid/keyboard.inc index b13f1b1a76..d8c95e0a7b 100644 --- a/kernel/branches/Kolibri-acpi/hid/keyboard.inc +++ b/kernel/branches/Kolibri-acpi/hid/keyboard.inc @@ -34,6 +34,7 @@ uglobal ctrl_alt_del db 0 kb_lights db 0 + old_kb_lights db 0 align 4 hotkey_scancodes rd 256 ; we have 256 scancodes @@ -113,6 +114,83 @@ set_keyboard_data: pop ebp edi esi ebx ret ;--------------------------------------------------------------------- +struct KEYBOARD +next dd ? +prev dd ? +functions dd ? +userdata dd ? +ends +struct KBDFUNC +strucsize dd ? +close dd ? +setlights dd ? +ends + +iglobal +keyboards: + dd keyboards + dd keyboards +endg +uglobal +keyboard_list_mutex MUTEX +endg + +register_keyboard: + push ebx + push sizeof.KEYBOARD + pop eax + call malloc + test eax, eax + jz .nothing + mov ecx, [esp+4+4] + mov [eax+KEYBOARD.functions], ecx + mov ecx, [esp+8+4] + mov [eax+KEYBOARD.userdata], ecx + xchg eax, ebx + mov ecx, keyboard_list_mutex + call mutex_lock + mov ecx, keyboards + mov edx, [ecx+KEYBOARD.prev] + mov [ebx+KEYBOARD.next], ecx + mov [ebx+KEYBOARD.prev], edx + mov [edx+KEYBOARD.next], ebx + mov [ecx+KEYBOARD.prev], ebx + mov ecx, [ebx+KEYBOARD.functions] + cmp [ecx+KBDFUNC.strucsize], KBDFUNC.setlights + jbe .unlock + mov ecx, [ecx+KBDFUNC.setlights] + test ecx, ecx + jz .unlock + stdcall ecx, [ebx+KEYBOARD.userdata], dword [kb_lights] +.unlock: + mov ecx, keyboard_list_mutex + call mutex_unlock + xchg eax, ebx +.nothing: + pop ebx + ret 8 + +delete_keyboard: + push ebx + mov ebx, [esp+4+4] + mov ecx, keyboard_list_mutex + call mutex_lock + mov eax, [ebx+KEYBOARD.next] + mov edx, [ebx+KEYBOARD.prev] + mov [eax+KEYBOARD.prev], edx + mov [edx+KEYBOARD.next], eax + call mutex_unlock + mov ecx, [ebx+KEYBOARD.functions] + cmp [ecx+KBDFUNC.strucsize], KBDFUNC.close + jbe .nothing + mov ecx, [ecx+KBDFUNC.close] + test ecx, ecx + jz .nothing + stdcall ecx, [ebx+KEYBOARD.userdata] +.nothing: + pop ebx + ret 4 +;--------------------------------------------------------------------- align 4 irq1: movzx eax, word[TASK_COUNT]; top window process @@ -281,8 +359,11 @@ send_scancode: xor [kb_state], eax xor [kb_lights], bl + push ecx call set_lights + pop ecx .writekey: + pushad ; test for system hotkeys movzx eax, ch cmp bh, 1 @@ -335,9 +416,16 @@ send_scancode: mov [edi+4], ax mov eax, [kb_state] mov [edi+6], ax + + cmp [PID_lock_input], dword 0 + je .nohotkey + + popad jmp .exit.irq1 ;-------------------------------------- .nohotkey: + popad + cmp [keyboard_mode], 0; return from keymap jne .scancode @@ -384,10 +472,43 @@ send_scancode: ret ;--------------------------------------------------------------------- set_lights: + push ebx esi + mov ecx, keyboard_list_mutex + call mutex_lock + mov esi, keyboards +.loop: + mov esi, [esi+KEYBOARD.next] + cmp esi, keyboards + jz .done + mov eax, [esi+KEYBOARD.functions] + cmp dword [eax], KBDFUNC.setlights + jbe .loop + mov eax, [eax+KBDFUNC.setlights] + test eax, eax + jz .loop + stdcall eax, [esi+KEYBOARD.userdata], dword [kb_lights] + jmp .loop +.done: + mov ecx, keyboard_list_mutex + call mutex_unlock + pop esi ebx + ret + +ps2_set_lights: mov al, 0xED call kb_write - mov al, [kb_lights] + mov al, [esp+8] call kb_write + ret 8 + +;// mike.dld ] +check_lights_state: + mov al, [kb_lights] + cmp al, [old_kb_lights] + jz .nothing + mov [old_kb_lights], al + call set_lights +.nothing: ret ;--------------------------------------------------------------------- numlock_map: diff --git a/kernel/branches/Kolibri-acpi/hid/mousedrv.inc b/kernel/branches/Kolibri-acpi/hid/mousedrv.inc index 51c58b0c46..8be0836b7c 100644 --- a/kernel/branches/Kolibri-acpi/hid/mousedrv.inc +++ b/kernel/branches/Kolibri-acpi/hid/mousedrv.inc @@ -26,14 +26,14 @@ uglobal align 4 mousecount dd 0x0 mousedata dd 0x0 -Y_UNDER_subtraction_CUR_hot_y: - dd 0 -X_UNDER_subtraction_CUR_hot_x: - dd 0 Y_UNDER_sub_CUR_hot_y_add_curh: - dd 0 + dw 0 +Y_UNDER_subtraction_CUR_hot_y: + dw 0 X_UNDER_sub_CUR_hot_x_add_curh: - dd 0 + dw 0 +X_UNDER_subtraction_CUR_hot_x: + dw 0 endg iglobal @@ -447,15 +447,15 @@ redrawmouse: mov ax, [Y_UNDER] sub eax, [esi+CURSOR.hot_y] - mov [Y_UNDER_subtraction_CUR_hot_y], eax + mov [Y_UNDER_subtraction_CUR_hot_y], ax add eax, [cur.h] - mov [Y_UNDER_sub_CUR_hot_y_add_curh], eax + mov [Y_UNDER_sub_CUR_hot_y_add_curh], ax mov ax, [X_UNDER] sub eax, [esi+CURSOR.hot_x] - mov [X_UNDER_subtraction_CUR_hot_x], eax + mov [X_UNDER_subtraction_CUR_hot_x], ax add eax, [cur.w] - mov [X_UNDER_sub_CUR_hot_x_add_curh], eax + mov [X_UNDER_sub_CUR_hot_x_add_curh], ax ;-------------------------------------- align 4 @@: diff --git a/kernel/branches/Kolibri-acpi/kernel.asm b/kernel/branches/Kolibri-acpi/kernel.asm index c0738b7c27..c12b0d35c4 100644 --- a/kernel/branches/Kolibri-acpi/kernel.asm +++ b/kernel/branches/Kolibri-acpi/kernel.asm @@ -402,6 +402,12 @@ high_code: mov ecx, disk_list_mutex call mutex_init + mov ecx, keyboard_list_mutex + call mutex_init + + mov ecx, unpack_mutex + call mutex_init + ; SAVE REAL MODE VARIABLES mov ax, [BOOT_VAR + BOOT_IDE_BASE_ADDR] mov [IDEContrRegsBaseAddr], ax @@ -447,11 +453,13 @@ high_code: movzx eax, word [BOOT_VAR+BOOT_X_RES]; X max mov [_display.width], eax + mov [display_width_standard], eax dec eax mov [Screen_Max_X], eax mov [screen_workarea.right], eax movzx eax, word [BOOT_VAR+BOOT_Y_RES]; Y max mov [_display.height], eax + mov [display_height_standard], eax dec eax mov [Screen_Max_Y], eax mov [screen_workarea.bottom], eax @@ -473,6 +481,10 @@ high_code: mov [_WinMapSize], eax call calculate_fast_getting_offset_for_WinMapAddress +; for Qemu or non standart video cards +; Unfortunately [BytesPerScanLine] does not always +; equal to [_display.width] * [ScreenBPP] / 8 + call calculate_fast_getting_offset_for_LFB mov esi, BOOT_VAR+0x9080 movzx ecx, byte [esi-1] @@ -507,6 +519,10 @@ v20ga24: mov [GETPIXEL], dword Vesa20_getpixel32 no_mode_0x12: + mov [MOUSE_PICTURE], dword mousepointer + mov [_display.check_mouse], check_mouse_area_for_putpixel + mov [_display.check_m_pixel], check_mouse_area_for_getpixel + ; -------- Fast System Call init ---------- ; Intel SYSENTER/SYSEXIT (AMD CPU support it too) bt [cpu_caps], CAPS_SEP @@ -592,7 +608,7 @@ no_mode_0x12: mov ax, tss0 ltr ax - mov [LFBSize], 0x800000 + mov [LFBSize], 0xC00000 call init_LFB call init_fpu call init_malloc @@ -670,16 +686,26 @@ no_mode_0x12: rep stosd ; REDIRECT ALL IRQ'S TO INT'S 0x20-0x2f - + mov esi, boot_initirq + call boot_log call init_irqs + + mov esi, boot_picinit + call boot_log call PIC_init + mov esi, boot_v86machine + call boot_log ; Initialize system V86 machine call init_sys_v86 + mov esi, boot_inittimer + call boot_log ; Initialize system timer (IRQ0) call PIT_init + mov esi, boot_initapic + call boot_log ; Try to Initialize APIC call APIC_init @@ -697,6 +723,8 @@ no_mode_0x12: stdcall enable_irq, 14 stdcall enable_irq, 15 + mov esi, boot_enablint_ide + call boot_log ; Enable interrupts in IDE controller mov al, 0 mov dx, 0x3F6 @@ -705,9 +733,25 @@ no_mode_0x12: out dx, al ;!!!!!!!!!!!!!!!!!!!!!!!!!! -include 'detect/disks.inc' +; mov esi, boot_detectdisks +; call boot_log +;include 'detect/disks.inc' + mov esi, boot_detectfloppy + call boot_log +include 'detect/dev_fd.inc' + mov esi, boot_detecthdcd + call boot_log +include 'detect/dev_hdcd.inc' + mov esi, boot_getcache + call boot_log +include 'detect/getcache.inc' + mov esi, boot_detectpart + call boot_log +include 'detect/sear_par.inc' ;!!!!!!!!!!!!!!!!!!!!!!!!!! + mov esi, boot_init_sys + call boot_log call Parser_params if ~ defined extended_primary_loader @@ -727,6 +771,9 @@ if 0 mov ax, [OS_BASE+0x10000+bx_from_load] cmp ax, 'r1'; if using not ram disk, then load librares and parameters {SPraid.simba} je no_lib_load + + mov esi, boot_loadlibs + call boot_log ; LOADING LIBRARES stdcall dll.Load, @IMPORT ; loading librares for kernel (.obj files) call load_file_parse_table ; prepare file parse table @@ -734,24 +781,13 @@ if 0 no_lib_load: end if -; LOAD FONTS I and II - - stdcall read_file, char, FONT_I, 0, 2304 - stdcall read_file, char2, FONT_II, 0, 2560 - - mov [MOUSE_PICTURE], dword mousepointer - mov [_display.check_mouse], check_mouse_area_for_putpixel - mov [_display.check_m_pixel], check_mouse_area_for_getpixel - - mov esi, boot_fonts - call boot_log - ; Display APIC status mov esi, boot_APIC_found cmp [irq_mode], IRQ_APIC je @f mov esi, boot_APIC_nfound @@: + call boot_log ; PRINT AMOUNT OF MEMORY mov esi, boot_memdetect @@ -774,10 +810,10 @@ end if ; BUILD SCHEDULER - call build_scheduler; sys32.inc +; call build_scheduler; sys32.inc - mov esi, boot_devices - call boot_log +; mov esi, boot_devices +; call boot_log mov [pci_access_enabled], 1 @@ -978,6 +1014,8 @@ first_app_found: ; SET KEYBOARD PARAMETERS mov al, 0xf6 ; reset keyboard, scan enabled call kb_write + test ah, ah + jnz .no_keyboard ; wait until 8042 is ready xor ecx, ecx @@ -986,6 +1024,15 @@ first_app_found: and al, 00000010b loopnz @b +iglobal +align 4 +ps2_keyboard_functions: + dd .end - $ + dd 0 ; no close + dd ps2_set_lights +.end: +endg + stdcall register_keyboard, ps2_keyboard_functions, 0 ; mov al, 0xED ; Keyboard LEDs - only for testing! ; call kb_write ; call kb_read @@ -1003,6 +1050,7 @@ first_app_found: call set_lights ;// mike.dld ] stdcall attach_int_handler, 1, irq1, 0 +.no_keyboard: ; SET MOUSE @@ -1053,6 +1101,7 @@ if defined debug_com_base end if + mov eax, [cpu_count] test eax, eax jnz @F @@ -1125,6 +1174,7 @@ osloop: call checkidle call check_fdd_motor_status call check_ATAPI_device_event + call check_lights_state call check_timers jmp osloop ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; @@ -2025,6 +2075,8 @@ sys_end: ;------------------------------------------------------------------------------ align 4 restore_default_cursor_before_killing: + pushfd + cli mov eax, [def_cursor] mov [ecx+APPDATA.cursor], eax @@ -2048,6 +2100,7 @@ restore_default_cursor_before_killing: mov [current_cursor], esi @@: mov [redrawmouse_unconditional], 1 + popfd ; call [draw_pointer] call __sys_draw_pointer ret @@ -2078,6 +2131,8 @@ sys_system_table: dd sysfn_meminfo ; 20 = get extended memory info dd sysfn_pid_to_slot ; 21 = get slot number for pid dd sysfn_min_rest_window ; 22 = minimize and restore any window + dd sysfn_min_windows ; 23 = minimize all windows + dd sysfn_set_screen_sizes ; 24 = set screen sizes for Vesa sysfn_num = ($ - sys_system_table)/4 endg ;------------------------------------------------------------------------------ @@ -2108,13 +2163,13 @@ sysfn_shutdown: ; 18.9 = system shutdown endg ;------------------------------------------------------------------------------ sysfn_terminate: ; 18.2 = TERMINATE + push ecx cmp ecx, 2 jb noprocessterminate mov edx, [TASK_COUNT] cmp ecx, edx ja noprocessterminate mov eax, [TASK_COUNT] - push ecx shl ecx, 5 mov edx, [ecx+CURRENT_TASK+TASKDATA.pid] add ecx, CURRENT_TASK+TASKDATA.state @@ -2135,7 +2190,6 @@ sysfn_terminate: ; 18.2 = TERMINATE @@: popa .restore_end: - add esp, 4 ;-------------------------------------- ;call MEM_Heap_Lock ;guarantee that process isn't working with heap mov [ecx], byte 3; clear possible i40's @@ -2144,8 +2198,9 @@ sysfn_terminate: ; 18.2 = TERMINATE cmp edx, [application_table_status]; clear app table stat jne noatsc and [application_table_status], 0 - noatsc: - noprocessterminate: +noatsc: +noprocessterminate: + add esp, 4 ret ;------------------------------------------------------------------------------ sysfn_terminate2: @@ -2383,20 +2438,19 @@ sysfn_getfreemem: shl eax, 2 mov [esp+32], eax ret - +;------------------------------------------------------------------------------ sysfn_getallmem: mov eax, [MEM_AMOUNT] shr eax, 10 mov [esp+32], eax ret - -; // Alver, 2007-22-08 // { +;------------------------------------------------------------------------------ sysfn_pid_to_slot: mov eax, ecx call pid_to_slot mov [esp+32], eax ret - +;------------------------------------------------------------------------------ sysfn_min_rest_window: pushad mov eax, edx ; ebx - operating @@ -2427,14 +2481,52 @@ sysfn_min_rest_window: dec eax mov [esp+32], eax ret -; } \\ Alver, 2007-22-08 \\ +;------------------------------------------------------------------------------ +sysfn_min_windows: + call minimize_all_window + mov [esp+32], eax + call change_task + ret +;------------------------------------------------------------------------------ +sysfn_set_screen_sizes: + cmp [SCR_MODE], word 0x13 + jbe .exit + cmp [_display.select_cursor], select_cursor + jne .exit + + cmp ecx, [display_width_standard] + ja .exit + + cmp edx, [display_height_standard] + ja .exit + + pushfd + cli + mov eax, ecx + mov ecx, [BytesPerScanLine] + mov [_display.width], eax + dec eax + mov [_display.height], edx + dec edx +; eax - new Screen_Max_X +; edx - new Screen_Max_Y + mov [do_not_touch_winmap], 1 + call set_screen + mov [do_not_touch_winmap], 0 + popfd + call change_task +.exit: + ret +;------------------------------------------------------------------------------ uglobal -;// mike.dld, 2006-29-01 [ screen_workarea RECT -;// mike.dld, 2006-29-01 ] +display_width_standard dd 0 +display_height_standard dd 0 +do_not_touch_winmap db 0 window_minimize db 0 sound_flag db 0 + endg UID_NONE=0 @@ -2448,49 +2540,61 @@ version_inf: dd __REV__ version_end: endg - +;------------------------------------------------------------------------------ +align 4 sys_cachetodiskette: cmp ebx, 1 jne .no_floppy_a_save mov [flp_number], 1 jmp .save_image_on_floppy +;-------------------------------------- +align 4 .no_floppy_a_save: cmp ebx, 2 jne .no_floppy_b_save mov [flp_number], 2 +;-------------------------------------- +align 4 .save_image_on_floppy: call save_image mov [esp + 32], dword 0 cmp [FDC_Status], 0 je .yes_floppy_save +;-------------------------------------- +align 4 .no_floppy_b_save: mov [esp + 32], dword 1 +;-------------------------------------- +align 4 .yes_floppy_save: ret - +;------------------------------------------------------------------------------ uglobal ; bgrchanged dd 0x0 align 4 bgrlockpid dd 0 bgrlock db 0 endg - +;------------------------------------------------------------------------------ +align 4 sys_background: - cmp ebx, 1 ; BACKGROUND SIZE jnz nosb1 test ecx, ecx -; cmp ecx,0 jz sbgrr + test edx, edx -; cmp edx,0 jz sbgrr +;-------------------------------------- +align 4 @@: ;;Maxis use atomic bts for mutexes 4.4.2009 bts dword [bgrlock], 0 jnc @f call change_task jmp @b +;-------------------------------------- +align 4 @@: mov [BgrDataWidth], ecx mov [BgrDataHeight], edx @@ -2502,6 +2606,8 @@ sys_background: cmp eax, static_background_data jz @f stdcall kernel_free, eax +;-------------------------------------- +align 4 @@: ; calculate RAW size xor eax, eax @@ -2509,10 +2615,14 @@ sys_background: cmp [BgrDataWidth], eax jae @f mov [BgrDataWidth], eax +;-------------------------------------- +align 4 @@: cmp [BgrDataHeight], eax jae @f mov [BgrDataHeight], eax +;-------------------------------------- +align 4 @@: mov eax, [BgrDataWidth] imul eax, [BgrDataHeight] @@ -2530,6 +2640,8 @@ sys_background: jz .memfailed mov [img_background], eax jmp .exit +;-------------------------------------- +align 4 .memfailed: ; revert to static monotone data mov [img_background], static_background_data @@ -2538,15 +2650,18 @@ sys_background: mov [BgrDataWidth], eax mov [BgrDataHeight], eax mov [mem_BACKGROUND], 4 +;-------------------------------------- +align 4 .exit: popad mov [bgrlock], 0 - - sbgrr: +;-------------------------------------- +align 4 +sbgrr: ret - +;------------------------------------------------------------------------------ +align 4 nosb1: - cmp ebx, 2 ; SET PIXEL jnz nosb2 @@ -2555,6 +2670,8 @@ nosb1: jz @f cmp eax, static_background_data jz .ret +;-------------------------------------- +align 4 @@: mov ebx, [mem_BACKGROUND] add ebx, 4095 @@ -2568,34 +2685,39 @@ nosb1: and edx, 0x00FFFFFF;255*256*256+255*256+255 add edx, ebx mov [eax+ecx], edx +;-------------------------------------- +align 4 .ret: ret +;------------------------------------------------------------------------------ +align 4 nosb2: - cmp ebx, 3 ; DRAW BACKGROUND jnz nosb3 +;-------------------------------------- +align 4 draw_background_temp: -; cmp [bgrchanged],1 ;0 -; je nosb31 -;draw_background_temp: -; mov [bgrchanged],1 ;0 mov [background_defined], 1 - mov byte[BACKGROUND_CHANGED], 1 call force_redraw_background - nosb31: +;-------------------------------------- +align 4 +nosb31: ret - nosb3: - +;------------------------------------------------------------------------------ +align 4 +nosb3: cmp ebx, 4 ; TILED / STRETCHED jnz nosb4 cmp ecx, [BgrDrawMode] je nosb41 mov [BgrDrawMode], ecx -; mov [bgrchanged],1 - nosb41: +;-------------------------------------- +align 4 +nosb41: ret - nosb4: - +;------------------------------------------------------------------------------ +align 4 +nosb4: cmp ebx, 5 ; BLOCK MOVE TO BGR jnz nosb5 cmp [img_background], static_background_data @@ -2604,25 +2726,34 @@ draw_background_temp: jnz .fin cmp esi, 4 ja .fin - @@: +;-------------------------------------- +align 4 +@@: ; bughere mov eax, ecx mov ebx, edx add ebx, [img_background];IMG_BACKGROUND mov ecx, esi call memmove - .fin: +;-------------------------------------- +align 4 +.fin: ret - nosb5: - +;------------------------------------------------------------------------------ +align 4 +nosb5: cmp ebx, 6 jnz nosb6 +;-------------------------------------- +align 4 ;;Maxis use atomic bts for mutex 4.4.2009 @@: bts dword [bgrlock], 0 jnc @f call change_task jmp @b +;-------------------------------------- +align 4 @@: mov eax, [CURRENT_TASK] mov [bgrlockpid], eax @@ -2640,11 +2771,15 @@ draw_background_temp: mov ecx, [mem_BACKGROUND] add ecx, 0xFFF shr ecx, 12 +;-------------------------------------- +align 4 .z: mov eax, [page_tabs+ebx*4] test al, 1 jz @f call free_page +;-------------------------------------- +align 4 @@: mov eax, [page_tabs+esi*4] or al, PG_UW @@ -2656,9 +2791,13 @@ draw_background_temp: inc esi loop .z ret +;-------------------------------------- +align 4 .nomem: and [bgrlockpid], 0 mov [bgrlock], 0 +;------------------------------------------------------------------------------ +align 4 nosb6: cmp ebx, 7 jnz nosb7 @@ -2677,6 +2816,8 @@ nosb6: push eax shr ecx, 12 dec ecx +;-------------------------------------- +align 4 @@: and dword [page_tabs+eax*4], 0 mov edx, eax @@ -2693,13 +2834,77 @@ nosb6: and [bgrlockpid], 0 mov [bgrlock], 0 ret +;-------------------------------------- +align 4 .err: and dword [esp+32], 0 ret - +;------------------------------------------------------------------------------ +align 4 nosb7: - ret + cmp ebx, 8 + jnz nosb8 + mov eax, [BG_Rect_X_left_right] + mov [esp + 32], eax ; eax = [left]*65536 + [right] + mov eax, [BG_Rect_Y_top_bottom] + mov [esp + 20], eax ; ebx = [top]*65536 + [bottom] + ret +;------------------------------------------------------------------------------ +align 4 +nosb8: + cmp ebx, 9 + jnz nosb9 +; ecx = [left]*65536 + [right] +; edx = [top]*65536 + [bottom] + mov eax, [Screen_Max_X] + mov ebx, [Screen_Max_Y] +; check [right] + cmp cx, ax + ja .exit +; check [left] + ror ecx, 16 + cmp cx, ax + ja .exit +; check [bottom] + cmp dx, bx + ja .exit +; check [top] + ror edx, 16 + cmp dx, bx + ja .exit + + movzx eax, cx ; [left] + movzx ebx, dx ; [top] + + shr ecx, 16 ; [right] + shr edx, 16 ; [bottom] + + mov [background_defined], 1 + + mov [draw_data+32 + RECT.left], eax + mov [draw_data+32 + RECT.top], ebx + + mov [draw_data+32 + RECT.right], ecx + mov [draw_data+32 + RECT.bottom], edx + + inc byte[REDRAW_BACKGROUND] +;-------------------------------------- +align 4 +.exit: + ret +;------------------------------------------------------------------------------ +align 4 +nosb9: + ret +;------------------------------------------------------------------------------ +align 4 +uglobal + BG_Rect_X_left_right dd 0x0 + BG_Rect_Y_top_bottom dd 0x0 +endg +;------------------------------------------------------------------------------ +align 4 force_redraw_background: and [draw_data+32 + RECT.left], 0 and [draw_data+32 + RECT.top], 0 @@ -2711,9 +2916,8 @@ force_redraw_background: pop ebx eax inc byte[REDRAW_BACKGROUND] ret - +;------------------------------------------------------------------------------ align 4 - sys_getbackground: ; cmp eax,1 ; SIZE dec ebx @@ -2723,7 +2927,8 @@ sys_getbackground: mov ax, [BgrDataHeight] mov [esp+32], eax ret - +;------------------------------------------------------------------------------ +align 4 nogb1: ; cmp eax,2 ; PIXEL dec ebx @@ -2734,6 +2939,8 @@ nogb1: jz @f cmp eax, static_background_data jz .ret +;-------------------------------------- +align 4 @@: mov ebx, [mem_BACKGROUND] add ebx, 4095 @@ -2746,21 +2953,26 @@ nogb1: and eax, 0xFFFFFF mov [esp+32], eax +;-------------------------------------- +align 4 .ret: ret - nogb2: +;------------------------------------------------------------------------------ +align 4 +nogb2: ; cmp eax,4 ; TILED / STRETCHED dec ebx dec ebx jnz nogb4 mov eax, [BgrDrawMode] - nogb4: +;-------------------------------------- +align 4 +nogb4: mov [esp+32], eax ret - +;------------------------------------------------------------------------------ align 4 - sys_getkey: mov [esp + 32], dword 1 ; test main buffer @@ -2782,12 +2994,18 @@ sys_getkey: mov ebx, KEY_BUFF call memmove pop eax +;-------------------------------------- +align 4 .ret_eax: mov [esp + 32], eax ret +;-------------------------------------- +align 4 .finish: ; test hotkeys buffer mov ecx, hotkey_buffer +;-------------------------------------- +align 4 @@: cmp [ecx], ebx jz .found @@ -2795,6 +3013,8 @@ sys_getkey: cmp ecx, hotkey_buffer + 120 * 8 jb @b ret +;-------------------------------------- +align 4 .found: mov ax, [ecx + 6] shl eax, 16 @@ -2803,11 +3023,9 @@ sys_getkey: and dword [ecx + 4], 0 and dword [ecx], 0 jmp .ret_eax - +;------------------------------------------------------------------------------ align 4 - sys_getbutton: - mov ebx, [CURRENT_TASK] ; TOP OF WINDOW STACK mov [esp + 32], dword 1 movzx ecx, word [WIN_STACK + ebx * 2] @@ -2821,12 +3039,12 @@ sys_getbutton: and al, 0xFE ; delete left button bit mov [BTN_COUNT], byte 0 mov [esp + 32], eax +;-------------------------------------- +align 4 .exit: ret - - +;------------------------------------------------------------------------------ align 4 - sys_cpuusage: ; RETURN: @@ -3203,12 +3421,9 @@ endg uglobal background_defined db 0 ; diamond, 11.04.2006 endg - +;----------------------------------------------------------------------------- align 4 -; check misc - checkmisc: - cmp [ctrl_alt_del], 1 jne nocpustart @@ -3216,7 +3431,8 @@ checkmisc: call fs_execute_from_sysdir mov [ctrl_alt_del], 0 - +;-------------------------------------- +align 4 nocpustart: cmp [mouse_active], 1 jne mouse_not_active @@ -3232,7 +3448,7 @@ nocpustart: movzx eax, word [MOUSE_X] movzx edx, word [MOUSE_Y] - +;-------------------------------------- align 4 .set_mouse_event: add edi, 256 @@ -3242,7 +3458,8 @@ align 4 cmp edi, [esp] ; skip if filtration active jne .skip - +;-------------------------------------- +align 4 .pos_filter: test [ebx+TASKDATA.event_mask], 0x40000000 jz .set @@ -3260,50 +3477,69 @@ align 4 add esi, [ebx-twdw+WDATA.box.height] cmp edx, esi ja .skip +;-------------------------------------- +align 4 .set: - or [edi+SLOT_BASE+APPDATA.event_mask], 100000b + or [edi+SLOT_BASE+APPDATA.event_mask], 100000b ; set event 6 +;-------------------------------------- +align 4 .skip: loop .set_mouse_event pop eax - +;-------------------------------------- +align 4 mouse_not_active: - cmp byte[BACKGROUND_CHANGED], 0 - jz no_set_bgr_event - xor edi, edi - mov ecx, [TASK_COUNT] -set_bgr_event: - add edi, 256 - or [edi+SLOT_BASE+APPDATA.event_mask], 16 - loop set_bgr_event - mov byte[BACKGROUND_CHANGED], 0 -no_set_bgr_event: cmp byte[REDRAW_BACKGROUND], 0 ; background update ? jz nobackgr + cmp [background_defined], 0 jz nobackgr -; mov [draw_data+32 + RECT.left],dword 0 -; mov [draw_data+32 + RECT.top],dword 0 -; mov eax,[Screen_Max_X] -; mov ebx,[Screen_Max_Y] -; mov [draw_data+32 + RECT.right],eax -; mov [draw_data+32 + RECT.bottom],ebx +;-------------------------------------- +align 4 @@: + push eax + mov eax, [draw_data+32 + RECT.left] + shl eax, 16 + add eax, [draw_data+32 + RECT.right] + mov [BG_Rect_X_left_right], eax ; [left]*65536 + [right] + + mov eax, [draw_data+32 + RECT.top] + shl eax, 16 + add eax, [draw_data+32 + RECT.bottom] + mov [BG_Rect_Y_top_bottom], eax ; [top]*65536 + [bottom] + pop eax + call drawbackground - xor eax, eax - xchg al, [REDRAW_BACKGROUND] - test al, al ; got new update request? +; DEBUGF 1, "K : drawbackground\n" +; DEBUGF 1, "K : backg x %x\n",[BG_Rect_X_left_right] +; DEBUGF 1, "K : backg y %x\n",[BG_Rect_Y_top_bottom] +;--------- set event 5 start ---------- + push ecx edi + xor edi, edi + mov ecx, [TASK_COUNT] +;-------------------------------------- +align 4 +set_bgr_event: + add edi, 256 + or [edi+SLOT_BASE+APPDATA.event_mask], 10000b ; set event 5 + loop set_bgr_event + pop edi ecx +; call change_task - because the application must have time to call f.15.8 + call change_task +;--------- set event 5 stop ----------- + dec byte[REDRAW_BACKGROUND] ; got new update request? jnz @b + mov [draw_data+32 + RECT.left], eax mov [draw_data+32 + RECT.top], eax mov [draw_data+32 + RECT.right], eax mov [draw_data+32 + RECT.bottom], eax mov [MOUSE_BACKGROUND], byte 0 - +;-------------------------------------- +align 4 nobackgr: - - ; system shutdown request - +; system shutdown request cmp [SYS_SHUTDOWN], byte 0 je noshutdown @@ -3315,28 +3551,31 @@ nobackgr: lea ecx, [edx-1] mov edx, OS_BASE+0x3040 jecxz @f +;-------------------------------------- +align 4 markz: mov [edx+TASKDATA.state], byte 3 add edx, 0x20 loop markz +;-------------------------------------- +align 4 @@: - - no_mark_system_shutdown: - +no_mark_system_shutdown: dec byte [SYS_SHUTDOWN] je system_shutdown - +;-------------------------------------- +align 4 noshutdown: - - mov eax, [TASK_COUNT] ; termination mov ebx, TASK_DATA+TASKDATA.state mov esi, 1 - +;-------------------------------------- +align 4 newct: mov cl, [ebx] cmp cl, byte 3 jz terminate + cmp cl, byte 4 jz terminate @@ -3345,11 +3584,9 @@ newct: dec eax jnz newct ret - -; redraw screen - +;----------------------------------------------------------------------------- +align 4 redrawscreen: - ; eax , if process window_data base is eax, do not set flag/limits pushad @@ -3360,8 +3597,9 @@ redrawscreen: ;mov ecx,0 ; redraw flags for apps xor ecx, ecx - newdw2: - +;-------------------------------------- +align 4 +newdw2: inc ecx push ecx @@ -3406,45 +3644,58 @@ redrawscreen: mov eax, [draw_limits.left] ; eax = area x start ecx = window x end cmp ecx, eax jb ricino - - bgli: - +;-------------------------------------- +align 4 +bgli: cmp dword[esp], 1 jnz .az -; cmp byte[BACKGROUND_CHANGED], 0 -; jnz newdw8 + cmp byte[REDRAW_BACKGROUND], 0 jz .az + mov dl, 0 lea eax, [edi+draw_data-window_data] mov ebx, [draw_limits.left] cmp ebx, [eax+RECT.left] jae @f + mov [eax+RECT.left], ebx mov dl, 1 - @@: +;-------------------------------------- +align 4 +@@: mov ebx, [draw_limits.top] cmp ebx, [eax+RECT.top] jae @f + mov [eax+RECT.top], ebx mov dl, 1 - @@: +;-------------------------------------- +align 4 +@@: mov ebx, [draw_limits.right] cmp ebx, [eax+RECT.right] jbe @f + mov [eax+RECT.right], ebx mov dl, 1 - @@: +;-------------------------------------- +align 4 +@@: mov ebx, [draw_limits.bottom] cmp ebx, [eax+RECT.bottom] jbe @f + mov [eax+RECT.bottom], ebx mov dl, 1 - @@: +;-------------------------------------- +align 4 +@@: add byte[REDRAW_BACKGROUND], dl jmp newdw8 - .az: - +;-------------------------------------- +align 4 +.az: mov eax, edi add eax, draw_data-window_data @@ -3462,16 +3713,16 @@ redrawscreen: cmp dword [esp], 1 jne nobgrd inc byte[REDRAW_BACKGROUND] - - newdw8: - nobgrd: +;-------------------------------------- +align 4 +newdw8: +nobgrd: mov [eax + WDATA.fl_redraw], byte 1 ; mark as redraw - - ricino: - - not_this_task: - +;-------------------------------------- +align 4 +ricino: +not_this_task: pop ecx cmp ecx, [TASK_COUNT] @@ -3479,11 +3730,10 @@ redrawscreen: pop eax popad - ret - +;----------------------------------------------------------------------------- +align 4 calculatebackground: ; background - mov edi, [_WinMapAddress] ; set os to use all pixels mov eax, 0x01010101 mov ecx, [_WinMapSize] @@ -3491,19 +3741,14 @@ calculatebackground: ; background rep stosd mov byte[REDRAW_BACKGROUND], 0 ; do not draw background! - mov byte[BACKGROUND_CHANGED], 0 - ret - +;----------------------------------------------------------------------------- uglobal imax dd 0x0 endg - - - +;----------------------------------------------------------------------------- +align 4 delay_ms: ; delay in 1/1000 sec - - push eax push ecx @@ -3517,8 +3762,9 @@ delay_ms: ; delay in 1/1000 sec and al, 0x10 mov ah, al cld - - cnt1: +;-------------------------------------- +align 4 +cnt1: in al, 0x61 and al, 0x10 cmp al, ah @@ -3529,9 +3775,8 @@ delay_ms: ; delay in 1/1000 sec pop ecx pop eax - ret - +;----------------------------------------------------------------------------- align 4 set_app_param: mov edi, [TASK_BASE] @@ -3542,17 +3787,17 @@ set_app_param: xchg eax, [edi + TASKDATA.event_mask] ; set new event mask mov [esp+32], eax ; return old mask value ret - - - +;----------------------------------------------------------------------------- +align 4 delay_hs: ; delay in 1/100 secs ; ebx = delay time push ecx push edx mov edx, [timer_ticks] - - newtic: +;-------------------------------------- +align 4 +newtic: mov ecx, [timer_ticks] sub ecx, edx cmp ecx, ebx @@ -3561,16 +3806,15 @@ delay_hs: ; delay in 1/100 secs call change_task jmp newtic - - zerodelay: +;-------------------------------------- +align 4 +zerodelay: pop edx pop ecx - ret - +;----------------------------------------------------------------------------- align 16 ;very often call this subrutine memmove: ; memory move in bytes - ; eax = from ; ebx = to ; ecx = no of bytes @@ -3591,15 +3835,19 @@ memmove: ; memory move in bytes pop ecx and ecx, 11b jz .finish - @@: +;-------------------------------------- +align 4 +@@: rep movsb - - .finish: +;-------------------------------------- +align 4 +.finish: pop ecx edi esi - .ret: +;-------------------------------------- +align 4 +.ret: ret - - +;----------------------------------------------------------------------------- ; Sysfunction 34, read_floppy_file, is obsolete. Use 58 or 70 function instead. ;align 4 ; @@ -3937,6 +4185,14 @@ align 4 jmp sys_putimage_bpp ;-------------------------------------- align 4 +@@: + cmp esi, 9 + jnz @f + mov ebp, putimage_get9bpp + mov esi, putimage_init9bpp + jmp sys_putimage_bpp +;-------------------------------------- +align 4 @@: cmp esi, 15 jnz @f @@ -3998,6 +4254,7 @@ align 4 putimage_init24bpp: lea eax, [eax*3] putimage_init8bpp: +putimage_init9bpp: ret ;----------------------------------------------------------------------------- align 16 @@ -4018,6 +4275,14 @@ putimage_get8bpp: inc esi ret 4 ;----------------------------------------------------------------------------- +align 16 +putimage_get9bpp: + lodsb + mov ah, al + shl eax, 8 + mov al, ah + ret 4 +;----------------------------------------------------------------------------- align 4 putimage_init1bpp: add eax, ecx @@ -4444,17 +4709,17 @@ f66call: dd sys_process_def.1 ; 1 = set keyboard mode dd sys_process_def.2 ; 2 = get keyboard mode dd sys_process_def.3 ; 3 = get keyboard ctrl, alt, shift - dd sys_process_def.4 - dd sys_process_def.5 + dd sys_process_def.4 ; 4 = set system-wide hotkey + dd sys_process_def.5 ; 5 = delete installed hotkey + dd sys_process_def.6 ; 6 = disable input, work only hotkeys + dd sys_process_def.7 ; 7 = enable input, opposition to f.66.6 endg - - - - +;----------------------------------------------------------------------------- +align 4 sys_process_def: dec ebx - cmp ebx, 5 - jae .not_support ;if >=6 then or eax,-1 + cmp ebx, 7 + jae .not_support ;if >=8 then or eax,-1 mov edi, [CURRENT_TASK] jmp dword [f66call+ebx*4] @@ -4462,33 +4727,28 @@ sys_process_def: .not_support: or eax, -1 ret - +;----------------------------------------------------------------------------- +align 4 .1: shl edi, 8 mov [edi+SLOT_BASE + APPDATA.keyboard_mode], cl ret - +;----------------------------------------------------------------------------- +align 4 .2: ; 2 = get keyboard mode shl edi, 8 movzx eax, byte [SLOT_BASE+edi + APPDATA.keyboard_mode] mov [esp+32], eax ret -; xor eax,eax -; movzx eax,byte [shift] -; movzx ebx,byte [ctrl] -; shl ebx,2 -; add eax,ebx -; movzx ebx,byte [alt] -; shl ebx,3 -; add eax,ebx +;----------------------------------------------------------------------------- +align 4 .3: ;3 = get keyboard ctrl, alt, shift - ;// mike.dld [ mov eax, [kb_state] - ;// mike.dld ] mov [esp+32], eax ret - +;----------------------------------------------------------------------------- +align 4 .4: mov eax, hotkey_list @@: @@ -4513,7 +4773,8 @@ sys_process_def: @@: and dword [esp+32], 0 ret - +;----------------------------------------------------------------------------- +align 4 .5: movzx ebx, cl lea ebx, [hotkey_scancodes+ebx*4] @@ -4547,8 +4808,45 @@ sys_process_def: mov [eax], edx mov [esp+32], edx ret +;----------------------------------------------------------------------------- +align 4 +.6: + pushfd + cli + mov eax, [PID_lock_input] + test eax, eax + jnz @f +; get current PID + mov eax, [CURRENT_TASK] + shl eax, 5 + mov eax, [eax+CURRENT_TASK+TASKDATA.pid] +; set current PID for lock input + mov [PID_lock_input], eax +@@: + popfd + ret +;----------------------------------------------------------------------------- +align 4 +.7: + mov eax, [PID_lock_input] + test eax, eax + jz @f +; get current PID + mov ebx, [CURRENT_TASK] + shl ebx, 5 + mov ebx, [ebx+CURRENT_TASK+TASKDATA.pid] +; compare current lock input with current PID + cmp ebx, eax + jne @f - + xor eax, eax + mov [PID_lock_input], eax +@@: + ret +;----------------------------------------------------------------------------- +uglobal + PID_lock_input dd 0x0 +endg ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; 61 sys function. ;; ;; in eax=61,ebx in [1..3] ;; @@ -4624,6 +4922,8 @@ syscall_writetext: ; WriteText pop esi add ebx, ebp mov eax, edi + test ecx, 0x08000000 ; redirect the output to the user area + jnz dtext xor edi, edi jmp dtext @@ -4736,9 +5036,28 @@ syscall_cdaudio: ; CD call .free ; pop eax ret - +;----------------------------------------------------------------------------- +align 4 +syscall_getpixel_WinMap: ; GetPixel WinMap + cmp ebx, [Screen_Max_X] + jbe @f + cmp ecx, [Screen_Max_Y] + jbe @f + xor eax, eax + jmp .store +;-------------------------------------- +align 4 +@@: + mov eax, [d_width_calc_area + ecx*4] + add eax, [_WinMapAddress] + movzx eax, byte[eax+ebx] ; get value for current point +;-------------------------------------- +align 4 +.store: + mov [esp + 32], eax + ret +;----------------------------------------------------------------------------- align 4 - syscall_getpixel: ; GetPixel mov ecx, [Screen_Max_X] inc ecx @@ -4751,9 +5070,8 @@ syscall_getpixel: ; GetPixel call dword [GETPIXEL]; eax - x, ebx - y mov [esp + 32], ecx ret - +;----------------------------------------------------------------------------- align 4 - syscall_getarea: ;eax = 36 ;ebx = pointer to bufer for img BBGGRRBBGGRR... @@ -4789,9 +5107,12 @@ syscall_getarea: add ebp, edi add ebx, edx - +;-------------------------------------- +align 4 .start_y: push ecx edx +;-------------------------------------- +align 4 .start_x: push eax ebx ecx add eax, ecx @@ -4813,9 +5134,89 @@ syscall_getarea: jnz .start_y popad ret - +;----------------------------------------------------------------------------- align 4 +syscall_putarea_backgr: +;eax = 25 +;ebx = pointer to bufer for img BBGGRRBBGGRR... +;ecx = [size x]*65536 + [size y] +;edx = [start x]*65536 + [start y] + pushad + mov edi, ebx + mov eax, edx + shr eax, 16 + mov ebx, edx + and ebx, 0xffff + dec eax + dec ebx +; eax - x, ebx - y + mov edx, ecx + shr ecx, 16 + and edx, 0xffff + mov esi, ecx +; ecx - size x, edx - size y + mov ebp, edx + dec ebp + shl ebp, 2 + imul ebp, esi + + mov esi, ecx + dec esi + shl esi, 2 + + add ebp, esi + add ebp, edi + + add ebx, edx +;-------------------------------------- +align 4 +.start_y: + push ecx edx +;-------------------------------------- +align 4 +.start_x: + push eax ecx + add eax, ecx + + mov ecx, [ebp] + rol ecx, 8 + test cl, cl ; transparensy = 0 + jz .no_put + + xor cl, cl + ror ecx, 8 + + pushad + mov edx, [d_width_calc_area + ebx*4] + add edx, [_WinMapAddress] + movzx edx, byte [eax+edx] + cmp dl, byte 1 + jne @f + + call dword [PUTPIXEL]; eax - x, ebx - y +;-------------------------------------- +align 4 +@@: + popad +;-------------------------------------- +align 4 +.no_put: + pop ecx eax + + sub ebp, 4 + dec ecx + jnz .start_x + + pop edx ecx + dec ebx + dec edx + jnz .start_y + + popad + ret +;----------------------------------------------------------------------------- +align 4 syscall_drawline: ; DrawLine mov edi, [TASK_BASE] @@ -4885,22 +5286,6 @@ socket: ; Socket interface mov [esp+24], ebx ret -align 4 - -read_from_hd: ; Read from hd - fn not in use - - mov edi, [TASK_BASE] - add edi, TASKDATA.mem_start - add eax, [edi] - add ecx, [edi] - add edx, [edi] - call file_read - - mov [esp+36], eax - mov [esp+24], ebx - - ret - paleholder: ret ;------------------------------------------------------------------------------ @@ -4920,7 +5305,26 @@ calculate_fast_getting_offset_for_WinMapAddress: ret ;------------------------------------------------------------------------------ align 4 +calculate_fast_getting_offset_for_LFB: +; calculate data area for fast getting offset to LFB + xor eax, eax + mov ecx, [_display.height] + inc ecx + mov edi, BPSLine_calc_area + cld +@@: + stosd + add eax, [BytesPerScanLine] + dec ecx + jnz @r + ret +;------------------------------------------------------------------------------ +align 4 set_screen: +; in: +; eax - new Screen_Max_X +; ecx - new BytesPerScanLine +; edx - new Screen_Max_Y cmp eax, [Screen_Max_X] jne .set @@ -4944,6 +5348,9 @@ set_screen: pushad + cmp [do_not_touch_winmap], 1 + je @f + stdcall kernel_free, [_WinMapAddress] mov eax, [_display.width] @@ -4954,9 +5361,18 @@ set_screen: mov [_WinMapAddress], eax test eax, eax jz .epic_fail +; store for f.18.24 + mov eax, [_display.width] + mov [display_width_standard], eax + mov eax, [_display.height] + mov [display_height_standard], eax +@@: call calculate_fast_getting_offset_for_WinMapAddress - +; for Qemu or non standart video cards +; Unfortunately [BytesPerScanLine] does not always +; equal to [_display.width] * [ScreenBPP] / 8 + call calculate_fast_getting_offset_for_LFB popad call repos_windows diff --git a/kernel/branches/Kolibri-acpi/memmap.inc b/kernel/branches/Kolibri-acpi/memmap.inc index 2dd9d062a8..4eb597df30 100644 --- a/kernel/branches/Kolibri-acpi/memmap.inc +++ b/kernel/branches/Kolibri-acpi/memmap.inc @@ -68,7 +68,7 @@ ; 3c dword cpu usage in cpu timer tics ; ; -; 5000 -> 68FF display width fast calc area (6k6) +; 5000 -> 68FF free (6k6) ; 6900 -> 6EFF saved picture under mouse pointer (1k5) ; ; 6F00 -> 6FFF free (256) @@ -137,7 +137,7 @@ ; FF00 byte 1 = system shutdown request ; FF01 byte task activation request? ; FFF0 byte >0 if redraw background request from app -; FFF1 byte >0 if background changed +; FFF1 byte free ; FFF2 write and read bank in screen ; FFF4 byte 0 if first mouse draw & do not return picture under ; FFF5 byte 1 do not draw pointer @@ -147,8 +147,8 @@ ; 0x8006CC00 -> 6DBFF stack at boot time (4Kb) ; -; 0x8006DC00 -> 6E5FF basic text font II -; 0x8006E600 -> 6Efff basic text font I +; 0x8006DC00 -> 6E5FF free (2560) +; 0x8006E600 -> 6Efff free (2560) ; 0x8006F000 -> 6FFFF main page directory ; 0x80070000 -> 7FFFF data of retrieved disks and partitions (Mario79) @@ -204,15 +204,18 @@ ; 0x80284000 -> 28BFFF HDD DMA AREA (32k) ; 0x8028C000 -> 297FFF free (48k) ; -; 0x80298000 -> 29ffff auxiliary table for background smoothing code (32k) +; 0x80298000 -> 29FFFF auxiliary table for background smoothing code (32k) ; -; 0x802A0000 -> 2B00ff wav device buffer (64k) -; 0x802A0000 -> 2B00ff wav device status (256) -; 0x802B0100 -> 2Bffff free (63k8) -; 0x802C0000 -> 2C3fff button info (8k) +; 0x802A0000 -> 2B00FF wav device buffer (64k) +; 0x802A0000 -> 2B00FF wav device status (256) ; -; 0000 word number of buttons -; first button entry at 0x10 +; 0x802B0100 -> 2B3FFD free (15k7) +; +; 0x802B3FEE -> 2B3FEF button info (64K+ 16 + 2 byte) +; 2B3FEE 0000 word number of buttons +; 2B3FF0 first button entry +; +; button entry at 0x10 ; +0000 word process number ; +0002 word button id number : bits 00-15 ; +0004 word x start @@ -221,7 +224,10 @@ ; +000A word y size ; +000C word button id number : bits 16-31 ; -; 0x802C4000 -> 2CFFFF free (48k) +; 0x802C4000 -> 2C9FFF area for fast getting offset to LFB (24k) +; BPSLine_calc_area +; 0x802CA000 -> 2CFFFF area for fast getting offset to _WinMapAddress (24k) +; d_width_calc_area ; ; 0x802D0000 -> 2DFFFF reserved port area (64k) ; @@ -231,25 +237,29 @@ ; dword end port ; dword 0 ; -; 0x802E0000 -> 2EFFFF irq data area (64k) -; 0x802F0000 -> 2FFFFF low memory save (64k) +; 0x802E0000 -> 2EFFFF irq data area (64k) ;BOOT_VAR ; -; 0x80300000 -> 31FFFF tcp memory (128k) -; 0x80320000 -> 327FFF tcp memory (32k) +; 0x802F0000 -> 2F3FFF tcp memory stack_data_start eth_data_start (16k) ; -; 0x80328000 -> 32FFFF !vrr driver (32k) - -; 0x80330000 -> 377FFF skin data (32k) - -; 0x80338000 -> 338FFF draw data - 256 entries (4k) +; 0x802F4000 -> 30ffff stack_data | stack_data_end (112k) +; +; 0x80310000 -> 317fff resendQ (32k) +; +; 0x80318000 -> 31ffff skin_data (32k) +; +; 0x80320000 -> 323FF3 draw data - 256 entries (4k) ; 00 dword draw limit - x start ; 04 dword draw limit - y start ; 08 dword draw limit - x end ; 0C dword draw limit - y end -; 0x80339000 -> 3BFFF3 free (12k) -; 0x8033BFF4 -> 33BFFF background info -; 0x8033C000 page map (length b = memsize shr 15) -; 0x8033C000 + b start of static pagetables +; +; 0x8032BFF4 -> 32BFFF background info +; 0x80323FF4 BgrDrawMode +; 0x80323FF8 BgrDataWidth +; 0x80323FFC BgrDataHeight +; +; 0x80324000 page map (length b = memsize shr 15) +; 0x80324000 + b start of static pagetables ; 0x803FFFFF <- no direct address translation beyond this point ; ============================================================= diff --git a/kernel/branches/Kolibri-acpi/network/eth_drv/drivers/pcnet32.inc b/kernel/branches/Kolibri-acpi/network/eth_drv/drivers/pcnet32.inc index 5c77e4b856..730d69b074 100644 --- a/kernel/branches/Kolibri-acpi/network/eth_drv/drivers/pcnet32.inc +++ b/kernel/branches/Kolibri-acpi/network/eth_drv/drivers/pcnet32.inc @@ -242,7 +242,7 @@ endg pcnet32_dwio_read_csr: push edx lea edx, [ebp+PCNET32_DWIO_RAP] - mov ebx, eax + mov eax, ebx out dx, eax lea edx, [ebp+PCNET32_DWIO_RDP] in eax, dx @@ -267,7 +267,7 @@ pcnet32_dwio_write_csr: pcnet32_dwio_read_bcr: push edx lea edx, [ebp+PCNET32_DWIO_RAP] - mov ebx, eax + mov eax, ebx out dx, eax lea edx, [ebp+PCNET32_DWIO_BDP] in eax, dx @@ -709,10 +709,10 @@ pcnet32_probe: mov eax, 2 call dword [pcnet32_access.write_bcr] mov ebx, 1 - mov eax, (pcnet32_private and 0xffff) + mov eax, ((pcnet32_private - OS_BASE) and 0xffff) call dword [pcnet32_access.write_csr] mov ebx, 2 - mov eax, (pcnet32_private shr 16) and 0xffff + mov eax, ((pcnet32_private - OS_BASE) shr 16) and 0xffff call dword [pcnet32_access.write_csr] mov ebx, 0 mov eax, 1 diff --git a/kernel/branches/Kolibri-acpi/video/blitter.inc b/kernel/branches/Kolibri-acpi/video/blitter.inc index 9544682586..a83898254e 100644 --- a/kernel/branches/Kolibri-acpi/video/blitter.inc +++ b/kernel/branches/Kolibri-acpi/video/blitter.inc @@ -202,6 +202,7 @@ purge .dy1 align 4 blit_32: + xchg bx, bx push ebp push edi push esi @@ -270,9 +271,10 @@ blit_32: mov edi, ebp - imul edi, [_display.pitch] +; imul edi, [_display.pitch] + mov edi, [BPSLine_calc_area+edi*4] ; imul ebp, [_display.width] - mov ebp, [d_width_calc_area + ebp*4] + mov ebp, [d_width_calc_area+ebp*4] add ebp, ebx add ebp, [_WinMapAddress] @@ -298,7 +300,13 @@ blit_32: lea edi, [edi+ebx*4] + mov ebx, 1 + test [esp+72], dword 0x10 + jnz @F + mov ebx, [CURRENT_TASK] +@@: + align 4 .outer32: xor ecx, ecx @@ -365,7 +373,12 @@ align 4 .core_24: lea ebx, [ebx+ebx*2] lea edi, [LFB_BASE+edi+ebx] + mov ebx, 1 + test [esp+72], dword 0x10 + jnz @F + mov ebx, [CURRENT_TASK] +@@: align 4 .outer24: diff --git a/kernel/branches/Kolibri-acpi/video/cursors.inc b/kernel/branches/Kolibri-acpi/video/cursors.inc index 6429e01b9e..1e882cac09 100644 --- a/kernel/branches/Kolibri-acpi/video/cursors.inc +++ b/kernel/branches/Kolibri-acpi/video/cursors.inc @@ -353,6 +353,8 @@ create_cursor: stdcall init_cursor, eax, esi +align 4 +.add_cursor: mov ecx, [.hcursor] lea ecx, [ecx+CURSOR.list_next] lea edx, [_display.cr_list.next] @@ -363,9 +365,6 @@ create_cursor: popfd mov eax, [.hcursor] -;-------------------------------------- -align 4 -.check_hw: cmp [_display.init_cursor], 0 je .fail @@ -385,14 +384,14 @@ align 4 shr ebx, 16 movzx ecx, bh movzx edx, bl - mov [eax+CURSOR.hot_x], ecx - mov [eax+CURSOR.hot_y], edx + mov [edi+CURSOR.hot_x], ecx + mov [edi+CURSOR.hot_y], edx xchg edi, eax mov ecx, 1024 cld rep movsd - jmp .check_hw + jmp .add_cursor ;------------------------------------------------------------------------------ align 4 proc load_cursor stdcall, src:dword, flags:dword @@ -619,9 +618,7 @@ proc move_cursor_24 stdcall, hcursor:dword, x:dword, y:dword mov [_dy], edx ; mul dword [BytesPerScanLine] - mov eax, [d_width_calc_area + eax*4] - lea eax, [eax + eax*2] - + mov eax, [BPSLine_calc_area+eax*4] lea edx, [LFB_BASE+ecx*3] add edx, eax mov [cur_saved_base], edx @@ -645,6 +642,8 @@ align 4 sub edi, [y] inc ebx inc edi + sub ebx, [_dx] + sub edi, [_dy] mov [cur.w], ebx mov [cur.h], edi @@ -738,9 +737,7 @@ proc move_cursor_32 stdcall, hcursor:dword, x:dword, y:dword mov [_dy], edx ; mul dword [BytesPerScanLine] - mov eax, [d_width_calc_area + eax*4] - shl eax, 2 - + mov eax, [BPSLine_calc_area+eax*4] lea edx, [LFB_BASE+eax+ecx*4] mov [cur_saved_base], edx @@ -763,6 +760,8 @@ align 4 sub edi, [y] inc ebx inc edi + sub ebx, [_dx] + sub edi, [_dy] mov [cur.w], ebx mov [cur.h], edi @@ -840,10 +839,10 @@ check_mouse_area_for_getpixel_new: ;-------------------------------------- push eax ebx ; offset X - mov ecx, [X_UNDER_subtraction_CUR_hot_x] + movzx ecx, word [X_UNDER_subtraction_CUR_hot_x] sub eax, ecx ; x1 ; offset Y - mov ecx, [Y_UNDER_subtraction_CUR_hot_y] + movzx ecx, word [Y_UNDER_subtraction_CUR_hot_y] sub ebx, ecx ; y1 ;-------------------------------------- ; ebx = offset y @@ -879,41 +878,49 @@ check_mouse_area_for_putpixel_new: ; eax = new color ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb .no_mouse_area - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae .no_mouse_area + sub cx, [Y_UNDER_subtraction_CUR_hot_y] + jb .no_mouse_area + rol ecx, 16 ;-------------------------------------- ; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] - jb .no_mouse_area - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] jae .no_mouse_area + + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb .no_mouse_area + + ror ecx, 16 ;-------------------------------------- align 4 .1: push eax -; offset X - mov ax, [X_UNDER_subtraction_CUR_hot_x] - sub cx, ax ; x1 - ror ecx, 16 -; offset Y - mov ax, [Y_UNDER_subtraction_CUR_hot_y] - sub cx, ax ; y1 ;-------------------------------------- ; ecx = (offset x) shl 16 + (offset y) push ebx mov ebx, ecx shr ebx, 16 ; x and ecx, 0xffff ; y + + cmp ecx, [cur.h] + jae @f + + cmp ebx, [cur.w] + jb .ok +;-------------------------------------- +align 4 +@@: +; DEBUGF 1, "K : SHIT HAPPENS: %x %x \n", ecx,ebx + pop ebx + jmp .sh ; SORRY! SHIT HAPPENS! +;-------------------------------------- +align 4 +.ok: ; ecx = offset y ; ebx = offset x - mov eax, [esp + 4] - push ebx ecx imul ecx, [cur.w] ;y add ecx, ebx @@ -949,10 +956,14 @@ align 4 test eax, 0xFF000000 jz @f - pop ecx + add esp, 4 ret ;-------------------------------------- align 4 +.sh: + mov ecx, -1 +;-------------------------------------- +align 4 @@: pop eax ;-------------------------------------- @@ -1019,6 +1030,8 @@ align 4 ;-------------------------------------- align 4 @@: + stdcall load_cursor, clock_arrow, dword LOAD_FROM_MEM + mov [def_cursor_clock], eax stdcall load_cursor, def_arrow, dword LOAD_FROM_MEM mov [def_cursor], eax ret @@ -1034,4 +1047,8 @@ align 4 def_arrow: file 'arrow.cur' ;------------------------------------------------------------------------------ +align 4 +clock_arrow: + file 'arrow_clock.cur' +;------------------------------------------------------------------------------ diff --git a/kernel/branches/Kolibri-acpi/video/vesa20.inc b/kernel/branches/Kolibri-acpi/video/vesa20.inc index db053a65d2..d1373d4c01 100644 --- a/kernel/branches/Kolibri-acpi/video/vesa20.inc +++ b/kernel/branches/Kolibri-acpi/video/vesa20.inc @@ -72,8 +72,7 @@ align 4 .no_mouseunder: ;-------------------------------------- ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - lea ebx, [ebx + ebx*2] + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [eax+eax*2]; edi = x*3 add edi, ebx ; edi = x*3+(y*y multiplier) mov ecx, [LFB_BASE+edi] @@ -105,8 +104,7 @@ align 4 .no_mouseunder: ;-------------------------------------- ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - shl ebx, 2 + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [ebx+eax*4]; edi = x*4+(y*y multiplier) mov ecx, [LFB_BASE+edi] ;-------------------------------------- @@ -243,19 +241,7 @@ align 4 ; pointer to screen mov edx, [putimg.abs_cy] ; imul edx, [BytesPerScanLine] - - mov edx, [d_width_calc_area + edx*4] - cmp bl, 4 - je .32 - lea edx, [edx+edx*2] - jmp @f -;------------------------------------- -align 4 -.32: - shl edx, 2 -;------------------------------------- -align 4 -@@: + mov edx, [BPSLine_calc_area+edx*4] mov eax, [putimg.abs_cx] ; movzx ebx, byte [ScreenBPP] ; shr ebx, 3 @@ -420,29 +406,38 @@ align 4 jne .skip ;-------------------------------------- push ecx - mov ecx, [putimg.real_sy_and_abs_cy + 4] +;-------------------------------------- +align 4 +.sh: + neg ecx + add ecx, [putimg.real_sx_and_abs_cx + 4] +;-------------------------------------- +; check for X + cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] + jae .no_mouse_area + + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb .no_mouse_area + + shl ecx, 16 + + add ecx, [putimg.real_sy_and_abs_cy + 4] sub ecx, edi ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb .no_mouse_area - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae .no_mouse_area - rol ecx, 16 - add ecx, [putimg.real_sx_and_abs_cx + 4] - sub ecx, [esp] -;-------------------------------------- -; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] + sub cx, [Y_UNDER_subtraction_CUR_hot_y] jb .no_mouse_area - - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] - jae .no_mouse_area ;-------------------------------------- ; check mouse area for putpixel call check_mouse_area_for_putpixel_new.1 + cmp ecx, -1 ;SHIT HAPPENS? + jne .no_mouse_area + + mov ecx, [esp] + jmp .sh ;-------------------------------------- align 4 .no_mouse_area: @@ -622,29 +617,38 @@ align 4 jne .skip ;-------------------------------------- push ecx - mov ecx, [putimg.real_sy_and_abs_cy + 4] +;-------------------------------------- +align 4 +.sh: + neg ecx + add ecx, [putimg.real_sx_and_abs_cx + 4] +;-------------------------------------- +; check for X + cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] + jae .no_mouse_area + + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb .no_mouse_area + + shl ecx, 16 + + add ecx, [putimg.real_sy_and_abs_cy + 4] sub ecx, edi ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb .no_mouse_area - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae .no_mouse_area - rol ecx, 16 - add ecx, [putimg.real_sx_and_abs_cx + 4] - sub ecx, [esp] -;-------------------------------------- -; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] + sub cx, [Y_UNDER_subtraction_CUR_hot_y] jb .no_mouse_area - - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] - jae .no_mouse_area ;-------------------------------------- ; check mouse area for putpixel call check_mouse_area_for_putpixel_new.1 + cmp ecx, -1 ;SHIT HAPPENS? + jne .no_mouse_area + + mov ecx, [esp] + jmp .sh ;-------------------------------------- align 4 .no_mouse_area: @@ -740,9 +744,7 @@ Vesa20_putpixel24: mov cx, bx ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - lea ebx, [ebx + ebx*2] - + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [eax+eax*2]; edi = x*3 mov eax, [esp+32-8+4] ;-------------------------------------- @@ -771,9 +773,7 @@ Vesa20_putpixel24_new: mov cx, bx ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - lea ebx, [ebx + ebx*2] - + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [eax+eax*2]; edi = x*3 mov eax, [esp+32-8+4] ;-------------------------------------- @@ -785,21 +785,23 @@ Vesa20_putpixel24_new: jnz @f ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb @f - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae @f + sub cx, [Y_UNDER_subtraction_CUR_hot_y] + jb @f + rol ecx, 16 ;-------------------------------------- ; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] - jb @f - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] jae @f + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb @f + + ror ecx, 16 + call check_mouse_area_for_putpixel_new.1 ;-------------------------------------- align 4 @@ -819,9 +821,7 @@ Vesa20_putpixel32: mov cx, bx ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - shl ebx, 2 - + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [ebx+eax*4]; edi = x*4+(y*y multiplier) mov eax, [esp+32-8+4]; eax = color ;-------------------------------------- @@ -849,9 +849,7 @@ Vesa20_putpixel32_new: mov cx, bx ; imul ebx, [BytesPerScanLine] ; ebx = y * y multiplier - mov ebx, [d_width_calc_area + ebx*4] - shl ebx, 2 - + mov ebx, [BPSLine_calc_area+ebx*4] lea edi, [ebx+eax*4]; edi = x*4+(y*y multiplier) mov eax, [esp+32-8+4]; eax = color ;-------------------------------------- @@ -863,21 +861,23 @@ Vesa20_putpixel32_new: jnz @f ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb @f - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae @f + sub cx, [Y_UNDER_subtraction_CUR_hot_y] + jb @f + rol ecx, 16 ;-------------------------------------- ; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] - jb @f - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] jae @f + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb @f + + ror ecx, 16 + call check_mouse_area_for_putpixel_new.1 ;-------------------------------------- align 4 @@ -1238,19 +1238,7 @@ align 4 ; pointer to screen mov edx, [drbar.abs_cy] ; imul edx, [BytesPerScanLine] - - mov edx, [d_width_calc_area + edx*4] - cmp bl, 4 - je .32 - lea edx, [edx+edx*2] - jmp @f -;------------------------------------- -align 4 -.32: - shl edx, 2 -;------------------------------------- -align 4 -@@: + mov edx, [BPSLine_calc_area+edx*4] mov eax, [drbar.abs_cx] imul eax, ebx add edx, eax @@ -1406,29 +1394,32 @@ align 4 sub ecx, esi ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb .no_mouse_area - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae .no_mouse_area + sub cx, [Y_UNDER_subtraction_CUR_hot_y] + jb .no_mouse_area + rol ecx, 16 add ecx, [drbar.real_sx_and_abs_cx] sub ecx, edi ;-------------------------------------- ; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] - jb .no_mouse_area - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] jae .no_mouse_area + + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb .no_mouse_area + + ror ecx, 16 ;-------------------------------------- ; check mouse area for putpixel + push eax call check_mouse_area_for_putpixel_new.1 mov [edx], ax shr eax, 16 mov [edx + 2], al - mov eax, [drbar.color] + pop eax jmp .skip ; store to real LFB ;-------------------------------------- @@ -1590,27 +1581,30 @@ align 4 sub ecx, esi ;-------------------------------------- ; check for Y - cmp cx, [Y_UNDER_subtraction_CUR_hot_y] - jb .no_mouse_area - cmp cx, [Y_UNDER_sub_CUR_hot_y_add_curh] jae .no_mouse_area + sub cx, [Y_UNDER_subtraction_CUR_hot_y] + jb .no_mouse_area + rol ecx, 16 add ecx, [drbar.real_sx_and_abs_cx] sub ecx, edi ;-------------------------------------- ; check for X - cmp cx, [X_UNDER_subtraction_CUR_hot_x] - jb .no_mouse_area - cmp cx, [X_UNDER_sub_CUR_hot_x_add_curh] jae .no_mouse_area + + sub cx, [X_UNDER_subtraction_CUR_hot_x] + jb .no_mouse_area + + ror ecx, 16 ;-------------------------------------- ; check mouse area for putpixel + push eax call check_mouse_area_for_putpixel_new.1 mov [edx], eax - mov eax, [drbar.color] + pop eax jmp .skip ; store to real LFB ;-------------------------------------- @@ -1654,18 +1648,7 @@ dp2: ; and LFB data (output for our function) [edi] ; mov eax, [BytesPerScanLine] ; mul ebx - mov eax, [d_width_calc_area + ebx*4] - cmp [ScreenBPP], byte 32 - je .32 - lea eax, [eax+eax*2] - jmp @f -;------------------------------------- -align 4 -.32: - shl eax, 2 -;------------------------------------- -align 4 -@@: + mov eax, [BPSLine_calc_area+ebx*4] xchg ebp, eax add ebp, eax add ebp, eax @@ -1811,19 +1794,7 @@ vesa20_drawbackground_stretch: ; and LFB data (output for our function) [edi] ; mov eax, [BytesPerScanLine] ; mul ebx - mov eax, [d_width_calc_area + ebx*4] - cmp [ScreenBPP], byte 32 - je .32 - lea eax, [eax+eax*2] - jmp @f -;------------------------------------- -align 4 -.32: - shl eax, 2 -;------------------------------------- -align 4 -@@: - + mov eax, [BPSLine_calc_area+ebx*4] xchg ebp, eax add ebp, eax add ebp, eax